; zxGammon: backgammon for the 48K ZX Spectrum, you against Gnubby, a ; little gnu with a neural-net Z80 engine for a brain. Money games, or matches to ; 1, 3, 5 or 7 points, with the doubling cube (and the Crawford rule). ; ; Loaded at $5e00 and started there: the game, then from $8000 (clear of ; the memory the screen slows) the engine. The engine works in ; $d700-$f3ff, the game in $db00-$deff; the cube's table for matches is ; at $f400, Gnubby's pictures after it (a block of their own), the game's ; latest record at $fb00 (see log.asm), and the stack is below $ffff. ; Interrupts stay off throughout: the keyboard is read directly, and the ; engine reads its weights off the stack pointer. WORK equ $d700 METTAB equ $f400 ; the cube's thresholds in a match, by score and ; cube: loaded apart, above the work area MASC equ METTAB+1260 ; Gnubby, 128 a mood (16 cells): loaded with ; the cube's table, after it org $5e00 jp start include "ram.asm" include "play.asm" include "screen.asm" include "input.asm" include "log.asm" ; ------------------------------------------------------------------ RAM G equ WORK+$400 GB equ G ; the game: the player's checkers, then at +32 ; Gnubby's, each from their own side TB0 equ G+$40 ; the player's turn's start ANIM equ G+$80 ; Gnubby's play, a step at a time CSTEPS equ G+$c0 ; its steps (points, then dice) SAID equ G+$100 ; what Gnubby last said TXT equ G+$180 ; what he is to say NUMBUF equ G+$200 GV equ G+$210 DIE1 equ GV+0 ; the dice, as rolled DIE2 equ GV+1 U1 equ GV+2 ; each played U2 equ GV+3 NDONE equ GV+4 ; checkers moved this turn NMAX equ GV+5 ; as many as the roll must move MUSTHI equ GV+6 ; only one die can be played, and the larger can CUBE equ GV+7 OWNER equ GV+8 ; 0 the middle, 1 the player, 2 Gnubby MLEN equ GV+9 ; the match's length, 0 for money SCH equ GV+10 ; the scores (2 each) SCC equ GV+12 CRAW equ GV+14 ; 1 in the Crawford game, 2 after it TURN equ GV+15 ; 0 the player, 1 Gnubby CURS equ GV+16 ; the point the player moves from (25: none) MOOD equ GV+17 ; Gnubby: 0 calm, 1 happy, 2 sad, 3 thinking SEED equ GV+18 ; (2) SHOWN equ GV+20 ; the dice shown: 1 the player's, 2 Gnubby's, ; 3 one each MXA equ GV+21 NEED equ GV+22 WINNER equ GV+23 GAMMON equ GV+24 POINTS equ GV+25 TATTR equ GV+26 PCOL equ GV+27 FATTR equ GV+28 TMPI equ GV+29 TOPPT equ GV+30 TSTEP equ GV+31 ; (2) SN equ GV+33 SATT equ GV+34 SDIR equ GV+35 SMAX equ GV+36 UZERO equ GV+37 TXP equ GV+38 ; (2) CNT equ GV+40 PLAYED equ GV+41 ; Gnubby has just played (what he said, in TXT) RECP equ GV+42 ; the cube: the record of thresholds (2) CFLAG equ GV+45 ; a contact position (2), or a race (0) OWNED equ GV+46 ; the doubler owns the cube TAKEQ equ GV+47 ; a take, not a double CT1 equ GV+48 ; thresholds: double from or take below (2) CT2 equ GV+50 ; too good from (2) UP equ GV+52 ; the board is on the screen (see setup) SAIDNEW equ GV+53 ; what Gnubby says is still to be shown NCK equ GV+54 ; a point's cells with checkers (2 each) LSHOWN equ GV+55 ; what was drawn last: whose dice, LTRAY equ GV+56 ; the checkers off (2), LCUBE equ GV+58 ; the cube (3), LSCORE equ GV+61 ; the score (4) DIG3 equ GV+65 ; small digits to draw (3) SROW equ GV+68 SLINE equ GV+69 PIPOFF equ GV+70 ; the pip counts hidden (the I key) DOTS equ GV+71 ; the dots shown while Gnubby thinks (0-3) ; The keys the game will take now, for whatever shows them (as the website ; does, under its emulator's screen): KWAIT is 1 while it waits for a key ; (0 while it works or thinks), and KSET which keys, as one of K_ANY.. KWAIT equ GV+72 KSET equ GV+73 K_ANY equ 0 ; any key, to go on K_TITLE equ 1 ; M (money), 1, 3, 5, 7 (a match) K_ROLL equ 2 ; R (roll), I (pips) K_ROLLD equ 3 ; R, D (double), I K_MOVE equ 4 ; Q, A (the cursor up and down), SPACE (move), ; 1, 2 (by that die), D (swap), U (undo), ; H (hint), I K_DONE equ 5 ; ENTER (done), U (undo) K_TAKE equ 6 ; Y (take), N (pass) K_AGAIN equ 7 ; Y, N (another game) TXT2 equ G+$280 ; ----------------------------------------------------------------- data START: db 0,0,0,0,0,5,0,3,0,0,0,0,5,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0 db 0,0,0,0,0,5,0,3,0,0,0,0,5,0,0,0,0,0,0,0,0,0,0,2,0,0,0,0,0,0,0,0 ; small digits, 3 dots by 5, a row a byte SDIG: db 7,5,5,5,7 db 2,6,2,2,7 db 7,1,7,4,7 db 7,1,3,1,7 db 5,5,7,1,1 db 7,4,7,1,7 db 7,4,7,5,7 db 7,1,2,2,2 db 7,5,7,5,7 db 7,5,7,1,7 db 7,5,7,4,4 ; P db 7,2,2,2,7 ; I S_TITLE: db "ZXGAMMON",0 S_WITH: db "WITH GNUBBY #",0 S_MENU: db "M MONEY GAME||1 1 POINT MATCH||3 3 POINT MATCH||5 5 POINT MATCH||7 7 POINT MATCH",0 S_FOOT: db "FOR THE ZX SPECTRUM 48K",0 S_HELLO: db "HI! I'M GNUBBY. LET'S PLAY!|PRESS A KEY TO SEE WHO STARTS.",0 S_YOUROLL: db "YOU ROLL ",0 S_IROLL: db ", I ROLL ",0 S_TIE: db ".|A TIE! AGAIN...",0 S_YOUSTART: db ".|YOU START! (PRESS A KEY)",0 S_ISTART: db ".|I START! (PRESS A KEY)",0 S_ROLL: db "YOUR TURN! R: ROLL THE DICE",0 S_ROLLDBL: db "YOUR TURN! R: ROLL D: DOUBLE",0 S_MOVE: db "Q/A: UP/DOWN SPACE: MOVE|D:SWAP U:UNDO H:HINT I:PIPS",0 S_DONE: db "ALL DONE? ENTER: YES|U: UNDO",0 S_NOMOVE: db "OH NO, YOU CAN'T MOVE!|PRESS A KEY.",0 S_HINT: db "HMM, LET ME SEE",0 S_THINK: db "HMM, LET ME THINK",0 S_ICANT: db "OOPS, I CAN'T MOVE!",0 S_IPLAY: db "I PLAY ",0 S_BAR: db "BAR",0 S_OFF: db "OFF",0 S_DBLYOU: db "YOU DOUBLE? HMM",0 S_CUBEQ: db "SHALL I DOUBLE? HMM",0 S_ITAKE: db "I TAKE! THE CUBE IS MINE.|PRESS A KEY.",0 S_IPASS: db "I PASS. YOU WIN THIS ONE!|PRESS A KEY.",0 S_IDOUBLE: db "I DOUBLE TO ",0 S_TAKEQ: db "!|TAKE (Y) OR PASS (N)?",0 S_YOUTAKE: db "BRAVE! GOOD LUCK!",0 S_YOUWIN: db "YOU WIN ",0 S_IWIN: db "I WIN ",0 S_POINT: db " POINT",0 S_GAMMON: db " - GAMMON!",0 S_BACKG: db " - BACKGAMMON!",0 S_YAY: db "|YAY! WELL PLAYED!",0 S_HEHE: db "|HEHE!",0 S_NL: db "|",0 S_MATCHYOU: db "YOU WIN THE MATCH! #",0 S_MATCHME: db "I WIN THE MATCH. GOOD GAME!",0 S_AGAIN: db " AGAIN? (Y/N)",0 S_TO: db "TO ",0 S_CRAW: db "CRAW",0 FONT: incbin "font" ; characters 32 to 95 CHK: incbin "checker" ; a checker, 2 cells by 2; then with counts 1-15 TRI: incbin "triangle" ; a point, 2 bytes a line from its base DICE: incbin "dice" ; 32 a face: its four cells CUBEG: incbin "cube" ; the cube face on, 32 a value: 1 (as 64), 2, 4, ... 128 MONEYREC: incbin "moneyrec" ; the cube's thresholds in money play (see play.asm) PTNUM: incbin "ptnum" ; the points' numbers, 1 to 24: two cells each ; The engine above $8000, clear of the memory the screen contends for. GAMEEND: ds $8000-$ include "gen.asm" include "encode.asm" include "features.asm" include "net.asm" include "choose.asm" include "data.asm" ENGINEEND: