;========================================================================== ; RBlade by Thibaut Chevalier ; version 4.1 Copyright 20/03/2002 ; You can use parts of this code as long as you give credit to me ; but you are not allowed to do any changes to this game without asking me ;========================================================================== ;============================ Game Variables ====================== _textshadow = $c0f9 special_counter = _textshadow+1 graph_key_state = _textshadow+2 table_key_state = _textshadow+3 jump_info = _textshadow+4 ; bit 0 = mute, bit 1 = liu_kang, bit 2 = late, bit 3 = crash, bit 4 = flip or no last_trick = _textshadow+5 ; last trick to see if the next is the same (less points) : bit 0 = rotation, bit 1 = late rotation, bit 2 = flip, bit 3 = invert, bit 4 = grind, but 5 = special lest_last_trick = _textshadow+6 coordx = _textshadow+7 ; coordy = _textshadow+8 ; coordinates of the rider position = _textshadow+9 ; position on the vert (0..26), 13 = flat direction = _textshadow+10 ; bit0 = direction (0=left / 1=right) ; bit1 = fakie yes/no (0=no / 1=yes) speed = _textshadow+11 ; speed (1..7) overall_speed = _textshadow+12 ; speed of the program (1..5) * vertical_speed = _textshadow+13 ; temporary speed variable (for jumps) * don't split *** !!! rotation_index = _textshadow+14 ; (0,2,4,6) with a loop 0->6 or 6->0 * rotation_degree = _textshadow+15 ; =(rotation in degrees)/90 , positive or negative temporary = _textshadow+16 temporary_2 = _textshadow+17 temporary_3 = _textshadow+18 previous_value_of_rotation = _textshadow+19 sloppy_arrival_Y_N = _textshadow+20 ; just to remember that the arrival is sloppy menu_cursor_position = _textshadow+21 game_mode = _textshadow+22 ; 0=free skate, 1=contest second_row_pen_col = _textshadow+23 score = _textshadow+24 ; (two bytes) stack_save = _textshadow+26 ; (two bytes) time200 = _textshadow+28 time = _textshadow+29 ; time variable (used in contest mode) time_previous = _textshadow+30 time's_up = _textshadow+31 time_run = _textshadow+32 ; decide whether the time has to decrease or not (1 or 0) flip_index = _textshadow+33 flip_number = _textshadow+34 temporary_4_5 = _textshadow+35 ; (two bytes) temporary_6 = _textshadow+37 ;================ aliases ========================= _asm_exec_ram = $d748 _vputmap = $4aa1 ; display variable width character (A=char) _runindicoff = $4ab1 _runindicon = $4aad _clrLCD = $4a7e _penCol = $c37c _curRow = $0c00f ; cursor row _vputs = $4aa5 _puts = $4A37 ; display a zero-terminated string (HL=ptr) _pause = $4d43 GET_KEY = $5371 K_NOKEY = $00 ; no key K_F5 = $31 ; F5 K_F4 = $32 ; F4 K_ENTER = $09 ; Enter K_EXIT = $37 ; exit K_DOWN = $01 ; Down K_LEFT = $02 ; Left K_RIGHT = $03 ; Right K_UP = $04 ; Up K_PLUS = $0A ; + K_MINUS = $0B ; - K_CLEAR = $0F ; Clear K_6 = $13 K_0 = $21 ; 0, Y K_9 = $14 ; 9, N UNPACK_HL = $4044 _OP1 = $c089 onFlags = $09 _user_int_ram = $d2fd ; Area where interrupt handler goes _cphlde = $403C _SET_ABS_SRC_ADDR = $4647 _SET_ABS_DEST_ADDR = $5285 _SET_MM_NUM_BYTES = $464f _MM_LDIR = $52ed _EX_AHL_BDE = $45f3 _ahl_Plus_2_Pg3 = $4c3f _asapvar = $0D6FC ; name of the current asm prog _clrScrn = 4A82h ; clear LCD screen and _textShadow _move10b = $427b ; move to bytes from hl to de .org _asm_exec_ram nop jp ProgStart .dw 0 .dw ShellTitle ShellTitle: .db "RBlade v4.1 by Thibaut Chevalier",0 ProgStart: pop bc ld (stack_save), bc ; save the calling adress (has a use for find_stack_loop) push bc call _runindicoff ld a, 36 ld (menu_cursor_position), a ; set the position of the arrow at the top (and when the game reboot no) call OpenGray ; start grayscale and the time code reboot: call GET_KEY ; avoid immediate exit if the user press exit during the game call Blank_screen call draw_rollerman call draw_title ld bc, (256*20)+2 ld (_penCol), bc ld hl, my_name_string call _vputs ld bc, (256*26)+17 ld (_penCol), bc call _vputs ld bc, (256*37)+9 ld (_penCol), bc call _vputs ld bc, (256*43)+9 ld (_penCol), bc call _vputs ld bc, (256*49)+9 ld (_penCol), bc call _vputs ld bc, (256*55)+9 ld (_penCol), bc call _vputs ld hl, arrow ld a, (menu_cursor_position) ld e, 0 ld d, a call PutSprite8xGrid menu_getkey_loop: call GET_KEY cp K_UP jr z, cursor_up cp K_DOWN jr z, cursor_down cp K_ENTER jr z, start_all cp K_EXIT jp z, finish jr menu_getkey_loop cursor_up: ld a, (menu_cursor_position) ld e, 0 ld d, a ld hl, no_arrow call PutSprite8xGrid ld a, d sub 6 ld d, a cp 30 jr nz, common_cursor_routine ld d, 54 jr common_cursor_routine cursor_down: ld a, (menu_cursor_position) ld e, 0 ld d, a ld hl, no_arrow call PutSprite8xGrid ld a, d add a, 6 ld d, a cp 60 jr nz, common_cursor_routine ld d, 36 common_cursor_routine: ld hl, arrow call PutSprite8xGrid ld a, d ld (menu_cursor_position), a jr menu_getkey_loop start_all: xor a ld (game_mode), a ld a, (menu_cursor_position) cp 36 jr z, free_skate_mode cp 42 jr z, contest_mode cp 48 jp z, high_scores_displaying jp finish free_skate_mode: call Blank_screen ld hl, menu_1_string jr both_modes contest_mode: call Blank_screen ld a, 1 ld (game_mode), a ld hl, menu_2_string both_modes: ld bc, (20<<8)+41 ld (_penCol),bc call _vputs ld hl, time200 ld (hl), 1 ; time200 inc hl ld (hl), 60 ; time inc hl ld (hl), 60 ; time_previous inc hl ld (hl), 0 ; time's_up inc hl ld (hl), 0 ; time_run ld hl,0 ; reset_score ld (score), hl jr no_clearing crash_restart: ; if riders crashes, restart here (it doesn't reset score) call Blank_screen call score_display no_clearing: ld hl, VertData ld de, $fe70 ld bc, 400 ldir ld de, _plotSScreen+$6+$270 ld bc, 400 ldir ; draws the VERT :) ld hl,string_name-1 ; address of one byte before 'stringname' label rst 20h ; same as 'call _Mov10toOP1' rst 10h ; same as 'call _FindSym' jr c, no_string ; variable doesn't exist call _EX_AHL_BDE ; load data absolute adress in ahl call _ahl_Plus_2_Pg3 ; add 2 because the first two bytes are trash ld d, 0 ld bc, 912 add hl, bc adc a, d ; 32 bit addition call _SET_ABS_SRC_ADDR ; load it in the ldir source ld hl, _plotSScreen+554 call _SET_ABS_DEST_ADDR ; load destination adress ld b, 19 call draw_half_stuff no_string: ld hl, $fc1f ; begin at 2nd row, colomn 15 ld b, 38 regle_loop: ld a, b and %00000010 cp 2 ; draw 2 black rows, 2 white rows... jr z, black_part white_part: ld (hl), %00001010 jr go_to_djnz black_part: ld (hl), %00001110 go_to_djnz: ld de, $3200 or a sbc hl, de ld (hl), %00001110 ; write on the second bit plane... add hl, de ; ... and return to the 1st ld de, 16 add hl, de ; go to next row djnz regle_loop ld bc, (38<<8)+1 ; draws score board ld d, 89 call DrawHoriz ld bc, (37<<8)+2 ld d, 90 call DrawHoriz ld bc, (37<<8)+27 ld d, 90 call DrawHoriz ld bc, (38<<8)+28 ld d, 89 call DrawHoriz ld bc, (39<<8)+18 ld d, 88 call DrawHoriz ld bc, (2<<8)+37 ld d, 27 call DrawVert ld bc, (1<<8)+38 ld d, 28 call DrawVert ld bc, (1<<8)+89 ld d, 28 call DrawVert ld bc, (2<<8)+90 ld d, 27 call DrawVert ld bc, (43<<8)+0 ld d, 45 call DrawHoriz ld bc, (82<<8)+0 ld d, 84 call DrawHoriz ld hl, _plotSScreen+58 ld b, 25 gray_background_loop: push bc ld (hl), %00000111 inc hl ld (hl), %11111111 ld d, h ld e, l inc de ld bc, 6 ldir ld (hl), %11100000 ld bc, 9 add hl, bc pop bc djnz gray_background_loop ld hl, initialization ld de, jump_info call _move10b ; set variables ld a, %11000000 ld (_plotSScreen+7), a ld hl, overall_indicator ld de, 0 call PutSprite8xGrid ld bc, (6<<8)+23 call GetBack16 ld hl, Rider1down call PutSprite16Masked ld a, (game_mode) or a jr z, dont_draw_seconds ld bc, (56<<8)+119 ld (_penCol), bc ; coodonates of text to draw (time) set 3,(iy+5) ; white text on black background ld a, (time) cp 10 jr nc, long_time_2 ld hl, spaces_string+4 call _vputs long_time_2: ld a, (time) ld h, 0 ld l, a ; hl = time value call DisplayHL ; displays new value of time res 3,(iy+5) ; black text on white background ; black text on white background dont_draw_seconds: call _pause_n_exit ld hl, indicator ld de, (56<<8)+0 call PutSprite8xGrid call delay_start ld bc, (6<<8)+23 call RestoreBack16 ld bc, (9<<8)+25 call GetBack16 ld hl, Rider2down call PutSprite16Masked call redraw_copings call delay_start call RestoreBack16 ld bc, (17<<8)+34 call GetBack16 ld hl, Rider3down call PutSprite16Masked ld hl, $fd45 ld b, 6 call clear_board ; clear down-part of the board call score_display ; displays score instead of game mode call key_counter_init ld a, 1 ld (time_run), a ;===================== Main loop : The rider is on the half-pipe ================== loop: ld hl, speed ld b, (hl) inc hl ld a, (hl) ; overall_speed sub b ld b, a ; calculate in b the number of halt loops to do according te the overall_speed and the rider speed sla b ; multiply this time by two to obtain the time on a 2 pixels move ld a, b or a jr z, no_delai_loop ; don't execute the djnz if speed is 0 delay_loop: ld hl, special_counter ld a, (graph_key_state) or a jr nz, look_for_graph_key_up ld a,%01011111 out (1),a in a,(1) bit 6,a jr nz, table_key ld a, 1 ld (graph_key_state), a inc (hl) jr table_key look_for_graph_key_up: ld a,%01011111 out (1),a in a,(1) bit 6,a jr z, table_key ld a, 0 ld (graph_key_state), a table_key: ld a, (table_key_state) or a jr nz, look_for_table_key_up ld a,%01101111 out (1),a in a,(1) bit 6,a jr nz, do_djnz ld a, 1 ld (table_key_state), a inc (hl) jr do_djnz look_for_table_key_up: ld a,%01101111 out (1),a in a,(1) bit 6,a jr z, do_djnz ld a, 0 ld (table_key_state), a do_djnz: ;push bc ; ld bc, (32<<8)+0 ; ld (_penCol), bc ; ld a, (hl) ; ld h, 0 ; ld l, a ; call DisplayHL ;pop bc halt call update_time ; update the time on the screen if necessary djnz delay_loop no_delai_loop: call check_key_presses ; check keypresse for overall speed change ld a, (position) or a jp z, jump_left_side ; start jump routine if the rider is at one of the side on the vert cp 26 jp z, jump_right_side ; start jump routine change_dir: ld a, (position) cp 12 jr nz, not_on_the_flat_left ld a, (direction) and %00000001 jr z, not_on_the_flat_left ld a, (jump_info) and $8 ; mask everything but the bit 3 = crashed or not jp nz, crash_n_slow_left ; goto slowing routine if riders crashes ld a, (time's_up) or a jp nz, crash_n_slow_left ; or if time's up call speed_inc ; rider on the left side of the flat, going down jr not_on_the_flat_right not_on_the_flat_left: ld a, (position) cp 14 jr nz, not_on_the_flat_right ld a, (direction) and %00000001 jr nz, not_on_the_flat_right ld a, (jump_info) and $8 ; mask everything but the bit 3 = crashed or not jp nz, crash_n_slow_right ; goto slowing routine if riders crashes ld a, (time's_up) or a jp nz, crash_n_slow_right ; or if time's up call speed_inc ; rider on the right side of the flat, going down not_on_the_flat_right: ld a, (direction) and %00000001 ; only keeps bit 0 (direction) jp z, left ; moves rider to the left jr right ; esle moves rider to the right speed_inc: ; increase rider speed and update the indicator (white vertical indicator on the down-left corner) ld hl, speed ld a, 7 cp (hl) ret z ; does not increase if speed=7 (limit) inc (hl) ld b, (hl) ; b = speed ld a, 63 sub b ld d, a ld e, 0 call FindPixel ; find adress to change ld (hl), %10011111 ; update the screen (first plane) ld de, $3200 or a sbc hl, de ld a, %11111111 ld (hl), a ; (2nd plane) ret ;==================== Rider Moving ====================== right: call get_coord call RestoreBack16 ld a, (position) cp 12 jr z, flat_d ; on the flat cp 13 jp z, flat_d inc a ld (position), a jr right_into_left flat_d: inc b inc b ld a, b cp 83 jr nz, still_on_the_flat_d ld a, 14 ld (position), a zoup_d; ld hl, Sprites_table jr insersion still_on_the_flat_d: ld a, 13 ld (position), a ; 13 = rider on the flat call save_coord jr zoup_d left: call get_coord call RestoreBack16 ld a, (position) cp 14 jr z, flat_g ; on the flat cp 13 jr z, flat_g dec a ld (position), a right_into_left: ; same code from now for both directions ld b, a add a, a add a, b ; a*3 ld c, a ld b, 0 ld hl, moves_table add hl, bc ld b, (hl) inc hl ld c, (hl) ; bc = coord of the rider call save_coord inc hl ld e, (hl) ; djnz counter (rider number (1..6) ld a, e ld (temporary), a ld hl, Sprites_table-2 sla e ld d, 0 add hl, de insersion: ld a, (jump_info) and %00001000 jr nz, find_crashed_sprite_adress ; if rider crashes, goto find sprite adress call adjust_sprite_pointer_adress ld d, (hl) ; hl is the 'sprite adress' memory location inc hl ld e, (hl) ; ld de, (hl) ld h, e ld l, d ; now hl is the correct sprite adress insersion_for_crash: call GetBack16 call PutSprite16Masked jp loop flat_g: dec b dec b ld a, b cp 29 jr nz, still_on_the_flat_g ld a, 12 ld (position), a zoup_g; ld hl, Sprites_table+6 jr insersion still_on_the_flat_g: ld a, 13 ld (position), a ; 13 = rider on the flat call save_coord jr zoup_g find_crashed_sprite_adress: push bc ld de, 64 ld hl, Crashed_Sprites-64 ld a, (temporary) ld b, a crashed_search_loop: add hl, de djnz crashed_search_loop ; get correct crashed_sprite adress adding 64 bytes "temporary" times pop bc ; get saved value of bc jr insersion_for_crash ; goto display the sprite ;======================= End of main loop ====================== ;======================= Jumps engines =========================== jump_right_side: call check_invert ; check if invert_key is pressed, and if true execute other stuff call check_special call load_rotation_index ld a, (speed) ld (vertical_speed), a ; temporary speed variable ld b, a ld a, %00000001 ; bit0 = 1 means up, bit1 = 0 means right ld (temporary_2), a call jump_routine ; same routine for all directions and sides ; here, rider is going up call get_coord call swap_layers ld a, 2 ld (vertical_speed), a ; from 2 to 'speed' xor a ld (temporary_2), a ld a, (speed) ld b, a dec b ; first djnz counter call jump_routine ; now, rider is going down ld hl, $fe6f call end_of_jump ; stuff do do at the end of the jump (score...) call calcul_score call get_coord call swap_layers call key_counter_init jp change_dir jump_left_side: call check_invert ; check if invert_key is pressed, and if true execute other stuff call check_special call load_rotation_index ld a, (speed) ld (vertical_speed), a ; temporary speed variable ld b, a ld a, %00000011 ld (temporary_2), a call jump_routine ; same routine for all directions and sides ; here, rider is going up call get_coord call swap_layers ld a, 2 ld (vertical_speed), a ; from 2 to 'speed' ; ld a, %00000010 ; a is already 2 ld (temporary_2), a ld a, (speed) ld b, a dec b ; first djnz counter call jump_routine ; now, rider is going down ld hl, $fe6f call end_of_jump ; stuff do do at the end of the jump (score...) call calcul_score ; calculate score for this jump and displays it call get_coord call swap_layers call key_counter_init jp change_dir ;========================= Routines used by the jump engine =============================== jump_routine: ; routine used in 4 differents cases (up and down, left and right) factor_loop: push bc ld a, (vertical_speed) ld b, a speed_length_up: ; rider goes up or down 'vertical_speed' x at speed 'vertical_speed' push bc call get_coord call RestoreBack16 call swap_layers ; swap the regle's layers but not at the top of the jump ld a, (temporary_2) and %00000001 jr nz, jump_up inc c ; rider goes down 1 pixel jr jump_up_down jump_up: dec c ; rider goes up 1 pixel jump_up_down: call GetBack16 call save_coord ld a, (jump_info) and %00010000 jr nz, find_flip_adress ; if the rider flips, find flip's adresses ld a, (temporary_2) and %00000010 jr nz, jump_left ld hl, RightJump_table jr find_sprite_adress jump_left: ld hl, LeftJump_table find_sprite_adress: ld a, (rotation_index) ld d, 0 ld e, a add hl, de ; get adress of sprite adress :) call check_grab ; check of grab-key press, and if pressed, adjust adress flip_insersion: call relative_jump_too_looooooooong vertical_delay_loop: halt call update_time ; update the time on the screen if necessary djnz vertical_delay_loop call check_key_presses pop bc djnz speed_length_up call check_rider_rotation call draw_degrees ld hl, vertical_speed ld d, (hl) ld a, (temporary_2) and %00000001 jr nz, jump_up_2 inc d ; vertical_speed increasing jr jump_up_down_2 jump_up_2: dec d ; vertical_speed decreasing jump_up_down_2: ld (hl), d pop bc djnz factor_loop ret find_flip_adress: ; djnz factor relative jump is too big if i put this code inside ld a, (temporary_2) and %00000010 ld d, a ld a, (direction) srl a add a, d sla a ; * sla a ; * sla a ; * multiply a by 8 ld d, a ld a, (flip_index) add a, d ; add 0,2,4 or 6 ; now we have the position in the table*2 (because every line is a woed) ld d, 0 ld e, a ld hl, Right_flip_table add hl, de jr flip_insersion swap_layers: push bc ld a, c add a, 7 ld d, a ld e, 120 call FindPixel ld a, (hl) ld de, $3200 or a sbc hl, de ld b, (hl) ld (hl), a add hl, de ld (hl), b ; swap layers pop bc ret relative_jump_too_looooooooong: ld d, (hl) inc hl ld e, (hl) ld h, e ld l, d ; get sprite adress call PutSprite16xGrid ld hl, overall_speed ld a, (hl) inc hl ld b, (hl) ; vertical_speed sub b ld b, a ret ;------------------------------------------------------------------------------- update_time: ; this routine is not executed in the interrupt code, because sometimes it crashs ; so the interrupt code just modify the time in the memory, and this routine after on the screen push af push bc ld a, (time_previous) ld b, a ld a, (time) cp b jr z, return_with_double_pop2 push hl push de ld (time_previous), a ld bc, (56<<8)+119 ld (_penCol), bc ; coodonates of text to draw (time) set 3,(iy+5) ; white text on black background cp 10 ; a = time jr nc, long_time cp 9 jr z, time_9 ld a, (_penCol) add a, 4 ld (_penCol), a long_time: ld a, (time) ld h, 0 ld l, a ; hl = time value call DisplayHL ; displays new value of time res 3,(iy+5) ; black text on white background pop de pop hl return_with_double_pop2: pop bc pop af ret time_9: ld hl, spaces_string+4 call _vputs jr long_time key_counter_init: ld hl, special_counter xor a ld (hl), a inc hl ld (hl), a inc hl ld (hl), a ; reset special_counter, graph_key_state and table_key_state ret delay_start: ; just a 35 halt pause ld d, b ; saves b into d ld b, 35 delay_start_loop halt call update_time ; update the time on the screen if necessary djnz delay_start_loop ld b, d ; restore b ret adjust_sprite_pointer_adress: ld a, (direction) or a ; rider run to the left, not in fakie (no change) ret z cp 3 ; rider run to the right, in fakie (no change) ret z ld a, (temporary) cp 4 jr c, big_addition small_addition: ld de, 6 jr do_add big_addition: ld de, 18 do_add: add hl, de ; rider is now turned to the right ret get_coord: ; loads coord in b and c push hl ld hl, coordx ld b, (hl) inc hl ld c, (hl) pop hl ret save_coord: ; saves b and c coord push hl ld hl, coordx ld (hl), b inc hl ld (hl), c pop hl ret check_key_presses: ; warning, we are under a call !! ld a,%00111111 out (1),a in a,(1) bit 1,a call z, overall_speed_dec ; F4 ld a,%00111111 out (1),a in a,(1) rrca call nc, overall_speed_inc ; F5 ld a,%00111111 out (1),a in a,(1) rlca jp nc, pause_routine ; More ld a,%01111101 out (1),a in a,(1) bit 6,a jp z, teacher_key_routine ; Clear ld a,%00111111 out (1),a in a,(1) bit 6,a jp z, reboot_and_find ; EXIT ret check_rider_rotation: ld a,%01111110 out (1),a in a,(1) bit 2,a jr z, right_rotate ld a,%01111110 out (1),a in a,(1) bit 1,a jr z, left_rotate ld a,%01111110 out (1),a in a,(1) bit 3,a jr z, up_flip ld a,%01111110 out (1),a in a,(1) rrca ret c down_flip: ld a, (rotation_degree) or a ret nz ; if the rider has turned, he can't flip ld hl, jump_info ld a, (hl) or %00010000 ld (hl), a ld hl, flip_number jr decrease_it ; same stuff that with a rotation, but with other variables up_flip: ld a, (rotation_degree) or a ret nz ; if the rider has turned, he can't flip ld hl, jump_info ld a, (hl) or %00010000 ld (hl), a ld hl, flip_number jr increase_it ; same stuff that with a rotation, but with other variables left_rotate: ld a, (jump_info) and %00010000 ret nz ; DONT ROTATE AFTER A FLIP call set_late_if_true ld hl, rotation_degree decrease_it: dec (hl) ; save number of 90 degrees rotation for scores and display dec hl ; ld hl, rotation_index dec (hl) dec (hl) ; sub 2 to the rotation-index ld a, (hl) cp -2 ; if previous content was 0, it will be 6 ret nz ld a, 6 ld (hl), a ret ; decrease rotation_index (0.2.4.6) right_rotate: ld a, (jump_info) and %00010000 ret nz ; DONT ROTATE AFTER A FLIP call set_late_if_true ld hl, rotation_degree increase_it: inc (hl) ; save number of 90 degrees rotation for scores and display dec hl ; ld hl, rotation_index inc (hl) inc (hl) ; add 2 to the rotation-index ld a, (hl) cp 8 ; if previous content was 6, it will be 0 ret nz xor a ld (hl), a ret ; increase rotation_index (0.2.4.6) set_late_if_true: ld a, (rotation_degree) or a ret nz ld a, (temporary_2) and %00000001 ;cp 0 ret nz ld hl, jump_info ld a, (hl) or %00000100 ld (hl), a ret load_rotation_index: ld hl, $fc35 ld b, 15 call clear_board ; clears the upper part of the board ld a, 41 ld (second_row_pen_col), a xor a ld (jump_info), a xor a ; = ld a, 0 ld hl, flip_index ld (hl), a inc hl ld (hl), a ; flip_number ld hl, rotation_degree ld (hl), a ld (previous_value_of_rotation), a ld a, (direction) and %00000010 jr nz, fakie_position xor a jr save_index fakie_position: ld a, 4 save_index: dec hl ; rotation_index ld (hl), a ret check_grab: ld a,%00111111 out (1),a in a,(1) bit 5,a jr nz, check_liu_kang ; no mute push bc push hl ld hl, jump_info ld a, (hl) and %00000001 jr nz, already_muted ld a, (hl) or %00000001 ld (hl), a ; write to jump_info = mute activated ld a, (second_row_pen_col) ld b, 11 ld c, a ld (_penCol),bc ; get last writing coordonates ld hl, mute_string call _vputs ld a, (_penCol) ld (second_row_pen_col), a ; save the new ones already_muted: pop hl pop bc ld de, 16 add hl, de ; get mute-trick sprites adress ret check_liu_kang: ld a,%01011111 out (1),a in a,(1) rlca ret c push bc push hl ld hl, jump_info ld a, (hl) and %00000010 ;cp 2 jr nz, already_liu_kangd ld a, (hl) or %00000010 ld (hl), a ; write to jump_info = mute activated ld a, (second_row_pen_col) ld b, 11 ld c, a ld (_penCol),bc ld hl, liu_kang_string call _vputs ld a, (_penCol) ld (second_row_pen_col), a already_liu_kangd: pop hl pop bc ld de, 32 add hl, de ; get liu_kang-trick sprites adress ret end_of_jump: ld hl, direction ld a, (hl) xor %00000001 ld (hl), a ; change direction of the rider (bit 0 of direction) ld a,(flip_index) or a jr z, no_crash_with_flip ld hl, jump_info ; crash_with_flip ld a, (hl) or %00001000 ; set bit 3 as a crash message ld (hl), a ld a, (speed) call dec_rider_speed; rider loses speed ld a, (hl) ; hl is loaded with speed cp 2 call nz,dec_rider_speed no_crash_with_flip: xor a ld (sloppy_arrival_Y_N), a ; reset sloopy_arrival_Y_N (it will be set if the arrival is really sloppy) ld hl, direction ld a, (rotation_index) cp 2 jp z, sloppy_arrival cp 6 jp z, sloppy_arrival speed_loss_return: ld hl, direction ld a, (rotation_index) or a jr z, fakie_arrival ld a, (hl) and %11111101 ; reset bit 1 (fakie off) ld (hl), a jr not_fakie_shh fakie_arrival: ; rider arrives fakie ld a, (hl) or %00000010 ; set bit 1 (fakie on) ld (hl), a not_fakie_shh: ld a, (jump_info) and %00001000 jp nz, crash_routine ; exit this part of code if riders crash ld bc, (256*4)+40 ld (_penCol),bc ld a, (sloppy_arrival_Y_N) or a call nz, sloppy_display ; if the arrival is sloppy, DISPLAYS the word sloppy, and update the pen position (penCol) jr end_of_jump_insersion sloppy_display: ld hl, sloppy_string call _vputs ; col and row already set ret draw_degrees: ; routine not only used at the end of the jump, but also to update the rotation counter in the score board ld a, (flip_number) or a jr nz, draw_number_of_flip ; if the trick is a rotation... ld a, (previous_value_of_rotation) ld b, a ld a, (rotation_degree) cp b jr z, flickerless_drawing ; if the value hasn't changed, do not display it again (else it will flicker) ld (previous_value_of_rotation), a ld bc, (256*4)+40 ld (_penCol),bc end_of_jump_insersion: ; label used for the end of the jump only ld hl, 0 ld a, (rotation_degree) ld b, a ; djnz counter (90*b) or a jr z, rotation_0 rla ; bit 7 is now in the carry flag call c, two_complement ; if carry flag is set, the number is negative, execute two_complement ld de, 90 calculate_rotation_djnz: add hl, de djnz calculate_rotation_djnz call DisplayHL ; hl = number of degrees to draw ld a, (jump_info) and %00000100 ret z ; return if the jump is not a "late" ld hl, late_string jp _vputs ; call _vputs and return rotation_0: ld a, (direction) and %00000010 ret z ld a, (jump_info) and %00010000 ret nz ld hl, zero_to_fakie_string jp _vputs ; call _vputs and return two_complement: ld d, 2 ; set d as a "backflip" message (only useful when displaying filp number) ld a, b neg ld b, a ret flickerless_drawing: ld (previous_value_of_rotation), a ret draw_number_of_flip: ; if the trick is a flip... ld c, a ; a = (flip_number) ld a, (previous_value_of_rotation) ld b, a ld a, c cp b jr z, flickerless_drawing ; if the value hasn't changed, do not display it again (else it will flicker) ld (previous_value_of_rotation), a ld bc, (256*4)+40 ld (_penCol),bc ld a, (flip_number) ld b, a rla ; bit 7 is now in the carry flag ld d, 0 ; 0 if frontflip, if backflip, d is set during the routine two_complement call c, two_complement ; if carry flag is set, the number is negative, execute two_complement ld a, b srl a srl a ; divide by 4 (the last 3 bits don't matter) or a ; cp 0 ret z ; the flip rotation is less than one flip, then print nothing cp 2 jr z, print_double cp 3 jr z, print_triple print_return: ld a, d or a jr z, print_backflip ld hl, frontflip_string jr step_to_print print_backflip: ld hl, backflip_string step_to_print: jp _vputs ; call _vputs and return print_double: ld hl, double_string call _vputs jr print_return print_triple: ld hl, triple_string call _vputs jr print_return sloppy_arrival: ld a, (speed) cp 6 jr c, no_crash ld hl, jump_info ld a, (hl) or %00001000 ; set bit 3 as a crash message ld (hl), a no_crash: ld hl, rotation_degree ld a, (hl) rla jr c, negative_rotation positive_rotation: inc (hl) ; increase rotation_degree (add 90 degrees to previous rotation) dec hl ; ld hl, rotation_index inc (hl) inc (hl) ld a, (hl) cp 8 jr nz, sloppy_arrival_end_of_code xor a ; ld a, 0 (if previous value of rotation_index was 6, now it is 0 ld (hl), a jr sloppy_arrival_end_of_code negative_rotation: dec (hl) ; increase rotation_degree in negative (add 90 degrees to previous rotation) dec hl ; ld hl, rotation_index dec (hl) dec (hl) ld a, (hl) ; if rotation_index was 2, now it is 0 / if it was 6, now it is 4) sloppy_arrival_end_of_code: ld a, 1 ld (sloppy_arrival_Y_N), a ; but remember type of arrival (good or sloppy) (message sloppy=1) ld a, (speed) call dec_rider_speed; rider loses speed ld a, (hl) ; hl is loaded with speed cp 2 call nz,dec_rider_speed jp speed_loss_return dec_rider_speed: ld b, a ld a, 63 sub b ld d, a ld e, 0 call FindPixel ld (hl), %11111111 ld de, $3200 or a sbc hl, de ld a, %10011111 ld (hl), a ld hl, speed dec (hl) ; change speed in the memory ret overall_speed_dec: push bc push af ; saves a because sometimes, a is the GET_KEY value ld hl, overall_speed ld a, (hl) cp 12 jr z, return_with_double_pop inc a ld (hl), a ; change overall_speed ; save changes on the screen ld b, a ld a, 13 sub b inc a ; a = overall_speed 1<=a<=5 ld b, a ; ready for djnz ld e, 0 ; colomn for Findpixel overall_speed_dec_djnz: ld d, b dec d ; row for FindPixel call FindPixel ; get adress and bitmask cpl and (hl) ; turns pixel off in register a ld (hl), a ; saves changes on the screen inc e inc e ; goes to the next colomn djnz overall_speed_dec_djnz pop af pop bc ret overall_speed_inc: push bc push af ; saves a because sometimes, a is the GET_KEY value ld hl, overall_speed ld a, (hl) cp 8 jr z, return_with_double_pop dec a ld (hl), a ld b, a ld a, 13 sub b ; a = overall_speed 1<=a<=5 ld b, a ; ready for djnz ld e, 0 ; colomn for Findpixel overall_speed_inc_djnz: ld d, b dec d ; row for FindPixel call FindPixel or (hl) ; turns pixel on in register a ld (hl), a ; saves changes on the screen inc e inc e ; goes to the next colomn djnz overall_speed_inc_djnz return_with_double_pop: pop af pop bc ret ; before returning from the "change" overall speed routine, we have to pop 2 words of the stack score_display: ld bc, (20<<8)+41 ld (_penCol),bc ld hl, score_string call _vputs ld bc, 0 score_only_insersion: ld de, 0 ld a, (game_mode) or a ; cp 0 jr z, free_mode ; if the mode is free skate, reset score at every trick ld de, (score) ; get old score in de free_mode: ex de, hl ; hl = old score value, bc = trick score value (or 0 if not the end of a trick) add hl, bc ; add jump score if it is the end of the jump (else bc=0) ld (score), hl ; save new score value call DisplayHL ld hl, spaces_string ; call _vputs ; erases text after score if necessary ret calcul_score: ld bc, (20<<8)+64 ld (_penCol),bc ld c, %00000001 ; c will contain the information on this trick to compare it from the previous ones ; 1 = rotation ld hl, 0 ld de, 10 ; if rotation : score = 10 * rotation_degree ld a, (rotation_degree) or a call z, rotation_0_score_1 ld b, a rla call c, two_complement ld d, 0 ; reset d if it was set by two's complement ld a, (sloppy_arrival_Y_N) or a ; cp 0 jr z, calculate_rotation_score_djnz inc b calculate_rotation_score_djnz: add hl, de djnz calculate_rotation_score_djnz rotation_0_score_2: ld de, 25 ld a, (jump_info) ld b, a and %00000001 jr z, no_mute add hl, de ; add 25 to the score if mute no_mute: ld a, b and %00000010 jr z, no_liu_kang add hl, de ; add 25 to the score if liu_kang no_liu_kang: ld a, (sloppy_arrival_Y_N) or a jr z, no_sloppy_2 srl h rr l ; divide hl by 2 srl h rr l ; divide hl by 2 no_sloppy_2: ld a, (jump_info) and %00000100 jr z, no_late sla l ; multiply hl by 2 if "late" rl h sla l rl h ; multiply hl by 2 if "late" ld c, %00000010 no_late: ld d, c ; load trick kind in d call look_for_score_reduction ; but score into bc and reduce it if the trick is the same than the previous ones, d = current trick jp score_only_insersion look_for_score_reduction: ld b, h ld c, l ; load the score for this trick in bc ld hl, last_trick ld a, (hl) cp d jr nz, and_previous_one srl b rr c ; divide bc by 2 and_previous_one: inc hl ; ld hl, last_last_trick ld e, (hl) ld (hl), a dec hl ld (hl), d ; save the current trick in last_trick (for the next time) ld a, d cp e ret nz srl b rr c ; divide bc by 2 ret rotation_0_score_1: ld c, %00000100 ld de, 20 ; if flip : score = 20 * flip_number ld a, (flip_number) or a ret nz ld c, %00000000 ; no flip : then c = 0 pop de jr rotation_0_score_2 crash_routine: ld hl, $fc35 ld b, 15 call clear_board ; clears the uppper-part of the score board ld bc, (256*4)+41 ld (_penCol),bc ld hl, crash_string call _vputs ; displays "Crash !" pop bc ; annulate a call effect (call end_of_jump) jp change_dir ; doesn't execute calcul_score crash_n_slow_left: ; RIDERS SLIDES ON THE FLAT ld a, 1 ld (temporary_3), a ld hl, Rider1crashed jr crash_n_slow_both_direction crash_n_slow_right: ld a, 255 ; a = -1 ld (temporary_3), a ld hl, Rider4crashed crash_n_slow_both_direction: ld a, (speed) ld b, a speed_dec_loop: push bc ; b djnz value constant_speed_loop: push bc ; other b djnz value call get_coord call RestoreBack16 ld a, (temporary_3) add a, b ld b, a ; change sprite colomn (inc or dec), the row remains the same call GetBack16 call save_coord call PutSprite16Masked ; hl is always the sprite adress push hl ld hl, speed ld b, (hl) ; speed inc hl ld a, (hl) ; overall_speed sub b ld b, a ; calculate in b number of halt loops to do according to the overall_speed and the rider speed horizontal_delay_loop: halt call update_time ; update the time on the screen if necessary djnz horizontal_delay_loop pop hl pop bc djnz constant_speed_loop push hl ld a, (speed) ; loads a with speed for the next routine call dec_rider_speed ; dec rider speed in the memory and on the screen (vertical indicator) pop hl pop bc djnz speed_dec_loop xor a ld (time_run), a call _pause_n_exit ld a, (time's_up) or a jp nz, check_if_highscore ; if time's up, checks score jp crash_restart check_special: ld a, (speed) cp 7 ret nz ; return if speed is not max (7) ld a, (overall_speed) ld b, a ld a, 12 sub b ; 0 = fastest speed, 5 = slowest speed ld hl, key_count_depending_on_overall_speed ld b, 0 ld c, a add hl, bc ld b, (hl) ; b = min number of key hits to do the special trick ld a, (special_counter) cp b ret c ld hl, direction ld a, (hl) and %00000010 ret nz ; return if the guy is fakie ld hl, $fc35 ld b, 15 call clear_board ; clears the upper part of the board ld hl, special_string ld bc, (256*4)+41 ld (_penCol),bc call _vputs ld a, (direction) or a jr z, left_special right_special: ld hl, Rider6up_mute jr special_both_sides left_special: ld hl, Rider3up_mute special_both_sides: ld (temporary_4_5), hl ld a, 255 ld (temporary_6), a ld hl, speed inc (hl) call special_trick_jump_routine call do_flash call do_void ld hl, coordx ld b, (hl) ld a, 112 sub b ; change horizontal coordonate from left to right or from right to left ld (hl), a ld a, (direction) or a jr z, left_special_2 right_special_2: ld hl, Rider3down_mute jr special_both_sides_2 left_special_2: ld hl, Rider6down_mute special_both_sides_2: ld (temporary_4_5), hl ld a, 1 ld (temporary_6), a call get_coord call GetBack16 call do_void call do_flash call special_trick_jump_routine ld hl, speed dec (hl) ld hl, position ld b, (hl) ld a, 26 sub b ld (hl), a ; change position from 0 to 26 or from 26 to 0 ld bc, (20<<8)+64 ld (_penCol),bc ; set row and colomn for new score value display ld d, %00100000 ; trick_kind ld hl, 500 ; trick score jp calcul_n_display_score special_trick_jump_routine: ld b, 32 special_trick_loop: push bc call get_coord call RestoreBack16 ld a, (temporary_6) add a, c ld c, a ; update y-coordonate call save_coord call GetBack16 ld hl, (temporary_4_5) call PutSprite16xGrid ld hl, speed ld b, (hl) inc hl ld a, (hl) ; overall_speed sub b ld b, a ; calculate in b the number of halt loops to do according te the overall_speed and the rider speed sla b ; multiply this time by two to obtain the time on a 2 pixels move ld a, b or a jr z, no_delai_loop2; don't execute the djnz if speed is 0 delay_loop2: halt call update_time ; update the time on the screen if necessary djnz delay_loop2 no_delai_loop2: pop bc djnz special_trick_loop ret do_flash: call get_coord ld e, b ld d, 0 ld hl, flash_1 call PutSprite8xGrid ld a, 8 add a, e ld e, a ld c, a call PutSprite8xGrid ld e, b ld d, 8 call PutSprite8xGrid ld e, c call draw_wait_n_clear ret do_void: ld e, b ld d, 4 ld hl, void_1 call PutSprite8xGrid ld a, 8 add a, e ld e, a call draw_wait_n_clear ret draw_wait_n_clear: call PutSprite8xGrid ld b, 30 flash_djnz: halt djnz flash_djnz call get_coord call RestoreBack16 ret check_invert: ld a,%01101111 out (1),a in a,(1) rlca ret c ; returns if 'x-var' is not pressed ld hl, $fc35 ld b, 15 call clear_board ; clears the uppper-part of the score board ld bc, (256*4)+41 ld (_penCol),bc ld hl, invert_string ; if trick is not a royale, this string will be displayed xor a ld (jump_info), a ; 0 means invert ld a, %00001000 ld (temporary_2), a ; kind_of_trick = (bit3) invert ld de, 0 ; the offset is 0 for the invert sprites ld a,%01111110 out (1),a in a,(1) bit 3,a call z, init_top_makio ; if up is pressed, do a top makio ld a,%01111110 out (1),a in a,(1) rra call nc, init_royale ; if down is pressed, do a royale call _vputs ; displays "invert" or "royale" or "top makio" call get_coord call RestoreBack16 ld a, b cp 16 jr nz, right_side_trick left_side_trick: ld bc, (11<<8)+25 ld hl, Invert_left_1 jr both_sides_trick right_side_trick: ld bc, (101<<8)+25 ld hl, Invert_right_1 both_sides_trick: add hl, de ; add the offset to find the correct sprite adress, according to the trick call GetBack16 push hl call create_a_masked_sprite ld hl, Not_masked call PutSprite16Masked call redraw_copings pop hl ld e, 60 call haltx_waiting ; wait 60 halt ld de, 32 add hl, de ; goto 2nd sprite adress push hl call create_a_masked_sprite ld hl, Not_masked call PutSprite16Masked call redraw_copings pop hl ld e, 60 ; if rider does not crash, the halt loop is 60 halt long ld d, 0 check_key_150_times: call update_time ; update the time on the screen if necessary halt ld a,%01101111 out (1),a in a,(1) rlca jr c, end_of_invert inc d ld a, d cp 150 jr nz, check_key_150_times ld a, $08 ; time as passed : rider falls ld (jump_info), a ld e, 30 ; if rider does crashes, the halt loop is 30 halt long end_of_invert: ld a, d ld (temporary), a push de or a ; reset carry flag ld de, 32 sbc hl, de ; goes (back) to the 1st sprite adress push hl call create_a_masked_sprite ld hl, Not_masked call PutSprite16Masked call redraw_copings pop hl pop de call haltx_waiting ; wait "e" halt call RestoreBack16 call get_coord call GetBack16 ld hl, direction ld a, (hl) xor $01 ; change bit 0 of direction (direction) ld (hl), a ld a, (jump_info) cp 8 jp z, crash_routine ; if bit 3 set, crash message --> crash_routine pop bc ; annulates the call effect ld bc, (20<<8)+64 ld (_penCol),bc ; set row and colomn for new score value display ld hl, temporary ld a, (hl) inc hl ; ld hl, temporary_2 ld d, (hl) ; d = (temporary2) = trick kind ld h, 0 ld l, a ; hl = a = score for this trick calcul_n_display_score: call look_for_score_reduction call score_only_insersion ; calculate new total score value and displays it call key_counter_init jp change_dir ; end of trick haltx_waiting: ld d, b ld b, e ; e is the input variable x_waiting_loop halt call update_time ; update the time on the screen if necessary djnz x_waiting_loop ld b, d ret create_a_masked_sprite: push bc ld de, Not_masked ld bc, 32 ldir ; copy the none masked sprite in the first memory part of a masked sprit pop bc ret init_royale: ld hl, direction ld a, (hl) xor %00000010 ld (hl), a ; inverts the side of the rider (fakie - normal) ld hl, royale_string ld a, %00010000 ld (temporary_2), a ; kind of trick = (bit 4) grind ld de, 128 ; the offset for the sprites ld a, (direction) and %00000010 ret z ld de, 128*2 ret init_top_makio: ld hl, direction ld a, (hl) or %00000010 ld (hl), a ; put the rider fakie ld hl, top_makio_string ld a, %00010000 ld (temporary_2), a ; kind of trick = (bit 4) grind ld de, 128*3 ; the offset for the sprites ret redraw_copings: ld a, %11111110 ld ($fe71), a ld (_plotSScreen+$6+$281), a ld a, %11111111 ld ($fe81), a ld a, %01111111 ld ($fe7e), a ld (_plotSScreen+$6+$28e), a ld a, %11111111 ld ($fe8e), a ret teacher_key_routine: res 2,(iy+$23) ; disable time counting down xor a ld (time_run), a ld a,$01 out ($03),a ; shutdown calculator halt ; if ON is pressed, restart ld a,$0b out ($03),a res 4,(iy+$09) ; goes into paused_routine set 2,(iy+$23) ; enable interrupt ; I I ; I I ; I I ; \ / ; \ / pause_routine: xor a ld (time_run), a ld hl, $fd45 ld b, 6 call clear_board ; clear down-part of the board ld bc, (20<<8)+52 ld (_penCol),bc ld hl, paused_string call _vputs call GET_KEY pause_key_loop: call GET_KEY ld hl, pause_key_loop push hl ; push pause_key_loop adress so it will return to it after overall_speed_dec or inc or contrast - or + cp K_F4 jp z, overall_speed_dec cp K_F5 jp z, overall_speed_inc cp K_MINUS jr z, contrast_minus cp K_PLUS jr z, contrast_plus pop hl cp K_EXIT jp z, reboot_and_find cp K_CLEAR jr z, teacher_key_routine cp K_NOKEY jr z, pause_key_loop ld hl, $fd45 ld b, 6 call clear_board ; clears "Pause (enter)" call score_display ; displays "Score:" and its value ld a, 1 ld (time_run), a jp check_key_presses contrast_plus: push af ld a, ($C008) ; get contrast value inc a ; increase it ld ($C008), a ; save it in the memory out (2), a ; send it to the port pop af ret contrast_minus: push af ld a, ($C008) ; same thing dec a ; decrease contrast value ld ($C008), a out (2), a pop af ret clear_board: ; clears a 6-wide zone of the screen on b rows vertical_loop: ld c, b ld b, 6 horizontal_loop: xor a ld (hl), a inc hl djnz horizontal_loop ld de, 10 add hl, de ld b, c djnz vertical_loop ret draw_rollerman: ; draws big skater sprite on the right part of the screen (64*57) ld hl,string_name-1 ; address of one byte before 'stringname' label rst 20h ; same as 'call _Mov10toOP1' rst 10h ; same as 'call _FindSym' jr c, no_picture ; variable doesn't exist call _EX_AHL_BDE ; load data absolute adress in ahl call _ahl_Plus_2_Pg3 ; add 2 because the first two bytes are trash call _SET_ABS_SRC_ADDR ; load it in the ldir source xor a ld hl, $fc00+$8+$30 call _SET_ABS_DEST_ADDR ; load destination adress ld b, 57 call draw_half_stuff ld hl, _plotSScreen+$6+$8+$30 call _SET_ABS_DEST_ADDR ; load destination adress ld b, 57 jp draw_half_stuff draw_half_stuff: roller_loop: push bc xor a push hl ld hl, 8 call _SET_MM_NUM_BYTES ; set the ldir lenght call _MM_LDIR ; do the ldir pop hl ld bc, 16 add hl, bc call _SET_ABS_DEST_ADDR ; load destination adress pop bc djnz roller_loop ret no_picture: ld bc, (256*29)+84 ld (_penCol), bc ld hl, picture_not_found_string call _vputs ld bc, (256*36)+81 ld (_penCol), bc jp _vputs draw_title: ld hl,string_name-1 ; address of one byte before 'stringname' label rst 20h ; same as 'call _Mov10toOP1' rst 10h ; same as 'call _FindSym' jr c, display_ugly_RBlade ; variable doesn't exist call _EX_AHL_BDE ; load data absolute adress in ahl call _ahl_Plus_2_Pg3 ; add 2 because the first two bytes are trash ld d, 0 ld bc, 912 add hl, bc adc a, d ; 32 bit addition call _SET_ABS_SRC_ADDR ; load it in the ldir source ld hl, $fc00 call _SET_ABS_DEST_ADDR ; load destination adress ld b, 19 call draw_half_stuff ld hl, _plotSScreen+$6 call _SET_ABS_DEST_ADDR ; load destination adress ld b, 16 jp draw_half_stuff display_ugly_RBlade: ld bc, (256*2)+1 ld (_curRow), bc ld hl, No_string_title jp _puts Blank_screen: ld hl, $fc00 ld (hl), 0 ld de, $fc00+1 ld bc, 1023 ldir ld hl, _plotSScreen+6 ld (hl), 0 ld de, _plotSScreen+7 ld bc, 1023 ldir ret ;============================ High scores stuff ========================== cut: ld de, 10 add hl, de ; hl is where to save the new hiscore ld de, (score) ld (hl), d inc hl ld (hl), e ; save current score at his place ret check_if_highscore: ld hl, (score) ; we're gonna compare it with the old ones in the table ld de, 0 call _cphlde jp z, reboot ld bc, high_scores_table+10 ; first score's adress ld a, 1 ld (temporary), a ; temporary will be the counter (1..8) find_place_loop: ld a, (bc) ld d, a inc bc ld a, (bc) ld e, a ; load bc with the score at this row of the table call _cphlde ; compare user score with 1st, then 2nd... scores of the table jr nc, place_found ; user has a high score !! ld a, (temporary) cp 8 jp z, go_to_reboot ; no highscore, reboot the game (goto main menu) inc a ld (temporary), a ; inc counter (go to next place in the table) push hl ld hl, 11 add hl, bc ld b, h ld c, l ; add 11 to bc (go to the next score) pop hl jr find_place_loop place_found: ; (temporary) is the place, now we have to slide down the end of the table ld h, b ld l, c ; ld hl, bc ld bc, 11 or a ; reset carry sbc hl, bc ; hl is the source of the next ldir (next line in the table) ld (temporary_2), hl ; save this adress to write the name further ld (temporary_4_5), hl ; save it another time in the case where the user presses clear ld a, (temporary) cp 8 jr nz, piti_jump ld de, nothing_to_slide ; user has the lower score : we're just gonna write on the old lower score push de jr cut ; it will return to "nothing to slide" piti_jump: ld b, a ld a, 8 sub b ; do "8-place" = number of scores to save elsewhere (at (freespace)) ld c, a ld b, 11 ; djnz counter (multiplication by 12) mult12_loop: add a, c djnz mult12_loop ; at the end, a has been multiplied by 12 ld b, 0 ld c, a ; bc = lenght of the code to copy with ldir ld de, free_space+6 ; de = destination for ldir push hl push bc ; save source (hl) and lenght (bc) ldir pop bc pop hl call cut inc hl ; now, we've to reconstitute the end of the table ex de, hl ; now the source is the data at (free_space), and destination in the hiscores table (now de) ld hl, free_space+6 ; hl = source, lenght is the same ldir ld hl, high_scores_table ld a, 49 ; same as ld a, '1' (49 is the ascii equivalent for '1') rewrite_numbers_loop: ld (hl), a ld bc, 12 add hl, bc inc a cp 57 ; 57 means that a is '9', so we stop here jr nz, rewrite_numbers_loop ; this code rewrites positions from 1 to 8 (in the high_scores_table memory) nothing_to_slide: ld hl, $fc35 ld b, 15 call clear_board ; clears the upper part of the board ld bc, (256*4)+40 ld (_penCol),bc ld hl, new_hs_string call _vputs ld bc, (256*11)+40 ld (_penCol),bc call _vputs ; hl is automaticaly "enter_your_name_string" clear_name_return: ld hl, $fd45 ld b, 6 call clear_board ; clear down-part of the board ld bc, (18<<8)+39 ld d, 27 call DrawVert ; draws a vertical line next to the icon (on the left side) ld bc, (18<<8)+48 ld d, 27 call DrawVert ; draws a vertical line next to the icon (on the left side) ld a, (temporary) ; were're gonna draw the small icon sla a sla a sla a sla a ; mult a by 16 ld hl, icons-16 ld b, 0 ld c, a add hl, bc ; find the icon adress ld de, (19<<8)+40 call PutSprite8xGrid xor a ld (speed), a ; just a temporary use ld hl, (temporary_2) inc hl inc hl inc hl ld (temporary_2), hl ld bc, (20<<8)+50 ld (_penCol),bc ; load pen row and col other_character: ld a, '_' call _vputmap ld a, (_penCol) sub 4 ld (_penCol), a wrong_character: call GET_KEY cp K_NOKEY jr z, wrong_character cp K_ENTER jr z, erase_the_end ; saving finished cp K_CLEAR jr z, clear_name sub $0a cp $2f-$0a jr nc, wrong_character ld hl, characters ld b, 0 ld c, a ; bc = offset add hl, bc ; get adress of our character ld a, (hl) ; our charcter is in the register a or a jr z, wrong_character ; in the table, 0 means that it is not a character key push af call _vputmap ; write the letter ld hl, (temporary_2) ld b, 0 ld a, (speed) ld c, a add hl, bc pop af ld (hl), a ; saves the character in the hiscore table ld a, (speed) inc a ld (speed), a cp 6 ; if a (=speed)= 6, stop to check for keys jr nz, other_character ld a, (_penCol) ; reset a single pixel if the sixth letter was a 'I' ld e, a ld d, 25 call FindPixel cpl and (hl) ; reset a pixel ld (hl), a ; save changes to the screen enter_loop: call GET_KEY cp K_CLEAR jr z, clear_name cp K_ENTER jr nz, enter_loop jr high_scores_displaying clear_name: ld hl, (temporary_4_5) ld (temporary_2), hl jp clear_name_return erase_the_end: ld a, (speed) ld hl, (temporary_2) ld b, 0 ld c, a add hl, bc erase_loop: ld (hl), ' ' inc hl ld a, (hl) or a jr nz, erase_loop ;jr high_scores_displaying high_scores_displaying: call Blank_screen call draw_rollerman ld hl, $fc00 call black_band ld hl, _plotSScreen+6 call black_band set 3,(iy+5) ; white text on black background ld bc, (0<<8)+13 ld (_penCol),bc ld hl, high_scores_title_string call _vputs res 3,(iy+5) ; black text on white background ld bc, (0<<8)+63 ld d, 63 call DrawHoriz ld bc, (7<<8)+0 ld d, 63 call DrawVert ld bc, (7<<8)+63 ld d, 63 call DrawVert ld hl, high_scores_table ld bc, (11<<8)+4 ld (_penCol),bc ld b, 8 ; DJNZ counter hs_displaying_loop: push bc ; save b (djnz counter) call _vputs ; displays the name ld d, (hl) inc hl ld e, (hl) push hl ex de, hl ; load score in hl (for DisplayHL) ld bc, (_penCol) ld c, 43 ; colomn of the score (c is always the row) ld (_penCol),bc call DisplayHL ; displays score pop hl ; load saved value of hl (pointer) inc hl ; go to the next name (hl is the pointer) ld bc, (_penCol) ld c, 4 ld a, 6 ; this is what we're going to add to the row add a, b ; we add it ld b, a ; place the result in b (because it was only in a) ld (_penCol), bc; save b and c values at _penCol and _PenRow adresses (add 6 to the row, and set colomn at 5) pop bc ; get djnz counter djnz hs_displaying_loop ld a, 0 ld (game_mode), a ; set free skate mode else the highscore routine could be executed another time hs_loop: call GET_KEY cp K_ENTER jr z, reboot_and_find cp K_EXIT jr z, reboot_and_find cp K_CLEAR jr z, clear_highscores jr hs_loop jr go_to_reboot ; if user press enter during _pause_n_exit, return too with this line (it is to economize space that I use _pause_n_exit clear_highscores: set 3,(iy+5) ; white text on black background ld bc, (0<<8)+7 ld (_penCol),bc ld hl, clear_high_scores_string call _vputs res 3,(iy+5) ; black text on white background clear_hs_loop: call GET_KEY cp K_9 jp z, high_scores_displaying cp K_0 jr nz, clear_hs_loop ld de, high_scores_table ld b, 8 clear_loop: ld a, 3*16+9 sub b ld (de), a inc de push bc ld bc, 11 ld hl, model ldir pop bc djnz clear_loop jp high_scores_displaying black_band: ld b, 7 black_band_loop: push bc ld (hl), $ff ld d, h ld e, l inc de ld bc, 7 ldir ld bc, 9 add hl, bc pop bc djnz black_band_loop ret _pause_n_exit: call GET_KEY cp K_ENTER ret z cp K_EXIT jr z, reboot_and_find jr _pause_n_exit ;=========================== Exit of the prog ====================== reboot_and_find: find_stack_loop: ld hl, (stack_save) pop de ; search the adress where the program is executed call _cphlde jr nz, find_stack_loop ; if it is not this adress, continue poping values push de ; de is this adress : replace it on the stack ld a, (game_mode) cp 1 jr nz, go_to_reboot ld a, (time) cp 60 jp nz, check_if_highscore go_to_reboot: jp reboot ; go back to the start of the program finish: ld hl,_asapvar ;hl->name of program rst 20h ;copy to OP1 rst 10h ;_findsym xor a ld hl,data_start-_asm_exec_ram+4 ;offset add hl,de ;hl=pointer to data in original prog adc a,b ;in case we overlapped pages call _SET_ABS_DEST_ADDR xor a ;no absolute addressing now ld hl,data_start ;get data from here call _SET_ABS_SRC_ADDR ld hl,data_end-data_start ;number of bytes to save call _SET_MM_NUM_BYTES call _MM_LDIR ;copy data call _clrScrn call CloseGray call _runindicon ret ; return to TI-OS ;========================= Sprite displaying Routines ======================== ;================================================================================================================ ; PutSprite16MaskedBlackscale : Draw a 16*16 Black&White masked sprite in grayscale mode everywhere on the screen ; by Thibaut Chevalier (203 bytes) ; in: hl = start of the 16*16 masked sprite (the two first byte must be height and width) ; b = x (0,127) and c = y (0,63) ; out: Sprite drawn ; All registers destroyed ;================================================================================================================ PutSprite16Masked: push hl push bc push de push bc ; save the position of the sprite ld c, b ; we temporary save b (x position) into c ld de, virtual_sprite ; first, i'm going to copy your sprite in virtual_sprite, which is a 24*16 masked temporary sprite ld b, 32 ; with djnz, we're now ready for 32 loop Mcopy_loop: ldi ; copy first byte of the row inc bc ; go back to the previous value of bc (particulary b) ldi ; same thing with the second byte inc bc xor a ; same as ld a, 0 ld (de), a ; reset the third byte of the row inc de ; hl point to the next row of virtual_sprite : Remember, virtual_sprite is a 24*16 sprite (3 bytes large) djnz Mcopy_loop ; dec b and if b=0, then the sprite is finished copied (16 rows of data and 16 rows of mask) ld a, c ; c is the x position and %00000111 ; get in a the colomn of the sprite on the grid (0..7) ; now, we're gonna slide virtual_sprite a time on the right ;cp 0 ; compare this value from 0 jr z, Mno_slide ; if a=0, we don't modify virtual_sprite ld b, a ; b is the number of 1-bit slides Mslide_loop2: ld c, b ; now c is the number of 1-bit slides: this instruction save b in c before each slide (because b is destroyed during it) ld b, 32 ; we have 32 rows to slide ld hl, virtual_sprite Mslide_loop1: or a ; now carry flag is reset (we want to inser 0 on the left) rr (hl) ; first byte of the row is rotated 1-bit position through the carry flag push af ; save the content of the carry flag inc hl pop af ; load the previous content of the carry flag (we inser bit-0 of the first byte) rr (hl) ; second byte of the row is rotated 1-bit position through the carry flag push af ; save the content of the carry flag inc hl pop af ; load the previous content of the carry flag (we inser bit-0 of the second byte) rr (hl) ; third byte of the row is rotated 1-bit position through the carry flag ; now one row has been slided one time inc hl ; hl point at the next row djnz Mslide_loop1 ; dec b and if b=0, then virtual_sprite has been slided right 1-bit position (16 rows of data and 16 rows of mask) ld b, c ; get the number of slides that have been done (saved in c) djnz Mslide_loop2 Mno_slide: pop bc ; restore the initials values of b and c ld d, c ld e, b ; Findpixel need e = x and d = y call FindPixel ; now hl is the start of diplay memory ld de, virtual_sprite ; de is the start of the sprite we prepare just before push de ; save the adress of the virtual sprite MRestore_mid: push hl ; save the adress where the sprite has to be drawn call Mwrite_to_buffer_16x pop hl ld bc, $3200 or a sbc hl, bc ; obtain the adress to write at in the _plotSScreen memory (2nd bit plane) pop de ; start of the virtual sprite or background sprite, depends on what has been pushed call Mwrite_to_buffer_16x ; de is the at the middle of the virtual sprite pop de pop bc pop hl ret ; it's all over !! (register a destroyed) Mwrite_to_buffer_16x: ld b, 16 ; we have 16 rows to draw (each 3 bytes large) Mdraw_loop: push bc ; save counter (b) value call Mmask_loop ; draw the byte of the current adress to the screen with masking inc hl ; hl point to the next byte on the screen inc de ; de point to the second byte of the current row of virtual_sprite call Mmask_loop ; draw the byte of the current adress to the screen with masking inc hl ; hl point to the next byte on the screen inc de ; de point to the third byte of the current row of virtual_sprite call Mmask_loop ; draw the byte of the current adress to the screen with masking ld bc, 14 ; load bc for a 16-bit addition add hl, bc ; hl point to the first row of the next colomn (on the screen) inc de ; de too (for the sprite, we just have to increment de) pop bc ; restore the counter (b) value for 'djnz' djnz Mdraw_loop ; execute the loop 16 times, each time for one row ret ; return to the calling part of routine Mmask_loop: ld a, (de) ; get byte to draw in register a or (hl) ; set pixels without destroying the background ld (hl), a ; save changes to screen ex de, hl ; de = display adress / hl = data adress ld bc, 48 ; 48 is what we need to add to the current sprite adress to point at the corresponding mask add hl, bc ; hl point to mask ld a, (hl) ; a = mask or a ; set carry flag without destroying the register a sbc hl, bc ; hl point again to the data adress (in sprite memory) ld b, (hl) ; b = data, a = mask xor b ; pixels we want to be off are set in register a cpl ; now they are reset and the others set ex de, hl ; de = data adress / hl = display adress and (hl) ; reset pixels without destroying the background ld (hl), a ; save changes to screen ret ; return to the calling part of routine virtual_sprite: ; virtual_sprite is a 24*16 masked temporary sprite .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 ;============================================================================================================ ; GetBack16 : Get a 16*16 grayscale sprite from the screen into background_sprite & background_sprite2 ; by Thibaut Chevalier (188 bytes) ; in: b = x (0,127) and c = y (0,63) ; out: background_sprite in a grayscale sprite that countain the 16*16 area beginning at (b, c) on the screen ; All registers destroyed ; To restore background_sprite, load bc with (x, y) and call RestoreBack16 (only!) ;============================================================================================================ GetBack16: push hl push bc ; saves registers at the start and pop them at the end push de push bc ld d, c ld e, b ; Findpixel need e = x and d = y call FindPixel ; now hl is the start of display memory push hl ; save the adress where we are going to copy from (1st bit plane) ld de, background_sprite call Mcopy_from_screen_to_background_sprite pop hl ld bc, $3200 or a sbc hl, bc ; adress where we are going to copy from (2nd bit plane) ld de, background_sprite2 call Mcopy_from_screen_to_background_sprite pop bc ld d, $ff ld e, $00 ld a, %00000111 and b jr z, Mno_prep ld b, a Mprep_slide: srl d rr e djnz Mprep_slide Mno_prep: ld hl, background_sprite call Mmake_borders_call ld hl, background_sprite2 call Mmake_borders_call ld b, 16 ld hl, background_mask Mmake_mask: ld (hl), d inc hl ld (hl), $FF inc hl ld (hl), e inc hl djnz Mmake_mask ; it has made the mask in the first area ld hl, background_mask ld de, background_mask2 ld bc, 48 ldir ; copy it in the second area pop de pop bc pop hl ret RestoreBack16: push hl push bc push de ; saves registers ld d, c ld e, b ; Findpixel need e = x and d = y call FindPixel ; now hl is the start of display memory ld de, background_sprite+96 ; de is the start of the background_sprite2 push de ; push it (it will be popped in the main PutSprite16xMaskedBlackscale routine ld de, background_sprite ; de is the start of the background_sprite jp MRestore_mid background_sprite: ; background_sprite is a 24*16 sprite (1st part) .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 background_mask: .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 background_sprite2: ; background_sprite2 is a 24*16 sprite (2nd part) .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 background_mask2: .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 .db 0, 0, 0, 0, 0, 0 Mcopy_from_screen_to_background_sprite: ex de, hl ; de = display memory / hl = background_sprite adress ld b, 16 ; with djnz, we're now ready for 16 loop Mcopy_loop2: push bc ld a, (de) ; get the first byte of the row on the screen in a ld (hl), a ; save it in the first byte at the same row in temp_sprite inc de ; ready to read the next byte on the screen inc hl ; ready to write the second byte in temp_sprite ld a, (de) ; get the second byte of the row in a ld (hl), a ; save it in the second byte at the same row in temp_sprite inc de ; de point to the next row of your sprite inc hl ; ready to write the third byte of virtual_sprite ld a, (de) ; get the third byte of the row on the screen in a ld (hl), a ; save it in the third byte at the same row in temp_sprite inc hl ; ready to write the next row in temp_sprite ex de, hl ; we can not add a number to de, so we exange it with hl, and we recover hl after ld bc, 14 add hl, bc ; add 14 to hl ex de, hl ; Eventually, add 14 to de: de point at the next row on the screen, hl is recovered pop bc ; restore counter value (b) djnz Mcopy_loop2 ; dec b and if b=0, then the sprite is finished copied (16 rows of data and 16 rows of mask) ret Mmake_borders_call: ld b, 16 Mmake_borders: ld a, d and (hl) ld (hl), a inc hl inc hl ld a, e and (hl) ld (hl), a inc hl djnz Mmake_borders ret ; * End of the routine code * (don't FindPixel routine) ; ======================================================================================================= ; ============================================================= ; Dan Eble & James Yopp FindPixel routine ; Input: D = y, E = x ; Output: HL= addr in vid mem, A = bitmask, C is modified ; ============================================================= FindPixel: ld hl,FP_Bits ld a,e and $07 ; a = bit offset add a,l ld l,a adc a,h sub l ld h,a ld c,(hl) ; c = bitmask for (hl) ; 48 t-states up to this point ld hl,FP_RLD ld (hl),d ld a,e ; a = x/8 (byte offset within row) rrca rrca rrca rld or $FC ld l,(hl) ld h,a ; hl -> byte in vid mem ld a,c ; now a = bitmask for (hl) ; 121 t-states up to this point ret FP_RLD: .db $00 FP_Bits: .db $80,$40,$20,$10,$08,$04,$02,$01 ;================================================================================================== ; Draws a 16x16 Black(grayscale) Sprite (from a none grayscale sprite) on the grid at (b/8, c/8), 0<=b<=127 horizontally and 0<=c<=63 vertically ;=================================================================================================== PutSprite16xGrid: push hl push bc ld e, b ld d, c push hl push hl call FindPixel pop de push hl call write_to_buffer_16x ; write on 1st plane pop hl ld bc, $3200 or a sbc hl, bc pop de call write_to_buffer_16x ; write on 2nd plane pop bc pop hl ret ; hl and bc are saved write_to_buffer_16x: ld b, 16 P16xgridloop: ld a, (de) ld (hl), a inc hl inc de ld a, (de) ld (hl), a ld a, b ld bc, 15 add hl, bc ld b, a inc de djnz P16xgridloop ret ;===================================================================================================== ; Draws a 8x8 Grayscale Sprite on the grid at (e/8, d), 0<=e<=127 horizontally and 0<=d<=63 vertically ;===================================================================================================== PutSprite8xGrid: push de push bc push hl call FindPixel pop de push hl call write_to_buffer_8x pop hl ld bc, VIDEO_MEM-_plotSScreen-6 ; difference beetween the two buffer areas or a sbc hl, bc call write_to_buffer_8x ex de, hl pop bc pop de ret ; all registers destroyed but bc and hl write_to_buffer_8x: ld b, 8 P8xgridloop: ld a, (de) ; de = source ld (hl), a ; hl = destination ld a, b ; temporary save of b in a ld bc, 16 add hl, bc ld b, a ; restore b as the djnz counter inc de djnz P8xgridloop ret ;============================================================== ; Draw a Black (grayscale) line between points (b,c) and (d,c) ;============================================================== DrawHoriz: push bc push de ld e, b ld d, c call draw_point pop de pop bc ld a, b cp d ret z inc b jr DrawHoriz draw_point: call FindPixel or (hl) ld (hl), a ld bc, VIDEO_MEM-_plotSScreen-6 ; difference beetween the two buffer areas or a sbc hl, bc or (hl) ld (hl), a ret ;============================================================== ; Draw a Black (grayscale) line between points (c,b) and (c,d) ;============================================================== DrawVert: push bc push de ld e, c ld d, b call draw_point pop de pop bc ld a, b cp d ret z inc b jr DrawVert ;==================================================================== ; DisplayHL: (idea from SCaBBy/Mardell) [Assembly Coder's Zenith] ; Display HL as a 5-digit decimal number with no leading zeros ; out: AF, HL, BC, DE destroyed ;==================================================================== DisplayHL: ld c,'0' ; save ascii value for zero ld de,_OP1+5 ; point to end of the buffer xor a ; zero terminate string ld (de),a ; set last byte to zero DisplayHLl: call UNPACK_HL ; next digit dec de ; next position add a,c ; convert to ascii ld (de),a ; save digit ld a,h ; load upper byte or l ; check with lower byte for zero jr nz,DisplayHLl ; loop ex de,hl ; point to buffer call _vputs ; print number ret ; we're done #include "RBladeInterrupt.asm" #include "RBladeJumpSprites.asm" #include "RBladeStaticSprites.asm" #include "RBladeData.asm" #include "RBladeFlipSprites.asm" ;======================= String ========================= mute_string: .db " +mute",0 liu_kang_string: .db " +liu k.", 0 sloppy_string: .db "sloppy",0 paused_string: .db "Paused",0 score_string: .db "Score: ",0 late_string: .db "late",0 invert_string: .db "invert",0 royale_string: .db "royale",0 top_makio_string: .db "top makio", 0 zero_to_fakie_string: .db "0 to fakie", 0 double_string: .db "doubl ", 0 triple_string: .db "triple ", 0 backflip_string: .db "backflip", 0 frontflip_string: .db "frontflp", 0 crash_string: .db "crash !",0 my_name_string: .db "by Thibaut Chevalier",0 version_string: .db "version 4.1",0 menu_1_string: .db "free skate",0 menu_2_string: .db "contest",0 menu_3_string: .db "high scores",0 menu_4_string: .db "exit",0 spaces_string: .db " ", 0 new_hs_string: .db "new hiscore !", 0 enter_your_name_string: .db "your name :", 0 high_scores_title_string: .db "High Scores", 0 clear_high_scores_string: .db "Reset hs ? (Y/N)", 0 picture_not_found_string: .db "picture",0 .db "not found",0 No_string_title: .db "RBlade", 0 string_name: .db $06,"RBdata" special_string: .db "teleportation", 0 ;============================ Data ================================== moves_table: ; coord table left_side: .db 16,32,3,16,34,3,16,36,3,16,38,3 .db 14,38,2,16,40,2,18,42,2 .db 19,43,1,21,43,1 .db 23,44,1,25,44,1,27,44,1,29,45,1 middle: .db 0,0,0 right_side: .db 83,45,4,85,44,4,87,44,4,89,44,4 .db 91,43,4,93,43,4 .db 94,42,5,96,40,5,98,38,5 .db 96,38,6,96,36,6,96,34,6,96,32,6 characters: .db "xtoje",0,0," wsnid",0,0 .db "zvrmhc",0,0,"yuqlgb",0,0,0,"-pkfa" key_count_depending_on_overall_speed: .db 39,33,28,20,13 ;==================== High scores info (names and scores) =================== data_start: high_scores_table: .db "1. ------",0,0,0 .db "2. ------",0,0,0 .db "3. ------",0,0,0 .db "4. ------",0,0,0 .db "5. ------",0,0,0 .db "6. ------",0,0,0 .db "7. ------",0,0,0 .db "8. ------",0,0,0 data_end: model: .db ". ------",0,0,0 ;======================== Initialization ==================== initialization: .db 0 ; jump_info .db 255 ; last_trick .db 255 ; last_last_trick .db 17 ; coordx .db 34 ; coordy .db 1 ; position .db 1 ; direction (rider isn't in fakie, goes to the right) .db 4 ; speed .db 9 ; overall_speed free_space: .end