kolibrios/programs/games/attack/attack.asm

905 lines
23 KiB
NASM
Raw Permalink Normal View History

; Initially written by CH@YKIN EVGENY, 2009
; Then disassembled for fun by dunkaist, 2017
use32
org 0
db 'MENUET01'
dd 1
dd start
dd I_END
dd stacktop
dd stacktop
dd 0, 0
include 'proc32.inc'
include 'struct.inc'
include 'macros.inc'
include 'encoding.inc'
CLIENT_WIDTH = 300
CLIENT_HEIGHT = 200
HEALTH_INIT = 24
HEALTH_BONUS = 3
HEALTH_LEVEL_UP = 297
BULLET_DAMAGE = 12
BULLETS_CNT = 4
NOTE_DAMAGE = 0x31
NOTE_SAVE = 0x63
NOTE_WIN_0 = 0x36
NOTE_WIN_1 = 0x35
NOTE_WIN_2 = 0x31
NOTE_LOST_0 = 0x0d
NOTE_LOST_1 = 0x09
NOTE_LOST_2 = 0x20
BULLET_SIZE = 7
SHIELD_SIZE = 20
DELAY_INIT = 10
DELAY_NOTE = 10
DELAYS_PER_GAME_STEP = 10
NW = 1 ; north west
SW = 2
NE = 3
SE = 4
macro draw_bullet off_on, x, y {
mov eax, 7
mov ebx, _pic_bullet_#off_on
mov ecx, (BULLET_SIZE SHL 16) + BULLET_SIZE
mov edx, x
imul edx, edx, 0x10000
add edx, y
mcall
}
macro draw_shield side, x, y {
mov eax, 7
mov ebx, pic_shield_#side
mov ecx, (SHIELD_SIZE SHL 16) + SHIELD_SIZE
mov edx, x
imul edx, edx, 0x10000
add edx, y
mcall
}
macro play_note note {
mov eax, note
mov dword [speaker.note], eax
mov eax, 55
mov ebx, eax
mov esi, speaker
mcall
}
start:
mcall 48, 3, sys_colors, sizeof.system_colors
jmp menu
menu:
mcall 10
cmp eax, 1
jz .redraw
cmp eax, 2
jz .button
cmp eax, 3
jz .key
jmp menu
.redraw:
jmp .draw
.button:
mcall 2
cmp ah, '1'
jz .init_game
cmp ah, '2'
jz .resume_game
jmp menu
.init_game:
mov eax, 13
mov ebx, 0
imul ebx, ebx, 0x10000
add ebx, CLIENT_WIDTH
mov ecx, 0
imul ecx, ecx, 0x10000
add ecx, CLIENT_HEIGHT
mov edx, 0
mcall
mov [game_started], 0
mov [shield_position], SE
mov [finish_draw], 1
mov [next_bullet_side_prng], 3
mov [next_bullet_side], SE
mov [bullet_1_pos], 1
mov [bullet_2_pos], 2
mov [bullet_3_pos], 3
mov [bullet_4_pos], 4
mov eax, NW
mov [bullet_1_side], eax
mov eax, SW
mov [bullet_2_side], eax
mov eax, NE
mov [bullet_3_side], eax
mov eax, SE
mov [bullet_4_side], eax
mov eax, 1
mov [bullet_pos], eax
mov eax, NW
mov [bullet_side], eax
mov eax, 1
mov [cur_bullet], eax
mov eax, 1
mov [delays_cnt], eax
mov eax, HEALTH_INIT
mov [health], eax
mov eax, DELAY_INIT
mov [delay], eax
jmp redraw_window
.resume_game:
mov eax, 13
mov ebx, 0
imul ebx, ebx, 0x10000
add ebx, CLIENT_WIDTH
mov ecx, 0
imul ecx, ecx, 0x10000
add ecx, CLIENT_HEIGHT
mov edx, 0
mcall
jmp redraw_window
.key:
mcall 17
cmp ah, 0x01 ; close button
jnz menu
.exit:
mcall -1
.draw:
mov eax, [finish_draw]
cmp eax, 1
jz .draw.start
jmp .draw.finish
.draw.finish:
mcall 12, 2
jmp .draw.start
.draw.start:
mov eax, 0
mov [finish_draw], eax
mcall 12, 1
mcall 48, 4
mov [skin_height], eax
mcall 48, 4
mov [skin_height], eax
mov eax, 0
mov ebx, (100 SHL 16) + CLIENT_WIDTH + 10
mov ecx, 100
imul ecx, ecx, 0x10000
add ecx, CLIENT_HEIGHT + 4
add ecx, [skin_height]
mov edx, 0x33000000
mov edi, window_title
mcall
mov eax, 13
mov ebx, 0
imul ebx, ebx, 0x10000
add ebx, CLIENT_WIDTH + 1
mov ecx, 0
imul ecx, ecx, 0x10000
add ecx, CLIENT_HEIGHT
mov edx, 0
mcall
mcall 4, (140 SHL 16) + 60, 0x10bbbbbb, msg_ataka, msg_ataka.size
mcall 4, (140 SHL 16) + 61, 0x10bbbbbb, msg_ataka, msg_ataka.size
mcall 4, (141 SHL 16) + 61, 0x10bbbbbb, msg_ataka, msg_ataka.size
mcall 4, (141 SHL 16) + 60, 0x10bbbbbb, msg_ataka, msg_ataka.size
mcall 4, ( 55 SHL 16) + 190, 0x10444444, msg_copyright, msg_copyright.size
mov eax, 4
mov ebx, (34 SHL 16) + 160
mov ecx, 0x888888
mov edx, msg_control_by_numpad
mov esi, 40
.print_line:
mcall
add ebx, 10 ; one line down
add edx, 40
cmp byte [edx], 'x'
jnz .print_line
mcall 4, (110 SHL 16) + 95, 0x10999999, msg_new_game, msg_new_game.size
mov eax, [game_started]
cmp eax, 0
jz menu
mcall 4, (110 SHL 16) + 110, 0x10999999, msg_continue, msg_continue.size
jmp menu
redraw_window:
mov eax, [finish_draw]
cmp eax, 1
jz redraw_window.start
mcall 12, 2
jmp redraw_window.start
redraw_window.start:
mov eax, 0
mov [finish_draw], eax
mcall 12, 1
mcall 48, 4
mov [skin_height], eax
mov eax, 0
mov ebx, (100 SHL 16) + CLIENT_WIDTH + 10
mov ecx, 100
imul ecx, ecx, 0x10000
add ecx, CLIENT_HEIGHT + 4
add ecx, [skin_height]
mov edx, 0x33000000
mov edi, window_title
mcall
jmp draw_field
game_loop:
mov [game_started], 1
mov eax, [health]
cmp eax, HEALTH_LEVEL_UP
jg level_up
cmp eax, 0
jl lost
jmp game_alive
level_up:
mov eax, HEALTH_INIT
mov [health], eax
mov eax, [delay]
cmp eax, 10 ; delay for level_0
jz level_up_1
mov eax, [delay]
cmp eax, 8 ; delay for level_1
jz level_up_2
mov eax, [delay]
cmp eax, 7
jz level_up_3
mov eax, [delay]
cmp eax, 6
jz level_up_4
mov eax, [delay]
cmp eax, 5
jz level_up_5
mov eax, [delay]
cmp eax, 4
jz level_up_6
mov eax, [delay]
cmp eax, 3
jz win
jmp game_alive
lost:
mcall 5, DELAY_NOTE
play_note NOTE_LOST_0
mcall 5, DELAY_NOTE
play_note NOTE_LOST_1
mcall 5, DELAY_NOTE
play_note NOTE_LOST_2
mov [game_started], 0
mcall 4, (105 SHL 16) + 100, 0xff0000, msg_you_lost, msg_you_lost.size
mcall 5, 100
mov eax, SE
mov [shield_position], eax
mov eax, 1
mov [finish_draw], eax
mov eax, 3
mov [next_bullet_side_prng], eax
mov eax, SE
mov [next_bullet_side], eax
mov eax, 1
mov [bullet_1_pos], eax
mov eax, 2
mov [bullet_2_pos], eax
mov eax, 3
mov [bullet_3_pos], eax
mov eax, 4
mov [bullet_4_pos], eax
mov eax, NW
mov [bullet_1_side], eax
mov eax, SW
mov [bullet_2_side], eax
mov eax, NE
mov [bullet_3_side], eax
mov eax, SE
mov [bullet_4_side], eax
mov eax, 1
mov [bullet_pos], eax
mov eax, NW
mov [bullet_side], eax
mov eax, 1
mov [cur_bullet], eax
mov eax, 1
mov [delays_cnt], eax
mov eax, HEALTH_INIT
mov [health], eax
mov eax, DELAY_INIT
mov [delay], eax
jmp menu.draw
level_up_1:
mov eax, 8
mov [delay], eax
jmp game_alive
level_up_2:
mov eax, 7
mov [delay], eax
jmp game_alive
level_up_3:
mov eax, 6
mov [delay], eax
jmp game_alive
level_up_4:
mov eax, 5
mov [delay], eax
jmp game_alive
level_up_5:
mov eax, 4
mov [delay], eax
jmp game_alive
level_up_6:
mov eax, 3
mov [delay], eax
jmp game_alive
win:
mcall 5, DELAY_NOTE
play_note NOTE_WIN_0
mcall 5, DELAY_NOTE
play_note NOTE_WIN_1
mcall 5, DELAY_NOTE
play_note NOTE_WIN_2
mcall 5, DELAY_NOTE
mov [game_started], 0
mov eax, DELAY_INIT
mov [delay], eax
mcall 4, (105 SHL 16) + 100, 0xff0000, msg_you_won, msg_you_won.size
mcall 5, 200
jmp menu.draw
game_alive:
; draw max health bar
mov eax, 13
mov ebx, 0
imul ebx, ebx, 0x10000
add ebx, CLIENT_WIDTH + 1
mov ecx, 0
imul ecx, ecx, 0x10000
inc ecx
mov edx, 0xff0000
mcall
; draw left health bar
mov eax, 13
mov ebx, 0
imul ebx, ebx, 0x10000
add ebx, [health]
mov ecx, 0
imul ecx, ecx, 0x10000
inc ecx
mov edx, 0x0000ff
mcall
mov eax, [next_bullet_side_prng]
inc eax
mov [next_bullet_side_prng], eax
mov eax, [next_bullet_side_prng]
cmp eax, 1
jz ._1
mov eax, [next_bullet_side_prng]
cmp eax, 2
jz ._2
mov eax, [next_bullet_side_prng]
cmp eax, 3
jz ._3
mov eax, [next_bullet_side_prng]
cmp eax, 4
jz ._4
mov eax, [next_bullet_side_prng]
cmp eax, 5
jz ._5
mov eax, [next_bullet_side_prng]
cmp eax, 6
jz ._6
mov eax, [next_bullet_side_prng]
cmp eax, 7
jz ._7
mov eax, [next_bullet_side_prng]
cmp eax, 8
jz ._8
mov eax, [next_bullet_side_prng]
cmp eax, 9
jg ._9
mov eax, 3
mov [next_bullet_side], eax
jmp check_event
._1:
mov eax, 1
mov [next_bullet_side], eax
jmp check_event
._2:
mov eax, 4
mov [next_bullet_side], eax
jmp check_event
._3:
mov eax, 3
mov [next_bullet_side], eax
jmp check_event
._4:
mov eax, 4
mov [next_bullet_side], eax
jmp check_event
._5:
mov eax, 1
mov [next_bullet_side], eax
jmp check_event
._6:
mov eax, 2
mov [next_bullet_side], eax
jmp check_event
._7:
mov eax, 1
mov [next_bullet_side], eax
jmp check_event
._8:
mov eax, 2
mov [next_bullet_side], eax
jmp check_event
._9:
mov eax, 3
mov [next_bullet_side], eax
mov eax, 1
mov [next_bullet_side_prng], eax
jmp check_event
check_event:
mcall 5, [delay]
mcall 11
cmp eax, 1
jz redraw_window
cmp eax, 2
jz .button
cmp eax, 3
jz .key
jmp draw_field
.key:
mov al, 17
mcall
cmp ah, 1
jnz draw_field
mcall -1
.button:
mov al, 2
mcall
cmp ah, 0xb0 ; arrow left / numpad 4
jz .move_shield_tl
cmp ah, 0xb5 ; end / numpad 1
jz .move_shield_bl
cmp ah, 0xb3 ; arrow right / numpad 6
jz .move_shield_tr
cmp ah, 0xb7 ; page down / numpad 3
jz .move_shield_br
cmp ah, 0xb0 ; never happens, fixme
jz menu.draw
cmp ah, 'p' ; 'p' for pause
jz menu.draw
cmp ah, '4'
jz .move_shield_tl
cmp ah, '1'
jz .move_shield_bl
cmp ah, '6'
jz .move_shield_tr
cmp ah, '3'
jz .move_shield_br
jmp draw_field
.move_shield_tl:
mov eax, 1
mov [shield_position], eax
jmp draw_field
.move_shield_bl:
mov eax, 2
mov [shield_position], eax
jmp draw_field
.move_shield_tr:
mov eax, 3
mov [shield_position], eax
jmp draw_field
.move_shield_br:
mov eax, 4
mov [shield_position], eax
jmp draw_field
draw_field:
mcall 18, 14
; mcall 65, pic_bg, (CLIENT_WIDTH SHL 16) + CLIENT_HEIGHT, 0, 8, paletter, 0
mov eax, 65
mov ebx, pic_bg
mov ecx, (CLIENT_WIDTH SHL 16) + CLIENT_HEIGHT
mov edx, 0
mov esi, 8 ; indexed image
mov edi, palette
mov ebp, 0
mcall
mov eax, [shield_position]
cmp eax, NW
jz .shield_nw
cmp eax, SW
jz .shield_sw
cmp eax, NE
jz .shield_ne
cmp eax, SE
jz .shield_se
.shield_nw:
draw_shield nw, 90, 70
jmp draw_bullets
.shield_sw:
draw_shield sw, 90, 105
jmp draw_bullets
.shield_ne:
draw_shield ne, CLIENT_HEIGHT, 70
jmp draw_bullets
.shield_se:
draw_shield se, CLIENT_HEIGHT, 105
jmp draw_bullets
draw_bullets: ; off
draw_bullet off, 90, 70
draw_bullet off, 75, 58
draw_bullet off, 59, 46
draw_bullet off, 89, 117
draw_bullet off, 74, 129
draw_bullet off, 56, 144
draw_bullet off, 211, 68
draw_bullet off, 224, 57
draw_bullet off, 236, 46
draw_bullet off, 210, 119
draw_bullet off, 223, 131
draw_bullet off, 237, 143
jmp draw_bullets_on
draw_bullets_on:
mov eax, [cur_bullet]
cmp eax, 1
jz ._1
cmp eax, 2
jz ._2
cmp eax, 3
jz ._3
cmp eax, 4
jz ._4
._1:
mov eax, [bullet_1_pos]
mov [bullet_pos], eax
mov eax, [bullet_1_side]
mov [bullet_side], eax
jmp bullet_on_defined
._2:
mov eax, [bullet_2_pos]
mov [bullet_pos], eax
mov eax, [bullet_2_side]
mov [bullet_side], eax
jmp bullet_on_defined
._3:
mov eax, [bullet_3_pos]
mov [bullet_pos], eax
mov eax, [bullet_3_side]
mov [bullet_side], eax
jmp bullet_on_defined
._4:
mov eax, [bullet_4_pos]
mov [bullet_pos], eax
mov eax, [bullet_4_side]
mov [bullet_side], eax
jmp bullet_on_defined
bullet_on_defined:
mov eax, [bullet_side]
cmp eax, NW
jz bullet_nw
cmp eax, SW
jz bullet_sw
cmp eax, NE
jz bullet_ne
cmp eax, SE
jz bullet_se
bullet_nw:
mov eax, [bullet_pos]
cmp eax, 1
jz bullet_nw_dist._1
cmp eax, 2
jz bullet_nw_dist._2
cmp eax, 3
jz bullet_nw_dist._3
cmp eax, 4
jz bullet_nw_dist._4
cmp eax, 5
jz bullet_nw_dist._5
bullet_sw:
mov eax, [bullet_pos]
cmp eax, 1
jz bullet_sw_dist._1
cmp eax, 2
jz bullet_sw_dist._2
cmp eax, 3
jz bullet_sw_dist._3
cmp eax, 4
jz bullet_sw_dist._4
cmp eax, 5
jz bullet_sw_dist._5
bullet_ne:
mov eax, [bullet_pos]
cmp eax, 1
jz bullet_ne_dist._1
cmp eax, 2
jz bullet_ne_dist._2
cmp eax, 3
jz bullet_ne_dist._3
cmp eax, 4
jz bullet_ne_dist._4
cmp eax, 5
jz bullet_ne_dist._5
bullet_se:
mov eax, [bullet_pos]
cmp eax, 1
jz bullet_se_dist._1
cmp eax, 2
jz bullet_se_dist._2
cmp eax, 3
jz bullet_se_dist._3
cmp eax, 4
jz bullet_se_dist._4
cmp eax, 5
jz bullet_se_dist._5
bullet_nw_dist:
._1:
draw_bullet on, 44, 33
jmp bullet_on_drawn
._2:
draw_bullet on, 59, 46
jmp bullet_on_drawn
._3:
draw_bullet on, 75, 58
jmp bullet_on_drawn
._4:
draw_bullet on, 90, 70
jmp bullet_on_drawn
._5:
jmp bullet_on_drawn
bullet_sw_dist:
._1:
draw_bullet on, 42, 156
jmp bullet_on_drawn
._2:
draw_bullet on, 56, 144
jmp bullet_on_drawn
._3:
draw_bullet on, 74, 129
jmp bullet_on_drawn
._4:
draw_bullet on, 89, 117
jmp bullet_on_drawn
._5:
jmp bullet_on_drawn
bullet_ne_dist:
._1:
draw_bullet on, 250, 34
jmp bullet_on_drawn
._2:
draw_bullet on, 236, 46
jmp bullet_on_drawn
._3:
draw_bullet on, 224, 57
jmp bullet_on_drawn
._4:
draw_bullet on, 211, 68
jmp bullet_on_drawn
._5:
jmp bullet_on_drawn
bullet_se_dist:
._1:
draw_bullet on, 251, 156
jmp bullet_on_drawn
._2:
draw_bullet on, 237, 143
jmp bullet_on_drawn
._3:
draw_bullet on, 223, 131
jmp bullet_on_drawn
._4:
draw_bullet on, 210, 119
jmp bullet_on_drawn
._5:
jmp bullet_on_drawn
bullet_on_drawn:
mov eax, [cur_bullet]
inc eax
mov [cur_bullet], eax
mov eax, [cur_bullet]
cmp eax, BULLETS_CNT + 1
jz all_bullets_drawn
jmp draw_bullets_on
all_bullets_drawn:
mov eax, 1
mov [cur_bullet], eax
jmp check_for_game_step
check_for_game_step:
mov eax, [delays_cnt]
cmp eax, DELAYS_PER_GAME_STEP
jz game_step
jmp no_game_step
no_game_step:
mov eax, [delays_cnt]
inc eax
mov [delays_cnt], eax
jmp game_loop
game_step:
mov eax, 1
mov [delays_cnt], eax
mov eax, [bullet_1_pos]
inc eax
mov [bullet_1_pos], eax
mov eax, [bullet_2_pos]
inc eax
mov [bullet_2_pos], eax
mov eax, [bullet_3_pos]
inc eax
mov [bullet_3_pos], eax
mov eax, [bullet_4_pos]
inc eax
mov [bullet_4_pos], eax
mov eax, [bullet_1_pos]
cmp eax, 6
jz bullet_1_new
mov eax, [bullet_2_pos]
cmp eax, 6
jz bullet_2_new
mov eax, [bullet_3_pos]
cmp eax, 6
jz bullet_3_new
mov eax, [bullet_4_pos]
cmp eax, 6
jz bullet_4_new
jmp check_bullet_hit
bullet_1_new:
play_note NOTE_SAVE
mov eax, 1
mov [bullet_1_pos], eax
mov eax, [next_bullet_side]
mov [bullet_1_side], eax
jmp check_bullet_hit
bullet_2_new:
play_note NOTE_SAVE
mov eax, 1
mov [bullet_2_pos], eax
mov eax, [next_bullet_side]
mov [bullet_2_side], eax
jmp check_bullet_hit
bullet_3_new:
play_note NOTE_SAVE
mov eax, 1
mov [bullet_3_pos], eax
mov eax, [next_bullet_side]
mov [bullet_3_side], eax
jmp check_bullet_hit
bullet_4_new:
play_note NOTE_SAVE
mov eax, 1
mov [bullet_4_pos], eax
mov eax, [next_bullet_side]
mov [bullet_4_side], eax
jmp check_bullet_hit
check_bullet_hit:
mov eax, [bullet_1_pos]
cmp eax, 5
jz bullet_1_hit
mov eax, [bullet_2_pos]
cmp eax, 5
jz bullet_2_hit
mov eax, [bullet_3_pos]
cmp eax, 5
jz bullet_3_hit
mov eax, [bullet_4_pos]
cmp eax, 5
jz bullet_4_hit
jmp game_loop
bullet_1_hit:
mov eax, [bullet_1_side]
cmp eax, [shield_position]
jz save
jmp damage
bullet_2_hit:
mov eax, [bullet_2_side]
cmp eax, [shield_position]
jz save
jmp damage
bullet_3_hit:
mov eax, [bullet_3_side]
cmp eax, [shield_position]
jz save
jmp damage
bullet_4_hit:
mov eax, [bullet_4_side]
cmp eax, [shield_position]
jz save
jmp damage
damage:
mov eax, [health]
sub eax, BULLET_DAMAGE
mov [health], eax
play_note NOTE_DAMAGE
jmp game_loop
save:
mov eax, [health]
add eax, HEALTH_BONUS
mov [health], eax
play_note NOTE_SAVE
jmp game_loop
skin_height dd 0
shield_position dd SE
finish_draw dd 1 ; 0 -- finish, 1 -- start
next_bullet_side_prng dd 3
next_bullet_side dd SE
bullet_1_pos dd 1
bullet_2_pos dd 2
bullet_3_pos dd 3
bullet_4_pos dd 4
bullet_1_side dd NW
bullet_2_side dd SW
bullet_3_side dd NE
bullet_4_side dd SE
bullet_pos dd 1 ; nearest to the gun
bullet_side dd NW
cur_bullet dd NW
delays_cnt dd 1
health dd HEALTH_INIT
delay dd DELAY_INIT
game_started dd 0
speaker:
.duration db 0x90
.note db 0x30
.end db 0x00
pic_bg:
file 'picture_bg.rgba'
pic_shield_sw:
file 'shield_sw.rgb'
pic_shield_nw:
file 'shield_nw.rgb'
pic_shield_ne:
file 'shield_ne.rgb'
pic_shield_se:
file 'shield_se.rgb'
_pic_bullet_off:
file 'bullet_off.rgb'
_pic_bullet_on:
file 'bullet_on.rgb'
sz msg_copyright, '(c) 2009 CH@YKIN EVGENY'
msg_new_game cp866 '1 новая игра'
msg_new_game.size = $ - msg_new_game
msg_continue cp866 '2 продолжить'
msg_continue.size = $ - msg_continue
msg_you_lost cp866 ' вы проиграли'
msg_you_lost.size = $ - msg_you_lost
msg_you_won cp866 'ПОБЕДА :)'
msg_you_won.size = $ - msg_you_won
msg_control_by_numpad cp866 'Управление клавишами NumLock клавиатуры'
msg_control_by_numpad.size = $ - msg_control_by_numpad
msg_controls cp866 ' 1, 4, 6, 3 и пауза Р(Eng). x'
msg_controls.size = $ - msg_controls
palette:
file 'palette.rgba'
sz msg_ataka, 'ATAKA'
window_title db 'ATAKA V 1.0',0
I_END:
sys_colors system_colors
rb 0x80d
stacktop: