⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 snake.asm

📁 汇编贪吃蛇游戏  图形界面下的
💻 ASM
📖 第 1 页 / 共 2 页
字号:

;************************************************************************************************
;   SNAKE 1.0 by Hotou 2005 CopyRight (C) Detective    *
;    Compile by Tasm v3.0      *
;            *
;  This is a snake game.Play it with the cross key on the keyboard.  *
;  I whrite this for the work of ASM course in Tianjin University.   *
;  This version is commpleted on 30-08-2005 at home.    *
;            *
;  Blog:  http://hotou.blogchina.com/     *
;  Web:  http://hotou.vicp.net/      *
;  E-mail:  http://ehotou@hotmail.com/     *
;************************************************************************************************
;     所有子程序列表
; show_start_msg 显示开始提示信息
; Cutsnake 显示蛇一段
; Cutfood  显示食物
; Clearcut 清除格
; Hetfood  产生新食物
; Check_key 处理键盘响应
; Check_die 处理死亡的响应
; Check_eat 处理吃到食物的响应
; Show_point 打印分数(进制转换)
; Run_snake 蛇运动
; Init_snake 蛇初始化
; Clear_area 清空游戏区域
; Show_title 打印游戏标题
; HLine  画横线函数
; VLine  画竖线函数
; Rec  画无填充矩形
; SetGb    设置光标位置
; Msg  显示字符串
; Rand  产生随机数
;******************************************************************************************
.model small
;******************************************************************************************
.stack 200
;******************************************************************************************
.data
    ;蛇的参数以及游戏参数

Len  db 5  ;蛇的长度
Life  db  1  ;蛇的生命
Body  dw 200 dup(0) ;蛇的身体位置
Direction dw 256  ;(0,1)(O,-1)(1,0)(-1,0)
Score  db 'Score00000' ;得分
snake_color db 09  ;蛇颜色
speed  db 0  ;速度
gameover db 0  ;游戏结束标记
Point  db 0  ;得分数
food_color db 04  ;食物色
foodX  dw ?  ;食物坐标
foodY  dw ?
seed  dw 200  ;随即数种子
num1 dw 4
num3 dw 3
;******************************************************************************************
    ;显示方面的参数

topline  dw 20  ;上边界
leftline dw 60  ;左边界
cut_x  dw 4  ;每格宽
cut_y  dw 3  ;每格长
max_x  dw 49  ;最大格数(横)
max_y  dw 49  ;最大格数(纵)
msg1  db 'Hotou snakes'
msg2  db 'SNAKE With TASM3.0 by Hotou 2005 CopyRight (C) Detective'
msg3  db 'Game is over!'
msg4  db 'Press any key! Esc for exit'
msg5  db 'ESC for back, Space for retry'
flash  db 8eh ;字体颜色(黄)
green  db 02h ;字体颜色(绿)
white  db 0fh ;字体颜色(白)
;******************************************************************************************
    ;键盘扫描码
LEFT     EQU     4Bh  
RIGHT    EQU     4Dh
UP       EQU     48h
DOWN     EQU     50h
QUIT  EQU 01h
SPACE  EQU 39h
;******************************************************************************************
    ;LOGO by bsascii

