diff --git a/.gitignore b/.gitignore index 3d5c26b..4753944 100644 --- a/.gitignore +++ b/.gitignore @@ -18,3 +18,4 @@ wave *.wav *.mp4 scratch +.kodiak.dat diff --git a/kodiak.tal b/kodiak.tal index 7e62cdd..84e0cca 100644 --- a/kodiak.tal +++ b/kodiak.tal @@ -33,7 +33,7 @@ ( - #6c queen of hearts, face down ) ( - #93 three of diamonds, held ) -( zero page - currently using 232 of 256 bytes ) +( zero page - currently using 254 of 256 bytes ) |0000 @stock $34 ( draw pile - 52 bytes, 24 bytes at start ) @waste $18 ( face up pile - 24 bytes ) @@ -61,8 +61,11 @@ @audio [ $1 ( is audio enabled? ) &pos $2 ] ( position in music ) @easy $1 ( true: draw 1 card false: draw 3 cards ) - @width $2 - @height $2 + @width $2 ( screen width ) + @height $2 ( screen height ) + @seconds $1 ( when to count time ) + @tick $1 ( already counted? ) +( 256 bytes ) |0100 ( metadata ) @@ -73,6 +76,7 @@ #8d12 .System/g DEO2 #4d12 .System/b DEO2 + load-scores init-screen ( set up vectors ) @@ -90,6 +94,9 @@ #0231 #0580 ;triangle #0004 #64 .Audio3 setup-audio #011f #00b0 ;noise #0200 #44 .Audio4 setup-audio + .DateTime/sec DEI .seconds STZ + #00 .tick STZ + start-audio ( display about window when first starting ) @@ -105,6 +112,53 @@ 01 ( 1 extended field ) ( icon ) 83 =icon-24 +@score-file ".kodiak.dat 00 + +@score-data $a + +@save-scores ( -> ) + LIT2r =score-data + LIT2 "ko STH2kr STA2 INC2r INC2r + ;draw-scores/games LDA2 STH2kr STA2 INC2r INC2r + ;draw-scores/wins LDA2 STH2kr STA2 INC2r INC2r + ;draw-scores/time LDA2 STH2kr STA2 INC2r INC2r + .easy LDZ #01 AND #00 STH2r STA2 + + ;score-file .File1/name DEO2 + #000a .File1/len DEO2 + ;score-data .File1/w DEO2 + JMP2r + +@load-scores ( -> ) + ;score-file .File1/name DEO2 + #000a .File1/len DEO2 + ;score-data .File1/r DEO2 + + ( dat file should be exactly 10 bytes ) + .File1/ok DEI2 #000a NEQ2 ?&invalid + + ( first two bytes must be "ko" ) + ;score-data LDA2 LIT2 "ko NEQ2 ?&invalid + + ( next 6 bytes contains 3 shorts ) + ;score-data INC2 INC2 + LDA2k ;draw-scores/games STA2 INC2 INC2 + LDA2k ;draw-scores/wins STA2 INC2 INC2 + LDA2k ;draw-scores/time STA2 INC2 INC2 + + ( next byte contains easy/hard bit ) + LDA #01 AND .easy STZ + + ( last byte ignored, for now ) + JMP2r + + &invalid + #0000 ;draw-scores/games STA2 + #0000 ;draw-scores/wins STA2 + #0000 ;draw-scores/time STA2 + #00 .easy STZ + JMP2r + @setup-audio ( adsr* sample* slen* dur* vol^ dev^ -> ) STHk #0e ORA DEO ( [dev^] ; <-vol ) STHkr #0a ORA DEO2 ( [dev^] ; <-slen ) @@ -113,6 +167,13 @@ STHr #08 ORA DEO2 ( ; <-adsr ) JMP2r +@inc-games ( -> ) + ;draw-scores/games LDA2k INC2 SWP2 STA2 JMP2r + +@restart + is-game-won ?{ inc-games save-scores } + ( >> ) + @reset init-rng-from-datetime init-stock @@ -159,7 +220,7 @@ JMP2r @quit ( -> brk ) - #010f DEO BRK ( TODO: save game? save stats? ) + is-game-won ?{ inc-games } save-scores #010f DEO BRK @dump-byte ( byte^ -- ) DUP #04 SFT /hex #0f AND ( >> ) @@ -215,6 +276,7 @@ @draw ( -> ) draw-background + draw-scores draw-buttons draw-decorations draw-stock @@ -388,6 +450,18 @@ LDAk load-ch #00 .Screen/sprite DEO ( s* ) INC2 !&loop ( s+1* ) +@print-dec ( x* y* n* -> ) + #01 ,pr-digit/a STR + STH2 .Screen/y DEO2 .Screen/x DEO2 + #01 .Screen/auto DEO + STH2r #2710 pr-digit #03e8 pr-digit #0064 pr-digit #000a pr-digit !pr-digit/emit + +@pr-digit ( n* d* -> n%d* ) + DIV2k STH2k MUL2 SUB2 STH2r + DUP2 #0000 EQU2 LIT [ &a 01 ] AND ?&leading-zero + &emit #00 ,&a STR NIP LIT "0 ADD load-ch #00 .Screen/sprite DEO JMP2r + &leading-zero POP2 #20 load-ch #00 .Screen/sprite DEO JMP2r + @load-ch ( c^ -> ) #00 SWP #30 SFT2 ;font ADD2 .Screen/addr DEO2 JMP2r @@ -430,6 +504,17 @@ .easy LDZ ?&easy ;hard-button JMP2r &easy ;easy-button JMP2r +@draw-scores ( -> ) + .width LDZ2 #002c SUB2 #0029 ;text/games print-str + .width LDZ2 #002c SUB2 #0032 LIT2 [ &games $2 ] print-dec + .width LDZ2 #002c SUB2 #0041 ;text/wins print-str + .width LDZ2 #002c SUB2 #004a LIT2 [ &wins $2 ] print-dec + .width LDZ2 #002c SUB2 #0059 ;text/time print-str + .width LDZ2 #002c SUB2 #0062 LIT2 [ &time $2 ] print-dec + JMP2r + +@text [ &n "12345 00 &games "games 00 &wins 20 "wins 00 &time 20 "time 00 ] + @draw-buttons ( -> ) .height LDZ2 #000c SUB2 #0008 OVR2 restart-button-addr draw-button @@ -676,7 +761,14 @@ @on-audio ( -> brk ) .audio LDZ ?{ BRK } play-audio BRK +@update-time ( -> ) + .DateTime/sec DEI .seconds LDZ EQU STHk + .tick LDZ AND ?{ STHr #00 EQU .tick STZ JMP2r } + ;draw-scores/time LDA2k INC2 SWP2 STA2 + #00 .tick STZ !draw + @on-refresh ( -> brk ) + update-time #00 .move/card LDZ EQU ?{ update-move } on-refresh-bear ( ; possibly refresh bear ) .frame LDZk INC SWP STZ ( ; increment frame counter ) @@ -1040,14 +1132,16 @@ DUP2 #00a8 LTH2 ?&no DUP2 #00c8 LTH2 ?&difficulty &no POP2 #00 JMP2r - &restart POP2 reset #01 JMP2r + &restart POP2 restart #01 JMP2r &quit POP2 quit #01 JMP2r &audio POP2 toggle-audio #01 JMP2r &about POP2 open-about #01 JMP2r &difficulty POP2 toggle-difficulty #01 JMP2r @on-game-win ( -> ) - !draw-buttons + ;draw-scores/games LDA2k INC2 SWP2 STA2 + ;draw-scores/wins LDA2k INC2 SWP2 STA2 + save-scores !draw-buttons @is-game-won ( -> bool^ ) .foundation #04 OVR ADD SWP ( lim^ start^ ) @@ -1151,7 +1245,7 @@ @on-press ( -> ) .Controller/key DEI #0d EQU ?dump-state ( ; 0x0d: return ) - .Controller/key DEI #1b EQU ?reset ( ; 0x1b: esc ) + .Controller/key DEI #1b EQU ?restart ( ; 0x1b: esc ) .Controller/key DEI #20 EQU ?auto-move ( ; 0x20: space ) JMP2r