Tetris - игра

Всякие игры. Для всех платформ.

Tetris - игра

Сообщение rvg » 23 сен 2023, 20:19

Tetris - программа откуда-то, не помню чья. Tasm нужен для сборки.
Так как она не использует графический режим (думаю запустится)
и в современной ОС. Собрать программу нужно таким образом:
Tasm Tetris
Tlink Tetris
 Развернуть: Tetris.asm
Код: Выделить всё
%TITLE "Tetris.asm"

   IDEAL

   P386
   SMART
   JUMPS
   LOCALS   @@

   MODEL   small
   STACK   256

VGA_SEGMENT   equ 0A000h
VGA_SEGMENT_T   equ 0B800h

LEFT      = 4Bh      ; Key values
RIGHT      = 4Dh
DOWN      = 50h
SPACE      = 39h
ENTERK      = 1Ch
ESCAPE      = 1
F10      = 44h

   DATASEG

exCode      db 0

VGASeg      dw VGA_SEGMENT_T   ; Vga Segment in High Memmory

CustomFont   db 14 dup(-1), 192, 128, -1, -2, 12 dup(-4), 0, 0

PieceStart   dw offset Piece1, offset Piece2
      dw offset Piece3, offset Piece4
      dw offset Piece5, offset Piece6
      dw offset Piece7

   db 1         ; AND mask
Piece1   db -1, 0, 1, 0, 2, 0      ; ЬЬЬЬ
   db 0, -1, 0, 1, 0, 2

   db 3         ; AND mask
Piece2   db 1, -1, 1, 0, -1, 0   ; ЫЬЬ
   db 1, 1, 0, 1, 0, -1
   db -1, 1, -1, 0, 1, 0
   db -1, -1,  0,-1, 0, 1

   db 3         ; AND mask
Piece3   db -1,-1, -1, 0, 1, 0   ; ЬЬЫ
   db 1,-1, 0,-1, 0, 1
   db 1, 1, 1, 0, -1, 0
   db -1, 1, 0, 1, 0,-1

   db 3         ; AND mask
Piece4   db 1, 0, 0, -1, -1, 0   ; ЬЫЬ
   db 0, 1, 1, 0, 0,-1
   db -1, 0, 0, 1, 1, 0
   db  0,-1, -1, 0, 0, 1

   db 1         ; AND mask
Piece5   db -1, 0, 0,-1, 1,-1      ; ЬЫЯ
   db  0, 1, -1, 0, -1,-1

   db 1         ; AND mask
Piece6   db 1, 0, 0,-1, -1,-1      ; ЯЫЬ
   db 0,-1, -1, 0, -1, 1

   db 0         ; AND mask
Piece7   db 0,-1, -1,-1, -1, 0   ; ЫЫ

TitleStr      db '* TinyTetris v1.0 *',0
PlayAgain   db 'Play again (Y/N) ?',0
OverStr      db ' G A M E  O V E R ',0
ScoreStr      db 'Score:',0
LevelStr      db 'Level:',0
LinesStr      db 'Lines:',0
LeftStr      db 'Lines Left:',0

Spaces10      db 3 dup(?)
Spaces7      db 8 dup(?)
GOBottom   db 19 dup(?)
GOTop      db 19 dup(?)

RandNum   dw ?,?
Score      dw ?
Lines      dw ?
Level      dw ?
DelayTime   dw ?
LinesLeft      dw ?

Piece      dw ?
Rotate      dw ?
X      dw ?
Y      dw ?

szBuffer      db 256 dup (?)

   CODESEG

proc   Tetris
   pusha
   call   ClearScreen

   mov   di, 18         ; Start at (9, 0)
   mov   cx, 25         ; 25 lines
   mov   ax, 7FB1h      ; Color and character

