推箱子_无操作系统

 

 


; box.s
    ; 推箱子,运行不需操作系统,自有引导扇区,软盘引导
    ; 玩法:W S A D 上下左右,Q 退出,R 重玩当前一关
      ; 初学汇编,求师友
 
 
  ; NASM 16位 实模式
  ; Ubuntu
  ; nasm -o box.bin box.s
 ; sudo dd if=box.bin of=/dev/fd0 bs=512 count=15 conv=notrunc
 ; Bochs 模拟
   
   
   ; 函数调用约定
   ; 参数从右向左压栈,由调用函数平衡栈
   ; 被调用函数返回后与调用前相比,栈中元素及栈大小不改变
   ; 被调用方不维护 ax, bx, cx, dx,但保证维护其它寄存器
   ; 函数返回值 ax, bx, cx, dx
   
   
   ; 代码为将来改进做好了准备(常数, 变量 和 未实现的函数)
   ; 如 人物各方向不同,移动动画,使用斜视图实现3D效果
   
   
   ; 常数
           ; 程序占用扇区总数,不超过 0xFFFF 字节
   %define  SEC_NUM   15
           ; 每个扇区大小 字节
   %define  SEC_SIZE  0x200
           ; 显示
   %define  VIDEO_ID        0x13
   %define  VIDEO_HORZ_P    320
 %define  VIDEO_VERT_P    200
 %define  VIDEO_P         (VIDEO_HORZ_P*VIDEO_VERT_P)
 %define  VIDEO_SEG       0xA000
 %define  VIDEO_PAL_PORT  0x03C8 
 %define  VIDEO_COL_PORT  0x03C9
         ; 栈,考虑对齐
 %define  STACK_TOP  0xFF00
 %define  STACK_SEG  0x8000
         ; 引导
 %define  BOOT_SEG   0x7C0
         ; 级别总数(级别为 1 .. LEVEL_MAX )
 %define  LEVEL_MAX  4
         ; 按键虚拟键码
 %define  VK_NULL    0xFFFF 
 %define  VK_W       ('W')
 %define  VK_A       ('A')
 %define  VK_S       ('S')
 %define  VK_D       ('D')
 %define  VK_Q       ('Q')
 %define  VK_R       ('R')
         ; 游戏状态
 %define  GS_WIN     0x1
 %define  GS_QUIT    0x2
 %define  GS_REPLAY  0x3
 
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; 设置
 [bits 16]
         ; org 0x7C00
 
         ; 初始化 cs, ip
         jmp BOOT_SEG : BOOT
 BOOT : 
         ; 初始化段寄存器
         mov ax, cs
         mov ds, ax
         mov es, ax
         mov fs, ax
         mov gs, ax
         ; 初始化 栈
         mov ax, STACK_SEG
         mov ss, ax
         mov ax, STACK_TOP
         mov sp, ax
 
         ; 读入整个程序
         ; 偷懒,假设要读取的扇区都在 0 磁道,若扇区数增加,需修改此段代码
         mov ah, 0x2
         mov al, SEC_NUM
         dec al
         ; mov cx, 0x0001  悲剧!!!!
         mov cx, 0x0002
         mov dx, 0x0000
         mov bx, SEC_SIZE
         int 0x13
 
         ; 初始化显示方式
         call initVideo
 
         ; 跳入 main 执行
         call main
 
         ; 跳入 shutdown 关机
         call shutdown
 
         times (0x200-2-($-$$)) db 0
         db 0x55
         db 0xAA
 
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; 地图
 ;                                      
 ; 地图单元
 ;                                        
 ;         *          ------------                 
 ;        *****              ^             
 ;       *********           |               
 ;      *************                           
 ;      |  *********|                      
 ;      | +   ***** |       UNIT_VERT_P            
 ;      |+       *  |                   
 ;      +        |  +                            
 ;         +     | +         |             
 ;            +  |+          V      
 ; 位置点-->     @     ----------                       
 ;                                                  
 ;      |           |                               
 ;      |UNIT_HORZ_P|                               
 ;                                                  
 ;                                                  
 ;                                                  
 ; 地图布局                                  
 ; 单元点坐标以单元为单位,常量 *_U
 ; 像素点坐标以像素为单位,常量 *_P
 ; 坐标点格式(x,y),先水平,后垂直
  ; 单元点的像素坐标为其右下角像素的像素坐标
  ; 水平 MAP_HORZ_U 个单元
  ; 垂直 MAP_VERT_U 个单元
  ; 单元点(xu,yu) in [0 .. MAP_HORZ_U)*[0 .. MAP_VERT_U)
  ; 像素点(xp,yp) in [0 .. VIDEO_HORZ_P)*[0 .. VIDEO_VERT_P)
 ; 二维图片实现3D效果,暂未使用,待扩充
 ; 绘制从左上角单元开始,至右下角单元结束,实现3D效果
 ; 地图原点为地图左上角单元(xu=0,yu=0)的像素坐标
 ; 
 ;    +--------------------------> xu in [0 .. MAP_HORZ_U)
 ;    |                            xp in [0 .. VIDEO_HORZ_P)
 ;    |                  *                       
 ;    |                 *   *                    
 ;    |                *       *                 
 ; yu |               *           *              
 ; yp |              *               *           
 ;    v   ----------*                   *------------
 ;                  |  *               *|        
 ;        DY_HORZ_P |     *           * |      DY_VERT_P
 ;                  |        *       *  |         
 ;                  |           *   *   |            
 ;        ----------+--------------@----+-------------  
 ;                  |              |    |              
 ;                  |   DX_HORZ_P  |    |             
 ;                  |              |    |            
 ;                                  DX_VERT_P         
 ;                                                  
 
         ; 注意正负号,作为增量
 %define  DX_VERT_P    (0)
 %define  DY_VERT_P    (22)
 %define  DX_HORZ_P    (22)
 %define  DY_HORZ_P    (0)
 
 %define  UNIT_HORZ_P  (22)
 %define  UNIT_VERT_P  (22)
 %define  UNIT_P       (UNIT_HORZ_P*UNIT_VERT_P)
 
 %define  MAP_HORZ_U   8
 %define  MAP_VERT_U   8
 %define  MAP_U        (MAP_HORZ_U*MAP_VERT_U)
 
         ; 单元 id,一字节,使用位或,一个单元可以为 BOX+DEST 或BOX+FLOOR
 %define  UID_SPACE   0x01
 %define  UID_FLOOR   0x02
 %define  UID_WALL    0x04
 %define  UID_BOX     0x08
 %define  UID_DEST    0x10
 %define  UID_PLAYER  0x20
         ; 一字节
 %define  DIR_UP     0x0
 %define  DIR_DOWN   0x1
 %define  DIR_LEFT   0x2
 %define  DIR_RIGHT  0x3
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void main()
 ; 主程序
 main : 
         mov byte[level], 0x1
 .PLAY : 
         movzx ax, byte[level]
         cmp ax, LEVEL_MAX
         ja .COMPLETE
 
         call initOneLevel
         call playOneLevel
 
         cmp ax, GS_QUIT
         je .QUIT
         cmp ax, GS_REPLAY
         je .REPLAY
         cmp ax, GS_WIN
         jne .ERR
         inc byte[level]
 .REPLAY : 
         jmp .PLAY
 .COMPLETE : 
         call initOneLevel
         jmp .EXIT
 .QUIT : 
         mov byte[level], LEVEL_MAX+1
         call initOneLevel
         jmp .EXIT
 .ERR : 
         jmp .EXIT
 .EXIT : 
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void shutdown()
 ; 关机
 shutdown : 
         ; 暂时死循环吧
         jmp $
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void initOneLevel()
 ; 初始化 level 级别
 initOneLevel : 
         push si
         push di
         movzx ax, byte[level]
         mov cx, MAP_SIZE
         mul cx
         mov si, MAP_CUR
         add si, ax
         mov di, MAP_CUR
         cld
         rep movsb
         pop di
         pop si
         call eraseAll
         call drawAll
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax playOneLevel()
 ; 玩 level 级别
 ; 返回 GS_WIN   GS_REPLAY   GS_QUIT
 playOneLevel : 
 .PLAY : 
         call getKey
         cmp ax, VK_Q
         je .QUIT
         cmp ax, VK_R
         je .REPLAY
 
         movzx cx, byte[px_u]
         movzx dx, byte[py_u]
         cmp ax, VK_W
         je .UP
         cmp ax, VK_S
         je .DOWN
         cmp ax, VK_A
         je .LEFT
         cmp ax, VK_D
         je .RIGHT
         jmp .PLAY
 .UP : 
         mov byte[dir], DIR_UP
         sub dx, 2
         push dx
         push cx
         inc dx
         push dx
         push cx
         jmp .TMOVE
 .DOWN : 
         mov byte[dir], DIR_DOWN
         add dx, 2
         push dx
         push cx
         dec dx
         push dx
         push cx
         jmp .TMOVE
 .LEFT : 
         mov byte[dir], DIR_LEFT
         sub cx, 2
         push dx
         push cx
         inc cx
         push dx
         push cx
         jmp .TMOVE
 .RIGHT : 
         mov byte[dir], DIR_RIGHT
         add cx, 2
         push dx
         push cx
         dec cx
         push dx
         push cx
 .TMOVE : 
         ; BOX
         mov ax, UID_BOX
         push ax
         call isUidU
         add sp, 2
         test ax, ax
         jnz .BOX
         ; FLOOR
         mov ax, UID_FLOOR
         push ax
         call isUidU
         add sp, 2
         test ax, ax
         jnz .WALK
         ; DEST
         mov ax, UID_DEST
         push ax
         call isUidU
         add sp, 2
         test ax, ax
         jnz .WALK
         jmp .CANTMOVE
 .BOX : 
         push bp
         mov bp, sp
         mov ax, [bp+8]
         push ax
         mov ax, [bp+6]
         push ax
         call isInMapU
         test ax, ax
         jz .ENDBOX
         mov ax, UID_BOX
         push ax
         call isUidU
         add sp, 2
         test ax, ax
         jnz .ENDBOX
         mov ax, UID_WALL
         push ax
         call isUidU
         add sp, 2
         test ax, ax
         jz .PUSHBOX
 .ENDBOX : 
         mov sp, bp
         pop bp
         add sp, 8
         jmp .MOVED
 .PUSHBOX : 
         mov ax, [bp+8]
         mov cx, MAP_HORZ_U
         mul cx
         add ax, [bp+6]
         push si
         mov si, MAP_CUR
         add si, ax
         ; movzx ax, [si] 悲剧!!!!
         mov al, [si]
         xor al, UID_BOX
         mov [si], al
         pop si
         mov ax, [bp+4]
         mov cx, MAP_HORZ_U
         mul cx
         add ax, [bp+2]
         push si
         mov si, MAP_CUR
         add si, ax
         mov al, [si]
         xor al, UID_BOX
         mov [si], al
         pop si
         mov ax, [bp+2]
         mov [px_u], al
         mov ax, [bp+4]
         mov [py_u], al
         jmp .ENDBOX
 .WALK : 
         pop ax
         mov [px_u], al
         pop ax
         mov [py_u], al
         add sp, 4
         jmp .MOVED
 .CANTMOVE : 
         add sp, 8
 .MOVED : 
         call drawAll
         call judgeWin
         test ax, ax
         jnz .WIN
         jmp .PLAY
 .WIN : 
         mov ax, GS_WIN
         jmp .EXIT
 .REPLAY : 
         mov ax, GS_REPLAY
         jmp .EXIT
 .QUIT : 
         mov ax, GS_QUIT
 .EXIT : 
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax isUidU( uid, xu, yu )
 ; 判断单元点(xu,yu)是否为uid
 ; ax!=0 是,   ax==0 否
 ; 若此单元点不在地图中,返回 否
 isUidU : 
         push bp
         mov bp, sp
         mov ax, [bp+8]
         push ax
         mov ax, [bp+6]
         push ax
         call isInMapU
         add sp, 4
         test ax, ax
         jz .EXIT
         mov ax, [bp+8]
         mov cx, MAP_HORZ_U
         mul cx
         add ax, [bp+6]
         push si
         mov si, MAP_CUR
         add si, ax
         movzx ax, byte[si]
         pop si
         and ax, [bp+4]
 .EXIT : 
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax isInMapU( xu, yu )
 ; 判断单元点(xu,yu)是否在地图中(所在点为SPACE算不在地图中)
 ; ax!=0 在,    ax==0 不在
 isInMapU : 
         push bp
         mov bp, sp
         mov bx, [bp+4]
         cmp bx, MAP_HORZ_U
         jae .NO
         mov ax, [bp+6]
         cmp ax, MAP_VERT_U
         jae .NO
         mov cx, MAP_HORZ_U
         mul cx
         add ax, bx
         push si
         mov si, MAP_CUR
         add si, ax
         mov al, [si]
         pop si
         test al, UID_SPACE
         jnz .NO
 .YES : 
         mov ax, 1
         jmp .EXIT
 .NO : 
         mov ax, 0
 .EXIT : 
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax judgeWin()
 ; 判断是否胜利,ax==0 否,ax!=0 胜
 ; 简单化,扫描整个地图
 judgeWin : 
         push si
         mov si, MAP_CUR
         mov cx, MAP_U
 .judgeWin : 
         xor bx, bx
         movzx ax, byte[si]
         test ax, UID_DEST
         jz .skip1
         inc bx
 .skip1 : 
         test ax, UID_BOX
         jz .skip2
         inc bx
 .skip2 : 
         cmp bx, 1
         je .LOSE
         inc si
         loop .judgeWin
 .WIN : 
         mov ax, 1
         jmp .EXIT
 .LOSE  : 
         mov ax, 0
 .EXIT : 
         pop si
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void eraseAll()
 ; 清除所有图像
 eraseAll : 
         mov ax, 01
         mov cx, VIDEO_P
         push es
         mov bx, VIDEO_SEG
         mov es, bx
         push di
         mov di, 0
         cld
         rep stosb
         pop di
         pop es
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void drawAll()
 ; 直接重绘地图,无关背景
 ; 兼容3D效果,从左上角到右下角顺序绘制
 drawAll : 
         push si
 
         mov si, MAP_CUR
         mov bx, 0 ; yu
         mov cx, MAP_VERT_U
 .drawAll1 : 
         push cx
 
         mov ax, 0 ; xu
         mov cx, MAP_HORZ_U
 .drawAll2 : 
         push cx
 
         push bx
         push ax
         movzx cx, byte[si]
         inc si
         push cx
         call drawUidU
         pop cx
         pop ax
         pop bx
 
         inc ax
         pop cx
         loop .drawAll2
 
         inc bx
         pop cx
         loop .drawAll1
 
         pop si
 
         movzx ax, byte[py_u]
         push ax
         movzx ax, byte[px_u]
         push ax
         mov ax, UID_PLAYER
         push ax
         call drawUidU
         add sp, 6
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void drawUidU( uid, xu, yu )
 ; 绘制单元坐标为(xu,yu)的单元uid
 ; uid == UID_FLOOR, 
 drawUidU : 
         push bp
         mov bp, sp
         mov ax, [bp+8]
         push ax
         mov ax, [bp+6]
         push ax
         call convU2P
         add sp, 4
         push bx
         push ax
         mov ax, [bp+4]
         push ax
         call drawUid
         add sp, 6
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax, bx  convU2P( xu, yu )
 ; 单元坐标转换为像素坐标,依据 orgx_p, orgy_p
 ; 返回 ax==xp, bx=yp
 ; 适应3D侧视图
 convU2P : 
         push bp
         mov bp, sp
         movzx ax, byte[orgx_p]
         movzx bx, byte[orgy_p]
 .convU2P_L1 : 
         mov cx, [bp+4]
         test cx, cx
         jz .convU2P_L2
 .convU2P1 : 
         add ax, DX_HORZ_P
         add bx, DY_HORZ_P
         loop .convU2P1
 .convU2P_L2 : 
         mov cx, [bp+6]
         test cx, cx
         jz .EXIT
 .convU2P2 : 
         add ax, DX_VERT_P
         add bx, DY_VERT_P
         loop .convU2P2
 .EXIT : 
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void drawUid( uid, xp, yp )
 ; 绘制像素点为(xp,yp)且类型为uid的单元点
 ; uid == UID_SPACE, UID_FLOOR, 
 drawUid : 
         push bp
         mov bp, sp
         mov ax, [bp+4]
         push ax
         call convUid2Uoff
         pop bx
         mov bx, [bp+8]
         push bx
         mov bx, [bp+6]
         push bx
         push ax
         call drawUoff
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax convUid2Uoff( uid )
 ; uid == UID_FLOOR,      uoff = UOFF_FLOOR, 
 ; 不依赖 uid 和 uoff 的定义,无跳表,大量比较
 ; 处理了player的方向dir
 ; BOX+DEST或BOX+FLOOR 按BOX处理,所以注意测试顺序
 convUid2Uoff : 
         push bp
         mov bp, sp
         mov ax, [bp+4]
 .SPACE : 
         test ax, UID_SPACE
         jz .BOX
         mov ax, UOFF_SPACE
         jmp .EXIT
 .BOX : 
         test ax, UID_BOX
         jz .FLOOR
         mov ax, UOFF_BOX
         jmp .EXIT
 .FLOOR : 
         test ax, UID_FLOOR
         jz .WALL
         mov ax, UOFF_FLOOR
         jmp .EXIT
 .WALL : 
         test ax, UID_WALL
         jz .DEST
         mov ax, UOFF_WALL
         jmp .EXIT
 .DEST : 
         test ax, UID_DEST
         jz .PLAYER
         mov ax, UOFF_DEST
         jmp .EXIT
 .PLAYER : 
         test ax, UID_PLAYER
         jz .ELSE
         mov al, [dir]
     .UP : 
         cmp al, DIR_UP
         jne .DOWN
         mov ax, UOFF_PLAYER_UP
         jmp .EXIT
     .DOWN : 
         cmp al, DIR_DOWN
         jne .LEFT
         mov ax, UOFF_PLAYER_DOWN
         jmp .EXIT
     .LEFT : 
         cmp al, DIR_LEFT
         jne .RIGHT
         mov ax, UOFF_PLAYER_LEFT
         jmp .EXIT
     .RIGHT : 
         cmp al, DIR_RIGHT
         jne .ELSE
         mov ax, UOFF_PLAYER_RIGHT
         jmp .EXIT
 .ELSE : 
         mov ax, UOFF_SPACE 
 .EXIT : 
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void drawUoff( uoff, xp, yp )
 ; 绘制像素点为(xp,yp)且地图单元位图偏移为uoff的单元点
 ; off == UOFF_SPACE, UOFF_FLOOR, 
 drawUoff : 
         ; 悲剧!!!!
         push bp
         mov bp, sp
         push si
         push di
         push es
 
         mov si, [bp+4]
 
         mov cx, VIDEO_SEG
         mov es, cx
 
         mov ax, [bp+8]
         sub ax, UNIT_VERT_P
         inc ax
         mov cx, VIDEO_HORZ_P
         mul cx
         mov bx, [bp+6]
         sub bx, UNIT_HORZ_P
         inc bx
         add ax, bx
         mov di, ax
 
         mov cx, UNIT_VERT_P
 .drawUoff1 : 
         push cx
 
         mov cx, UNIT_HORZ_P
 .drawUoff2 : 
         mov al, [ds:si]
         test al, al
         jz .drawUoff3
         mov [es:di], al
 .drawUoff3 : 
         inc si
         inc di
         loop .drawUoff2
 
         sub di, UNIT_HORZ_P
         add di, VIDEO_HORZ_P
         pop cx
         loop .drawUoff1
 
         pop es
         pop di
         pop si
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax peekKey()
 ; 获取键盘输入,不阻塞
 ; 若无输入返回 VK_NULL
 ; 若有输入,取出,且不将其从缓冲区中清除
 peekKey : 
         mov ah, 1
         int 0x16
         jz .VK_NULL
         push ax
         call convKey2Vk
         add sp, 2
         jmp .EXIT
 .VK_NULL : 
         mov ax, VK_NULL
 .EXIT : 
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax getKey()
 ; 获取键盘输入,阻塞
 ; 若无输入,阻塞
 ; 若有输入,取出,且将其从缓冲区中清除
 getKey : 
         mov ah, 0
         int 0x16
         push ax
         call convKey2Vk
         add sp, 2
         cmp ax, VK_NULL
         je getKey
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func ax convKey2Vk( bios_ax )
 ; 将BIOS键盘输入转换为虚拟键码
 ; 不依赖任何编码,大量比较
 convKey2Vk : 
         push bp
         mov bp, sp
         mov ax, [bp+4]
 
         cmp al, 'W'
         je .VK_W
         cmp al, 'w'
         je .VK_W
         
         cmp al, 'A'
         je .VK_A
         cmp al, 'a'
         je .VK_A
         
         cmp al, 'S'
         je .VK_S
         cmp al, 's'
         je .VK_S
 
         cmp al, 'D'
         je .VK_D
         cmp al, 'd'
         je .VK_D
 
         cmp al, 'Q'
         je .VK_Q
         cmp al, 'q'
         je .VK_Q
 
         cmp al, 'R'
         je .VK_R
         cmp al, 'r'
         je .VK_R
 
         jmp .VK_NULL
 .VK_W : 
         mov ax, VK_W
         jmp .EXIT
 .VK_A : 
         mov ax, VK_A
         jmp .EXIT
 .VK_S : 
         mov ax, VK_S
         jmp .EXIT
 .VK_D : 
         mov ax, VK_D
         jmp .EXIT
 .VK_Q : 
         mov ax, VK_Q
         jmp .EXIT
 .VK_R : 
         mov ax, VK_R
         jmp .EXIT
 .VK_NULL : 
         mov ax, VK_NULL
 .EXIT : 
         mov sp, bp
         pop bp
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void sleep( t )
 ; 等待 t 毫秒,等待中的输入被清除(清空输入缓冲区)
 ; 移动动画使用
 sleep : 
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; 调色板
 BOX_PAL : 
         ; r   g    b
         db 63, 63, 00 ; 00 透明色
                 ; SPACE
         db 00, 00, 00 ; 01 背景色
         db 00, 00, 00 ; 02
         db 00, 00, 00 ; 03
         db 00, 00, 00 ; 04
         db 00, 00, 00 ; 05
                 ; FLOOR
         db 16, 22, 28 ; 06
         db 21, 26, 32 ; 07
         db 00, 07, 15 ; 08
         db 00, 00, 00 ; 09
         db 00, 00, 00 ; 10
                 ; WALL
         db 00, 07, 15 ; 11
         db 63, 63, 63 ; 12
         db 14, 20, 22 ; 13
         db 30, 31, 38 ; 14
         db 37, 42, 45 ; 15
                 ; BOX
         db 60, 60, 60 ; 16
         db 25, 30, 06 ; 17
         db 44, 47, 21 ; 18
         db 55, 56, 37 ; 19
         db 00, 07, 15 ; 20
                 ; DEST
         db 60, 60, 30 ; 21
         db 00, 07, 15 ; 22
         db 00, 00, 00 ; 23
         db 00, 00, 00 ; 24
         db 00, 00, 00 ; 25
                 ; PLAYER
         db 00, 07, 15 ; 26
         db 60, 60, 60 ; 27
         db 00, 00, 00 ; 28
         db 60, 44, 62 ; 29
         db 63, 28, 62 ; 30
         db 00, 32, 63 ; 31
         db 00, 00, 00 ; 32
         db 00, 00, 00 ; 33
 BOX_PAL_NUM : equ $-BOX_PAL
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; func void initVideo()
 ; 初始化显示方式
 initVideo : 
         ; 设置显示方式
         mov ax, 0x0013
         int 0x10
 
         ; 设置调色板
         xor bx, bx  ; rgbrgbrgb
         xor cx, cx  ; index 0
 .iVset : 
         cmp bx, BOX_PAL_NUM
         je .iVexit
 
         ; 调色板 index
         mov dx, VIDEO_PAL_PORT
         mov ax, cx
         out dx, al
         inc cx
 
         ; 调色板颜色
         mov dx, VIDEO_COL_PORT
         mov al, [ds:BOX_PAL+bx]
         out dx, al
         inc bx
         mov al, [ds:BOX_PAL+bx]
         out dx, al
         inc bx
         mov al, [ds:BOX_PAL+bx]
         out dx, al
         inc bx
 
         jmp .iVset
 .iVexit : 
         ret
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; 地图单元位图
 ; (繁琐的工作,还好有 Vim + 自制的MageX )
 UOFF_SPACE : 
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
         db 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01, 01
 UOFF_FLOOR : 
         db 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 07, 07, 07, 07, 06, 06, 07, 07, 07, 07, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 08
         db 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08, 08
 UOFF_WALL : 
         db 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11
         db 11, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 13, 11
         db 11, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 13, 13, 11
         db 11, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 13, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 13, 13, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 13, 13, 13, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 12, 12, 14, 14, 13, 13, 13, 13, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 12, 12, 12, 13, 13, 13, 13, 13, 13, 13, 13, 13, 13, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 11
         db 11, 12, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 11
         db 11, 12, 12, 12, 12, 12, 12, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 14, 11
         db 11, 12, 12, 12, 12, 12, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 11
         db 11, 12, 12, 12, 12, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 11
         db 11, 12, 12, 12, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 11
         db 11, 12, 12, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 11
         db 11, 12, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 11
         db 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11, 11
 UOFF_BOX : 
         db 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20
         db 20, 06, 06, 06, 06, 06, 06, 06, 18, 18, 18, 18, 18, 18, 06, 06, 06, 06, 06, 06, 06, 20
         db 20, 06, 06, 06, 06, 06, 18, 18, 16, 16, 16, 16, 18, 18, 18, 18, 06, 06, 06, 06, 06, 20
         db 20, 06, 06, 06, 18, 18, 16, 16, 16, 16, 16, 16, 16, 16, 18, 18, 18, 18, 06, 06, 06, 20
         db 20, 06, 06, 18, 18, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 18, 18, 06, 06, 20
         db 20, 06, 06, 18, 16, 16, 16, 16, 16, 16, 17, 16, 16, 16, 16, 16, 16, 18, 18, 06, 06, 20
         db 20, 06, 18, 18, 16, 16, 16, 16, 16, 16, 17, 17, 16, 16, 16, 16, 18, 18, 18, 18, 06, 20
         db 20, 06, 18, 18, 18, 16, 16, 16, 16, 17, 17, 17, 17, 18, 16, 18, 18, 18, 18, 18, 06, 20
         db 20, 18, 18, 18, 18, 18, 16, 16, 16, 17, 17, 17, 17, 18, 18, 18, 18, 18, 18, 18, 18, 20
         db 20, 18, 18, 18, 18, 18, 18, 17, 17, 17, 17, 17, 17, 17, 17, 18, 18, 18, 18, 18, 18, 20
         db 20, 18, 18, 18, 18, 18, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 18, 18, 18, 18, 20
         db 20, 18, 18, 18, 18, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, 18, 18, 18, 18, 18, 20
         db 20, 18, 18, 18, 18, 18, 18, 17, 17, 17, 17, 17, 17, 17, 17, 18, 18, 18, 18, 18, 18, 20
         db 20, 18, 18, 18, 18, 18, 18, 18, 18, 17, 17, 17, 17, 18, 18, 19, 19, 18, 18, 18, 18, 20
         db 20, 06, 18, 18, 18, 18, 18, 18, 18, 17, 17, 17, 17, 18, 19, 19, 19, 18, 18, 18, 06, 20
         db 20, 06, 18, 18, 18, 18, 18, 18, 18, 18, 17, 17, 18, 19, 19, 19, 19, 18, 18, 18, 06, 20
         db 20, 06, 06, 18, 18, 18, 18, 18, 18, 19, 19, 17, 18, 19, 19, 19, 18, 18, 18, 06, 06, 20
         db 20, 06, 06, 18, 18, 18, 18, 18, 19, 19, 19, 19, 19, 19, 19, 18, 18, 18, 18, 06, 06, 20
         db 20, 06, 06, 06, 18, 18, 18, 19, 19, 19, 19, 19, 19, 19, 18, 18, 18, 18, 06, 06, 06, 20
         db 20, 06, 06, 06, 06, 06, 18, 18, 18, 18, 18, 18, 18, 18, 18, 18, 06, 06, 06, 06, 06, 20
         db 20, 06, 06, 06, 06, 06, 06, 06, 18, 18, 18, 18, 18, 18, 06, 06, 06, 06, 06, 06, 06, 20
         db 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20
 UOFF_DEST : 
         db 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 21, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 06, 06, 22
         db 22, 06, 06, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 21, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 21, 21, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 21, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 06, 22
         db 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22, 22
 UOFF_PLAYER_UP : 
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 31, 27, 27, 31, 29, 29, 31, 27, 27, 31, 29, 29, 29, 06, 06, 26
         db 26, 06, 29, 29, 29, 31, 28, 28, 31, 31, 31, 31, 28, 28, 31, 31, 31, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 27, 31, 31, 31, 31, 31, 27, 31, 31, 31, 31, 31, 31, 27, 29, 29, 06, 26
         db 26, 29, 29, 29, 27, 27, 31, 31, 31, 31, 27, 27, 31, 31, 31, 31, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 27, 27, 27, 31, 31, 27, 27, 27, 27, 31, 31, 27, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 27, 27, 27, 30, 30, 30, 30, 27, 27, 27, 29, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 29, 29, 27, 30, 30, 30, 30, 27, 29, 29, 29, 29, 29, 29, 29, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 30, 30, 30, 30, 30, 30, 29, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
 UOFF_PLAYER_DOWN : 
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 31, 27, 27, 31, 29, 29, 31, 27, 27, 31, 29, 29, 29, 06, 06, 26
         db 26, 06, 29, 29, 29, 31, 28, 28, 31, 31, 31, 31, 28, 28, 31, 31, 31, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 27, 31, 31, 31, 31, 31, 27, 31, 31, 31, 31, 31, 31, 27, 29, 29, 06, 26
         db 26, 29, 29, 29, 27, 27, 31, 31, 31, 31, 27, 27, 31, 31, 31, 31, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 27, 27, 27, 31, 31, 27, 27, 27, 27, 31, 31, 27, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 27, 27, 27, 30, 30, 30, 30, 27, 27, 27, 29, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 29, 29, 27, 30, 30, 30, 30, 27, 29, 29, 29, 29, 29, 29, 29, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 30, 30, 30, 30, 30, 30, 29, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
 UOFF_PLAYER_LEFT : 
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 31, 27, 27, 31, 29, 29, 31, 27, 27, 31, 29, 29, 29, 06, 06, 26
         db 26, 06, 29, 29, 29, 31, 28, 28, 31, 31, 31, 31, 28, 28, 31, 31, 31, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 27, 31, 31, 31, 31, 31, 27, 31, 31, 31, 31, 31, 31, 27, 29, 29, 06, 26
         db 26, 29, 29, 29, 27, 27, 31, 31, 31, 31, 27, 27, 31, 31, 31, 31, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 27, 27, 27, 31, 31, 27, 27, 27, 27, 31, 31, 27, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 27, 27, 27, 30, 30, 30, 30, 27, 27, 27, 29, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 29, 29, 27, 30, 30, 30, 30, 27, 29, 29, 29, 29, 29, 29, 29, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 30, 30, 30, 30, 30, 30, 29, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
 UOFF_PLAYER_RIGHT : 
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 31, 31, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 31, 27, 27, 31, 29, 29, 31, 27, 27, 31, 29, 29, 29, 06, 06, 26
         db 26, 06, 29, 29, 29, 31, 28, 28, 31, 31, 31, 31, 28, 28, 31, 31, 31, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 27, 31, 31, 31, 31, 31, 27, 31, 31, 31, 31, 31, 31, 27, 29, 29, 06, 26
         db 26, 29, 29, 29, 27, 27, 31, 31, 31, 31, 27, 27, 31, 31, 31, 31, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 27, 27, 27, 31, 31, 27, 27, 27, 27, 31, 31, 27, 27, 27, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 27, 27, 27, 27, 27, 30, 30, 27, 27, 27, 27, 27, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 27, 27, 27, 30, 30, 30, 30, 27, 27, 27, 29, 29, 29, 29, 29, 26
         db 26, 29, 29, 29, 29, 29, 29, 29, 27, 30, 30, 30, 30, 27, 29, 29, 29, 29, 29, 29, 29, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 26
         db 26, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 30, 30, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 29, 29, 29, 29, 29, 30, 30, 30, 30, 30, 30, 29, 29, 29, 29, 29, 06, 06, 26
         db 26, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 26
         db 26, 06, 06, 06, 06, 06, 06, 06, 29, 29, 29, 29, 29, 29, 06, 06, 06, 06, 06, 06, 06, 26
         db 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26, 26
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; 变量
         level : db 1
 ; 当前地图
 MAP_CUR : 
         times MAP_U db 0
         orgx_p : db 0
         orgy_p : db 0
         px_u   : db 0
         py_u   : db 0
         dir  : db 0
 MAP_SIZE : equ $-MAP_CUR
 
 ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
 ; 地图,级别从低到高按顺序,相对 MAP_CUR 定位
 
 %define SPACE    UID_SPACE
 %define FLOOR    UID_FLOOR
 %define WALL     UID_WALL
 %define DEST     UID_DEST
 %define BOX      (UID_FLOOR|UID_BOX)
 %define BOXDE    (UID_DEST|UID_BOX)
 %define PLAYE    UID_FLOOR
 
 MAP_LEVEL_1 : 
         db SPACE, SPACE, WALL,  WALL,  WALL,  SPACE, SPACE, SPACE
         db SPACE, SPACE, WALL,  DEST,  WALL,  SPACE, SPACE, SPACE
         db SPACE, SPACE, WALL,  FLOOR, WALL,  WALL,  WALL,  WALL
         db WALL,  WALL,  WALL,  BOX,   FLOOR, BOX,   DEST,  WALL
         db WALL,  DEST,  FLOOR, BOX,   FLOOR,   WALL,  WALL,  WALL
         db WALL,  WALL,  WALL,  WALL,  BOX,   WALL,  SPACE, SPACE
         db SPACE, SPACE, SPACE, WALL,  DEST,  WALL,  SPACE, SPACE
         db SPACE, SPACE, SPACE, WALL,  WALL,  WALL,  SPACE, SPACE
         db 90, 30, 4, 4, DIR_UP
 
 MAP_LEVEL_2 : 
         db SPACE, SPACE, WALL,  WALL,  WALL,  WALL,  SPACE, SPACE
         db SPACE, WALL,  WALL,  FLOOR, FLOOR, WALL,  SPACE, SPACE
         db SPACE, WALL,  FLOOR, BOX,   FLOOR, WALL,  SPACE, SPACE
         db SPACE, WALL,  WALL,  BOX,   FLOOR, WALL,  WALL,  SPACE
         db SPACE, WALL,  WALL,  FLOOR, BOX,   FLOOR, WALL,  SPACE
         db SPACE, WALL,  DEST,  BOX,   FLOOR, FLOOR, WALL,  SPACE
         db SPACE, WALL,  DEST,  DEST,  BOXDE, DEST,  WALL,  SPACE
         db SPACE, WALL,  WALL,  WALL,  WALL,  WALL,  WALL,  SPACE
         db 90, 30, 2, 2, DIR_UP
 
 MAP_LEVEL_3 : 
         db SPACE, WALL,  WALL,  WALL,  WALL,  WALL,  SPACE, SPACE
         db SPACE, WALL,  FLOOR, FLOOR, WALL,  WALL,  WALL,  SPACE
         db SPACE, WALL,  FLOOR, BOX,   FLOOR, FLOOR, WALL,  SPACE
         db WALL,  WALL,  WALL,  FLOOR, WALL,  FLOOR, WALL,  WALL
         db WALL,  DEST,  WALL,  FLOOR, WALL,  FLOOR, FLOOR, WALL
         db WALL,  DEST,  BOX,   FLOOR, FLOOR, WALL,  FLOOR, WALL
         db WALL,  DEST,  FLOOR, FLOOR, FLOOR, BOX,   FLOOR, WALL
         db WALL,  WALL,  WALL,  WALL,  WALL,  WALL,  WALL,  WALL
         db 90, 30, 2, 2, DIR_UP
 
 MAP_LEVEL_4 : 
         db SPACE, SPACE, WALL,  WALL,  WALL,  WALL,  WALL,  WALL
         db SPACE, WALL,  WALL,  FLOOR, FLOOR, WALL,  FLOOR, FLOOR
         db SPACE, WALL,  FLOOR, FLOOR, FLOOR, WALL,  FLOOR, FLOOR
         db SPACE, WALL,  BOX,   FLOOR, BOX,   FLOOR, BOX,   FLOOR
         db SPACE, WALL,  FLOOR, BOX,   WALL,  WALL,  FLOOR, FLOOR
         db WALL,  WALL,  FLOOR, BOX,   FLOOR, WALL,  FLOOR, WALL
         db DEST,  DEST,  DEST,  DEST,  DEST,  FLOOR, FLOOR, WALL
         db WALL,  WALL,  WALL,  WALL,  WALL,  WALL,  WALL,  WALL
         db 90, 30, 7, 1, DIR_UP
 
 MAP_LEVEL_COMPELETE : 
         db FLOOR, FLOOR, FLOOR, SPACE, SPACE, FLOOR, FLOOR, SPACE
         db FLOOR, SPACE, SPACE, SPACE, SPACE, FLOOR, SPACE, FLOOR
         db FLOOR, SPACE, SPACE, SPACE, SPACE, FLOOR, SPACE, FLOOR
         db FLOOR, FLOOR, FLOOR, SPACE, SPACE, FLOOR, SPACE, FLOOR
         db FLOOR, SPACE, SPACE, SPACE, SPACE, FLOOR, SPACE, FLOOR
         db FLOOR, SPACE, SPACE, SPACE, SPACE, FLOOR, SPACE, FLOOR
         db FLOOR, FLOOR, FLOOR, SPACE, SPACE, FLOOR, FLOOR, SPACE
         db SPACE, SPACE, SPACE, SPACE, SPACE, SPACE, SPACE, SPACE
         db 95, 40, 1, 3, DIR_UP
 


 

1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。 1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于人工智能、计算机科学与技术等相关专业,更为适合; 4、下载使用后,可先查看README.md或论文文件(如有),本项目仅用作交流学习参考,请切勿用于商业用途。 5、资源来自互联网采集,如有侵权,私聊博主删除。 6、可私信博主看论文后选择购买源代码。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值