tit1  db '  JNNN.   NN   (N    .NN      JNNN.   N)   JNN' 
tit2  db ' (NNNNN   NN.  (N    (NN.    (NNNNN.  N)  (NN`'
tit3  db ' NNNNNN)  NN)  (N    (NN)    NNNNNN)  N)  JN) '
tit4  db ' NN` 4N)  NNL  (N    JNN)   (NN` 4NL  N) (NN` '
tit5  db ' N)  (NN  NNN. (N    NFNL   (N)   NN  N) NN)  '
tit6  db ' NN.  ""  NNN) (N   (N)NN   NN    ``  N)(NN`  '
tit7  db ' NNNL.    NNNN (N   (N)(N.  NN        N)NN)   '
tit8  db ' (NNNNL   N)NN)(N   NN (N)  NN        NNNNN   '
tit9  db '  4NNNN)  N)(N)(N   NN (N)  NN        NNNNN)  '
tit10  db '   `4NNN  N)`NN(N  .N)  NN  NN        NNF(N)  '
tit11  db ' _.  `NN  N) NNNN  (NNNNNN  NN    JL  NN `NN  '
tit12  db '(N)   (N  N) (NNN  NNNNNNN) NN.   NN  N)  4N) '
tit13  db '(NL   NN  N) `NNN  NNNNNNN) (NL  (NF  N)  (NL '
tit14  db ' NNL_JNN  N)  4NN  NF   `NN  NNNNNN)  N)   NN '
tit15  db ' NNNNNNF  N)  (NN (N)    NN  (NNNNN   N)   (N)'
tit16  db ' (NNNNN`  N)  `NN (N`    4N   NNNN)   N)   (NN'
tit17  db '  `4NF`   "`   "" ""     `"`   `"`    "`    ""'
;******************************************************************************************
.code
main proc far
 mov ax , @data
 mov ds , ax

start: 
 mov ah , 00
 mov al , 12h
 int 10h    ;设置图形模式640*480

 call show_title   ;显示LOGO
 call show_start_msg  ;显示开始提示信息

 mov ah , 00h
 int 16h    ;等待按键
 cmp ah , QUIT   
 jz dos    ;ESC则退出,否则进入游戏
game_start: 
 mov ah , 00   ;设置图形模式320*200,游戏在此模式下运行
 mov al , 13h
 int 10h    

 mov cl , 10   ;边框颜色
 mov si , 63 
 mov bx , 22
 mov di , 256
 mov dx , 167
 call rec   ;打印边框

 ;call clear_area   ;游戏区域清空(效果)
 call Init_snake   ;初始化蛇
 call getfood   ;得到第一个食物
 call run_snake   ;开始运动蛇
exit:
 mov dx , 1010h   ;设置光标
        call SetGb
 mov bl , white   ;显示死亡信息
 lea bp , msg3
 mov cx , 13
 call Msg
 mov dx , 1605h
 mov bl , white   ;显示提示信息
 lea bp , msg5
 mov cx , 29
 call Msg
exit_loop:
 mov ah , 00h
 int 16h    ;等待按键
 cmp ah , QUIT
 jz start
 cmp ah , SPACE
 jz game_start
 jmp exit_loop   ;返回开始
dos:
 mov ah , 00
 mov al , 03
 int 10h    ;设置文本模式

 mov ah , 4ch
 int 21h    ;退出到DOS
main endp

;******************************************************************************************
;函数名: show_start_msg
;功能:  显示开始提示信息
;传递参数:      
;函数返回: 空
;******************************************************************************************
show_start_msg   proc near
 push ax
 push bx
 push cx
 push dx
 push si
 push di
 mov dx , 190bh
        call SetGb   ;设置光标
 mov bl , white
 lea bp , msg2   ;显示作者信息
 mov cx , 56
 call Msg   ;显示字符串

 mov dx , 1619h   ;设置光标
        call SetGb
 mov bl , 0a8h
 lea bp , msg4   ;显示提示信息
 mov cx , 27
 call Msg   ;显示字符串
 pop di
 pop si
 pop dx
 pop cx
 pop bx
 pop ax     
 ret
show_start_msg   endp

;******************************************************************************************
;函数名: cutsnake
;功能:  显示蛇一段
;传递参数:      
;  si/di 游戏空间行/游戏空间列(50*50)
;函数返回: 空
;******************************************************************************************
cutsnake   proc near
 push ax
 push bx
 push cx
 push dx
 push si
 push di

 mov cl , snake_color  ;置颜色

 mov ax,di   ;取坐标值
 mul cut_y   ;乘象素值
 add ax,topline   ;加上边界
 mov bx , ax   
 add ax , 2   
 mov dx , ax

 push bx
 push dx
 mov ax,si   ;取坐标值
 mul cut_x   ;乘象素值
 add ax,leftline   ;加上边界
 mov si , ax
 add ax , 3
 mov di , ax
 pop dx
 pop bx
 
 mov cx,si
 mov dx,bx
 mov al,snake_color
 call qiu
 ;call Rec   ;Rec的参数是cl颜色 si左边 bx上边 di右边 dx下边

 pop di
 pop si
 pop dx
 pop cx
 pop bx
 pop ax     
 
 ret
cutsnake   endp

;******************************************************************************************
;函数名: cutfood
;功能:  显示食物
;传递参数:      
;  si/di 游戏空间行/游戏空间列(50*50)
;函数返回: 空
;******************************************************************************************
cutfood   proc near
 push ax
 push bx
 push cx
 push dx
 push si
 push di

 mov cl , food_color  ;置颜色

 mov ax,di   ;取坐标值
 mul cut_y   ;乘象素值
 add ax,topline   ;加上边界
 mov bx , ax
 add ax , 2
 mov dx , ax

 push bx    
 push dx
 mov ax,si   ;取坐标值
 mul cut_x   ;乘象素值
 add ax,leftline   ;加上边界
 mov si , ax
 add ax , 3
 mov di , ax
 pop dx
 pop bx
mov cx,si
mov dx,bx
mov al,food_color
 ;call Rec   ;Rec的参数是cl颜色 si左边 bx上边 di右边 dx下边
call qiu
 pop di
 pop si
 pop dx
 pop cx
 pop bx
 pop ax     
 
 ret
cutfood   endp

;******************************************************************************************
;函数名: clearcut
;功能:  清除格
;传递参数:      
;  si/di 游戏空间行/游戏空间列(50*50)
;函数返回: 空
;******************************************************************************************
clearcut   proc near
 push ax
 push bx
 push cx
 push dx
 push si
 push di

 mov cl , 0   ;置颜色(黑)
 mov ax,di   ;取坐标值
 mul cut_y   ;乘象素值
 add ax,topline   ;加上边界
 mov bx , ax
 add ax , 2
 mov dx , ax

 push bx
 push dx
 mov ax,si   ;取坐标值
 mul cut_x   ;乘象素值
 add ax,leftline   ;加上边界
 mov si , ax
 add ax , 3
 mov di , ax
 pop dx
 pop bx
 mov al,0
 mov cx,si
mov dx,bx
 ;call Rec   ;Rec的参数是cl颜色 si左边 bx上边 di右边 dx下边
call qiu


 pop di
 pop si
 pop dx
 pop cx
 pop bx
 pop ax     
 ret
clearcut   endp

;******************************************************************************************
;函数名: Rand 
;功能:  产生指定范围大小的随机数
;传递参数:       
;  si 数字的范围最大值+1 
;函数返回: ax 返回随机数的值
;******************************************************************************************
Rand  proc
 push bx
 push cx
 push dx
 push si
 push di
       sti
       mov ah,0               ;读时钟计数器值
       int 1ah
      mov ax , seed
      add ax , dx
      and ax , 8fffh
      mov seed , ax   ;产生新种子
      mov dx , 0
      mov bx , si   ;指定随机数的范围
      div bx   
      mov ax , dx
 pop di
 pop si
 pop dx
 pop cx
 pop bx
       ret
Rand  endp

;******************************************************************************************
;函数名: getfood 
;功能:  产生新食物,即随机产生一组49*49的坐标
;传递参数:       
;   
;函数返回: foodx与foody的值
;******************************************************************************************
getfood proc
 push ax
 push bx
 push cx
 push dx
 push si
 push di

 mov si,49   ;置随机数范围(最大值+1)
 call Rand   ;产生随机数
 mov foodx,ax   ;赋予食物坐标x

 mov si,49   ;置随机数范围(最大值+1)
 call Rand   ;产生随机数
 mov foody,ax   ;赋予食物坐标x
 
 mov si,foodx
 mov di,foody
 call cutfood   ;画食物
 
 pop di
 pop si
 pop dx
 pop cx
 pop bx
 pop ax
 ret
getfood  endp

;******************************************************************************************
;函数名: Delay
;功能:  延时
;传递参数:      
;     
;函数返回: 
;******************************************************************************************
Delay proc
 push ax
 push cx    
 mov ax , 0ah
 sub ax , cx
 mov cx , ax