WellLoop:
   stosw            ; Left side of well
   mov   [word es:di+40], ax   ; Right side
   add   di, 158         ; Next line
   loop   WellLoop         ; Loop back

   mov   al, 7         ; Color
   mov   cx, 38         ; Print title string
   mov   dx, 0
   mov   si, offset TitleStr
   call   PutStr

   dec   cx         ; Print initial lines left
   dec   cx
   mov   dx, 17
   mov   si, offset LeftStr
   call   PutStr

   dec   dx         ; Print initial lines
   dec   dx
   mov   si, offset LinesStr
   call   PutStr

   dec   dx         ; Print initial level
   dec   dx
   mov   si, offset LevelStr
   call   PutStr

   dec   dx         ; Print initial score
   dec   dx
   mov   si, offset ScoreStr
   call   PutStr

; --- Initialization

   mov   ax, 0         ; Initialize variables
   mov   [Score], ax
   mov   [Level], 1
   mov   [Lines], ax
   mov   [LinesLeft], 5
   mov   [DelayTime], 1
   ;mov   [DelayTime], 750
   mov   [Rotate], ax
   mov   [X], 4
   mov   [Y], 24
   call   Rand7

   mov   [Piece], ax

MainLoop:
   call   ShowStatus

   mov   cx, [DelayTime]      ; Delay specified time
   ;mov   ax, [DelayTime]      ; Delay specified time
   call   Delay

   inc   bp         ; Ctr = (Ctr + 1) mod 4
   and   bp, 3

KeyLoop:
   mov   ah, 1         ; Check for keys
   int   16h
   jz   NoKeys

   call   LoadVals         ; Erase current piece
   mov   di, 0

   call   PutPiece

   mov   ax, 0         ; Get the key
   int   16h

   cmp   ah, LEFT         ; Left arrow?
   je   KeyLeft

   cmp   ah, RIGHT      ; Right arrow?
   je   KeyRight

   cmp   ah, DOWN      ; Down arrow?
   je   KeyDown

   cmp   ah, ENTERK      ; Enter?
   je   KeyDown

   cmp   ah, SPACE      ; Space?
   je   KeySpace

   cmp   ah, ESCAPE      ; Escape?
   je   KeyEsc

   cmp   ah, F10         ; F10?
   je   KeyF10
   jmp   KeyDone         ; Not a recognized key

KeyLeft:
   call   LoadVals         ; If it fits at (X - 1)
   dec   cx
   call   Fits
   jnc   KeyDone
   mov   [X], cx         ; move it to (X - 1)
   jmp   KeyDone

KeyRight:
   call   LoadVals         ; If it fits at (X + 1)
   inc   cx
   call   Fits
   jnc   KeyDone
   mov   [X], cx         ; move it to (X + 1)
   jmp   KeyDone

KeyDown:
   call   LoadVals         ; Load values
   mov   si, dx         ; Save old Y

DownLoop:
   dec   dx         ; While it fits at (Y-1)
   call   Fits         ; decrement Y
   jc   DownLoop
   inc   dx         ; Move to where it last fit
   mov   [Y], dx         ; Save it in Y
   call   PutPiece         ; Display the piece
   mov   ax, dx         ; Lock using (Y + old Y)
   add   ax, si
   call   PieceDown      ; Piece is down
   jmp   KeyDone         ; Done

KeySpace:
   call   LoadVals         ; Load values
   inc   ax         ; Next rotation
   and   ax, 3
   call   Fits         ; If it fits
   jnc   KeyDone
   mov   [Rotate], ax      ; Update rotation value
   jmp   KeyDone

KeyEsc:
   call   GameOver      ; Done with game

KeyF10:
   call   LVPutPiece      ; Show piece
   xor   ax, ax         ; Wait for a key
   int   16h

KeyDone:
   call   LVPutPiece      ; Show piece
   jmp   KeyLoop

; --- Piece Fall

NoKeys:
   test   bp, bp         ; Only if counter is zero
   jne   MainLoop

   call   LoadVals         ; Erase current piece
   xor   di, di
   call   PutPiece

   dec   dx         ; Check for fit at (Y - 1)
   call   Fits
   jnc   NoFit         ; Jump if it doesn't fit
   mov   [Y], dx         ; Save new Y
   call   LVPutPiece      ; Show piece
   jmp   MainLoop

