;Young lumberjack closure ;--------------------------------------------------- .IFNDEF TARGET .def TARGET = 800 ; 5200 .ENDIF ;--------------------------------------------------- OPT r+ ; saves 10 bytes, and probably works :) https://github.com/tebe6502/Mad-Assembler/issues/10 ;--------------------------------------------------- .macro build dta d"0.00" ; number of this build (4 bytes) .endm .macro RMTSong lda #:1 jsr RMTSongSelect .endm ;--------------------------------------------------- icl 'lib/ATARISYS.ASM' icl 'lib/MACRO.ASM' display = $a000 .zpvar temp .word = $80 .zpvar temp2 .word .zpvar tempbyte .byte .zpvar LowCharsetBase .byte .zpvar displayposition .word .zpvar DLI_A DLI_X dliCount .byte .zpvar RMT_blocked noSfx SFX_EFFECT .byte .zpvar AutoPlay .byte ; Auto Play flag ($80 - auto) RMT_zpvars = AutoPlay+1 ; POZOR!!! RMT vars go here ;--------------------------------------------------- org $2000 MODUL ;ins 'art/muzyka_stripped.rmt',+5 ; my RMT 1.28 on WINE is apparently broken. I lost some hair here (5, not 6) ;.align $100 ;icl 'art/rmtplayr.a65' ;--------------------------------------------------- .align $400 font_game_upper ins 'art/tu.fnt' ; font_game_lower_right ins 'art/tl_r.fnt' ; font_game_lower_left ins 'art/tl_l.fnt' ; dl_level .by $10 .by $44 .wo power_bar ; power indicator .by $04 .by $44 .wo gamescreen_middle ; branches :16 .by $04 .by $84 ; first DLI .by $44 animation_addr .wo gamescreen_lower1r :5 .by $04 .by $84 ; second DLI .by $04 .by $44 lastline_addr .wo last_line_r .by $41 .wo dl_level ;--------------------------------------------------- gamescreen_middle .ds 32*18 ; 18 lines screen_score = gamescreen_middle+6*32+14 screen_level = gamescreen_middle+9*32+13 ;--------------------------------------------------- icl 'art/anim_exported.asm' ; Animation sequence: ; - phase 1 page 1 (standard position) ; - phase 2 page 1 ; - phase 2 page 2 ; - phase 2 page 3 ; - phase 2 page 4 ; - phase 3 page 1 ; - phase 3 page 2 ; - phase 3 page 3 ; - phase 3 page 4 ; - phase 3 page 5 ; - phase 2 page 1 ; - phase 2 page 1 ; - phase 2 page 1 ; - phase 1 page 1 (standard position) ;-------------------------------------------------- ;icl 'lib/fileio.asm' ;-------------------------------------------------- ;-------------------------------------------------- .proc vint ;-------------------------------------------------- mva #0 dliCount ; mva #13 VSCROL ; FOX gfx mode only /* bit RMT_blocked bmi SkipRMTVBL ; ------- RMT ------- lda sfx_effect bmi lab2 asl @ ; * 2 tay ;Y = 2,4,..,16 instrument number * 2 (0,2,4,..,126) ldx #0 ;X = 0 channel (0..3 or 0..7 for stereo module) lda #0 ;A = 0 note (0..60) bit noSfx smi:jsr RASTERMUSICTRACKER+15 ;RMT_SFX start tone (It works only if FEAT_SFX is enabled !!!) lda #$ff sta sfx_effect ;reinit value lab2 jsr RASTERMUSICTRACKER+3 ;1 play ; ------- RMT ------- SkipRMTVBL */ /* ;sfx lda sfx_effect bmi lab2 asl ; * 2 tay ;Y = 2,4,..,16 instrument number * 2 (0,2,4,..,126) ldx #3 ;X = 3 channel (0..3 or 0..7 for stereo module) lda #12 ;A = 12 note (0..60) jsr RASTERMUSICTRACKER+15 ;RMT_SFX start tone (It works only if FEAT_SFX is enabled !!!) ; lda #$ff sta sfx_effect ;reinit value ; lab2 jsr RASTERMUSICTRACKER+3 skipSoundFrame */ jmp XITVBV .endp ;-------------------------------------------------- .proc IngameDLI1 ;-------------------------------------------------- pha lda dliCount bne secondDLI inc dliCount mva LowCharsetBase CHBASE mva #$0c COLPF2 mva #$c6 COLPF0 pla rti secondDLI sta WSYNC sta WSYNC sta WSYNC sta WSYNC mva #$86 COLPF2 pla rti .endp ;-------------------------------------------------- main ;-------------------------------------------------- jsr wait_for_depress jsr MakeDarkScreen jsr initialize RMTsong song_main_menu jsr StartScreen RMTSong song_ingame jsr ScoreClear gameloop jsr MakeDarkScreen jsr LevelScreen jsr PlayLevel jsr MakeDarkScreen ;jsr NextLevel ; RMTSong song_ingame jsr AudioInit ; after I/O jmp gameloop EndOfLife ;dec Lives ; decrease Lives ;lda Lives ;cmp #"0" ;beq gameOver ; if no lives - game over ;jsr NextLife jmp gameloop gameOver ;game over ;RMTSong song_game_over ;jsr HiScoreCheckWrite jsr GameOverScreen @ lda CONSOL and #@consol(start) ; START beq main lda TRIG0 ; fire jeq main jmp @- ;-------------------------------------------------- .proc StartScreen ;-------------------------------------------------- /* jsr MakeDarkScreen mwa #dl_start dlptrs lda #$0 ;+GTIACTLBITS sta GPRIOR sta COLBAKS lda #@dmactl(standard|dma) ; normal screen width, DL on, P/M off sta dmactls pause 1 StartLoop ;jmp StartLoop EndOfStartScreen */ rts .endp ;-------------------------------------------------- .proc LevelScreen ;-------------------------------------------------- jsr MakeDarkScreen ldx #2 mwa #dl_level dlptrs lda #@dmactl(narrow|dma) ; narrow screen width, DL on, P/M off sta dmactls mva #>font_game_upper CHBAS pause 5 rts .endp ;-------------------------------------------------- .proc GameOverScreen ;-------------------------------------------------- /* jsr MakeDarkScreen ldx #5 mwa #dl_over dlptrs lda #%00110010 ; normal screen width, DL on, P/M off sta dmactls pause 20 */ rts .endp ;-------------------------------------------------- .proc MakeDarkScreen ;-------------------------------------------------- mva #0 dmactls ; dark screen ; and wait one frame :) pause 1 rts .endp ;-------------------------------------------------- .proc PlayLevel ;-------------------------------------------------- loop ; PUT GAME HERE jsr wait_for_press jsr wait_for_depress jsr ScoreUp jsr AnimationR jsr wait_for_press jsr wait_for_depress jsr AnimationR jsr wait_for_press jsr wait_for_depress jsr AnimationL jsr wait_for_press jsr wait_for_depress jsr AnimationL NoAuto jmp loop LevelOver ; level over jsr wait_for_depress rts .endp ;-------------------------------------------------- .proc AnimationR ;-------------------------------------------------- mva #>font_game_lower_right LowCharsetBase mwa #last_line_r lastline_addr ; mwa #gamescreen_lower1r animation_addr ; waitRTC mwa #gamescreen_lower2r animation_addr waitRTC mwa #gamescreen_lower3r animation_addr waitRTC mwa #gamescreen_lower4r animation_addr waitRTC mwa #gamescreen_lower5r animation_addr waitRTC mwa #gamescreen_lower6r animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower7r animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower8r animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower9r animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower10r animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower2r animation_addr waitRTC waitRTC waitRTC mwa #gamescreen_lower1r animation_addr rts .endp ;-------------------------------------------------- .proc AnimationL ;-------------------------------------------------- mva #>font_game_lower_left LowCharsetBase mwa #last_line_l lastline_addr ; mwa #gamescreen_lower1l animation_addr ; waitRTC mwa #gamescreen_lower2l animation_addr waitRTC mwa #gamescreen_lower3l animation_addr waitRTC mwa #gamescreen_lower4l animation_addr waitRTC mwa #gamescreen_lower5l animation_addr waitRTC mwa #gamescreen_lower6l animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower7l animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower8l animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower9l animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower10l animation_addr waitRTC jsr branches_go_down mwa #gamescreen_lower2l animation_addr waitRTC waitRTC waitRTC mwa #gamescreen_lower1l animation_addr rts .endp ;-------------------------------------------------- .proc AudioInit ;-------------------------------------------------- ; pokeys init lda #3 sta skctl ; put Pokey into Init sta skctl+$10 ldx #8 lda #0 @ sta $D200,x ; clear all voices, set AUDCTL to 00 sta $D210,x ; clear all voices, set AUDCTL to 00 dex bpl @- rts .endp ;-------------------------------------------------- .proc initialize ;-------------------------------------------------- mva #>font_game_upper CHBAS mva #>font_game_lower_right LowCharsetBase mva #$00 PCOLR0 ; = $02C0 ;- - rejestr-cień COLPM0 mva #$00 COLBAKS mva #$88 COLOR0 mva #$f4 COLOR1 mva #$0c COLOR2 mva #$f6 COLOR3 ;mva #$ff COLOR4 mva #0 dliCount sta RMT_blocked lda #$ff sta sfx_effect JSR AudioInit jsr draw_branches /* ;RMT INIT ldx #MODUL ;hi byte of RMT module to Y reg lda #0 ;starting song line 0-255 to A reg jsr RASTERMUSICTRACKER ;Init */ mwa #gamescreen_lower1r animation_addr lda #@dmactl(standard|dma) sta dmactls mwa #dl_level dlptrs vdli IngameDLI1 ;VBI vmain vint,7 rts .endp ;-------------------------------------------------- .proc RmtSongSelect ; starting song line 0-255 to A reg ;-------------------------------------------------- /* cmp #song_main_menu beq noingame ; noMusic blocks only ingame songs bit noMusic spl:lda #song_silencio noingame */ /* mvx #$ff RMT_blocked ldx #MODUL ; hi byte of RMT module to Y reg jsr RASTERMUSICTRACKER ; Init mva #0 RMT_blocked */ rts .endp ;-------------------------------------------------- .proc wait_for_press ; ion ;-------------------------------------------------- lda TRIG0 beq press_ok lda CONSOL and:cmp #%00000111 beq wait_for_press press_ok rts .endp ;-------------------------------------------------- .proc wait_for_depress ; ion ;-------------------------------------------------- lda CONSOL and:cmp #%00000111 bne wait_for_depress lda TRIG0 beq wait_for_depress rts .endp ;-------------------------------- ; non ZP variables ;-------------------------------- branches_list .by 0,1,2,1,1 branches_anim_phase ; from 0 to 4 .by 1 score dta d"0000" level dta $1a, $1b, $1c, $1b, $1a, $24 dta d"1" ;-------------------------------------------------- .proc ScoreUp ;-------------------------------------------------- inc score+3 lda score+3 cmp #"9"+1 ; 9+1 character code bne ScoreReady lda #"0" ; 0 character code sta score+3 inc score+2 lda score+2 cmp #"9"+1 ; 9+1 character code bne ScoreReady lda #"0" ; 0 character code sta score+2 inc score+1 lda score+1 cmp #"9"+1 ; 9+1 character code bne ScoreReady lda #"0" ; 0 character code sta score+1 inc score ScoreReady rts .endp ;-------------------------------------------------- .proc ScoreClear ;-------------------------------------------------- lda #"0" ldx #3 @ sta score,x dex bpl @- rts .endp ;-------------------------------------------------- .proc ScoreToScreen ;-------------------------------------------------- ldx #3 @ lda score,x sta screen_score,x dex bpl @- rts .endp ;-------------------------------------------------- .proc LevelToScreen ;-------------------------------------------------- ldx #6 @ lda level,x sta screen_level,x dex bpl @- rts .endp ;-------------------------------------------------- .proc draw_branches ;-------------------------------------------------- ; branch 0 (off-screen if phase 0) draw_branch0 lda branches_anim_phase beq draw_branch1 tax ; this is partialy off-screen branch ; we must draw only visible lines ; now calculate start screen adress lda #5 sec sbc branches_anim_phase :5 asl ; skippedlines*32 tay ; to skip lines txa ; now calculate start screen adress :5 asl ; phase*32 ;clc adc #<(gamescreen_middle-5*32) sta temp lda #>(gamescreen_middle-5*32) adc #0 sta temp+1 ldx branches_list ; branch0 lda branch_addr_tableL,x sta temp2 lda branch_addr_tableH,x sta temp2+1 ; skiping off-screen lines ; ldy #$00 ; we hawe value in Y @ lda (temp2),y sta (temp),y iny cpy #(5*32) ;5 lines - skipped lines bne @- draw_branch1 lda branches_anim_phase ; now calculate start screen adress :5 asl ; phase*32 ;clc adc #gamescreen_middle adc #0 sta temp+1 ldy branches_list+1 ; branch1 lda branch_addr_tableL,y sta temp2 lda branch_addr_tableH,y sta temp2+1 ldy #$00 @ lda (temp2),y sta (temp),y iny cpy #(5*32) ;5 lines bne @- draw_branch2 lda branches_anim_phase ; now calculate start screen adress :5 asl ; phase*32 ;clc adc #<(gamescreen_middle+5*32) sta temp lda #>(gamescreen_middle+5*32) adc #0 sta temp+1 ldy branches_list+2 ; branch2 lda branch_addr_tableL,y sta temp2 lda branch_addr_tableH,y sta temp2+1 ldy #$00 @ lda (temp2),y sta (temp),y iny cpy #(5*32) ;5 lines bne @- jsr ScoreToScreen jsr LevelToScreen draw_branch3 lda branches_anim_phase ldx #(5*32) ; how many lines draw cmp #3 bne not_phase3 ldx #(4*32) ; how many lines draw not_phase3 cmp #4 bne not_phase4 ldx #(3*32) ; how many lines draw not_phase4 stx tempbyte ; now calculate start screen adress :5 asl ; phase*32 ;clc adc #<(gamescreen_middle+10*32) sta temp lda #>(gamescreen_middle+10*32) adc #0 sta temp+1 ldy branches_list+3 ; branch3 lda branch_addr_tableL,y sta temp2 lda branch_addr_tableH,y sta temp2+1 ldy #$00 @ lda (temp2),y sta (temp),y iny cpy tempbyte ;? lines bne @- draw_branch4 lda branches_anim_phase ; draw only if phase 0 or 1 or 2 cmp #3 bcs all_drawed ldx #(3*32) ; how many lines draw cmp #1 bne not_phase1 ldx #(2*32) ; how many lines draw not_phase1 cmp #2 bne not_phase2 ldx #(1*32) ; how many lines draw not_phase2 stx tempbyte ; now calculate start screen adress :5 asl ; phase*32 ;clc adc #<(gamescreen_middle+15*32) sta temp lda #>(gamescreen_middle+15*32) adc #0 sta temp+1 ldy branches_list+4 ; branch3 lda branch_addr_tableL,y sta temp2 lda branch_addr_tableH,y sta temp2+1 ldy #$00 @ lda (temp2),y sta (temp),y iny cpy tempbyte ;? lines bne @- all_drawed rts .endp ;-------------------------------------------------- .proc branches_go_down ;-------------------------------------------------- inc branches_anim_phase lda branches_anim_phase cmp #5 bne next_phase_only jsr new_branch next_phase_only jsr draw_branches rts .endp ;-------------------------------------------------- .proc new_branch ;-------------------------------------------------- mva #0 branches_anim_phase mva branches_list+3 branches_list+4 mva branches_list+2 branches_list+3 mva branches_list+1 branches_list+2 mva branches_list+0 branches_list+1 lda RANDOM ; 0, 1 or 2 and #%00000011 cmp #3 bne branch_ready lda #0 branch_ready sta branches_list+0 rts .endp ;-------------------------------------------------- branch_addr_tableL .by branch0 .by >branch1 .by >branch2 ;-------------------------------- ; names of RMT instruments (sfx) ;-------------------------------- sfx_ping = $07 sfx_pong = $08 ;-------------------------------- ; RMT songs (lines) ;-------------------------------- song_main_menu = $00 song_ingame = $07 song_game_over = $12 RUN main