.MODEL TINY public Print public TestSpace public Bottom public InitScreen public PrintLong public GameOverPrompt public RemovePause public PrintPause extrn RandSeed:word extrn Items:word BORDER_CHAR equ 32 BORDER_COLOR equ 29 HISCORE_TEXT_POS equ 0 SCORE_TEXT_POS equ 240 LEVEL_TEXT_POS equ 400 LOGO_POS equ 800 BY_POS equ 970 TORE_POS equ 1128 BAST_POS equ 1202 PREVIEW_TEXT_POS equ 134 GAME_OVER_POS equ 934 PLAY_AGAIN_POS equ 1654 PAUSE_POS equ 934 .DATA TetrisLogo label word db 'S',1 db 'm',2 db 'a',3 db 'l',4 db 'l',5 db 'T',6 db 'e',7 db 't',8 db 'r',9 db 'i',10 db 's',11 dw 0 db 'b',7 db 'y',7 dw 0 db 'T',1 db 'o',2 db 'r',3 db 'e',4 dw 0 db 'B',6 db 'a',7 db 's',8 db 't',9 db 'i',10 db 'a',11 db 'n',12 db 's',13 db 'e',14 db 'n',15 dw 0 db 'HISCORE:',0 db 'SCORE:',0 db 'LEVEL:',0 db 'Preview:',0 GameOverText label word db 'GAME OVER',0 db 'Play again?',0 RemovePauseText label byte db 5 dup (' ') db 0 PauseText db 'PAUSE',0 RowFill db 25 dup (?) .CODE InitScreen proc near mov ax,0001h ; Screen mode 1 int 10h xor di,di mov ax,0b800h mov es,ax mov cx,1000 xor ax,ax rep stosw ; Fill screen with 0 mov ax,BORDER_CHAR+256*BORDER_COLOR ; Horisontal lines mov di,28 mov cx,12 rep stosw ; Upper mov di,28+24*80 mov cx,12 rep stosw ; Lower mov cx,23 mov ax,BORDER_CHAR+256*BORDER_COLOR ; Vertical lines mov di,80+28 loop_s1: mov es:[di],ax add di,22 mov es:[di],ax add di,58 loop loop_s1 push es push ds pop es mov cx,25 mov di, offset RowFill mov ax,0 rep stosb ; Clear buffer pop es ; Print text mov di,LOGO_POS mov si,offset TetrisLogo call PrintColorString mov di,BY_POS call PrintColorString mov di,TORE_POS call PrintColorString mov di,BAST_POS call PrintColorString mov ah,1 mov di,HISCORE_TEXT_POS call PrintMonoString mov di,SCORE_TEXT_POS call PrintMonoString mov di,LEVEL_TEXT_POS call PrintMonoString mov di,PREVIEW_TEXT_POS call PrintMonoString ret InitScreen endp DeleteRow proc near ;bx=Row mov dx,0b800h mov es,dx dec bx mov cx,bx mov ax,bx mov dx,80 imul dx add ax,30 ; ax=source offset mov si,ax loop_d1: mov di,si add di,80 push cx mov cx,10 push ds push es pop ds rep movsw pop ds sub si,100 mov cl,byte ptr RowFill[bx] mov byte ptr RowFill[bx+1],cl dec bx pop cx loop loop_d1 ret DeleteRow endp Bottom proc near ;ax=ItemNr di=scroffset mov dx,0b800h mov es,dx mov dx,06 imul dx add ax, offset Items ; ax=ax*6 xor cx,cx ; for cx=0 to 3 loop_b1: mov bx,ax add bx,cx push ax mov al,byte ptr [bx+2] cbw shl ax,1 add di,ax mov ax,di xor dx,dx mov bx,80 div bx mov bx,ax inc byte ptr RowFill[bx] pop ax inc cx cmp cx,4 jne loop_b1 xor bx,bx loop_b2: cmp byte ptr RowFill[bx],10 jne not_full push bx call DeleteRow inc word ptr randseed pop bx not_full: inc bx cmp bx,24 jne loop_b2 ret Bottom endp TestSpace proc near ;ax= item_nr di=scroffs mov dx,0b800h mov es,dx mov dx,06 imul dx add ax, offset Items ; ax=ax*6 xor dx,dx ; for dx=0 to 3 loop1: mov bx,ax add bx,dx push ax mov al,byte ptr [bx+2] cbw shl ax,1 add di,ax pop ax cmp word ptr es:[di],0 jne bad inc dx cmp dx,4 jne loop1 mov ax,01 ret bad: xor ax,ax ret TestSpace endp Print proc near ;ax= item_nr di=scroffs si=T/F mov dx,0b800h mov es,dx mov dx,06 imul dx ; ax=ax*6 add ax, offset Items ; ax+=[_items] xor dx,dx ; for dx=3 to 0 cmp si,0 je loop2 mov bx,ax mov si,ds:[bx] loop2: mov bx,ax add bx,dx push ax mov al,byte ptr [bx+2] cbw shl ax,1 add di,ax pop ax mov es:[di],si inc dx cmp dx,4 jne loop2 ret Print endp PrintLong proc near mov bx,0b800h mov es,bx mov bx,10 more_digits: div bx add dx,'0'+256*7 mov es:[di],dx sub di,2 mov dx,0 cmp ax,0 jne short more_digits ret PrintLong endp PrintColorString proc near mov bx,0b800h mov es,bx color_loop: mov ax,ds:si inc si inc si and ax,ax jz color_done mov es:di,ax inc di inc di jmp color_loop color_done: ret PrintColorString endp PrintMonoString proc near mov bx,0b800h mov es,bx mono_loop: mov al,ds:si inc si and al,al jz mono_done mov es:di,ax inc di inc di jmp mono_loop mono_done: ret PrintMonoString endp GameOverPrompt proc near mov ah,1 mov di,GAME_OVER_POS mov si,offset GameOverText call near ptr PrintMonoString mov di,PLAY_AGAIN_POS call near ptr PrintMonoString ret GameOverPrompt endp RemovePause proc near xor ah,ah mov di,PAUSE_POS mov si,offset RemovePauseText call PrintMonoString ret RemovePause endp PrintPause proc near mov ah,1 mov di,PAUSE_POS mov si,offset PauseText call PrintMonoString ret PrintPause endp end