NoFit:
   call   LVPutPiece      ; Show piece
   mov   ax, dx         ; Lock using Y
   call   PieceDown      ; Piece is down
   call   LVPutPiece      ; Show piece
   jmp   MainLoop      ; Loop back

; --- Game Over

GameOver:
   pop   ax         ; Pop junk-word
   mov   cx, 11         ; Print GO-top string
   mov   dx, 11
   mov   si, offset GOTop
   mov   ax, 4
   call   PutStr

   inc   dx         ; Print game-over message
   mov   si, offset OverStr      ; in blinking blue
   mov   ax, 0C9h
   call   PutStr

   inc   dx         ; Print GO-bottom string
   mov   si, offset GOBottom
   mov   ax, 4
   call   PutStr

   mov   cx, 1
   ;mov   ax, 5000         ; Delay 1/2 second
   call   Delay

   call   FlushBuffer      ; Flush key buffer

   xor   ax, ax         ; Wait for a key
   int   16h

   popa            ; Restore registers
   ret

PieceDown:
   call   LockPiece
   cmp   dx, 24         ; Too high, game over
   jge   GameOver

   mov   [Rotate], 0      ; New piece, type (random, 0)
   call   Rand7
   mov   [Piece], ax
   mov   [X], 4         ; Position (4, 24)
   mov   [Y], 24
   call   FlushBuffer      ; Flush key buffer
   ret

LoadVals:
   mov   cx, [X]         ; Load piece values
   mov   dx, [Y]
   mov   bx, [Piece]
   mov   ax, [Rotate]
   mov   di, bx
   inc   di
   ret

LVPutPiece:
   call   LoadVals         ; Load piece values
   jmp   PutPiece

endp   Tetris

proc   LockPiece

   ; Locks a piece in place

   pusha            ; Save all registers

   mov   ax, [Level]      ; AX = Level
   imul   ax, 10         ; 10 * Level
   add   [Score], ax      ; add to score

   call   DelLines         ; Delete lines
   add   [Lines], ax      ; Adjust line counter
   sub   [LinesLeft], ax

   imul   ax, 50         ; Line score value
   add   [Score], ax      ; add to score

   cmp   [LinesLeft], 0      ; Done with level?
   jg   NotNew

   mov   [LinesLeft], 0      ; LinesLeft = 0
   call   ShowStatus      ; Show status

   call   ClearWell         ; Clear well
   imul   ax, [Level], 100      ; Score = Score + 100 * Level
   add   [Score], ax
   inc   [Level]         ; Next level

   ;imul   ax, [DelayTime], 7      ; Reduce delay by 12%
   ;shr   ax, 3
   ;mov   [DelayTime], ax

   imul   ax, [Level], 2      ; LinesLeft = 6 + 2 * Level
   add   ax, 6
   mov   [LinesLeft], ax

NotNew:
   call   ShowStatus      ; Show status

   popa            ; Restore registers
   ret
endp   LockPiece

proc   ShowStatus

   ; Display score, level, etc

   pusha            ; Save all registers

   mov   cx, 43         ; Clear Score field
   mov   dx, 11
   mov   si, offset Spaces7
   mov   al, 7
   call   PutStr

   inc   dx         ; Clear Level field
   inc   dx
   call   PutStr

   inc   dx         ; Clear Lines field
   inc   dx
   call   PutStr

   inc   dx         ; Clear Lines Left field
   inc   dx
   add   cx, 5
   add   si, 5
   call   PutStr

   mov   si, offset szBuffer      ; Offset of buffer
   mov   ax, [Score]      ; Get decimal string for Score
   mov   di, si
   call   Cvt16

   mov   cx, 43         ; Print it at (43, 11)
   mov   dx, 11
   mov   al, 0Ah
   call   PutStr

   mov   ax, [Level]      ; Get decimal string for Level
   mov   di, si
   call   Cvt16

   inc   dx         ; Print it at (43, 13)
   inc   dx
   mov   al, 0Ah
   call   PutStr

   mov   ax, [Lines]      ; Get decimal string for Lines
   mov   di, si
   call   Cvt16

   inc   dx         ; Print it at (43, 15)
   inc   dx
   mov   al, 0Ah
   call   PutStr

   mov   ax, [LinesLeft]      ; Get decimal string for Lines Left
   mov   di, si
   call   Cvt16

   mov   cx, 48         ; Print it at (48, 17)
   inc   dx
   inc   dx
   mov   al, 0Ah
   call   PutStr

   popa            ; Restore registers
   ret