M3_1: push cx    ;外层循环来控制延时速度
 mov cx , 8000  ;标准半秒应该是33144大小
M3_2: in al , 61h
 and al , 10h
 cmp al , ah
 je M3_1
 mov ah , al
 loop M3_2
 pop cx
 loop M3_1 
 pop cx
 pop ax
 ret
Delay endp

;******************************************************************************************
;函数名: Check_key
;功能:  处理键盘响应
;传递参数:      无
;     
;函数返回: Direction的值,gameover的值(按ESC时)
;******************************************************************************************
Check_key proc
 push ax
 push bx
 push cx
 push dx
 push si
 push di
 mov ah  , 01h 
 int 16h  
 jz  check_nokey;如果没有按键就继续
 ;mov ah , 0eh
 ;mov al , 7
 ;int 10h  
  mov ah , 00h   ;取得扫描码     
 int 16h  
 cmp ah , LEFT   ;往左移动  
  jz check_LEFT
 
 cmp ah , RIGHT   ;往右边移动
 jz check_RIGHT
  
 cmp ah , UP   ;往上移动
 jz check_UP
  
 cmp ah , DOWN   ;往下移动  
 jz check_DOWN

 cmp ah , QUIT   ;结束游戏
 jz check_QUIT

 jmp check_nokey
check_LEFT:
 mov ah , -1   ;(-1,0)
 mov al , 0

 mov bx , ax   ;检查是否反向
 add bx , Direction
 jz check_nokey
 
  
 mov Direction , ax
 jmp check_nokey

check_RIGHT:
 mov ah , 1   ;(1,0)
 mov al , 0

 mov bx , ax   ;检查是否反向
 add bx , Direction
 jz check_nokey
  mov Direction , ax
 jmp check_nokey
      
check_UP:
  mov ah , 0   ;(0,-1)
 mov al , -1

 mov bx , Direction  ;检查是否反向
 sub bl , 1
 jz check_nokey   
 mov Direction , ax
 jmp check_nokey

check_DOWN:
  mov ah , 0   ;(0,1)
 mov al , 1   
 
 mov bx , Direction  ;检查是否反向
 add bl , 1
 jz check_nokey
 mov Direction , ax
 jmp check_nokey

check_QUIT:
 jmp check_exit
 
check_exit:
 mov al,1   ;按下ESC键的情况
 mov gameover,al
check_nokey:
 pop di
 pop si
 pop dx
 pop cx
 pop bx
 pop ax
 ret
Check_key endp

;******************************************************************************************
;函数名: Check_die
;功能:  处理死亡的响应
;传递参数:      SI,DI为当前蛇头部的坐标
;     
;函数返回: 蛇参数的值
;******************************************************************************************
Check_die proc
 push ax
 push bx
 push cx
 push dx
 push si
 push di
 mov bx , offset Body
 cmp si , 49   ;检查是否到达边界
 jz dead1
 cmp si , 0
 jz dead2
 cmp di , 49
jz dead3
cmp di , 0
 jz dead4

 mov ax,si   ;检查是否接触蛇身
 mov dh,al   ;DX中获得当前坐标
 mov ax,di
 mov dl,al
 xor cx , cx
 mov cl , Len
 sub cl , 1   
   
check_die_loop: 
 mov ax , [bx+2]
 cmp ax , dx   ;取出蛇身信息进行比较
 jz dead    ;触及蛇身即死亡  
 dec cl  
 jz next
 add bx , 2
 jmp check_die_loop
dead:
 mov al,1   ;死亡即赋gameover值1
 mov gameover,al
 jmp next
 dead1: mov ax,[bx]
        mov  ah,1
         mov  [bx],ax
          jmp next
 dead2: ;mov ax,[bx]
          mov  ah,48
           mov  [bx],ax
         jmp next

 dead3: mov ax,[bx]
          mov  al,1
          
          mov  [bx],ax
          jmp next

 dead4: mov ax,[bx]
         mov  al,48
          mov  [bx],ax
          jmp next

next:
 pop di
 pop si
 pop dx
 pop cx

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -