DEVICE NOSLOT64K SLDOPT COMMENT WPMEM, ASSERTION, LOGPOINT INCLUDE "ok240/equates.inc" OUTPUT jack.com ; Monitor entry points ; -------------------------------------------------- mon_con_status EQU 0xE006 mon_con_in EQU 0xE009 ; Monitor variables ; -------------------------------------------------- ; R8 cursor_pos EQU 0xbfe1 curr_color EQU 0xbfe3 ; R5 ;cursor_pos EQU 0xbfed ;curr_color EQU 0xbfef ; BDOS Entries ; -------------------------------------------------- WARM_BOOT EQU 0x0000 ; Jump warm_boot (Restart) BDOS_ENTER EQU 0x0005 ; Jump bdos (CALL 5 to make CP/M requests) ; BDOS Functions C_WRITESTR EQU 9 ; Output string ; IO Ports ; -------------------------------------------------- SYS_DD17PB EQU 0xC1 ; Port B - [ROM14,13][REST][ENROM-][A18,17,16][32k] VID_DD67PB EQU 0xE1 ; Port B - [VSU,C/M,FL3..1,COL3..1] DD67PC EQU 0xE2 ; Port C - [USER3..1,STB-LP,BELL,TAPE3..1] ; Jumping jack constants ; -------------------------------------------------- arr_len EQU 0x20 stack EQU 0xbfc0 ORG 0x100 ; -------------------------------------------------- ; JAMPING JACK Entry point ; -------------------------------------------------- NOP NOP NOP JP j_start init_levels: LD HL, arr_len LD DE, j_arr_src1 LD BC, j_arr_src2 SCF CCF PUSH AF rol_32_l1: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l1 POP AF LD HL, arr_len LD DE, j_arr_src10 LD BC, j_arr_src11 SCF CCF PUSH AF rol_32_l2: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l2 POP AF LD HL, arr_len LD DE, j_arr_src2 LD BC, j_arr_src3 SCF CCF PUSH AF rol_32_l3: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l3 POP AF LD HL, arr_len LD DE, j_arr_src11 LD BC, j_arr_src12 SCF CCF PUSH AF rol_32_l4: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l4 POP AF LD HL, arr_len LD DE, j_arr_src3 LD BC, j_arr_src4 SCF CCF PUSH AF rol_32_l5: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l5 POP AF LD HL, arr_len LD DE, j_arr_src12 LD BC, j_arr_src13 SCF CCF PUSH AF rol_32_l6: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l6 POP AF LD HL, arr_len LD DE, j_arr_src4 LD BC, j_arr_src5 SCF CCF PUSH AF rol_32_l7: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l7 POP AF LD HL, arr_len LD DE, j_arr_src13 LD BC, j_arr_src14 SCF CCF PUSH AF rol_32_l8: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l8 POP AF LD HL, arr_len LD DE, j_arr_src5 LD BC, j_arr_src6 SCF CCF PUSH AF rol_32_l9: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l9 POP AF LD HL, arr_len LD DE, j_arr_src14 LD BC, j_arr_src15 SCF CCF PUSH AF rol_32_l10: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l10 POP AF LD HL, arr_len LD DE, j_arr_src6 LD BC, j_arr_src7 SCF CCF PUSH AF rol_32_l11: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l11 POP AF LD HL, arr_len LD DE, j_arr_src15 LD BC, j_arr_src16 SCF CCF PUSH AF rol_32_l12: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l12 POP AF LD HL, arr_len LD DE, j_arr_src7 LD BC, j_arr_src8 SCF CCF PUSH AF rol_32_l13: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l13 POP AF LD HL, arr_len LD DE, j_arr_src16 LD BC, j_arr_src17 SCF CCF PUSH AF rol_32_l14: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l14 POP AF LD HL, arr_len LD DE, j_arr_src8 LD BC, j_arr_src9 SCF CCF PUSH AF rol_32_l15: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l15 POP AF LD HL, arr_len LD DE, j_arr_src17 LD BC, j_arr_src18 SCF CCF PUSH AF rol_32_l16: POP AF LD A, (DE) RLA LD (BC), A PUSH AF INC DE INC BC DEC HL LD A, L OR H JP NZ, rol_32_l16 POP AF on_vram_acc: LD A, 0x10 OUT (SYS_DD17PB), A ; Turn off ROM VideoRAM @ 0xC000 wait_game_start: LD HL, (random_seed) ;= 0x13C6 LD C, 16 .i_rnd0: LD A, H ADD HL, HL AND 0x60 JP PE, .i_rnd1 INC HL .i_rnd1: DEC C JP NZ, .i_rnd0 LD (random_seed), HL ; 0x13C6 LD HL, (monstr_pos) ; 0x27AC LD C, 16 .i_rnd_m0: LD A, H ADD HL, HL AND 0x60 JP PE, .i_rnd_m1 INC HL .i_rnd_m1: DEC C JP NZ, .i_rnd_m0 LD (monstr_pos), HL ; 0x27AC NOP XOR A OUT (SYS_DD17PB), A ; Turn on ROM, disable VRAM CALL mon_con_in ; undefined mon_con_in() CP CTRL_C JP Z, exit_to_cpm CP ASCII_SP JP Z, game_start_ent CP ASCII_CR JP Z, game_start_ent NOP JP wait_game_start NOP NOP NOP NOP game_start_ent: LD A, 0x10 OUT (SYS_DD17PB), A ; VideoRAM @ 0xC000 no ROM NOP NOP NOP CALL clear_screen LD D, 0x20 LD A, (current_level_line) ;= 0x20 LD HL, first_lvl0_addr LD (level_gen_ptr_1), HL ;= 0x133D LD HL, first_lvl1_addr LD (level_gen_ptr_2), HL ;= 0x13FD generate_level_loop: PUSH AF LD HL, (random_seed) ;= 0x13C6 LD C, 0x10 rand_seed_loop: LD A, H ADD HL, HL AND 0x60 JP PE, rand_seed_skip INC HL rand_seed_skip: DEC C JP NZ, rand_seed_loop LD (random_seed), HL ;= 0x13C6 LD B, H POP AF CP B JP NC, fill_level_data1 CALL fill_6_zero_1 level_gen_loop2: LD B, L CP B JP NC, fill_level_data2 CALL fill_6_zero_2 level_gen_loop3: DEC D JP NZ, generate_level_loop LD A, 0x10 OUT (SYS_DD17PB), A ; VideoRAM @0xC000 no ROM CALL clear_screen PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (j_addr_75) ;= 0xC0D8 LD BC, j_arr_src_00 LD DE, lvl_plane_0 LD A, 0x1 draw_bottom_lines_loop: PUSH AF LD A, 0x20 draw_bottom_line_loop: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, draw_bottom_line_loop LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, draw_bottom_lines_loop POP HL POP DE POP BC POP AF LD HL, 0xc0dc ;= db LD (player_screen_addr), HL ;= 0xC0C8 ; Lifes at start LD A, 10 draw_lives_loop: LD (lives_counter), A ;= 0x1 CALL render_player_and_scene LD HL, (player_screen_addr) ;= 0xC0C8 INC H INC H LD (player_screen_addr), HL ;= 0xC0C8 LD A, (lives_counter) ;= 0x1 DEC A JP NZ, draw_lives_loop DEC H DEC H LD (last_life_screen_addr), HL ;= 0xD2DC LD HL, 0xc0c8 ;= db LD (player_screen_addr), HL ;= 0xC0C8 ; -------------------------------------------------- ; Draw treashure chest ; -------------------------------------------------- PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (chest_screen_addr) ;= 0xC400 LD BC, j_chest_c0 ; treashure chest color bit 0 LD DE, j_chest_c1 ; treashure chest color bit 1 LD A, 24 draw_treasure_chest_loop: PUSH AF LD A, 3 draw_chest_row_loop: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, draw_chest_row_loop LD A, H SUB 0x3 SUB 0x3 LD H, A INC L POP AF DEC A JP NZ, draw_treasure_chest_loop POP HL POP DE POP BC POP AF main_game_loop: CALL draw_level_lines CALL draw_level_lines CALL update_and_render_monster CALL player_monstr_hit ; Draw "fire" if active LD A, (fire_active_flag) OR A CALL NZ, handle_fire PUSH BC ; Disable VRAM access XOR A OUT (SYS_DD17PB), A ; Get Console status CALL mon_con_status OR A ; A = 0 - not keys, 0xFF - key pressed JP NZ, .is_key LD A, 0xff JP .no_key .is_key: ; Read Key CALL mon_con_in .no_key: LD B, A ; save key ; VideoRAM @0xC000 LD A, 0x10 OUT (SYS_DD17PB), A LD A, B POP BC CP KEY_LEFT JP Z, handle_left_key CP KEY_RIGHT JP Z, handle_player_move_right CP KEY_UP JP Z, handle_player_jump CP ASCII_SP JP Z, handle_fire_key CP 'C' JP Z, change_color_palette CP CTRL_C JP Z, exit_to_cpm NOP process_game_frame: LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H CP 0xbe JP Z, main_game_loop CP 0xfe JP Z, main_game_loop CALL render_player_and_scene CALL player_on_floor JP main_game_loop ; -------------------------------------------------- ; Change palette [COL3:1] ; -------------------------------------------------- change_color_palette: LD A, (save_video_mode) ;= 0x62 at start INC A CP 0x67 ; COL3:1 == 111b ? JP Z, .reset_color_pal .apply_color_mode: LD (save_video_mode), A OUT (VID_DD67PB), A ; [VSU, C/M, FL3:1, COL3:1] JP process_game_frame .reset_color_pal: LD A, 0x60 JP .apply_color_mode fill_level_data1: PUSH HL PUSH DE PUSH BC PUSH AF LD C, 0x3 LD HL, (level_gen_ptr_1) ;= 0x133D fill_ones_loop1: LD (HL), 0xff INC HL DEC C JP NZ, fill_ones_loop1 LD C, 0x3 fill_zeros_loop1: LD (HL), 0x00 INC HL DEC C JP NZ, fill_zeros_loop1 LD (level_gen_ptr_1), HL ;= 0x133D POP AF POP BC POP DE POP HL JP level_gen_loop2 fill_level_data2: PUSH HL PUSH DE PUSH BC PUSH AF LD C, 0x3 LD HL, (level_gen_ptr_2) ;= 0x13FD fill_ones_loop2: LD (HL), 0xff INC HL DEC C JP NZ, fill_ones_loop2 LD C, 0x3 fill_zeros_loop2: LD (HL), 0x00 INC HL DEC C JP NZ, fill_zeros_loop2 LD (level_gen_ptr_2), HL ;= 0x13FD POP AF POP BC POP DE POP HL JP level_gen_loop3 ; -------------------------------------------------- ; Fill 6 bytes by zero ; Inp: j_addr_1 -> buffer ; -------------------------------------------------- fill_6_zero_1: PUSH HL PUSH DE PUSH BC PUSH AF LD C, 6 LD HL, (level_gen_ptr_1) ;= 0x133D .fill_next: LD (HL), 0x00 INC HL DEC C JP NZ, .fill_next LD (level_gen_ptr_1), HL ;= 0x133D POP AF POP BC POP DE POP HL RET ; -------------------------------------------------- ; Fill 6 bytes by zero ; Inp: j_addr_2 -> buffer ; -------------------------------------------------- fill_6_zero_2: PUSH HL PUSH DE PUSH BC PUSH AF LD C, 6 LD HL, (level_gen_ptr_2) ;= 0x13FD .fill_next: LD (HL), 0x00 INC HL DEC C JP NZ, .fill_next LD (level_gen_ptr_2), HL ;= 0x13FD POP AF POP BC POP DE POP HL RET ; -------------------------------------------------- ; Draw horisontal moved level lines ; -------------------------------------------------- draw_level_lines: LD D, full_lvl_size LD HL, last_lvl0_addr ;= 0xBF scroll_level_left_loop: LD A, (HL) ;= 0xBF CP 0 JP Z, dll_lshift_skip_0 LD B, A RLCA ; cf<-[7:0]<-[7] AND 0xfe ; simple left shift LD (HL), A LD A, B RLCA AND 0x1 INC HL LD B, (HL) ;= 0xBF OR B LD (HL), A ;= 0xBF DEC HL DEC HL DEC D JP NZ, scroll_level_left_loop scroll_level_left_done: LD A, (last_lvl0_addr) ;= 0xBF LD (first_lvl0_addr), A LD D, full_lvl_size LD HL, first_lvl1_addr scroll_level_right_loop: LD A, (HL) CP 0 JP Z, dll_rshift_skip_0 LD B, A RRCA ; simple shift right AND 0x7f ; [0] -> [7:0] -> C LD (HL), A LD A, B RRCA AND 0x80 DEC HL LD B, (HL) ;= 0xBF OR B LD (HL), A ;= 0xBF INC HL INC HL DEC D JP NZ, scroll_level_right_loop scroll_level_right_done: LD A, (first_lvl1_addr) LD (last_lvl1_addr), A ;= 0x3 LD A, full_lvl_size LD (level_merge_counter), A LD BC, first_lvl0_addr LD DE, lvl_merged_0 LD HL, first_lvl1_addr merge_levels_loop: LD A, (BC) OR (HL) CPL LD (DE), A INC BC INC DE INC HL LD A, (level_merge_counter) DEC A LD (level_merge_counter), A OR A JP NZ, merge_levels_loop LD HL, 0xc018 ; draw level line LD (level_draw_addr), HL ;= 0xC0B8 PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (level_draw_addr) ;= 0xC0B8 LD BC, lvl_merged_0 LD DE, lvl_plane_0 LD A, 1 lvl_ln0_col_nxt: PUSH AF LD A, 32 lvl_ln0_row_nxt: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, lvl_ln0_row_nxt LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, lvl_ln0_col_nxt POP HL POP DE POP BC POP AF CALL calc_nxt_line_addr PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (level_draw_addr) ;= 0xC0B8 LD BC, lvl_merged_1 LD DE, lvl_plane_0 LD A, 0x1 lvl_ln1_col_nxt: PUSH AF LD A, 0x20 lvl_ln1_row_nxt: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, lvl_ln1_row_nxt LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, lvl_ln1_col_nxt POP HL POP DE POP BC POP AF CALL calc_nxt_line_addr PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (level_draw_addr) ;= 0xC0B8 LD BC, lvl_merged_2 LD DE, lvl_plane_0 LD A, 0x1 lvl_ln2_col_nxt: PUSH AF LD A, 0x20 lvl_ln2_row_nxt: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, lvl_ln2_row_nxt LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, lvl_ln2_col_nxt POP HL POP DE POP BC POP AF CALL calc_nxt_line_addr PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (level_draw_addr) ;= 0xC0B8 LD BC, lvl_merged_3 LD DE, lvl_plane_0 LD A, 0x1 lvl_ln3_col_nxt: PUSH AF LD A, 0x20 lvl_ln3_row_nxt: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, lvl_ln3_row_nxt LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, lvl_ln3_col_nxt POP HL POP DE POP BC POP AF CALL calc_nxt_line_addr PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (level_draw_addr) ;= 0xC0B8 LD BC, lvl_merged_4 LD DE, lvl_plane_0 LD A, 0x1 lvl_ln4_col_nxt: PUSH AF LD A, 0x20 lvl_ln4_row_nxt: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, lvl_ln4_row_nxt LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, lvl_ln4_col_nxt POP HL POP DE POP BC POP AF CALL calc_nxt_line_addr PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (level_draw_addr) ;= 0xC0B8 LD BC, lvl_merged_5 LD DE, lvl_plane_0 LD A, 1 lvl_ln5_col_nxt: PUSH AF LD A, 32 lvl_ln5_row_nxt: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, lvl_ln5_row_nxt LD A, H SUB 0x20 SUB 0x20 LD H, A INC L POP AF DEC A JP NZ, lvl_ln5_col_nxt POP HL POP DE POP BC POP AF RET calc_nxt_line_addr: LD HL, (level_draw_addr) ;= 0xC0B8 LD A, L ADD A, 0x20 LD L, A LD (level_draw_addr), HL ;= 0xC0B8 RET dll_lshift_skip_0: DEC HL DEC D JP NZ, scroll_level_left_loop JP scroll_level_left_done dll_rshift_skip_0: INC HL DEC D JP NZ, scroll_level_right_loop JP scroll_level_right_done ; -------------------------------------------------- ; Handle player movement to left ; -------------------------------------------------- handle_left_key: PUSH AF PUSH BC PUSH DE PUSH HL LD DE, j_player_tlt_c0 LD HL, j_player_tlt_c1 LD A, (player_anim_frame) OR A JP Z, calc_lt_fr_addr_end LD BC, 0x20 calc_lt_fr_addr: ADD HL, BC EX DE, HL ADD HL, BC EX DE, HL DEC A JP NZ, calc_lt_fr_addr calc_lt_fr_addr_end: LD (player_sprite_addr_0), HL ;= 0xCFD PUSH HL POP BC EX DE, HL LD (player_sprite_addr_1), HL ;= 0xE1D EX DE, HL LD HL, (player_screen_addr) ;= 0xC0C8 LD A, 0x10 kl_next_col: PUSH AF LD A, 0x2 kl_next_row: PUSH AF LD A, H CP 0xc0 JP C, draw_player_left_skip_row LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db LD A, H CP 0xff JP Z, draw_player_left_skip_col draw_player_left_next_row: INC H INC BC INC DE POP AF DEC A JP NZ, kl_next_row LD A, H SUB 0x2 SUB 0x2 LD H, A draw_player_left_next_col: INC L POP AF DEC A JP NZ, kl_next_col JP draw_player_left_end draw_player_left_skip_col: POP AF draw_player_left_skip_row_loop: INC BC INC DE DEC A JP NZ, draw_player_left_skip_row_loop LD A, (player_screen_addr+1) LD H, A JP draw_player_left_next_col draw_player_left_skip_row: INC H JP draw_player_left_next_row draw_player_left_end: POP HL POP DE POP BC POP AF LD A, (player_anim_frame) OR A JP Z, handle_left_key_no_turn DEC A update_turn_frame_left: LD (player_anim_frame), A LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H CP 0xbe JP Z, main_game_loop CP 0xfe JP Z, main_game_loop CALL player_on_floor JP main_game_loop handle_left_key_no_turn: LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H CP 0xca JP Z, l_key_ca check_left_boundary: CP 0xbe JP Z, left_key_boundary_be DEC H DEC H LD (player_screen_addr), HL ;= 0xC0C8 move_player_left: LD A, 0x3 JP update_turn_frame_left left_key_boundary_be: LD H, 0xfe LD (player_screen_addr), HL ;= 0xC0C8 JP move_player_left ; -------------------------------------------------- ; Handle player movement to right ; -------------------------------------------------- handle_player_move_right: PUSH AF PUSH BC PUSH DE PUSH HL LD DE, j_player_trt_c0 LD HL, j_player_trt_c1 LD A, (player_anim_frame) OR A JP Z, calc_right_frame_addr_end LD BC, 0x20 calc_rt_fr_addr: ADD HL, BC EX DE, HL ADD HL, BC EX DE, HL DEC A JP NZ, calc_rt_fr_addr calc_right_frame_addr_end: LD (player_sprite_addr_0), HL ;= 0xCFD PUSH HL POP BC EX DE, HL LD (player_sprite_addr_1), HL ;= 0xE1D EX DE, HL LD HL, (player_screen_addr) ;= 0xC0C8 LD A, 16 kr_next_col: PUSH AF LD A, 2 kr_next_row: PUSH AF LD A, H CP 0xc0 JP C, kr_coll_left LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db LD A, H CP 0xff JP Z, kr_coll_right kr_cont_left: INC H INC BC INC DE POP AF DEC A JP NZ, kr_next_row LD A, H SUB 0x2 SUB 0x2 LD H, A kr_cont_right: INC L POP AF DEC A JP NZ, kr_next_col JP draw_player_right_end kr_coll_right: POP AF draw_player_right_skip_col_loop: INC BC INC DE DEC A JP NZ, draw_player_right_skip_col_loop LD A, (player_screen_addr+1) LD H, A JP kr_cont_right kr_coll_left: INC H JP kr_cont_left draw_player_right_end: POP HL POP DE POP BC POP AF CALL player_monstr_hit LD A, (player_anim_frame) CP 3 JP Z, kr_last_frame ; next frame INC A update_turn_frame_right: LD (player_anim_frame), A LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H CP 0xfe JP Z, main_game_loop CP 0xbe JP Z, main_game_loop CALL player_on_floor JP main_game_loop kr_last_frame: LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H CP 0xc0 JP Z, check_left_key_ca check_right_boundary: CP 0xfe JP Z, move_player_right_boundary INC H INC H LD (player_screen_addr), HL ;= 0xC0C8 CALL player_monstr_hit move_player_right: XOR A JP update_turn_frame_right move_player_right_boundary: LD H, 0xbe LD (player_screen_addr), HL ;= 0xC0C8 JP move_player_right ; -------------------------------------------------- ; Handle player movement jump up ; -------------------------------------------------- handle_player_jump: LD HL, (player_screen_addr) ;= 0xC0C8 LD A, L CP 8 JP Z, main_game_loop CALL erase_player LD HL, (player_screen_addr) ; Move player coord Up LD A, L SUB 15 ; y-=15 LD L, A LD (player_screen_addr), HL CALL render_player_and_scene ; -------------------------------------------------- ; Play Jump Sound ; -------------------------------------------------- PUSH BC LD BC, 50 jump_sound_loop: LD A, 0xf OUT (DD67PC), A ;[USER3..1, STB-LP, BELL, TAPE3..1] PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 10 jump_sound_delay1: DEC DE LD A, D OR E JP NZ, jump_sound_delay1 POP AF POP BC POP DE POP HL LD A, 0 OUT (DD67PC), A ;[USER3..1, STB-LP, BELL, TAPE3..1] PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 10 jump_sound_delay2: DEC DE LD A, D OR E JP NZ, jump_sound_delay2 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, jump_sound_loop POP BC LD HL, (player_screen_addr) ;= 0xC0C8 DEC L LD A, (player_anim_frame) CP 2 JP NC, jmp_next_frame ; Check collision check_jump_collizion: LD A, (HL) ;= db OR A JP NZ, jump_collision DEC L INC H LD A, (HL) ;= db OR A JP NZ, jump_collision CALL erase_player ; no collision, move player up 32px (17+15) LD HL, (player_screen_addr) ;= 0xC0C8 LD A, L SUB 17 LD L, A LD (player_screen_addr), HL ;= 0xC0C8 CALL render_player_and_scene JP main_game_loop jump_collision: CALL erase_player ; move player back down LD HL, (player_screen_addr) ;= 0xC0C8 LD A, L ADD A, 15 LD L, A LD (player_screen_addr), HL ;= 0xC0C8 CALL render_player_and_scene CALL draw_death CALL player_on_floor JP main_game_loop ; -------------------------------------------------- ; Player on floor? ; -------------------------------------------------- player_on_floor: ; calc player floor addr LD HL, (player_screen_addr) ;= 0xC0C8 LD A, L ADD A, 16 LD L, A ; hl - floor LD A, (player_anim_frame) CP 2 JP NC, .floor_at_rt ; animation death .chk_floor: LD A, (HL) OR A JP Z, no_floor RET .floor_at_rt: INC H INC H JP .chk_floor ; -------------------------------------------------- ; No floor under foots, fall down ; -------------------------------------------------- no_floor: ; move player down CALL erase_player LD HL, (player_screen_addr) LD A, L ADD A, 16 LD L, A LD (player_screen_addr), HL ; redraw player CALL render_player_and_scene ; and recheck floor again LD HL, (player_screen_addr) LD A, L ADD A, 16 LD L, A LD A, (HL) ;= db OR A JP Z, no_floor draw_death: PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (player_screen_addr) ;= 0xC0C8 LD BC, j_play_death_c0 LD DE, j_play_death_c1 LD A, 16 dd_next_col: PUSH AF LD A, 2 dd_next_row: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, dd_next_row LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, dd_next_col POP HL POP DE POP BC POP AF PUSH BC ; make death sound LD BC, 0x32 dp_nxt_beep: LD A, 0xf OUT (DD67PC), A ; Bell+Tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 10 dp_dly_nxt1: DEC DE LD A, D OR E JP NZ, dp_dly_nxt1 POP AF POP BC POP DE POP HL LD A, 0 OUT (DD67PC), A ; Bell+Tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 10 dp_dly_nxt2: DEC DE LD A, D OR E JP NZ, dp_dly_nxt2 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, dp_nxt_beep POP BC LD HL, (player_screen_addr) ;= 0xC0C8 LD A, L CP 0xc8 JP Z, draw_grave_cross check_floor_down: LD A, 16 pl_next_frame: LD (frame_skip_counter), A CALL draw_level_lines CALL draw_level_lines CALL update_and_render_monster CALL player_monstr_hit LD A, (fire_active_flag) OR A CALL NZ, handle_fire LD HL, (player_screen_addr) LD A, L ADD A, 16 LD L, A LD A, (HL) ;= db OR A JP Z, no_floor LD A, (frame_skip_counter) ;= 0x1 DEC A JP NZ, pl_next_frame RET ; -------------------------------------------------- ; Draw level and monster ; -------------------------------------------------- render_player_and_scene: LD A, (player_anim_frame) LD B, A ADD A, B LD (player_anim_frame_offset), A PUSH AF PUSH BC PUSH DE PUSH HL LD DE, j_arr_src10 LD HL, j_arr_src1 LD A, (player_anim_frame_offset) OR A JP Z, render_player_frame_done LD BC, 0x20 calc_draw_frame_addr_loop: ADD HL, BC EX DE, HL ADD HL, BC EX DE, HL DEC A JP NZ, calc_draw_frame_addr_loop render_player_frame_done: LD (player_sprite_addr_0), HL ;= 0xCFD PUSH HL POP BC EX DE, HL LD (player_sprite_addr_1), HL ;= 0xE1D EX DE, HL LD HL, (player_screen_addr) ;= 0xC0C8 LD A, 16 draw_scene_player_col_loop: PUSH AF LD A, 2 draw_scene_player_row_loop: PUSH AF LD A, H CP 0xc0 JP C, draw_scene_skip_row LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db LD A, H CP 0xff JP Z, draw_scene_skip_col draw_scene_next_row: INC H INC BC INC DE POP AF DEC A JP NZ, draw_scene_player_row_loop LD A, H SUB 0x2 SUB 0x2 LD H, A draw_scene_next_col: INC L POP AF DEC A JP NZ, draw_scene_player_col_loop JP draw_scene_end draw_scene_skip_col: POP AF draw_scene_skip_row_loop: INC BC INC DE DEC A JP NZ, draw_scene_skip_row_loop LD A, (player_screen_addr+1) LD H, A JP draw_scene_next_col draw_scene_skip_row: INC H JP draw_scene_next_row draw_scene_end: POP HL POP DE POP BC POP AF CALL draw_level_lines CALL draw_level_lines CALL update_and_render_monster CALL player_monstr_hit LD A, (fire_active_flag) OR A CALL NZ, handle_fire RET jmp_next_frame: INC H INC H JP check_jump_collizion ; -------------------------------------------------- ; Erase player from scene ; -------------------------------------------------- erase_player: PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (player_screen_addr) LD BC, j_player_era_c0 LD DE, j_player_era_c1 LD A, 16 .ep_next_col: PUSH AF LD A, 2 .ep_next_row: PUSH AF LD A, (BC) LD (HL), A ;= db LD A, (DE) INC H LD (HL), A ;= db INC H INC BC INC DE POP AF DEC A JP NZ, .ep_next_row LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, .ep_next_col POP HL POP DE POP BC POP AF RET draw_grave_cross: PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (last_life_screen_addr) ;= 0xD2DC LD BC, j_gravecross_c0 LD DE, j_gravecross_c1 LD A, 16 dgc_next_col: PUSH AF LD A, 1 dgc_next_row: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, dgc_next_row LD A, H SUB 0x1 SUB 0x1 LD H, A INC L POP AF DEC A JP NZ, dgc_next_col POP HL POP DE POP BC POP AF LD HL, (last_life_screen_addr) ;= 0xD2DC LD A, H CP 0xc0 JP Z, handle_lost_life DEC H DEC H LD (last_life_screen_addr), HL ;= 0xD2DC JP check_floor_down handle_lost_life: CALL out_game_over reinit_game: LD A, 1 LD (monster_inactive_flag), A XOR A LD (player_anim_frame), A LD (fire_active_flag), A LD HL, 0xc0c8 ;= db LD (player_screen_addr), HL ;= 0xC0C8 JP on_vram_acc l_key_ca: LD A, L CP 0x8 JP Z, play_boundary_sound LD A, H JP check_left_boundary check_left_key_ca: LD A, L CP 0x8 JP Z, play_boundary_sound LD A, H JP check_right_boundary play_boundary_sound: PUSH BC LD BC, 250 boundary_sound_loop: LD A, 0xf OUT (DD67PC), A ; Bell+Tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 0x14 boundary_sound_delay1: DEC DE LD A, D OR E JP NZ, boundary_sound_delay1 POP AF POP BC POP DE POP HL LD A, 0x00 OUT (DD67PC), A ; Bell+Tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 0x14 boundary_sound_delay2: DEC DE LD A, D OR E JP NZ, boundary_sound_delay2 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, boundary_sound_loop POP BC LD A, (current_level_line) ;= 0x20 CP 80 JP Z, play_final_sound CALL draw_happy_end CALL clear_screen LD A, 0 OUT (SYS_DD17PB), A ; vram off, rom on ; Out message, Wait for key LD HL, (curr_color) PUSH HL LD A, 0 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x0870 LD (cursor_pos), HL LD DE, j_msg_pres_key ;= '\r' LD C, C_WRITESTR CALL BDOS_ENTER POP HL ; Repeat again !!! LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x870 LD (cursor_pos), HL LD DE, j_msg_pres_key ;= '\r' LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD A, 0x10 OUT (SYS_DD17PB), A ; vram @ c000 ; Init to default values XOR A LD (player_anim_frame), A LD A, (monster_speed) ;= 0x15 ADD A, 5 LD (monster_speed), A ;= 0x15 LD A, 1 LD (monster_inactive_flag), A LD A, (current_level_line) ;= 0x20 ADD A, 0x10 LD (current_level_line), A ;= 0x20 JP on_vram_acc ; -------------------------------------------------- ; Play final sound for winner ; -------------------------------------------------- play_final_sound: PUSH BC LD BC, 250 .fm_next_note: LD A, 0xf OUT (DD67PC), A ; "1" bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 40 .fm_delay1: DEC DE LD A, D OR E JP NZ, .fm_delay1 POP AF POP BC POP DE POP HL LD A, 0x00 OUT (DD67PC), A ; "0" bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 40 .fm_delay2: DEC DE LD A, D OR E JP NZ, .fm_delay2 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, .fm_next_note POP BC ; -------------------------------------------------- ; Display final message for winner ; -------------------------------------------------- display_final_messages: CALL clear_screen ; close VRAM access LD A, 0x00 OUT (SYS_DD17PB), A ; End Message 1 LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x80 LD (cursor_pos), HL LD DE, j_msg_fin1 LD C, C_WRITESTR CALL BDOS_ENTER POP HL ; End Message 2 LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0xA0 LD (cursor_pos), HL LD DE, j_msg_fin2 LD C, C_WRITESTR CALL BDOS_ENTER POP HL ; End Message 3 LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0xC0 LD (cursor_pos), HL LD DE, j_msg_fin3 ;= 0xda LD C, C_WRITESTR CALL BDOS_ENTER POP HL ; End Message 4 LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 208 LD (cursor_pos), HL LD DE, j_msg_fin4 ;= 0xD0 LD C, C_WRITESTR CALL BDOS_ENTER POP HL ; End Message, Wait key LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0xff LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x8e0 LD (cursor_pos), HL LD DE, j_msg_pres_key ;= '\r' LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD A, 16 LD (current_level_line), A ;= 0x20 LD A, 32 LD (monster_speed), A ;= 0x15 JP reinit_game ; -------------------------------------------------- ; Paint screen to green ; -------------------------------------------------- clear_screen: PUSH HL PUSH BC PUSH DE PUSH AF LD A, (save_video_mode) ;= 0x62 OUT (VID_DD67PB), A LD HL, 0xc000 LD D, 0x20 LD A, (color_mode_selector) AND 0x3 CP 0x00 JP Z, clear_screen_mode0 CP 0x1 JP Z, clear_screen_mode1 CP 0x2 JP Z, clear_screen_mode2 LD B, 0xff LD C, 0xff clear_screen_loop: LD E, 0xff clear_screen_row_loop: LD (HL), B ;= db INC H LD (HL), C ;= db DEC H INC HL DEC E JP NZ, clear_screen_row_loop INC HL INC H DEC D JP NZ, clear_screen_loop JP clear_screen_end clear_screen_mode0: LD C, 0x00 LD B, 0x00 JP clear_screen_loop clear_screen_mode1: LD B, 0x00 LD C, 0xff JP clear_screen_loop clear_screen_mode2: LD B, 0xff LD C, 0x00 JP clear_screen_loop clear_screen_end: POP AF POP DE POP BC POP HL RET include "jack_data.inc" ; -------------------------------------------------- ; Variables ; -------------------------------------------------- level_gen_ptr_1: dw first_lvl1_addr level_gen_ptr_2: dw lvl_merged_0 player_sprite_addr_0: dw j_arr_src1 player_sprite_addr_1: dw j_arr_src10 last_life_screen_addr: dw 0xD2DC ; -------------------------------------------------- ; ; Application entry point ; ; -------------------------------------------------- j_start: LD A, 0x00 OUT (SYS_DD17PB), A ; close VRAM LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x00 LD (cursor_pos), HL LD DE, j_set_vmode ; = 0x1B LD C, C_WRITESTR ; 9 CALL BDOS_ENTER POP HL LD (curr_color), HL LD (saved_color), HL PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x90 LD (cursor_pos), HL LD DE, j_msg_verion ; "ВЕРСИЯ 1.0" LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0xa0 LD (cursor_pos), HL LD DE, j_spaces_35 ; LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0xb0 LD (cursor_pos), HL LD DE, j_msg_instr1 ; Выстрел-клавиша "пробел", цвет "Ц" LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x2c0 LD (cursor_pos), HL LD DE, j_msg_anykey ; Нажмите любую клавишу LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD A, 0x10 OUT (SYS_DD17PB), A LD HL, 0xca18 LD B, 0x3 CALL j_draw_rv LD HL, 0xce20 LD B, 0x3 CALL j_draw_rv LD HL, 0xd220 LD B, 0x3 CALL j_draw_rv LD HL, 0xd618 LD B, 0x4 CALL j_draw_rv LD HL, 0xde18 LD B, 0x4 CALL j_draw_rv LD HL, 0xe218 LD B, 0x4 CALL j_draw_rv LD HL, 0xe618 LD B, 0x3 CALL j_draw_rv LD HL, 0xea08 LD B, 0x1 CALL j_draw_rv LD HL, 0xea18 LD B, 0x4 CALL j_draw_rv LD HL, 0xee18 LD B, 0x4 CALL j_draw_rv LD HL, 0xf418 LD B, 0x4 CALL j_draw_rv LD HL, 0xf818 LD B, 0x3 CALL j_draw_rv LD HL, 0xfc28 LD B, 0x2 CALL j_draw_rv LD HL, 0xd648 LD B, 0x5 CALL j_draw_rv LD HL, 0xda58 LD B, 0x4 CALL j_draw_rv LD HL, 0xe258 LD B, 0x4 CALL j_draw_rv LD HL, 0xe650 LD B, 0x4 CALL j_draw_rv LD HL, 0xee50 LD B, 0x1 CALL j_draw_rv LD HL, 0xee68 LD B, 0x1 CALL j_draw_rv LD HL, 0xf248 LD B, 0x6 CALL j_draw_rv LD HL, 0xf458 LD B, 0x1 CALL j_draw_rv LD HL, 0xf658 LD B, 0x2 CALL j_draw_rv LD HL, 0xf850 LD B, 0x1 CALL j_draw_rv LD HL, 0xfa48 LD B, 0x1 CALL j_draw_rv LD HL, 0xf868 LD B, 0x1 CALL j_draw_rv LD HL, 0xfa70 LD B, 0x1 CALL j_draw_rv LD HL, 0xc618 LD B, 0x2 CALL j_draw_rh LD HL, 0xc630 LD B, 0x2 CALL j_draw_rh LD HL, 0xd018 LD B, 0x1 CALL j_draw_rh LD HL, 0xd028 LD B, 0x1 CALL j_draw_rh LD HL, 0xd820 LD B, 0x1 CALL j_draw_rh LD HL, 0xda28 LD B, 0x1 CALL j_draw_rh LD HL, 0xdc20 LD B, 0x1 CALL j_draw_rh LD HL, 0xe418 LD B, 0x1 CALL j_draw_rh LD HL, 0xe428 LD B, 0x1 CALL j_draw_rh LD HL, 0xf020 LD B, 0x1 CALL j_draw_rh LD HL, 0xf228 LD B, 0x1 CALL j_draw_rh LD HL, 0xfa18 LD B, 0x2 CALL j_draw_rh LD HL, 0xfa30 LD B, 0x1 CALL j_draw_rh LD HL, 0xce48 LD B, 0x4 CALL j_draw_rh LD HL, 0xce68 LD B, 0x1 CALL j_draw_rh LD HL, 0xd070 LD B, 0x3 CALL j_draw_rh LD HL, 0xde48 LD B, 0x1 CALL j_draw_rh LD HL, 0xdc50 LD B, 0x1 CALL j_draw_rh LD HL, 0xe050 LD B, 0x1 CALL j_draw_rh LD HL, 0xdc60 LD B, 0x3 CALL j_draw_rh LD HL, 0xe848 LD B, 0x3 CALL j_draw_rh LD HL, 0xe870 LD B, 0x3 CALL j_draw_rh JP init_levels ; -------------------------------------------------- ; Draw vertical rectangles 8x8 ; Inp: HL - pos ; B - count ; -------------------------------------------------- j_draw_rv: CALL j_draw_sqare LD A, L ADD A, 8 ; next, 8 lines down LD L, A DEC B JP NZ, j_draw_rv RET ; -------------------------------------------------- ; Draw horisontal rectangles 8x8 ; Inp: HL - pos ; B - count ; -------------------------------------------------- j_draw_rh: CALL j_draw_sqare INC H ; next, 8 column right INC H DEC B JP NZ, j_draw_rh RET ; -------------------------------------------------- ; Draw single rectangle 8x8 ; Inp: HL - pos ; -------------------------------------------------- j_draw_sqare: LD (square_draw_addr), HL PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (square_draw_addr) LD BC, img_square_c0 ;= 0xFF LD DE, img_square_c1 LD A, 8 .dsq_next_row: PUSH AF LD A, 1 .dsq_next_col: PUSH AF LD A, (BC) ;= 0xFF LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, .dsq_next_col LD A, H SUB 1 SUB 1 LD H, A INC L POP AF DEC A JP NZ, .dsq_next_row POP HL POP DE POP BC POP AF RET db 0x60 db 0x00 j_set_vmode: db ASCII_ESC, '64$' ; Set mode 40x25 j_msg_verion: db ASCII_ESC, '43', 9 ; Set color db ASCII_ESC, '71' ; Set charset RUS db "WERSIQ 1.0" db " " db ASCII_CR, ASCII_LF, ' ' j_spaces_35: ds 35, ' ' db '$' j_msg_instr1: db ASCII_CR, ASCII_LF, ASCII_CR db 'wystrel-klawi{a "probel",cwet - "c"$' j_msg_anykey: db ASCII_CR, ASCII_LF, ASCII_LF, ASCII_LF, ASCII_LF db 'nAVMITE L@BU@ KLAWI[U $' db ' $' img_square_c0: ds 8, 0xff img_square_c1: ds 8, 0 ds 33, 0 db 0x90 db 0xc0 square_draw_addr: dw 0xEC70 ; -------------------------------------------------- ; Move and draw monster ; -------------------------------------------------- update_and_render_monster: ; draw at every 4th call LD A, (monster_update_interval) ; default = 4 DEC A LD (monster_update_interval), A OR A RET NZ ; LD A, 4 LD (monster_update_interval), A ; interval=4 ; LD A, (monster_inactive_flag) OR A JP Z, render_monster LD HL, (monstr_pos) ;= 0x27AC LD C, 16 monster_randomize: LD A, H ADD HL, HL AND 0x60 JP PE, monster_randomize_skip INC HL monster_randomize_skip: DEC C JP NZ, monster_randomize LD (monstr_pos), HL ;= 0x27AC LD A, (monster_speed) ;= 0x15 CP H JP NC, monster_reset_position RET monster_reset_position: LD HL, 0xfe08 LD (monster_screen_addr), HL ;= 0xE268 .next: LD HL, (monster_screen_addr) ;= 0xE268 LD A, 0x20 ADD A, L LD L, A LD (monster_screen_addr), HL ;= 0xE268 LD A, (monster_y_target) ;= 0xCC ADD A, 0x33 LD (monster_y_target), A ;= 0xCC LD B, A LD HL, (monstr_pos) ;= 0x27AC LD A, L CP B JP NC, .next XOR A LD (monster_inactive_flag), A ; -------------------------------------------------- render_monster: PUSH AF PUSH BC PUSH DE PUSH HL LD DE, monstr_img_c0 LD HL, monstr_img_c1 LD A, (monster_dir) ;= 0x1 OR A JP Z, monstr_0 LD BC, 0x60 monstr_no_nxt: ADD HL, BC EX DE, HL ADD HL, BC EX DE, HL DEC A JP NZ, monstr_no_nxt monstr_0: LD (monster_sprite_addr0), HL ;= 0x18FB PUSH HL POP BC EX DE, HL LD (monster_sprite_addr1), HL ;= 0x19BB EX DE, HL LD HL, (monster_screen_addr) ;= 0xE268 LD A, 16 dm_next_col: PUSH AF LD A, 6 dm_next_row: PUSH AF LD A, H CP 0xc0 JP C, dm_at_left LD A, (BC) ;= 0xe0 LD (HL), A LD A, (DE) INC H LD (HL), A LD A, H CP 0xff JP Z, dm_at_right dm_ret_left: INC H INC BC INC DE POP AF DEC A JP NZ, dm_next_row LD A, H SUB 6 SUB 6 LD H, A dm_ret_right: INC L POP AF DEC A JP NZ, dm_next_col JP dm_end dm_at_right: POP AF dm_skip_col_loop: INC BC INC DE DEC A JP NZ, dm_skip_col_loop LD A, (monster_screen_addr+1) LD H, A JP dm_ret_right dm_at_left: INC H JP dm_ret_left dm_end: POP HL POP DE POP BC POP AF LD A, (monster_dir) ;= 0x1 OR A JP Z, monster_move_right XOR A monster_move_update: LD (monster_dir), A ;= 0x1 LD HL, (monster_screen_addr) ;= 0xE268 LD A, H CP 0xb4 JP Z, monster_reset_state DEC H DEC H LD (monster_screen_addr), HL ;= 0xE268 RET monster_move_right: LD A, 0x1 JP monster_move_update monster_reset_state: XOR A LD (monster_y_target), A ;= 0xCC LD A, 1 LD (monster_inactive_flag), A RET ; -------------------------------------------------- ; Monster hit player? ; -------------------------------------------------- player_monstr_hit: LD HL, (player_screen_addr) INC H INC H LD B, H LD D, L LD HL, (monster_screen_addr) LD A, H CP B JP Z, .chl_lo_addr RET .chl_lo_addr: LD A, L CP D JP Z, handle_lost_life RET monster_speed: db 21 monster_update_interval: db 4 monster_y_target: db 204 monster_dir: db 1 monstr_img_c1: ; col: 0 db 0x00, 0xFC, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xfe db 0xFF, 0x03, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0x07 ; col: 1 db 0x00, 0x00, 0xf0, 0xFF, 0xFF, 0x0f, 0x00, 0x00 db 0xf0, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xc8, 0xFF ; col: 2 db 0xFF, 0xFF, 0x00, 0x00, 0xFC, 0xFF, 0xFF, 0xFF db 0x01, 0x00, 0xEE, 0xFF, 0xFF, 0xFF, 0x03, 0x00 ; col: 3 db 0xf6, 0xFF, 0xFF, 0xFF, 0x07, 0x00, 0x7B, 0xfe db 0xFF, 0xFF, 0x0f, 0x00, 0x3D, 0x38, 0x00, 0xFF ; col: 4 db 0x0f, 0x00, 0x1E, 0x38, 0x00, 0xF8, 0x0f, 0x00 db 0x00, 0x38, 0x00, 0xF8, 0x1D, 0x00, 0x00, 0x38 ; col: 5 db 0x00, 0xF8, 0x18, 0x00, 0x00, 0x38, 0x00, 0x3C db 0xF8, 0x00, 0x00, 0x1E, 0x00, 0x3F, 0x00, 0x00 ; col: 6 db 0xe0, 0xFF, 0x3F, 0x00, 0x00, 0x00, 0xfe, 0xFF db 0xFF, 0x30, 0x00, 0x00, 0x3F, 0xFF, 0xFF, 0x0F ; col: 7 db 0x00, 0x00, 0xc0, 0xFF, 0xFF, 0x3F, 0x00, 0x00 db 0xe0, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0xf0, 0xFF ; col: 8 db 0xFF, 0xFF, 0x01, 0x00, 0xFF, 0xFF, 0xFF, 0xFF db 0x01, 0x00, 0x7E, 0xfe, 0xFF, 0xFF, 0x1F, 0x00 ; col: 9 db 0x00, 0xfe, 0xFF, 0xFF, 0x3F, 0x00, 0x00, 0xfe db 0x01, 0xFF, 0x37, 0x00, 0x00, 0xEF, 0x01, 0xFF ; col: 10 db 0x67, 0x00, 0x80, 0xC7, 0x01, 0xFC, 0x0f, 0x00 db 0x80, 0xc3, 0x01, 0x38, 0x1F, 0x00, 0xc0, 0x81 ; col: 11 db 0x03, 0x38, 0x1C, 0x00, 0xe0, 0x81, 0x03, 0x1E db 0x1C, 0x00, 0xf0, 0x80, 0x03, 0x0f, 0x1E, 0x00 monstr_img_c0: ds 96, 0 ds 96, 0 monstr_pos: dw 0x27AC monster_screen_addr: dw 0xE268 monster_sprite_addr0: dw 0x18FB monster_sprite_addr1: dw 0x19BB ; -------------------------------------------------- ; Handle "Fire" key ; -------------------------------------------------- handle_fire_key: LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H CP 0xfe JP NC, main_game_loop LD A, (fire_active_flag) OR A JP NZ, main_game_loop LD A, 1 LD (fire_active_flag), A PUSH AF PUSH BC PUSH DE PUSH HL ; player fire animation LD HL, (player_screen_addr) ;= 0xC0C8 LD BC, j_player_firer_c0 LD DE, j_player_firer_c1 LD A, 16 ; 16 rows .hf_next_col: PUSH AF LD A, 2 ; 2col=16px .hl_next_row: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, .hl_next_row LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, .hf_next_col POP HL POP DE POP BC POP AF PUSH HL PUSH DE PUSH BC PUSH AF LD A, 0x00 OUT (SYS_DD17PB), A ; vram off, rom on ; -------------------------------------------------- ; Sound for fire (10 pulses) ; -------------------------------------------------- LD HL, 0xc100 ; 49408 LD DE, 10 .fire_snd_nxt: LD A, 0xf OUT (DD67PC), A ; "1" bell + tape CALL delay_hl XOR A OUT (DD67PC), A ; "0" bell + tape CALL delay_hl DEC DE LD A, E OR D JP NZ, .fire_snd_nxt LD A, 0x10 OUT (SYS_DD17PB), A ; vram @ 0xc000 POP AF POP BC POP DE POP HL JP fire_continue ; -------------------------------------------------- ; Small delay ; Inp: HL->delay ; Out: HL = HL+1 ; -------------------------------------------------- delay_hl: LD A, (HL) .next_hl: DEC A JP NZ, .next_hl INC HL RET ; -------------------------------------------------- fire_continue: NOP LD A, 6 LD (fire_frame_ctr), A XOR A LD (fire_state), A LD (fire_anim_frame), A JP main_game_loop handle_fire: ; firectr-- LD A, (fire_frame_ctr) ;= 0x6 DEC A LD (fire_frame_ctr), A ;= 0x6 OR A JP Z, clear_fire LD A, (fire_state) OR A JP Z, fire_init_pos draw_fire: LD A, (fire_anim_frame) OR A JP Z, draw_fire2 ; draw fire PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (fire_screen_addr) ;= 0x4F LD BC, j_fire_c0 LD DE, j_fire_c1 LD A, 1 .next_col: PUSH AF LD A, 2 .next_row: PUSH AF LD A, (BC) ;= 0xFF LD (HL), A ;= db LD A, (DE) ;= 0xFF INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, .next_row LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, .next_col POP HL POP DE POP BC POP AF XOR A LD (fire_anim_frame), A CALL check_fire_monster_collision LD HL, (fire_screen_addr) ;= 0x4F LD A, 0x4 CP 0xfc JP Z, clear_fire INC H INC H LD (fire_screen_addr), HL ;= 0x4F CALL player_on_floor draw_fire_end: CALL check_fire_monster_collision RET fire_init_pos: LD HL, (player_screen_addr) ;= 0xC0C8 LD A, H ADD A, 0x4 LD H, A LD A, L ADD A, 0x7 LD L, A LD (fire_screen_addr), HL ;= 0x4F LD A, 0x1 LD (fire_state), A JP draw_fire draw_fire2: PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (fire_screen_addr) ;= 0x4F LD BC, j_fire2_c0 ;= 0xFF LD DE, j_fire2_c1 ;= 0xFF LD A, 1 .next_col2: PUSH AF LD A, 2 .next_row2: PUSH AF LD A, (BC) ;= 0xFF LD (HL), A LD A, (DE) ;= 0xFF INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, .next_row2 LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, .next_col2 POP HL POP DE POP BC POP AF ; draw fire2 LD A, 1 LD (fire_anim_frame), A JP draw_fire_end check_fire_monster_collision: LD HL, (fire_screen_addr) ; = 0x4F EX DE, HL LD HL, (monster_screen_addr) ;= 0xE268 LD A, H CP D JP Z, fire_check_monster_hit_y RET fire_check_monster_hit_y: LD A, L ADD A, 0x7 CP E JP Z, fire_monster_hit RET clear_fire: PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (fire_screen_addr) ; = 0x4F LD BC, j_player_era_c0 LD DE, j_player_era_c1 LD A, 0x1 clear_fire_col_loop: PUSH AF LD A, 0x2 clear_fire_row_loop: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, clear_fire_row_loop LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, clear_fire_col_loop POP HL POP DE POP BC POP AF XOR A LD (fire_active_flag), A LD (fire_state), A LD A, 0x6 LD (fire_frame_ctr), A ; = 0x6 RET fire_monster_hit: PUSH BC LD BC, 300 fire_hit_sound_loop: LD A, 0xf OUT (DD67PC), A ; bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 0x5 j_mini_dly_snd: DEC DE LD A, D OR E JP NZ, j_mini_dly_snd POP AF POP BC POP DE POP HL LD A, 0x00 OUT (DD67PC), A ; bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 0x5 fire_hit_sound_delay2: DEC DE LD A, D OR E JP NZ, fire_hit_sound_delay2 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, fire_hit_sound_loop POP BC PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (monster_screen_addr) ; = 0xE268 LD BC, explosion_data_1 LD DE, explosion_data_2 LD A, 0x10 draw_explosion_loop_col: PUSH AF LD A, 0x6 draw_explosion_loop_row: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, draw_explosion_loop_row LD A, H SUB 0x6 SUB 0x6 LD H, A INC L POP AF DEC A JP NZ, draw_explosion_loop_col POP HL POP DE POP BC POP AF CALL clear_fire CALL draw_level_lines CALL draw_level_lines CALL player_on_floor PUSH BC LD BC, 0x96 explosion_sound_loop: LD A, 0xf OUT (DD67PC), A PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 0xa explosion_sound_delay1: DEC DE LD A, D OR E JP NZ, explosion_sound_delay1 POP AF POP BC POP DE POP HL LD A, 0x00 OUT (DD67PC), A PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 0xa explosion_sound_delay2: DEC DE LD A, D OR E JP NZ, explosion_sound_delay2 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, explosion_sound_loop POP BC PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (monster_screen_addr) ; = 0xE268 LD BC, explosion_data3 LD DE, explosion_data4 LD A, 0x10 draw_explosion2_loop_col: PUSH AF LD A, 0x5 draw_explosion2_loop_row: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, draw_explosion2_loop_row LD A, H SUB 0x5 SUB 0x5 LD H, A INC L POP AF DEC A JP NZ, draw_explosion2_loop_col POP HL POP DE POP BC POP AF CALL draw_level_lines CALL draw_level_lines CALL player_on_floor CALL erase_monster_and_move CALL erase_monster_and_move CALL erase_monster_and_move CALL erase_monster_and_move CALL draw_grave_and_move JP monster_reset_state ; -------------------------------------------------- erase_monster_and_move: PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (monster_screen_addr) ; = 0xE268 LD BC, j_player_era_c0 LD DE, j_player_era_c1 LD A, 0x10 erase_monster_loop_col: PUSH AF LD A, 0x2 erase_monster_loop_row: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A INC H INC BC INC DE POP AF DEC A JP NZ, erase_monster_loop_row LD A, H SUB 0x2 SUB 0x2 LD H, A INC L POP AF DEC A JP NZ, erase_monster_loop_col POP HL POP DE POP BC POP AF LD HL, (monster_screen_addr) ; = 0xE268 LD A, H ADD A, 0x4 LD H, A LD (monster_screen_addr), HL ; = 0xE268 RET ; -------------------------------------------------- draw_grave_and_move: LD HL, (last_life_screen_addr) ; = 0xD2DC LD A, H CP 0xfe RET Z INC H INC H LD (last_life_screen_addr), HL ; = 0xD2DC PUSH AF PUSH BC PUSH DE PUSH HL LD HL, (last_life_screen_addr) ; = 0xD2DC LD BC, grave_cross_data_1 LD DE, grave_cross_data_2 LD A, 0x10 draw_grave_loop_col: PUSH AF LD A, 0x1 draw_grave_loop_row: PUSH AF LD A, (BC) LD (HL), A LD A, (DE) INC H LD (HL), A ; = 0xFF INC H INC BC INC DE POP AF DEC A JP NZ, draw_grave_loop_row LD A, H SUB 0x1 SUB 0x1 LD H, A INC L POP AF DEC A JP NZ, draw_grave_loop_col POP HL POP DE POP BC POP AF RET fire_active_flag: db 0 fire_frame_ctr: db 0x6 fire_state: db 0x00 fire_anim_frame: db 0 ; Fire sign 1x16 pix j_fire2_c0: ; color plane 0 db 0xFF, 0x00 j_fire2_c1: ; color plane 1 db 0xFF, 0x00 ; Fire sign 1x16 pix j_fire_c0: ; color plane 0 db 0x00, 0xFF j_fire_c1: ; color plane 1 db 0x00, 0xFF ; Player fire r 16x16pix ; color plane 0 j_player_firer_c0: ; Col: 0 db 0xc0, 0x01, 0xe0, 0x03, 0xD0, 0x06, 0x90, 0x0C db 0xa0, 0x03, 0xc0, 0x03, 0x80, 0x01, 0x80, 0x0f ; Col: 1 db 0x80, 0x07, 0x80, 0x03, 0x00, 0x01, 0x00, 0x01 db 0x00, 0x01, 0x00, 0x01, 0x00, 0x01, 0x00, 0x03 ; color plane 1 j_player_firer_c1: ; Col: 0 db 0xc0, 0x01, 0xe0, 0x03, 0xD0, 0x06, 0x90, 0x0C db 0xa0, 0x03, 0xc0, 0x03, 0x80, 0x01, 0x80, 0x0f ; Col: 1 db 0x80, 0x07, 0x80, 0x03, 0x00, 0x01, 0x00, 0x01 db 0x00, 0x01, 0x00, 0x01, 0x00, 0x01, 0x00, 0x03 explosion_data_1: ds 32, 0 ds 32, 0 ds 32, 0 explosion_data_2: ; DS 32 db 0x00, 0x6C, 0xEF, 0x00, 0x00, 0x00, 0x00, 0x6D db 0x0C, 0x00, 0x00, 0x00, 0x60, 0x01, 0x6C, 0x1B db 0x00, 0x00, 0x6C, 0xB0, 0x61, 0x1B, 0x00, 0x00 db 0x00, 0x86, 0x0d, 0x00, 0x00, 0x00, 0xda, 0x26 ; DS 32 db 0x6C, 0x6B, 0x00, 0x00, 0x1A, 0xa0, 0x01, 0x6B db 0x03, 0x00, 0xc0, 0x2C, 0x6C, 0x00, 0x03, 0x00 db 0xD9, 0x80, 0x81, 0x5B, 0x03, 0x00, 0x00, 0x3A db 0x0C, 0x58, 0x00, 0x00, 0x00, 0x02, 0x00, 0x40 ; DS 32 db 0x0b, 0x00, 0x00, 0x0C, 0x00, 0x3C, 0x08, 0x00 db 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x0C db 0x00, 0x0e, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00 db 0x00, 0x00, 0x00, 0x0e, 0x00, 0xf0, 0x00, 0x00 explosion_data3: ; DS 32 db 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06 db 0x00, 0x00, 0x00, 0x43, 0xc0, 0x00, 0x00, 0x00 db 0x10, 0xc1, 0x16, 0x00, 0x30, 0x10, 0x0d, 0x10 db 0x00, 0x30, 0x43, 0x6C, 0x00, 0x00, 0x00, 0x10 ; DS 32 db 0x60, 0x06, 0x00, 0x00, 0x11, 0x08, 0x36, 0x00 db 0x00, 0xc1, 0x0C, 0x20, 0x00, 0x00, 0x00, 0x00 db 0x00, 0x00, 0x00, 0x20, 0x06, 0x04, 0x00, 0x00 db 0x0C, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00 ds 16, 0 explosion_data4: ds 16, 0 ds 32, 0 ds 32, 0 grave_cross_data_1: ;db[16] db 0x18, 0x3C, 0x42, 0x66, 0x5A, 0x3C, 0x18, 0x3C db 0x5A, 0xA5, 0x24, 0x24, 0x42, 0x42, 0x42, 0xc3 grave_cross_data_2: ;db[16] db 0x18, 0x3C, 0x42, 0x66, 0x5A, 0x3C, 0x18, 0x3C db 0x5A, 0xA5, 0x24, 0x24, 0x42, 0x42, 0x42, 0xc3 fire_screen_addr: dw 0xE44F ; -------------------------------------------------- ; Draw Big Jumping Jack and play sound ; -------------------------------------------------- draw_happy_end: CALL clear_screen LD HL, 0xde70 LD B, 0x2 CALL j_draw_rh LD HL, 0xdc78 LD B, 0x4 CALL j_draw_rh LD HL, 0xda80 LD B, 0x6 CALL j_draw_rh LD HL, 0xde88 LD B, 0x2 CALL j_draw_rh LD HL, 0xda88 LD B, 0x2 CALL j_draw_rv LD HL, 0xe488 LD B, 0x2 CALL j_draw_rv LD HL, 0xdc98 LD B, 0x4 CALL j_draw_rh LD HL, 0xdea0 LD B, 0x4 CALL j_draw_rv LD HL, 0xe0a0 LD B, 0x4 CALL j_draw_rv LD HL, 0xdca8 LD B, 0x1 CALL j_draw_rh LD HL, 0xe2a8 LD B, 0x1 CALL j_draw_rh LD HL, 0xdab0 LD B, 0x1 CALL j_draw_rh LD HL, 0xe4b0 LD B, 0x1 CALL j_draw_rh LD HL, 0xd8b8 LD B, 0x1 CALL j_draw_rh LD HL, 0xe6b8 LD B, 0x1 CALL j_draw_rh LD HL, 0xd6c0 LD B, 0x1 CALL j_draw_rh LD HL, 0xe8c0 LD B, 0x1 CALL j_draw_rh LD HL, 0xdcc0 LD B, 0x3 CALL j_draw_rv LD HL, 0xe2c0 LD B, 0x3 CALL j_draw_rv LD HL, 0xdad8 LD B, 0x3 CALL j_draw_rv LD HL, 0xe4d8 LD B, 0x3 CALL j_draw_rv LD HL, 0xd8e8 LD B, 0x1 CALL j_draw_rh LD HL, 0xe6e8 LD B, 0x1 CALL j_draw_rh PUSH BC LD BC, 0x64 j_nxt_snd_per: LD A, 0xf OUT (DD67PC), A ; bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 150 j_mini_dly_snd2: DEC DE LD A, D OR E JP NZ, j_mini_dly_snd2 POP AF POP BC POP DE POP HL LD A, 0x00 OUT (DD67PC), A ; bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 150 j_mini_dly_snd3: DEC DE LD A, D OR E JP NZ, j_mini_dly_snd3 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, j_nxt_snd_per POP BC CALL clear_screen LD HL, 0xde38 LD B, 0x2 CALL j_draw_rh LD HL, 0xdc40 LD B, 0x4 CALL j_draw_rh LD HL, 0xda48 LD B, 0x6 CALL j_draw_rh LD HL, 0xde50 LD B, 0x2 CALL j_draw_rh LD HL, 0xda50 LD B, 0x2 CALL j_draw_rv LD HL, 0xe450 LD B, 0x2 CALL j_draw_rv LD HL, 0xdc60 LD B, 0x4 CALL j_draw_rh LD HL, 0xd460 LD B, 0x1 CALL j_draw_rh LD HL, 0xea60 LD B, 0x1 CALL j_draw_rh LD HL, 0xd668 LD B, 0x1 CALL j_draw_rh LD HL, 0xe868 LD B, 0x1 CALL j_draw_rh LD HL, 0xd870 LD B, 0x3 CALL j_draw_rh LD HL, 0xe270 LD B, 0x3 CALL j_draw_rh LD HL, 0xde68 LD B, 0x4 CALL j_draw_rv LD HL, 0xe068 LD B, 0x4 CALL j_draw_rv LD HL, 0xd888 LD B, 0x3 CALL j_draw_rh LD HL, 0xe288 LD B, 0x3 CALL j_draw_rh LD HL, 0xd690 LD B, 0x1 CALL j_draw_rh LD HL, 0xe890 LD B, 0x1 CALL j_draw_rh LD HL, 0xd498 LD B, 0x1 CALL j_draw_rh LD HL, 0xea98 LD B, 0x1 CALL j_draw_rh LD HL, 0xd098 LD B, 0x1 CALL j_draw_rh LD HL, 0xee98 LD B, 0x1 CALL j_draw_rh LD HL, 0xd2a0 LD B, 0x1 CALL j_draw_rh LD HL, 0xeca0 LD B, 0x1 CALL j_draw_rh PUSH BC LD BC, 150 j_nxt_snd_per1: LD A, 0xf OUT (DD67PC), A ; bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 100 j_mini_dly_snd4: DEC DE LD A, D OR E JP NZ, j_mini_dly_snd4 POP AF POP BC POP DE POP HL LD A, 0x00 OUT (DD67PC), A ; bell + tape PUSH HL PUSH DE PUSH BC PUSH AF LD DE, 100 j_mini_dly_snd5: DEC DE LD A, D OR E JP NZ, j_mini_dly_snd5 POP AF POP BC POP DE POP HL DEC BC LD A, C OR B JP NZ, j_nxt_snd_per1 POP BC LD A, (happy_end_sound_counter) ;= 0x3 DEC A LD (happy_end_sound_counter), A ;= 0x3 OR A JP NZ, draw_happy_end LD A, 3 LD (happy_end_sound_counter), A ;= 0x3 RET ; -------------------------------------------------- ; Out big grave cross ; and messages ; -------------------------------------------------- out_game_over: CALL clear_screen LD HL, 0xe038 LD B, 0x9 CALL j_draw_rv LD HL, 0xdc48 LD B, 0x5 CALL j_draw_rh LD HL, 0xe258 LD B, 0x1 CALL j_draw_rh LD HL, 0xde60 LD B, 0x1 CALL j_draw_rh LD HL, 0xde80 LD B, 0x3 CALL j_draw_rh LD HL, 0xdc88 LD B, 0x5 CALL j_draw_rh LD HL, 0xda90 LD B, 0x7 CALL j_draw_rh LD A, 0x00 OUT (SYS_DD17PB), A LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0xaa8 LD (cursor_pos), HL LD DE, j_msg_game_over1 LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x2b8 LD (cursor_pos), HL LD DE, j_msg_game_over2 ;= 0x0d LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL LD HL, (curr_color) PUSH HL LD A, 0x00 LD L, A CPL LD H, A LD (curr_color), HL LD HL, 0x2c8 LD (cursor_pos), HL LD DE, j_msg_game_over3 ;= 0x20 LD C, C_WRITESTR CALL BDOS_ENTER POP HL LD (curr_color), HL j_wait_for_key: CALL mon_con_status OR A JP Z, j_wait_for_key LD A, 0x10 OUT (SYS_DD17PB), A ; vram @ 0xc000 RET happy_end_sound_counter: db 3 j_msg_game_over1: db 0x20, 0x0C, 0x09, 0xE4, 0xEF, 0xf0, 0xF2, 0xF9 db 0xE7, 0xe1, 0xEC, 0xF3, 0xF1, '$' j_msg_game_over2: db 0x0d, 0x0A, 0x20, 0xe5, 0xF3, 0xEC, 0xe9, 0xa0 db 0xE8, 0xEF, 0xF4, 0xe9, 0xF4, 0xe5, 0xa0, 0xe5 db 0xFD, 0xe5, 0x2C, 0xEE, 0xe1, 0xf6, 0xED, 0xe9 db 0xF4, 0xe5, 0xa0, 0xEC, 0xe0, 0xE2, 0xF5, 0xe0 db '$' j_msg_game_over3: db 0x20, 0xeb, 0xEC, 0xe1, 0xF7, 0xe9, 0xFB, 0xF5 db 0x0D, 0x0A, 0x22, 0xF3, 0xE2, 0xF2, 0xEF, 0xF3 db 0x22, 0x2D, 0xC4, 0xCC, 0xd1, 0xa0, 0xd7, 0xD9 db 0xc8, 0xcf, 0xC4, 0xc1, '$' db 0x00, 0x00, 0x00, 0x00, 0x00 ; -------------------------------------------------- ; ; -------------------------------------------------- exit_to_cpm: LD A, 0 OUT (SYS_DD17PB), A ; ROM on, Vram off LD HL,(saved_color) LD (curr_color), HL LD DE, reset_vmode LD C, C_WRITESTR CALL BDOS_ENTER JP WARM_BOOT ; return CP/M saved_color: dw 0 reset_vmode: db ASCII_ESC, "70" ; Set LAT Charset db ASCII_ESC, "60" ; Set mode 40x25 with cursor db ASCII_US, ASCII_FF, "$" ; Clear screen, home cursor j_fill_11: ds 690, 0 j_end_of_file: ; garbage cleaned