endp   ShowStatus

proc   PutBlock

   ; Put block on screen
   ; Supply CX = x, DX = y, AL = color

   pusha            ; Save all registers

   imul   di, dx, 160      ; DI = DX * 160
   add   di, cx         ; DI = DX * 160 + CX * 2
   add   di, cx
   test   al, al         ; If zero, erase block
   jz   short IS_ZERO

   mov   ah, al         ; AH = color
   shl   ah, 4
   add   ah, 8         ; Foreground = color + 8
   add   ah, al

   mov   al, 0CEh         ; Store first half
   stosw
   inc   ax         ; Store second half
   stosw
   popa            ; Restore registers
   ret            ; Return

IS_ZERO:
   mov   ax, 720h         ; Zero, store spaces
   stosw
   stosw
   popa            ; Restore registers
   ret
endp   PutBlock

proc   IsBlock

   ; Check for block
   ; Supply CX = x, DX = y
   ; Returns Carry = 1 if block

   pusha            ; Save all registers

   add   cx, cx
   add   cx, 10         ; Adjust to screen position
   neg   dx
   add   dx, 24
   imul   di, dx, 160      ; DI = DX * 160
   add   di, cx         ; DI = DX * 160 + CX * 2
   add   di, cx
   mov   al, [es:di]      ; Load byte
   cmp   al, 0CEh         ; If it's < 0CEh
   jb   NoBlock         ; it isn't a block

   stc            ; Set carry flag
   popa            ; Restore registers
   ret
NoBlock:
   clc            ; Clear carry flag
   popa            ; Restore registers
   ret
endp   IsBlock

proc   PutPiece

   ; Put piece in well
   ; Supply CX = x, DX = y
   ; BX = piece, AX = rotation, DI = color

   pusha            ; Save all registers

   mov   bp, di         ; Color in BP
   add   bx, bx
   mov   si, [PieceStart+bx]      ; SI = piece start
   and   al, [si-1]         ; AND mask
   imul   ax, 6         ; AX * 6
   add   si, ax         ; SI = piece offset

   mov   di, 4         ; 4 blocks
   xor   ax, ax         ; Start with (0, 0)

BlockLoop:
   push   cx dx         ; Save position
   mov   bl, ah         ; Get offsets in AX, BX
   cbw
   xchg   ax, bx
   cbw
   xchg   ax, bx
   add   cx, ax         ; Add in offsets
   add   dx, bx
   cmp   cx, 10         ; Out of well, don't show
   jae   BlockNope
   cmp   dx, 25
   jae   BlockNope
   add   cx, cx
   add   cx, 10         ; Adjust to screen position
   neg   dx
   add   dx, 24
   mov   ax, bp         ; Color in AL
   call   PutBlock         ; Show block

BlockNope:
   pop   dx cx         ; Restore position
   lodsw            ; Load word
   dec   di         ; Loop back using DI
   jnz   BlockLoop

   popa            ; Restore registers
   ret
endp   PutPiece

proc   Fits

   ; Check whether piece fits
   ; Supply CX = x, DX = y
   ; BX = piece, AX = rotation
   ; Returns: Carry = 1 if it fits, 0 if it doesn't

   pusha            ; Save all registers

   add   bx, bx
   mov   si, [PieceStart+bx]      ; SI = piece start
   and   al, [si-1]         ; AND mask
   imul   ax, 6         ; AX * 6
   add   si, ax         ; SI = piece offset

   mov   di, 4         ; 4 blocks
   xor   ax, ax         ; Start with (0, 0)
FitsLoop:
   push   cx dx         ; Save position
   mov   bl, ah         ; Get offsets in AX, BX
   cbw
   xchg   ax, bx
   cbw
   xchg   ax, bx
   add   cx, ax         ; Add in offsets
   add   dx, bx
   cmp   cx, 10         ; Out of well, doesn't fit
   jae   DoesntFit
   test   dx, dx
   jl   DoesntFit

   call   IsBlock         ; Check for block
   jc   DoesntFit

   pop   dx cx         ; Restore position
   lodsw            ; Load word
   dec   di         ; Loop back using DI
   jnz   FitsLoop

   stc            ; Set carry flag
   popa            ; Restore registers
   ret

DoesntFit:
   clc            ; Clear carry flag
   pop   dx cx         ; Pop extra off stack
   popa            ; Restore registers
   ret
endp   Fits

proc   DelLine

   ; Delete line
   ; Supply AX = y

   pusha            ; Save all registers
   push   ds         ; Save DS
   push   es         ; DS = ES
   pop   ds
   neg   ax         ; Adjust for screen position
   add   ax, 24
   xchg   dx, ax
   imul   di, dx, 160      ; DI = DX * 160
   add   di, 20         ; DI = DX * 160 + 20
   mov   si, di         ; SI = previous line
   sub   si, 160

ScDnLoop:
   push   si si         ; Save offsets
   mov   cx, 20         ; Move line
   rep   movsw
   pop   si di         ; DI = old SI,
   sub   si, 160         ; SI = old SI - 160
   dec   dx         ; Loop back using DX
   jnz   ScDnLoop

   pop   ds
   popa            ; Restore registers
   ret
endp   DelLine

proc   DelLines

   ; Delete all completed lines

   push   cx         ; Save CX
   xor   cx, cx         ; Zero CX
   mov   ax, 24         ; AX = 24
DelLoop:
   pusha            ; Save all registers
   xchg   dx, ax         ; Y in DX
   mov   cx, 9         ; CX = 9
LChkLoop:
   call   IsBlock         ; Check for block
   jnc   NotLine         ; Not a line if no block
   dec   cx         ; Loop back using CX
   jns   LChkLoop
   stc            ; Set carry flag
NotLine:
   popa            ; Restore registers
   jnc   $+6         ; Jump if not line
   call   DelLine         ; Delete line
   inc   cx         ; Increment counter
   dec   ax         ; Next line
   jns   DelLoop         ; Loop back
   xchg   ax, cx         ; Lines in AX
   pop   cx         ; Restore CX
   ret
endp   DelLines

proc   ClearWell

   ; Clear the well

   pusha            ; Save all registers

   mov   di, 20         ; Start at offset 20
   mov   dx, 25         ; 25 rows on screen
   mov   ax, 720h         ; Fill with spaces

ClearWLoop:
   mov   cx, 20         ; Width of well
   rep   stosw         ; Clear line
   add   di, 120         ; Go to next line
   dec   dx         ; Loop back using DX
   jnz   ClearWLoop
   popa            ; Restore registers
   ret
endp   ClearWell

proc   ClearScreen

   pusha         ; Save all registers

   xor   di, di      ; Zero DI
   mov   ax, 720h      ; Fill with spaces
   mov   cx, 4000      ; 4000 words
   rep   stosw      ; Clear screen
   popa         ; Restore registers
   ret
endp   ClearScreen

proc   PutStr

   ; Print ASCIIZ string
   ; CX, DX = position
   ; AL = color, DS:SI = string

   push   ax cx dx di

   imul   di, dx, 160   ; DI = DX * 160
   add   di, cx      ; DI = DX * 160 + CX * 2
   add   di, cx
   mov   ah, al      ; AH = color
@@10:
   lodsb         ; Load byte
   cmp   al, 0      ; Quit if zero
   je   @@99
   stosw         ; Store word
   jmp   @@10
@@99:
   pop   di dx cx ax
   ret
endp   PutStr

proc   FlushBuffer

   ; Flush keyboard buffer

   push   ds      ; Save DS
   push   0      ; DS = 0
   pop   ds
   push   [word 41Ah]   ; Key tail = key head
   pop   [word 41Ch]
   pop   ds      ; Restore DS
   ret
endp   FlushBuffer

proc        Cvt16

   ; Convert 16-bit binary to decimal
   ; Supply AX = binary value
   ; DS:DI = 5 bytes string space

   pusha         ; Save registers
   pop   di
   test   ax, ax      ; If zero, then just
   je   U16Zero      ; output a zero
   xor   cx, cx      ; Zero CX
   mov   si, 10      ; SI = 10

U16DivLoop:
   xor   dx, dx      ; Zero DX
   div   si      ; Divide by 10
   mov   bl, dl      ; Remainder in BL
   add   bl, 30h      ; Convert to digit
   push   bx      ; Save digit
   inc   cx      ; Increment CX
   test   ax, ax      ; Zero now?
   jnz   U16DivLoop   ; Loop back if not

U16PopLoop:
   pop   ax      ; Pop digit
   mov   [di], al      ; Store digit
   inc   di
   loop   U16PopLoop   ; Loop back

U16Ret:
   mov   [byte di], 0   ; Store ending null
   push   di      ; Restore registers
   popa
   ret

U16Zero:
   mov   [byte di], 30h   ; It was zero, so store a '0'
   inc   di
   jmp   U16Ret

endp   Cvt16

proc   Rand7

   ; Generate a random number from 1 to 7

   mov   ax, 7      ; Call Rand with value 7
   call   Rand
   ret
endp   Rand7

proc   Rand

   ; Generate a random number

   push   bx cx dx ax      ; Save registers, push AX
   mov   ax, 4E35h
   mul   [RandNum]      ; Here the Random Number is
   mov   cx, dx         ; multiplied by the value
   xchg   bx, ax         ; 015A4E35h This is one of
   imul   ax, [RandNum], 015Ah   ; the optimal values for
   add   cx, ax         ; this type of random number.
   imul   ax, [RandNum+2], 4E35h
   add   cx, ax
   add   bx, 1         ; Increment the number
   adc   cx, 0
   mov   [RandNum], bx      ; Save random number
   mov   [RandNum+2], cx
   xchg   ax, cx         ; Now the bits are re-arranged
   shl   ax, 1         ; and the number is divided by
   and   bx, 1         ; the value originally in AX
   add   ax, bx
   pop   bx
   xor   dx, dx
   div   bx
   xchg   ax, dx         ; Place result in AX
   pop   dx cx bx         ; Restore registers
   ret
endp   Rand

proc   Delay_1

   ; Supply AX = milliseconds * 10.

   pusha         ; Save all registers

   mov   dx, 100
   mul   dx
   mov   cx, dx
   xchg   dx, ax      ; CX:DX = time in microseconds
   mov   ah, 86h      ; INT 15/86 = BIOS delay
   int   15h
   popa         ; Restore registers
   ret
endp   Delay_1

proc   Delay

   ; Simple BIOS delay
   ; Requires number of reiterations in CX on entry

   push   ds
   mov   ax, 40h
   mov   ds, ax
   mov   bx, 6Ch      ; BIOS timer, 40:6C
@@10:
   mov   al, [bx]
@@99:
   cmp   al, [bx]      ; Is it the same?
   je   @@99      ; Yes, try again
   loop   @@10      ; Loop and decrement CX
   pop   ds      ; Restore registers and exit
   ret
endp   Delay

;
; Entry point
;
Start:
   mov   ax, @data   ; Set DS to point to data segment
   mov   ds, ax
   mov   es, ax

   mov   ax, 3      ; Set text mode
   int   10h

   mov   ax, 1110h   ; Set font chars CE, CF to
   mov   bx, 1000h   ; the 'block' image
   mov   cx, 2
   mov   dx, 0CEh
   mov   bp, offset CustomFont
   int   10h

   mov   ah, 2         ; Turn off the cursor by
   xor   bh, bh         ; placing it off the screen
   mov   dx, 1E00h
   int   10h

   mov   di, offset Spaces10      ; Set up space buffer
   mov   cx, 10
   mov   al, 20h

   rep   stosb         ; Copy, fill memory
   mov   al, 0
   stosb            ; Copy, fill memory

   mov   cx, 18         ; Set up top/bottom lines
   mov   al, 0DFh
   rep   stosb
   mov   al, 0
   stosb            ; Copy, fill memory
   mov   cx, 18
   mov   al, 0DCh
   rep   stosb
   mov   ax, 0
   stosb            ; Copy, fill memory

   push   ax         ; ES = 0
   pop   es

   mov   ax, [es:046Ch]      ; Seed random number with
   mov   [RandNum], ax      ; the BIOS time counter
   mov   ax, [es:046Eh]
   mov   [RandNum+2], ax

   ;push   0B800h         ; ES = 0B800h (text video memory)
   ;pop   es

   mov   es, [VGASeg]      ; Set ES to point to video segment

GameLoop:
   
   call   Tetris         ; Play game
   call   ClearScreen      ; Clear screen

   mov   al, 9Fh         ; Color = blinking white on blue
   mov   cx, 31         ; Print 'Play again?' string
   mov   dx, 12         ; in the middle of the screen
   mov   si, offset PlayAgain
   call   PutStr

   call   FlushBuffer      ; Flush key buffer

@@GETCH:
   xor   ax, ax         ; Get a key
   int   16h

   cmp   ah, 15h         ; If it's a 'Y', then play again
   je   GameLoop

   cmp   ah, 31h         ; If it's an 'N', then quit
   jne   @@GETCH

GameDone:

   mov   ax, 3         ; Set text mode, restore font
   int   10h
Exit:
   mov   ax, 3         ; Set 80x25x16 char mode
   int   10h

   mov   ah, 4Ch         ; Return to DOS
   mov   al, [exCode]
   int   21h

   END   Start
Вложения
Tetris.zip
(5.79 Кб) Скачиваний: 135
Аватара пользователя
rvg
Мастер Даунгрейда
 
Сообщения: 594
Зарегистрирован: 18 июл 2023, 14:12

Re: Tetris - игра

Сообщение rvg » 23 сен 2023, 20:21

Вот так выглядит
Вложения
Tetris1.jpg
Tetris1.jpg (98.11 Кб) Просмотров: 4501
Аватара пользователя
rvg
Мастер Даунгрейда
 
Сообщения: 594
Зарегистрирован: 18 июл 2023, 14:12


Re: Tetris - игра

Сообщение clihlt » 23 сен 2023, 21:41

Тетрис, это наверное первая игрушка, которую все пишут в детстве.
С уважением,
Владислав Васильев (aka clihlt).
Аватара пользователя
clihlt
Мастер Даунгрейда
 
Сообщения: 242
Зарегистрирован: 20 мар 2023, 21:17
Откуда: Брянск, СССР

Re: Tetris - игра

Сообщение Nika » 23 сен 2023, 21:49

Тот дистрибутив, что по ссылке, не очень удачный
- он ориентирован на WIN32-программирование
и всё дос-овское 16-битное оттуда вычищено.
Хотя работать в Windows он будет, и dos-программы собирать он может.

Впрочем, портабельный он там единственный, так уж получилось.
Последний раз редактировалось Nika 23 сен 2023, 22:00, всего редактировалось 1 раз.
Nika
Мастер Даунгрейда
 
Сообщения: 866
Зарегистрирован: 16 окт 2013, 23:21


Вернуться в Игры

Кто сейчас на конференции

Сейчас этот форум просматривают: нет зарегистрированных пользователей и гости: 1