quikman-rom.s

     1:  ; Quikman ROM cartridge for Commodore VIC20
     2:  ; written by Robert Hurst <robert@hurst-ri.us>
     3:  ; originally used Commodore VICMON (SYS 45056)
     4:  ; ported using the CA65 assembler (cc65.org)
     5:  ; updated version: 13-Dec-2008
     6:  ;
     7:  ; to assemble this source using cc65.org project:
     8:  ;   ca65.exe --cpu 6502 --listing quikman-rom.s
     9:  ;   ld65.exe -C doc/vic20-cartA.cfg -o quikman-rom.a0 quikman-rom.o
    10:  ;
    11:  ; to run the binary using viceteam.org project:
    12:  ;   xvic -memory none -ntsc -sound -joydev1 2 -cartA quikman-rom.a0
    13:  ; to run the binary using mess.org project:
    14:  ;   mess -view "Pixel Aspect (25:31)" vic20 -cart1 quikman-rom.a0
    15:  ;
    16:  ; pertinent VIC20 symbols
    17:  JIFFYH      = $A0       ; jiffy-clock hi byte value
    18:  JIFFYM      = $A1       ; jiffy-clock mid byte value
    19:  JIFFYL      = $A2       ; jiffy-clock low byte value
    20:  CLRPAGE     = $F4       ; color memory page (unexpanded = $97)
    21:  SCRNPAGE    = $0288     ; screen memory page (unexpanded = $1E)
    22:  CTRLCSHIFT  = $028D     ; keyboard flag: control/commodore/shift
    23:  CASSBUFF    = $033C     ; cassette buffer
    24:  VIC         = $9000     ; start of video interface chip registers
    25:  RESET       = $FD22     ; warm startup
    26:  CHROUT      = $FFD2     ; print character with cursor translation
    27:  GETIN       = $FFE4     ; get a character from keyboard queue
    28:  ;
    29:  ; my symbol / memory map
    30:  ;           = $00       ; base index (monster, sprite)
    31:  ;           = $01       ; index x2
    32:  ;           = $02       ; index x8
    33:  PPILLTIMER  = $10       ; powerpill effectiveness timer
    34:  FRUITTIMER  = $39       ; 0 - 250
    35:  FRUITFLAG   = $3A       ; zero or non-zero, if fruit has been activated
    36:  PPILLFLAG   = $3B       ; just ate a powerpill this turn (0=no)
    37:  CHOMP       = $3C       ; pointer into sound effect for fruit and fleeing monsters
    38:  CHEWING     = $3D       ; flag whether quikman just ate a dot or not
    39:  DIGIT       = $3E       ; award points at this digit place
    40:  POINTS      = $3F       ; how many points scored
    41:  OLDDIR      = $40       ; direction sprite was last moving in
    42:  NEWDIR      = $41       ; direction sprite wants to take, if valid by MAZEMOVE
    43:  JOYVAL      = $42       ; last joystick read value
    44:  QMANDIR     = $43       ; quikman's current direction (0=right,1=down,2=left,3=up)
    45:  FRAME       = $44       ; frame number
    46:  LIVES       = $45       ; 0 - 3
    47:  FLASHPILL   = $46       ; powerpill blink counter (0-30)
    48:  EXTRAQMAN   = $47       ; bonus quickman flag (0=unused)
    49:  DEMOQMAN    = $48       ; spirit of quickman index (0-3)
    50:  FRUITLEVEL  = $49       ; 0 - 12
    51:  DOTS        = $4A       ; 0 - 170
    52:  PENALTY     = $4B       ; $4B-$4E monsters are free-to-roam flag
    53:  ;           = $4F       ; $4F-$52 monsters current direction (0=right,1=down,2=left,3=up)
    54:  ;           = $53       ; $53,$55,$57,$59 monster's knowledge of quikman's "X" coord was
    55:  ;           = $54       ; $54,$56,$58,$5A monster's knowledge of quikman's "Y" coord was
    56:  MONMOVE     = $61       ; $61-$64 monster array for its next best move
    57:  ;           = $69       ; temporary var
    58:  FLEEINGSCORE= $70       ; fleeing monster score: 2, 4, 8, 16
    59:  ;           = $F7       ; $F7/$F8,$F9,$FA are screen cell pointers for sprite's position
    60:  ;           = $FE       ; $FC/$FD,$FE/$FF are color cell pointers for same
    61:  ;
    62:  ; program indirects (my sprite registers)
    63:  SPRITE      = $02A1     ; bitmask 0-7 controls sprite on/off
    64:  SPRITEX     = $02A2     ; $02A2,A4,A6,A8,AA,AC,AE,B0 each "X" coordinate
    65:  SPRITEY     = $02A3     ; $02A3,A5,A7,A9,AB,AD,AF,B1 each "Y" coordinate
    66:  SPRITECLR   = $02B2     ; $02B2-$02B9 color
    67:  SPRITEIMG1  = $02BA     ; $02BA-$02C1 low-byte of SPRITE image
    68:  SPRITEIMG2  = $02C2     ; $02C2-$02C9 hi-byte of SPRITE image
    69:  SPRITELAST  = $02CC     ; $02CC-$02DC keep last state of SPRITE registers
    70:  SAVEBACK    = $02DD     ; $02DD-$02E6 keep what's under the sprite's 2-cell
    71:  ;
    72:  ; other constants
    73:  FRUITCELL   = $1F1B     ; screen cell address of fruit
    74:  FRUITCELLCLR= $971B     ; color cell address of fruit
    75:  ;
    76:  ; uses standard VIC20 (unexpanded)
    77:          .org $A000
    78:          .segment "STARTUP"
    79:  ;
    80:  ;*********************************************************************
    81:  ; Commodore Cartridge boot sequence
    82:  ; load address of startup & restore key:
    83:          .word   MAIN
    84:          .word   NMI
    85:  ;               power-up signature: A0CBM
    86:          .byte   $41, $30, $C3, $C2, $CD
    87:  ;
    88:  ;*********************************************************************
    89:  ; RESTORE key was pressed by a frustrated player ...
    90:  NMI:
    91:          CLD
    92:          PLA             ; Y
    93:          TAY
    94:          PLA             ; X
    95:          TAX
    96:          PLA             ; A
    97:          JMP RESTART
    98:  ;
    99:  ;*********************************************************************
   100:  ; Starting entry point for this program
   101:  MAIN:
   102:          ; initialize VIC into usable state
   103:          JSR $FD8D   ; ramtas    Initialise System Constants (memory pointers)
   104:          JSR $FDF9   ; ioinit    Initialise I/O (timers are enabled)
   105:          JSR $E518   ; cint1     Initialize I/O (VIC reset, must follow ramtas)
   106:          JSR $FF8A   ; restor    Restore Vectors (required)
   107:          ;JSR $FF8D  ; vector    Change Vectors For User (not required)
   108:          ;LDA #$7F
   109:          ;STA $911E  ; disable NMI, so no reset key wanted?
   110:          ; my VIC chipset init
   111:          LDA VIC+$01
   112:          SBC #$04        ; adjust top scan line to accomodate extra row
   113:          STA VIC+$01
   114:          LDA #$80+$15    ; set for videoram @ $1E00 with 21-columns
   115:          STA VIC+$02     ; video matrix address + columns
   116:          LDA #$B0        ; $B0 = 10110000 = 24 rows + 8x8 height
   117:          STA VIC+$03     ; rows / character height
   118:          LDX #$FF        ; set for $1C00
   119:          STX VIC+$05     ; use programmable char set
   120:  ;
   121:  ;*********************************************************************
   122:  ; SOFT reset entry point
   123:  RESTART:
   124:          ; my interrupt vector init
   125:          SEI
   126:          LDX #<BACKGROUND
   127:          LDY #>BACKGROUND
   128:          STX $0314
   129:          STY $0315
   130:          CLI
   131:          ; seed BASIC RAM with game data
   132:          LDA #<MAZEDATA
   133:          STA $FC
   134:          LDA #>MAZEDATA
   135:          STA $FD
   136:          LDA #$00
   137:          STA $FE
   138:          LDA #$1A
   139:          STA $FF
   140:          LDY #$00
   141:  @copy:  LDA ($FC),Y
   142:          STA ($FE),Y
   143:          INY
   144:          BNE @copy
   145:          INC $FD
   146:          INC $FF
   147:          LDA $FF
   148:          CMP #$1E
   149:          BNE @copy
   150:          TYA
   151:  @snd:   STA VIC+$0A,Y   ; reset sound channels
   152:          INY
   153:          CPY #$04
   154:          BNE @snd
   155:          LDA #$8F        ; brown & highest
   156:          STA VIC+$0E     ; auxiliary color & volume
   157:          JSR RESTORE
   158:          LDX #$15
   159:  @msg:   LDA BANNERMSG,X
   160:          STA $1FE3,X
   161:          LDA #$03
   162:          STA $97E3,X
   163:          DEX
   164:          BPL @msg
   165:          LDA #$09        ; brown button, white font, just like the F-key
   166:          STA $97E3+$0E
   167:          STA $97E3+$0F
   168:  ;
   169:  DEMO:
   170:          JSR INITVARS
   171:          LDY #$00
   172:          STY LIVES
   173:          JSR GAMEOVER
   174:          LDY #$0A
   175:          STY SPRITE
   176:  @loop:  LDA FRAME
   177:          AND #$7F
   178:          BNE @slow
   179:          LDX VIC+$0F
   180:          INX
   181:          TXA
   182:          AND #$07
   183:          TAX
   184:          ORA #$08
   185:          STA VIC+$0F
   186:          JSR MAZEPAINT
   187:  @skip:  INC FRUITLEVEL
   188:          LDX FRUITLEVEL
   189:          CPX #$0D
   190:          BCC @fruit
   191:          STX PPILLFLAG   ; demo powerpill
   192:          LDX #$00
   193:          STX FRUITLEVEL
   194:  @fruit: LDA FRUIT,X
   195:          STA FRUITCELL
   196:          LDA FRUITCLR,X
   197:          STA FRUITCELLCLR
   198:          LDA #$40
   199:          STA FRUITTIMER
   200:          STA FRUITFLAG
   201:  @slow:  LDX JIFFYL
   202:          INX
   203:          INX
   204:  @wait:  CPX JIFFYL
   205:          BNE @wait
   206:          LDA SPRITE
   207:          EOR #$1E
   208:          STA SPRITE
   209:          JSR NPC         ; demo mode
   210:  @scan:  JSR SPRITES
   211:          JSR GETIN       ; get keyboard
   212:          CMP #$85        ; got F1 ?
   213:          BEQ RESETGAME   ; try again ...
   214:          LDA #$FF
   215:          STA $9122
   216:          LDA $9111
   217:          AND #$20        ; FIRE
   218:          BNE @loop
   219:  ;
   220:  ;*********************************************************************
   221:  RESETGAME:
   222:          LDA #$09
   223:          STA CHOMP
   224:          LDA #$03        ; start with 3-lives
   225:          STA LIVES
   226:          LDY #$FF        ; -1 will become 0 at start of "next" level
   227:          STY FRUITLEVEL
   228:          JSR GAMEOVER    ; clear status
   229:          LDX #$00        ; reset score
   230:          STX EXTRAQMAN   ; reset bonus
   231:  @loop1: LDA #$B0        ; each digit to "0"
   232:          STA SCORE-$9200,X ; into savebuffer
   233:          INX             ; do next digit
   234:          CPX #$06        ; all 6 of them
   235:          BNE @loop1
   236:  ;
   237:  STARTLVL:
   238:          JSR RESTORE     ; initialize new level
   239:  ;
   240:  RESETCHR:
   241:          JSR INITVARS
   242:          LDA #$1C        ; 1st page where quikman is on
   243:          STA SPRITEIMG2
   244:          LDA #$A8        ; start quikman off with a smug smile
   245:          STA SPRITEIMG1
   246:          LDA #$1F        ; turn on sprites 0-4
   247:          STA SPRITE
   248:          LDX #$0C
   249:  @smug:  LDA #$08
   250:          JSR PAUSE       ; then he sees there are monsters ...
   251:          DEX
   252:          BPL @smug
   253:          LDX #$05
   254:  @loop2: LDA $C377,X     ; print READY from ROM
   255:          AND #$BF
   256:          ORA #$80
   257:          STA $1F18,X
   258:          LDA #$07        ; make it yellow
   259:          STA $9718,X
   260:          LDA #$98        ; restore monster caged image (heh)
   261:          STA SPRITEIMG1,X
   262:          DEX
   263:          BNE @loop2      ; how geeky is that?
   264:          LDA #$C8        ; quikman gets ready
   265:          STA SPRITEIMG1
   266:          LDX #$18
   267:  @ready: LDA #$08
   268:          JSR PAUSE       ; wait 2+ seconds
   269:          DEX
   270:          BPL @ready
   271:          LDX #$00
   272:          LDA #$20        ; erase READY
   273:  @loop4: STA $1F19,X
   274:          INX
   275:          CPX #$05
   276:          BNE @loop4
   277:  ;
   278:  ; zero $39 - $43
   279:  ZEROVARS:
   280:          LDX #$00
   281:          STX FRUITFLAG
   282:          STX PPILLFLAG
   283:          STX CHEWING
   284:          LDX #$02
   285:          STX QMANDIR     ; start off going LEFT
   286:          STX JOYVAL      ; preload last joystick value as going LEFT
   287:  ;
   288:  ;*********************************************************************
   289:  PLAYLOOP:
   290:          LDA CTRLCSHIFT  ; is the player holding down any
   291:          BNE PLAYLOOP    ; control, commodore, shift key(s)?
   292:          LDA FRUITCELL
   293:          CMP #$21        ; is there fruit on display?
   294:          BCC @warp
   295:          LDX FRUITLEVEL
   296:          LDA FRUITCLR,X  ; restore fruit color
   297:          STA FRUITCELLCLR
   298:  @warp:  LDA #$0C        ; 10-levels to warp
   299:          SEC
   300:          SBC FRUITLEVEL  ; progressive speed
   301:          BCC @cruz
   302:          CMP #$03
   303:          BCS @pace
   304:  @cruz:  LDA #$03
   305:  @pace:  TAY
   306:  @sleep: INX
   307:          BNE @sleep
   308:          DEY
   309:          BNE @sleep      ; one 1000, two 1000, three 1000, ...
   310:          STY $00         ; quikman is sprite #0
   311:          STY $01
   312:          LDA QMANDIR
   313:          STA OLDDIR      ; save last direction quikman was going in
   314:          LDX JOYVAL      ; recall last joystick value
   315:          STY $9113
   316:          LDA #$7F
   317:          STA $9122
   318:          LDA $9120
   319:          AND #$80        ; JOY 3
   320:          BNE @joy0
   321:          LDX #$00
   322:  @joy0:  LDA #$FF
   323:          STA $9122
   324:          LDY $9111
   325:          TYA
   326:          AND #$08
   327:          BNE @joy1
   328:          LDX #$01
   329:  @joy1:  TYA
   330:          AND #$10
   331:          BNE @joy2
   332:          LDX #$02
   333:  @joy2:  TYA
   334:          AND #$04
   335:          BNE @joy3
   336:          LDX #$03
   337:  @joy3:  STX JOYVAL      ; save
   338:          TXA
   339:          STA NEWDIR      ; do the same for the joystick
   340:          JSR MAZEMOVE
   341:          BCS @skip1      ; is the direction valid?
   342:          LDA JOYVAL      ; yes,
   343:          STA QMANDIR     ; request quikman to move in direction of joystick
   344:          CLC
   345:          BCC @skip2
   346:  @skip1: LDA QMANDIR
   347:          STA NEWDIR
   348:          JSR MAZEMOVE    ; keep the current direction going?
   349:  @skip2: LDA SPRITEX
   350:          BNE @skip3      ; is quikman at end of tunnel left?
   351:          LDA #$9E
   352:          STA SPRITEX     ; put quikman at beginning of tunnel right
   353:  @skip3: CMP #$A0        ; is quikman at end of tunnel right?
   354:          BNE @skip4
   355:          LDA #$00
   356:          STA SPRITEX     ; put quikman at beginning of tunnel left
   357:  @skip4:
   358:          LDX #$B0        ; closed mouth
   359:          LDA SPRITEX
   360:          ORA SPRITEY
   361:          AND #$02
   362:          BNE @anim
   363:          LDA QMANDIR     ; take 0=right, 1=down, 2=left, 3=up value
   364:          ASL             ; multiply by 8 to get address
   365:          ASL
   366:          ASL
   367:          CLC
   368:          ADC #$B8        ; add base offset
   369:          TAX
   370:  @anim:  STX SPRITEIMG1
   371:  ;
   372:          LDX #$00        ; use X as a flag
   373:          LDA SPRITEX
   374:          AND #$07
   375:          CMP #$04
   376:          BNE @skip5      ; is quikman in the middle of a left/right cell?
   377:          INX
   378:          LDA QMANDIR     ; yes, 0=right, 2=left
   379:          EOR #$02
   380:          TAY
   381:          BEQ @skip6      ; going left, use 1st saveback cell
   382:          DEY
   383:          BNE @skip6      ; going right, use overflow saveback cell
   384:  @skip5: LDA SPRITEY
   385:          AND #$07
   386:          CMP #$03
   387:          BNE @skip6      ; is quikman in the middle of an up/down cell?
   388:          INX
   389:          LDY QMANDIR
   390:          CPY #$01        ; going down, use overflow saveback cell
   391:          BEQ @skip6
   392:          LDY #$00        ; going up, use 1st saveback cell
   393:  @skip6: CPX #$00
   394:          BNE @skip7      ; does quikman have something in its mouth?
   395:          JMP NPCNEXT     ; no, continue play
   396:  @skip7: LDA SAVEBACK,Y  ; retrieve the character from quikman's saveback buffer
   397:          CMP #$20
   398:          BNE @skip8
   399:          JMP PLAYLOOP    ; nothing to eat here, so move a bit faster
   400:          ; check what was just eaten ...
   401:  @skip8: TAX             ; save that something in X
   402:          LDA #$20
   403:          STA SAVEBACK,Y  ; replace the cell quikman is on with an empty space
   404:          CPX #$1E        ; is it a dot?
   405:          BNE POWERUP
   406:          LDA #$01
   407:          STA POINTS      ; score 1
   408:          STA CHEWING     ; quikman has to chew this dot, monsters keep movin'
   409:          LDA #$0A        ; score it @ 10-point digit
   410:          STA DIGIT
   411:  ;
   412:  POWERUP:
   413:          CPX #$21
   414:          BCC @skip1      ; is X < 33 ?
   415:          CPX #$29        ; no, is X >= 41 ?
   416:          BCS NPCNEXT     ; ate a piece of fruit?
   417:          TXA             ; YUMMY!
   418:          SEC
   419:          SBC #$21        ; strip off char code for score index
   420:          TAX
   421:          LDA FRUITSCORE,X
   422:          STA POINTS      ; award points
   423:          LDA #$09
   424:          STA DIGIT       ; in hundreds
   425:          STA CHOMP
   426:          CLC
   427:          BCC NPCNEXT
   428:  @skip1: CPX #$1F        ; ate a powerpill?
   429:          BNE EATING      ; no, but I did eat a dot
   430:          LDA #$05
   431:          STA POINTS      ; award 5-points
   432:          LDA #$0A
   433:          STA DIGIT       ; score @ 10-digit
   434:          STA PPILLFLAG
   435:          BEQ NPCNEXT     ; powerpills are dots on steroids, account for it
   436:  ;
   437:  EATING: INC DOTS        ; ate a dot, account for it
   438:          LDA DOTS
   439:          CMP #$AA        ; are all dots eaten?
   440:          BNE NPCNEXT
   441:  ;===    achieved end of level   ===
   442:  WONLEVEL:
   443:          LDA #$A8        ; quikman ends with a smug smile
   444:          STA SPRITEIMG1
   445:          LDA #$80
   446:          JSR PAUSE
   447:          LDA #$00
   448:          STA FRAME
   449:  @loop:  DEC FRAME
   450:          LDA FRAME
   451:          AND #$07
   452:          TAX
   453:          JSR MAZEPAINT
   454:          LDA FRAME
   455:          AND #$1F
   456:          BNE @next
   457:          LDA SPRITE
   458:          EOR #$1E
   459:          STA SPRITE      ; blink monsters
   460:  @next:  LDX #$04
   461:          LDA #$70        ; ghost ends small
   462:  @tiny:  STA SPRITEIMG1,X
   463:          DEX
   464:          BNE @tiny
   465:          JSR SPRITES
   466:          LDA FRAME
   467:          CMP #$06
   468:          BNE @loop       ; continue until true blue
   469:          LDA #$40
   470:          JSR PAUSE
   471:          LDX #$03
   472:  @loop1: LDA PENALTY,X
   473:          LDY FRUITLEVEL
   474:          INY
   475:  @loop2: LSR
   476:          DEY
   477:          BNE @loop2
   478:          STA PENALTY,X       ; after each level, the monsters dispatch quicker
   479:          DEX
   480:          BPL @loop1
   481:          JMP STARTLVL
   482:  ;
   483:  NPCNEXT:
   484:          JSR GETIN       ; get keyboard
   485:          CMP #$03        ; got STOP ?
   486:          BEQ WONLEVEL    ; CHEATER!!
   487:          JSR NPC
   488:          JSR SPRITES
   489:          JMP PLAYLOOP
   490:  ;
   491:  ;*********************************************************************
   492:  ; non-player characters & events
   493:  NPC:
   494:          LDA FRUITFLAG
   495:          BNE @skip3      ; is fruit already on display?
   496:          LDA DOTS
   497:          CMP #$4B        ; has the 75th dot been eaten?
   498:          BEQ @skip1
   499:          CMP #$7D        ; has the 125th dot been eaten?
   500:          BNE @skip3
   501:  @skip1: LDX FRUITLEVEL  ; prepare thy bonus
   502:          CPX #$0C        ; reach the last level?
   503:          BCC @skip2
   504:          LDX #$0C        ; only the key is left, and it leaves a bad metallic after-taste
   505:  @skip2: LDA FRUIT,X
   506:          STA FRUITCELL   ; display fruit
   507:          LDA FRUITCLR,X
   508:          STA FRUITCELLCLR
   509:          LDA #$FA        ; 250-moves and counting
   510:          STA FRUITTIMER  ; reset fruit timer
   511:          STA FRUITFLAG
   512:  @skip3: LDA FRUITTIMER  ; fruit is on display
   513:          BEQ @skip4      ; nothing to do
   514:          DEC FRUITTIMER  ; remove a tick
   515:          BNE @skip4      ; there is still time left
   516:          LDA #$20        ; time's up!
   517:          STA FRUITCELL   ; no more fruit
   518:  @skip4: LDA DOTS
   519:          CMP #$4C        ; has the 76th dot been eaten?
   520:          BEQ @skip5
   521:          CMP #$7E        ; has the 126th dot been eaten?
   522:          BNE @skip6
   523:  @skip5: LDA #$00
   524:          STA FRUITFLAG   ; more fruit potential on this level
   525:  ;
   526:  @skip6: LDA PPILLFLAG
   527:          BEQ KISSING     ; just swallowed a powerpill?
   528:          LDA #$00        ; account for that action
   529:          STA PPILLFLAG
   530:          LDA #$02        ; start scoring @ 200-points
   531:          STA FLEEINGSCORE
   532:          LDX FRUITLEVEL
   533:          TXA
   534:          AND #$07
   535:          BEQ @break      ; every 8-levels, keep timer up
   536:          CPX #$10
   537:          BCS @timer      ; 16-levels of powerpill timing
   538:          TXA
   539:  @break: ASL             ; x2
   540:          ASL             ; x2
   541:          AND #$3F
   542:          EOR #$3F        ; invert A
   543:          CPX #$05
   544:          BCC @timer      ; timer good to the 1st apple
   545:          LSR             ; 1/2
   546:  @timer: STA PPILLTIMER  ; set powerpill timer
   547:          LDY #$04
   548:  @loop1: LDX PENALTY-1,Y
   549:          BNE @skip7      ; is monster waiting in cage already?
   550:          LDA #$06        ; no, make monster blue
   551:          STA SPRITECLR,Y
   552:          LDA #$A0        ; make monster fleeing (0)
   553:          STA SPRITEIMG1,Y
   554:          LDA $4E,Y
   555:          EOR #$02        ; and reverse its direction
   556:          STA $4E,Y
   557:  @skip7: DEY
   558:          BNE @loop1
   559:  ;
   560:  ; check all monsters if any are in contact with quikman
   561:  KISSING:
   562:          LDY #$08
   563:  KISSME:
   564:          LDA LIVES
   565:          BEQ NEXTKISS
   566:          LDA SPRITEX
   567:          CMP SPRITEX,Y
   568:          BNE @skip3
   569:          LDA SPRITEY
   570:          SEC
   571:          SBC SPRITEY,Y
   572:          BCS @skip2
   573:          EOR #$FF
   574:  @skip2: CMP #$05
   575:          BCS @skip3
   576:          LDX #$FF
   577:          BNE ENGAGED     ; is quikman engaged with a monster?
   578:  @skip3: LDA SPRITEY
   579:          CMP SPRITEY,Y
   580:          BNE NEXTKISS
   581:          LDA SPRITEX
   582:          SEC
   583:          SBC SPRITEX,Y
   584:          BCS @skip4
   585:          EOR #$FF
   586:  @skip4: CMP #$05
   587:          BCC ENGAGED     ; is quikman engaged with a monster?
   588:  ;
   589:  NEXTKISS:
   590:          DEY             ; next monster
   591:          DEY             ; X,Y coord pair check
   592:          BNE KISSME
   593:          JMP MONSTERS    ; quikman is still freely running!
   594:  ;
   595:  ENGAGED:
   596:          TYA
   597:          LSR
   598:          TAX
   599:          LDA SPRITEIMG1,X
   600:          CMP #$70        ; is monster returning to cage?
   601:          BEQ NEXTKISS
   602:          CMP #$A0        ; is monster fleeing?
   603:          BNE DEAD        ; no, quikman bites the dust
   604:          LDA #$09        ; ahah!  caught a little sickly one!
   605:          STA DIGIT       ; in hundreds
   606:          LDA FLEEINGSCORE
   607:          STA POINTS      ; fleeing monster score
   608:          ASL             ; next is worth x2 bonus
   609:          STA FLEEINGSCORE
   610:          TYA
   611:          PHA
   612:          TXA
   613:          PHA
   614:          LDA #$D0
   615:          STA VIC+$0A
   616:          LDA SPRITE
   617:          EOR SPRITEMASK,X
   618:          STA SPRITE
   619:          LDX PPILLTIMER
   620:          LDA #$01
   621:          JSR PAUSE
   622:          LDA #$A8        ; quikman smiles
   623:          STA SPRITEIMG1
   624:          LDA #$01
   625:          JSR PAUSE
   626:          LDA JIFFYL
   627:          CLC
   628:          ADC #$20
   629:  @loop:  LDY JIFFYL
   630:          INY
   631:  @loop1: CPY JIFFYL
   632:          BNE @loop1
   633:          STX PPILLTIMER
   634:          INC VIC+$0A
   635:          CMP JIFFYL
   636:          BNE @loop       ; wait up to a jiffy
   637:          LDA #$00
   638:          STA VIC+$0A
   639:          PLA
   640:          TAX
   641:          PLA
   642:          TAY
   643:          LDA #$70        ; monster runs back to cage
   644:          STA SPRITEIMG1,X
   645:          LDA SPRITE
   646:          EOR SPRITEMASK,X
   647:          STA SPRITE
   648:          DEX
   649:          LDA MONSTERCLR,X
   650:          STA SPRITECLR+1,X
   651:          JMP NEXTKISS    ; is there another monster here?
   652:  ;
   653:  DEAD:
   654:          PLA             ; remove quikman's call to NPC from stack
   655:          PLA             ; because he just died . . .
   656:          LDX #$06
   657:  @oops:  LDA #$10
   658:          JSR PAUSE
   659:          DEX
   660:          BPL @oops
   661:          ; death sequence
   662:          LDA #$01        ; only feature quikman dying
   663:          STA SPRITE
   664:          LDA #$B0        ; low-order byte of 1st quikman image
   665:          STA SPRITEIMG1
   666:          LDX #$01
   667:  @loop:  LDA QUIKMANCLR,X ; reset monsters starting colors
   668:          STA SPRITECLR,X ; into their sprite color registers
   669:          LDA #$80        ; reset monsters as looking down
   670:          STA SPRITEIMG1,X
   671:          INX
   672:          CPX #$05
   673:          BNE @loop
   674:          LDA #$F0
   675:          STA VIC+$0C
   676:          LDA #$20
   677:          STA FRAME       ; rotate quikman 8 times
   678:  @loop1: LDA SPRITEIMG1
   679:          CMP #$D0        ; are we at the 4th quikman image?
   680:          BCC @skip
   681:          INC VIC+$0C
   682:          LDA #$B0        ; reset to 1st quikman image
   683:  @skip:  CLC
   684:          ADC #$08        ; advance to next image
   685:          STA SPRITEIMG1
   686:          DEC VIC+$0C     ; wooosh!
   687:          DEC VIC+$0C
   688:          DEC VIC+$0C
   689:          LDA #$04
   690:          JSR PAUSE
   691:          DEC FRAME
   692:          BNE @loop1      ; repeat next sequence
   693:          LDX #$D8
   694:          STX SPRITEIMG1  ; explode!
   695:          LDA #$0A
   696:          JSR PAUSE
   697:          LDX #$E0
   698:          STX SPRITEIMG1  ; smoke!
   699:          LDA #$08
   700:          JSR PAUSE
   701:          LDX #$E8
   702:          STX SPRITEIMG1  ; dust!
   703:          LDA #$06
   704:          JSR PAUSE
   705:          LDA #$00
   706:          STA SPRITE
   707:          STA VIC+$0C
   708:          LDA #$64
   709:          JSR PAUSE
   710:          DEC LIVES
   711:          BEQ FINALITY    ; any lives remaining?
   712:          LDX LIVES
   713:          LDA #$1B
   714:          STA $1FE4,X     ; avatar explodes
   715:          LDA #$0A
   716:          JSR PAUSE
   717:          LDA #$1C
   718:          STA $1FE4,X     ; avatar smoking
   719:          LDA #$08
   720:          JSR PAUSE
   721:          LDA #$1D
   722:          STA $1FE4,X     ; avatar dusted
   723:          LDA #$01
   724:          STA SPRITE
   725:          LDA #$D8
   726:          STA SPRITEIMG1
   727:          JSR INITVARS
   728:          LDA #$06
   729:          JSR PAUSE
   730:          LDX LIVES
   731:          LDA #$20
   732:          STA $1FE4,X     ; erase the avatar
   733:          JMP RESETCHR    ; quikman still has life -- try again!
   734:  ;
   735:  FINALITY:
   736:          LDY #00
   737:          STY SPRITE
   738:          JSR GAMEOVER
   739:          LDA #$F0        ; 4-second pause
   740:          JSR PAUSE
   741:          JMP DEMO        ; this game is really over now
   742:  ;
   743:  ;*********************************************************************
   744:  MONSTERS:
   745:          LDA #$04
   746:          STA $00         ; start with monster #4
   747:  ;
   748:  DOMONSTER:
   749:          LDA $00
   750:          TAY
   751:          ASL             ; x2
   752:          STA $01
   753:          LDX PENALTY-1,Y
   754:          BEQ ITMOVES     ; is this monster free to roam?
   755:          LDA FRAME
   756:          AND #$03
   757:          BEQ @anim
   758:          DEX             ; no, countdown to freedom
   759:          STX PENALTY-1,Y
   760:  @anim:  LDA #$98        ; reset monster as caged, but coming out
   761:          CPX #$10
   762:          BCC @eyes
   763:          TXA
   764:          AND #$08
   765:          BNE @skip
   766:          LDA #$78        ; reset monster as caged looking right
   767:          BNE @eyes
   768:  @skip:  LDA #$88        ; reset monster as caged looking left
   769:  @eyes:  STA SPRITEIMG1,Y
   770:          LDX $01
   771:          LDA SPRITEX,X
   772:          AND #$F8
   773:          STA SPRITEX,X
   774:  ;
   775:  NEXTMONSTER:
   776:          DEC $00         ; process next monster
   777:          BNE DOMONSTER
   778:          INC FRAME
   779:          INC $00
   780:          LDA SPRITEY+$02
   781:          CMP #$58        ; no bonus at cage row
   782:          BEQ @fini           
   783:          AND #$07
   784:          ORA SPRITEX+$02
   785:          AND #$0F
   786:          BEQ DOMONSTER
   787:          LDA CHEWING
   788:          BNE @skip1      ; is quikman eating a dot?
   789:  @fini:  RTS             ; no, we're done
   790:  @skip1: LDA DOTS
   791:          AND #$01
   792:          BNE @fini       ; quikman can swallow every other dot faster
   793:          JSR SPRITES     ; yes, chasing monsters get another turn
   794:          JMP MONSTERS
   795:  ;
   796:  ITMOVES:
   797:          LDA SPRITEIMG1,Y
   798:          CMP #$70
   799:          BNE @go         ; small ghost going home?
   800:          LDX $01         ; yes, get pairing index
   801:          LDA SPRITEX,X
   802:          CMP #$50
   803:          BNE @caged
   804:          LDA SPRITEY,X
   805:          CMP #$48
   806:          BNE @caged      ; is monster above cage ($50,$48 coord) doorway ?
   807:          INC SPRITEY,X   ; move into doorway
   808:          LDX #$01
   809:          STX $4E,Y       ; make direction DOWN to go into cage
   810:  @caged: LDA SPRITEY,X
   811:          CMP #$58
   812:          BNE @skip1      ; is monster at cage row level?
   813:          TYA
   814:          ASL
   815:          ASL
   816:          ASL
   817:          CLC
   818:          ADC #$40
   819:          CMP SPRITEX,X   ; is monster inside cage?
   820:          BNE @skip1
   821:          LDA #$98        ; restore monster caged image
   822:          STA SPRITEIMG1,Y
   823:          LDA CAGEDATA-1,Y
   824:          EOR #$FF
   825:          LSR
   826:          ADC #$20        ; compute waiting room time
   827:          STA PENALTY-1,Y ; monster is waiting
   828:          JMP NEXTMONSTER ; done moving
   829:  @go:    LDA FRAME
   830:          AND #$01
   831:          BEQ @cont       ; check for powerpill active?
   832:          LDA SPRITEIMG1,Y
   833:          CMP #$A0        ; this monster IS fleeing
   834:          BEQ NEXTMONSTER ; skip its turn
   835:  @cont:  LDX $01         ; no, get pairing index
   836:          LDA SPRITEX,X
   837:          CMP #$50
   838:          BNE @skip1
   839:          LDA SPRITEY,X
   840:          CMP #$58
   841:          BNE @skip1      ; is monster in cage ($50,$58 coord) doorway ?
   842:          DEC SPRITEY,X   ; move it a pixel UP to force it through the closed door
   843:          LDX #$03
   844:          STX $4E,Y       ; make direction UP to get out of cage
   845:          BNE @skip3
   846:  @skip1: LDA SPRITEX,X
   847:          BNE @skip2      ; is monster against the left-side of the tunnel?
   848:          LDX $00
   849:          STA $4E,X       ; force a change of direction to the right
   850:  @skip2: CMP #$9F        ; is monster against the right-side of the tunnel?
   851:          BNE @skip3
   852:          LDX $00
   853:          LDA #$02
   854:          STA $4E,X       ; force a change of direction to the left
   855:  @skip3: LDY #$00
   856:          LDX #$04
   857:  @loop1: STX MONMOVE-1,Y ; preset move priority as 0=right,1=down,2=left,3=up
   858:          INY
   859:          DEX
   860:          BNE @loop1
   861:          LDY $01         ; start of monster's calculated move
   862:          LDA SPRITEX,Y
   863:          AND #$07
   864:          BEQ @skip4      ; is monster horizontally aligned with a screen cell?
   865:          LDA SPRITEY,Y
   866:          AND #$07
   867:          BNE @skip5      ; is monster vertically aligned with a screen cell?
   868:  @skip4: JSR AI          ; yes, check to see if a direction change is in its future
   869:          CLC
   870:          BCC @skip6
   871:  @skip5: LDX $4E,Y       ; not in a position to make a direction change,
   872:          STX $61         ; so just keep monster going in its current direction
   873:  @skip6: LDY #$00
   874:          STY $04
   875:  @loop2: LDX $61,Y
   876:          TXA
   877:          LDX $00
   878:          EOR $4E,X
   879:          CMP #$02
   880:          BEQ @skip7      ; don't allow monsters to reverse direction on their own
   881:          LDX $61,Y
   882:          STX NEWDIR
   883:          LDY $00
   884:          LDX $4E,Y
   885:          STX OLDDIR
   886:          JSR MAZEMOVE    ; validate
   887:          BCC MAKEMOVE    ; is this a good move?
   888:  @skip7: INC $04
   889:          LDY $04
   890:          CPY #$04
   891:          BNE @loop2
   892:          LDY $00         ; reverse direction
   893:          LDA OLDDIR
   894:          EOR #$02
   895:          STA $4E,Y
   896:          JMP NEXTMONSTER
   897:  ;
   898:  MAKEMOVE:
   899:          LDY $00         ; commit to this move
   900:          LDX NEWDIR
   901:          STX $4E,Y       ; save as monster's current direction
   902:          LDA SPRITEIMG1,Y
   903:          CMP #$70        ; running back to cage
   904:          BEQ @mommy      ; to give birth again
   905:          CMP #$A0        ; fleeing from quikman
   906:          BEQ @anim
   907:          TXA
   908:          ASL             ; multiply by 8 to get address
   909:          ASL
   910:          ASL
   911:          CLC
   912:          ADC #$78        ; add base offset
   913:  @anim:  STA SPRITEIMG1,Y
   914:  @jmp:   JMP NEXTMONSTER
   915:  @mommy:
   916:          LDY $01         ; start of monster's calculated move
   917:          LDA SPRITEX,Y
   918:          ORA SPRITEY,Y
   919:          AND #$02
   920:          BEQ @jmp
   921:          JMP ITMOVES
   922:  ;
   923:  ; monster's artificial intelligence
   924:  AI:
   925:  ; first, preload $61-$64 with "best" moves this monster can make
   926:  ; to give quikman the kiss of death
   927:          LDX $01
   928:          LDA $51,X       ; retrieve this monster's "X" knowledge where quikman was
   929:          CMP SPRITEX,X   ; aligned?
   930:          BNE @math1      ; nope, compute intersect
   931:          LDA JIFFYL
   932:          AND #$01
   933:          BEQ @skip1      ; flip a coin
   934:  @math1: SEC
   935:          SBC SPRITEX,X
   936:          BCS @skip1
   937:          LDY #$02
   938:          STY MONMOVE     ; LEFT is better
   939:          LDY #$00
   940:          STY $64         ; RIGHT is worse
   941:          BEQ @skip2
   942:  @skip1: LDY #$00
   943:          STY MONMOVE     ; RIGHT is better
   944:          LDY #$02
   945:          STY $64         ; LEFT is worse
   946:  @skip2: LDA $52,X       ; retrieve this monster's "Y" knowledge where quikman was
   947:          CMP SPRITEY,X   ; aligned?
   948:          BNE @math2      ; nope, compute intersect
   949:          LDA JIFFYL
   950:          AND #$01
   951:          BEQ @skip3      ; flip a coin
   952:  @math2: SEC
   953:          SBC SPRITEY,X
   954:          BCS @skip3
   955:          LDY #$03
   956:          STY $62         ; UP is 2nd best
   957:          LDY #$01
   958:          STY $63         ; DOWN is 3rd best
   959:          BNE AI2
   960:  @skip3: LDY #$01        ; DOWN is 2nd best
   961:          STY $62
   962:          LDY #$03        ; UP is 3rd best
   963:          STY $63
   964:  ;
   965:  ; next, prioritize monster move, based upon its current location in respect to
   966:  ; its knowledge where quikman was considered last.
   967:  AI2:    LDX $01
   968:          TXA
   969:          ASL
   970:          ASL
   971:          ASL             ; x8
   972:          CMP JIFFYL
   973:          BCS @skip3      ; ignore priority during this time window
   974:          LDA $51,X
   975:          SEC
   976:          SBC SPRITEX,X
   977:          BCS @skip1
   978:          EOR #$FF
   979:  @skip1: STA $69
   980:          LDA $52,X
   981:          SEC
   982:          SBC SPRITEY,X
   983:          BCS @skip2
   984:          EOR #$FF
   985:  @skip2: CMP $69
   986:          BCC @skip3      ; can monster improve upon order of choices?
   987:          LDX MONMOVE     ; swap 1st & 2nd choices
   988:          LDY $62
   989:          STX $62
   990:          STY MONMOVE
   991:          LDY $63         ; swap 3rd & 4th choices
   992:          LDX $64
   993:          STY $64
   994:          STX $63
   995:  @skip3: LDY $00
   996:          LDA SPRITEIMG1,Y
   997:          CMP #$A0        ; is this monster fleeing?
   998:          BNE @fini       ; no, chase!
   999:          LDX MONMOVE     ; swap 1st & 3rd choices
  1000:          LDY $63
  1001:          STX $63
  1002:          STY MONMOVE
  1003:  @fini:  RTS
  1004:  ;
  1005:  ; reset monsters to default starting location
  1006:  INITVARS:
  1007:          LDX #$00
  1008:  @loop1: LDA STARTPOS,X  ; reset each sprite starting position
  1009:          STA SPRITEX,X
  1010:          INX
  1011:          CPX #$0A        ; 5 sprites per X,Y coordinate pair
  1012:          BNE @loop1
  1013:          LDY #$00
  1014:  @loop2: LDX CAGEDATA,Y
  1015:          STX PENALTY,Y
  1016:          INY
  1017:          CPY #$10
  1018:          BNE @loop2
  1019:          RTS
  1020:  ;
  1021:  ; restore sound/screen
  1022:  RESTORE:
  1023:          INC FRUITLEVEL
  1024:          LDA #$00
  1025:          STA SPRITE      ; turn off all sprites
  1026:          LDA #$0E        ; black / blue
  1027:          STA VIC+$0F     ; background / border color
  1028:          LDA #$93        ; Shift-HOME is clearscreen
  1029:          JSR CHROUT      ; print it
  1030:          LDX #$06        ; blue
  1031:          JSR MAZEPAINT
  1032:          LDX #$15        ; skip 1st & last row
  1033:  @draw:  LDA MAZEDATA,X
  1034:          STA $1E00,X
  1035:          LDA MAZEDATA+$E3,X
  1036:          STA $1EE3,X
  1037:          INX
  1038:          BNE @draw
  1039:          STX DOTS        ; and no dots are eaten (yet)
  1040:  @loop2: LDA QUIKMANCLR,X ; reset monsters starting colors
  1041:          STA SPRITECLR,X ; into their sprite color registers
  1042:          LDA #$80        ; reset monsters as looking down @ quikman
  1043:          STA SPRITEIMG1,X
  1044:          LDA #$1C
  1045:          STA SPRITEIMG2,X
  1046:          INX
  1047:          CPX #$05
  1048:          BNE @loop2
  1049:          LDY LIVES       ; paint lives remaining
  1050:          JSR GAMEOVER
  1051:          DEY
  1052:          BEQ @next
  1053:  @loop4: LDA #$19        ; quikman character
  1054:          STA $1FE4,Y     ; bottom-left of screen
  1055:          LDA #$07        ; use yellow
  1056:          STA $97E4,Y     ; and paint it
  1057:          DEY
  1058:          BNE @loop4
  1059:  @next:  LDY FRUITLEVEL
  1060:          LDX #$00
  1061:  @loop5: CPY #$0C        ; are we at the last level (key)?
  1062:          BCC @skip1
  1063:          LDY #$0C        ; only keys remain
  1064:  @skip1: LDA FRUIT,Y     ; fruit character
  1065:          STA $1FF1,X     ; bottom right of screen
  1066:          LDA FRUITCLR,Y  ; get its color
  1067:          STA $97F1,X     ; and paint it
  1068:          CPY #$00        ; did we paint the cherry yet?
  1069:          BEQ BEGIN       ; if so, we're done
  1070:          INX
  1071:          STX $FF
  1072:          LDA FRUITLEVEL
  1073:          SEC
  1074:          SBC $FF
  1075:          TAY
  1076:          CPX #$07        ; no more than 7 fruits to display
  1077:          BNE @loop5
  1078:  BEGIN:  ;LDA LIVES      ; allow new screen to be processed
  1079:  ;       BEQ @cont
  1080:  ;       LDA #$40
  1081:  ;@cont: JSR PAUSE       ; by player
  1082:          RTS
  1083:  ;
  1084:  ; recolor maze with some new paint in X
  1085:  MAZEPAINT:
  1086:          LDY #$15
  1087:  @loop:  LDA MAZEDATA,Y
  1088:          CMP #$29
  1089:          BCC @page2
  1090:          CMP #$3F
  1091:          BCS @page2
  1092:          LDA #$01
  1093:          TXA
  1094:          STA $9600,Y
  1095:  @page2: LDA MAZEDATA+$E3,Y
  1096:          CMP #$29
  1097:          BCC @skip
  1098:          CMP #$3F
  1099:          BCS @skip
  1100:          TXA
  1101:          STA $96E3,Y
  1102:  @skip:  INY
  1103:          BNE @loop
  1104:          RTS
  1105:  ;
  1106:  ; if move is valid, carry flag will be clear on return
  1107:  MAZEMOVE:
  1108:          LDY $01         ; get X,Y coord index
  1109:          LDA OLDDIR      ; get the last direction moving
  1110:          AND #$01        ; mask UP/DOWN
  1111:          BEQ @skip1      ; is direction LEFT/RIGHT?
  1112:          INY             ; no, then fetch the "Y" coordinate
  1113:  @skip1: LDA SPRITEX,Y   ; get one of sprite's coord
  1114:          AND #$07
  1115:          BEQ MAZEANY     ; at a crossroad?  check move in any 4-directions
  1116:          LDA NEWDIR
  1117:          CMP OLDDIR
  1118:          BEQ MYMOVE      ; still want to move in the same direction?
  1119:          EOR OLDDIR
  1120:          CMP #$02
  1121:          BEQ MYMOVE      ; is this a reverse direction request?
  1122:          SEC             ; no new move made
  1123:          RTS
  1124:  ;
  1125:  MAZEANY:
  1126:          JSR SPRITEPREP
  1127:          LDA $F8         ; reset screen hi-byte back into saved maze data
  1128:          SEC
  1129:          SBC #$04
  1130:          STA $F8
  1131:          LDX NEWDIR
  1132:          CPX #$02
  1133:          BCS @skip2      ; is X (2=left) or (3=up)?
  1134:          LDA $F7         ; no
  1135:          CLC
  1136:          ADC PEEKAHEAD,X ; look (0=right) or (1=down)
  1137:          BCC @skip1
  1138:          INC $F8
  1139:  @skip1: STA $F7
  1140:          CLC
  1141:          BCC @skip4      ; go validate
  1142:  @skip2: LDA $F7
  1143:          SEC
  1144:          SBC PEEKAHEAD-2,X
  1145:          BCS @skip3      ; look (2=left) or (3=up)
  1146:          DEC $F8
  1147:  @skip3: STA $F7
  1148:  @skip4: LDY #$00        ; validate
  1149:          LDA ($F7),Y
  1150:          CMP #$29        ; is this direction into a maze wall?
  1151:          BCC MYMOVE      ; good move?
  1152:          RTS
  1153:  ;
  1154:  ; continue this sprite's move in whatever is loaded in NEWDIR
  1155:  MYMOVE:
  1156:          LDA NEWDIR
  1157:          ASL             ; 0=0, 1=2, 2=4, 3=6, 4=8
  1158:          TAX
  1159:          LDY $01
  1160:          LDA INERTIA,X
  1161:          CLC
  1162:          ADC SPRITEX,Y
  1163:          STA SPRITEX,Y
  1164:          LDA INERTIA+1,X
  1165:          CLC
  1166:          ADC SPRITEY,Y
  1167:          STA SPRITEY,Y
  1168:          CLC
  1169:          RTS
  1170:  ;
  1171:  ;*********************************************************************
  1172:  ; my very own sprite routines
  1173:  ; major custom hack for this maze game implementation
  1174:  SPRITES:
  1175:          LDA #$00        ; start with sprite #0
  1176:          STA $00         ; current sprite # to render
  1177:  @loop1: ASL
  1178:          STA $01         ; current sprite (x2) pairing index
  1179:          ASL
  1180:          ASL
  1181:          STA $02         ; current sprite (x8) image index
  1182:          LDX $00
  1183:          LDA SPRITE
  1184:          AND SPRITEMASK,X
  1185:          BEQ @skip2      ; nothing to do?
  1186:          LDA SPRITELAST  ; what state was this sprite before?
  1187:          AND SPRITEMASK,X
  1188:          BEQ @skip1      ; it was "off"
  1189:          JSR ERASESPRITE ; was "on" before, and we still want it "on"
  1190:  @skip1: JSR SPRITEPREP  ; new sprite, go turn it "on"
  1191:          JSR PREPMATRIX
  1192:          JSR RENDER
  1193:          JSR PLACEMATRIX
  1194:          JMP @next
  1195:  @skip2: LDA SPRITELAST
  1196:          AND SPRITEMASK,X
  1197:          BEQ @next       ; still nothing to do?  Then do nothing ...
  1198:          JSR ERASESPRITE ; make this sprite disappear
  1199:  @next:  INC $00
  1200:          LDA $00
  1201:          CMP #$05        ; only 5-sprites needed in this game
  1202:          BNE @loop1
  1203:          LDX #$00
  1204:  @loop2: LDA SPRITE,X    ; save copy of current sprite registers
  1205:          STA SPRITELAST,X
  1206:          INX
  1207:          CPX #$11        ; all 17 values, not including colors
  1208:          BNE @loop2
  1209:          RTS             ; fini
  1210:  ;
  1211:  ; remove sprite from screen
  1212:  ERASESPRITE:
  1213:          JSR LASTSPRITEPREP
  1214:          JSR PREPMATRIX
  1215:          JSR RESTOREMATRIX
  1216:          RTS
  1217:  ;
  1218:  LASTSPRITEPREP:
  1219:          LDA $01         ; 0, 2, 4, 6, 8
  1220:          CLC
  1221:          ADC #<SPRITELAST
  1222:          BNE SPRITEPREP2
  1223:  ;
  1224:  ; prepares the following registers:
  1225:  ; $F7/$F8,$F9/$FA       screen cell pointers for sprite position
  1226:  ; $FC/$FD,$FE/$FF       color cell pointers for same
  1227:  SPRITEPREP:
  1228:          LDA $01         ; 0, 2, 4, 6, 8 index
  1229:          CLC
  1230:          ADC #<SPRITE
  1231:  SPRITEPREP2:
  1232:          TAX             ; save this register index
  1233:          LDA $0201,X     ; get "X" coordinate
  1234:          CMP #$A0
  1235:          BCC @skip1      ; is "X" at or beyond last column?
  1236:          SBC #$A0        ; yes, subtract 160-pixels wide
  1237:  @skip1: LSR             ; and divide by 8-pixel width
  1238:          LSR
  1239:          LSR
  1240:          STA $F7         ; save column offset from left screen
  1241:          STA $FC         ; save column offset from left color
  1242:          LDA SCRNPAGE    ; get high order byte of screen memory page
  1243:          STA $F8
  1244:          LDA CLRPAGE     ; get high order byte of screen color page
  1245:          AND #$FE        ; make it and "even" number
  1246:          STA $FD         ; save high order
  1247:          LDA $0202,X     ; get "Y" coordinate
  1248:          CMP #$B8
  1249:          BCC @skip2      ; is "Y" at or beyond last row?
  1250:          SBC #$B8        ; yes, subtract 184-pixels high
  1251:  @skip2: LSR             ; and divide by 8-pixel height
  1252:          LSR
  1253:          LSR
  1254:          TAY
  1255:          BEQ @fini       ; if on top row, no math required
  1256:          LDA $F7         ; get column offset
  1257:  @loop1: CLC
  1258:          ADC #$15        ; add 21 for next row
  1259:          BCC @skip3      ; overflow to next page?
  1260:          INC $F8         ; yes, increment high order bytes
  1261:          INC $FD
  1262:  @skip3: STA $F7         ; save column offset
  1263:          STA $FC
  1264:          DEY
  1265:          BNE @loop1      ; do for each "row"
  1266:  @fini:  LDA $F8         ; copy high-order bytes
  1267:          STA $FA         ; for overflow sprite character
  1268:          LDA $FD         ; do the same
  1269:          STA $FF         ; for color
  1270:  ; determine whether overflow character is to the right or down
  1271:          LDA $0201,X     ; get "X" coordinate
  1272:          AND #$07
  1273:          BEQ @vert       ; 0 assumes moving up/down?
  1274:          LDA $F7         ; ok, moving left/right then ...
  1275:          CLC
  1276:          ADC #$01        ; make overflow character to the right
  1277:          BCC @savel
  1278:  @saveh: INC $FA
  1279:          INC $FF
  1280:  @savel: STA $F9         ; save character offset
  1281:          STA $FE         ; save color offset
  1282:          RTS
  1283:  @vert:  LDA $F7
  1284:          CLC
  1285:          ADC #$15        ; make overflow character below
  1286:          BCC @savel
  1287:          BCS @saveh
  1288:  ;
  1289:  ; prepares saveback buffers for restoring, should a larger-numbered sprite be
  1290:  ; overlapping any part of a smaller-numbered sprite
  1291:  PREPMATRIX:
  1292:          LDY #$00
  1293:          LDA ($F7),Y     ; retrieve screen cell
  1294:          PHA
  1295:          LDY $01         ; 0, 2, 4, 6, 8 index
  1296:          LDA $0201,X
  1297:          AND #$07
  1298:          BNE @2cell
  1299:          LDA $0202,X
  1300:          AND #$07
  1301:          BEQ @start
  1302:  @2cell: LDY #$00
  1303:          LDA ($F9),Y     ; retrieve overflow cell
  1304:          PHA
  1305:          LDY $01         ; 0, 2, 4, 6, 8 index
  1306:          INY
  1307:  @start: TYA
  1308:          TAX
  1309:  @loop:  PLA
  1310:  @retry: CMP $01
  1311:          BCC @skip       ; is A < ME ?
  1312:          CMP #$0A
  1313:          BCS @skip       ; is A >= MAX ?
  1314:  ; there is a sprite # greater than us on top ...
  1315:          TAY
  1316:          LDA SAVEBACK,Y  ; get > sprite# saveback info
  1317:          CLC
  1318:          BCC @retry
  1319:  @skip:  STA SAVEBACK,X
  1320:          DEX
  1321:          CPX $01
  1322:          BEQ @loop
  1323:          RTS
  1324:  ;
  1325:  ; restores the sprite's saveback buffer to the screen squares it occupies
  1326:  ; erasure part 3
  1327:  RESTOREMATRIX:
  1328:          LDX $01
  1329:          LDA SAVEBACK,X  ; recover character
  1330:          LDY #$00
  1331:          STA ($F7),Y     ; restore to screen
  1332:          LDA #$01
  1333:          STA ($FC),Y     ; just leave "white" behind
  1334:          LDA SPRITELAST+1,X
  1335:          AND #$07
  1336:          BNE @2cell
  1337:          LDA SPRITELAST+2,X
  1338:          AND #$07
  1339:          BEQ @fini
  1340:  @2cell: LDA SAVEBACK+1,X
  1341:          STA ($F9),Y     ; restore to screen
  1342:          LDA #$01
  1343:          STA ($FE),Y     ; only color overflow if X or Y are offset
  1344:  @fini:  RTS
  1345:  ;
  1346:  ; render sprite within its character matrix by merging its image over its saveback
  1347:  ; $05/$06 points to graphic character
  1348:  RENDER:
  1349:          LDX $00         ; 0-4
  1350:          LDA SPRITEIMG1,X
  1351:          STA $05
  1352:          LDA SPRITEIMG2,X
  1353:          STA $06
  1354:          LDX $01         ; 0,2,4,6,8
  1355:          LDA SPRITEY,X
  1356:          AND #$07
  1357:          STA $03
  1358:          TAX             ; X will hold the sprite's Y coord
  1359:          LDY #$00        ; erase temp image matrix area
  1360:          TYA
  1361:  @loop1: STA CASSBUFF+$20,Y
  1362:          INY
  1363:          CPY #$10        ; customized from 4 to 2 character cells
  1364:          BNE @loop1
  1365:          TAY             ; copy 8x8 character image into temp matrix
  1366:  @loop2: LDA ($05),Y     ; $05/$06 points to character matrix to draw
  1367:          STA CASSBUFF+$20,X
  1368:          INX
  1369:          INY
  1370:          CPY #$08
  1371:          BNE @loop2
  1372:          LDX $01
  1373:          LDA SPRITEX,X
  1374:          AND #$07        ; get modulos on X coordinate
  1375:          TAY
  1376:          BEQ @skip1      ; if its zero, no shifting required
  1377:  @loop3: LDX #$00
  1378:  @loop4: CLC
  1379:          ROR CASSBUFF+$20,X
  1380:          ROR CASSBUFF+$28,X
  1381:          INX
  1382:          CPX #$08
  1383:          BNE @loop4
  1384:          DEY
  1385:          BNE @loop3
  1386:  @skip1: STY $FB         ; Y is always zero here
  1387:  @loop5: LDA $01         ; index x2
  1388:          CLC
  1389:          ADC $FB
  1390:          TAX             ; X is sprite custom character
  1391:          LDA #$1C        ; 1st page is where sprites are stored
  1392:          STA $06
  1393:          LDA SAVEBACK,X
  1394:          CMP #$80
  1395:          BCC @skip2      ; is character reversed?
  1396:          LDY #$80        ; yes, use start of ROM character set
  1397:          STY $06
  1398:  @skip2: AND #$1F        ; get modulos of first 32-characters
  1399:          ASL             ; and multiply by 8-pixel height
  1400:          ASL
  1401:          ASL
  1402:          STA $05         ; save as low-order byte index
  1403:          LDA SAVEBACK,X
  1404:          AND #$60        ; mask 01100000
  1405:          LSR             ; divide by 16
  1406:          LSR
  1407:          LSR
  1408:          LSR
  1409:          LSR
  1410:          CLC
  1411:          ADC $06         ; add result to high-order page index
  1412:          STA $06
  1413:          LDY #$00
  1414:          LDA $FB
  1415:          ASL
  1416:          ASL
  1417:          ASL
  1418:          TAX
  1419:  @loop6: LDA ($05),Y     ; copy 8x8 character image into behind matrix
  1420:          STA CASSBUFF+$30,X
  1421:          INX
  1422:          INY
  1423:          CPY #$08
  1424:          BNE @loop6
  1425:          INC $FB
  1426:          LDA $FB
  1427:          CMP #$02        ; only a 2-cell sprite now
  1428:          BNE @loop5
  1429:          LDY #$00
  1430:          LDA $02         ; 0, 8, 16, 24, 32
  1431:          ASL             ; 0, 16, 32, 48, 64
  1432:          TAX
  1433:  @loop7: LDA CASSBUFF+$20,Y
  1434:          ORA CASSBUFF+$30,Y
  1435:          STA $1C00,X
  1436:          INX
  1437:          INY
  1438:          CPY #$10        ; customized from 4 to 2 character cells
  1439:          BNE @loop7
  1440:          RTS
  1441:  ;
  1442:  ; puts the sprite character matrix on the screen
  1443:  PLACEMATRIX:
  1444:          LDA $01         ; 0, 2, 4, 6, 8
  1445:          LDY #$00
  1446:          STA ($F7),Y
  1447:          LDX $00
  1448:          LDA SPRITECLR,X
  1449:          STA ($FC),Y
  1450:          LDX $01
  1451:          LDA SPRITEX,X
  1452:          AND #$07
  1453:          BNE @color
  1454:          LDA SPRITEY,X
  1455:          AND #$07
  1456:          BEQ @fini
  1457:  @color: LDA ($FC),Y
  1458:          STA ($FE),Y     ; only color overflow if X & Y are offset
  1459:          INX
  1460:          TXA
  1461:          STA ($F9),Y
  1462:  @fini:  RTS
  1463:  ;
  1464:  ;*********************************************************************
  1465:  ; This section is dedicated to background processing, accomplished
  1466:  ; via the keyboard IRQ service, called 60-times per second (jiffy).
  1467:  BACKGROUND:
  1468:          CLD
  1469:          LDA $1EDC
  1470:          CMP #$C5
  1471:          BNE @esc
  1472:          LDA #$09
  1473:          STA $96DC       ; paint the cage door
  1474:  @esc:   LDA JIFFYL
  1475:          AND #$07
  1476:          BNE FLASH
  1477:          LDA PPILLTIMER  ; drain powerpill
  1478:          BEQ FLASH       ; is there still power left?
  1479:          CMP #$1F        ; yes ... but are they
  1480:          BCS DRAIN       ; getting confidence back?
  1481:          AND #$03        ; yes, let's warn quikman
  1482:          BNE DRAIN
  1483:          LDY #$04
  1484:  @pp1:   LDA SPRITEIMG1,Y
  1485:          CMP #$A0        ; is monster fleeing?
  1486:          BNE @pp2
  1487:          LDA SPRITECLR,Y
  1488:          EOR #$07        ; flash white / blue
  1489:          STA SPRITECLR,Y
  1490:  @pp2:   DEY
  1491:          BNE @pp1
  1492:  DRAIN:  DEC PPILLTIMER
  1493:          BNE FLASH
  1494:          LDY #$04
  1495:  @loop:  LDA MONSTERCLR-1,Y
  1496:          STA SPRITECLR,Y ; restore all monsters to their default colors
  1497:          LDA SPRITEIMG1,Y
  1498:          CMP #$70        ; is monster already going home?
  1499:          BEQ @next
  1500:          LDA #$98        ; restore monster chasing image
  1501:          STA SPRITEIMG1,Y
  1502:  @next:  DEY
  1503:          BNE @loop
  1504:  FLASH:  LDA FLASHPILL   ; powerpill flash
  1505:          CMP #$1E        ; 30-jiffies?
  1506:          BNE @skip1
  1507:          LDX #$00        ; reset counter
  1508:          STX FLASHPILL
  1509:  @loop1: LDA $1CF8,X     ; custom graphic char
  1510:          EOR $8288,X     ; rom graphic char
  1511:          STA $1CF8,X     ; redraw 8x8 char cell
  1512:          INX
  1513:          CPX #$08
  1514:          BNE @loop1
  1515:          LDA #$FE        ; render monster feet
  1516:          EOR $1C9F       ; custom graphic char
  1517:          STA $1C9F       ; redraw caged monster
  1518:          STA $1CA7       ; redraw fleeing monster
  1519:          STA $1C8F       ; looking left
  1520:          STA $1C97       ; looking up
  1521:          LDA #$7F        ; render monster feet
  1522:          EOR $1C7F       ; custom graphic char
  1523:          STA $1C7F       ; looking right
  1524:          STA $1C87       ; looking down
  1525:  @skip1: INC FLASHPILL
  1526:          LDA LIVES
  1527:          BNE @hi         ; playing?
  1528:          LDA JIFFYL      ; manufacture a moving quikman 'spirit'
  1529:          BEQ @hi
  1530:          LDA JIFFYM
  1531:          AND #$03
  1532:          BNE @hi
  1533:          INC DEMOQMAN
  1534:          LDA DEMOQMAN
  1535:          AND #$03
  1536:          ASL             ; x2 for pair
  1537:          TAY             ; for the monsters to 'chase'
  1538:          LDA CAGEDATA+$08,Y
  1539:          STA SPRITEX
  1540:          LDA CAGEDATA+$09,Y
  1541:          STA SPRITEY
  1542:  @hi:    LDX #$00        ; yes
  1543:  @loop3: LDA SCORE-$9200,X ; check current score against high score
  1544:          CMP MAZEDATA-$9200+$0F,X
  1545:          BCC @top        ; is quikman beating the high score?
  1546:          BNE @skip4      ; yes!
  1547:          INX
  1548:          CPX #$06
  1549:          BNE @loop3
  1550:  @skip4: LDX #$00
  1551:  @loop4: LDA SCORE-$9200,X       ; woot!
  1552:          STA MAZEDATA-$9200+$0F,X
  1553:          INX
  1554:          CPX #$06
  1555:          BNE @loop4
  1556:  @top:   LDX #$14        ; refresh top line
  1557:  @loop5: LDA MAZEDATA-$9200,X
  1558:          STA $1E00,X
  1559:          DEX
  1560:          BPL @loop5
  1561:  ADDPTS: LDY POINTS      ; award points to score on screen
  1562:          BEQ CLRPTS
  1563:  @loop1: LDX DIGIT
  1564:  @loop2: LDA MAZEDATA-$9200,X
  1565:          CMP #$B9        ; reach "9" ?
  1566:          BEQ @skip2
  1567:          INC MAZEDATA-$9200,X    ; ding!
  1568:          DEY
  1569:          BNE @loop1
  1570:          BEQ CLRPTS
  1571:  @skip2: LDA #$B0
  1572:          STA MAZEDATA-$9200,X    ; wrap to "0"
  1573:          DEX             ; and increment next order
  1574:          BNE @loop2
  1575:  CLRPTS: STY POINTS
  1576:          LDX #$00
  1577:          LDY #$00
  1578:  @loop6: LDA PENALTY,X
  1579:          BNE @next       ; not aware while caged
  1580:          LDA SPRITEIMG1+1,X
  1581:          CMP #$70
  1582:          BNE @go         ; small ghost going home?
  1583:          LDA #$50
  1584:          STA $53,Y
  1585:          LDA #$48
  1586:          STA $54,Y
  1587:          BNE @next
  1588:  @go:    LDA DOTS
  1589:          CMP #$A6        ; make them all "smart" with 5-dots or less
  1590:          BCS @skip5
  1591:          LDA CAGEDATA,X
  1592:          BEQ @skip5      ; is monster "smart"?  Red one is ...
  1593:          CMP JIFFYL      ; no, so check as often as it waits
  1594:          BNE @next       ; is its wait time equal to the jiffy clock?
  1595:  @skip5: LDA SPRITEX     ; update this monster's awareness to where quikman is
  1596:          STA $53,Y
  1597:          LDA SPRITEY
  1598:          STA $54,Y
  1599:  @next:  INY
  1600:          INY
  1601:          INX
  1602:          CPX #$04
  1603:          BNE @loop6
  1604:  ;
  1605:  wahka:  LDA CHEWING
  1606:          BEQ @skip1
  1607:          LDA #$91        ; start with an odd frequency
  1608:          STA VIC+$0C     ; ignite a voice
  1609:  @skip1: LDA #$00        ; dot is swallowed
  1610:          STA CHEWING
  1611:          LDA VIC+$0C
  1612:          BEQ @next1      ; is this voice mute?
  1613:          LDA VIC+$0C
  1614:          AND #$01
  1615:          BEQ @skip3      ; is it even?
  1616:          LDA VIC+$0C
  1617:          CLC
  1618:          ADC #$10        ; increase tone
  1619:          CMP #$F1
  1620:          BCC @skip2      ; is voice too high?
  1621:          SEC
  1622:          SBC #$01        ; make it even
  1623:  @skip2: STA VIC+$0C
  1624:          CLC
  1625:          BCC @next1      ; goto next effect
  1626:  @skip3: LDA VIC+$0C
  1627:          SEC
  1628:          SBC #$10        ; drain tone
  1629:          STA VIC+$0C
  1630:  @next1: LDX CHOMP
  1631:          BEQ @skip4
  1632:          LDA JIFFYL
  1633:          AND #$01
  1634:          BNE @skip4
  1635:          LDA SNDBIT,X    ; load tone data
  1636:          STA VIC+$0B
  1637:          DEC CHOMP
  1638:  @skip4: LDA EXTRAQMAN
  1639:          BNE @fini       ; already got bonus life
  1640:          LDA SCORE+1-$9200
  1641:          CMP #$B1        ; did quikman just score 10,000-points?
  1642:          BNE @fini
  1643:          STA EXTRAQMAN
  1644:          LDX LIVES
  1645:          LDA #$19
  1646:          STA $1FE4,X
  1647:          LDA #$07
  1648:          STA $97E4,X
  1649:          INC LIVES       ; reward
  1650:  @fini:  JMP $EABF       ; jump to hardware IRQ
  1651:  ;
  1652:  ; Pass A for number of jiffies to wait, while preserving X
  1653:  PAUSE:  PHA
  1654:          TXA
  1655:          PHA
  1656:          JSR SPRITES     ; redraw sprites
  1657:          PLA
  1658:          TAX
  1659:          PLA
  1660:          CLC
  1661:          ADC JIFFYL
  1662:  @loop:  CMP JIFFYL
  1663:          BNE @loop
  1664:          RTS
  1665:  ;
  1666:  ; Y > 0 erase; Y = 0 display
  1667:  GAMEOVER:
  1668:          LDX #$08
  1669:  @loop:  LDA GOTEXT,X    ; GAME OVER
  1670:          CPY #$00
  1671:          BEQ @dead
  1672:          LDA #$20        ; space
  1673:  @dead:  STA $1F17,X     ; print character
  1674:          STA $1B17,X
  1675:          LDA #$02        ; red
  1676:          STA $9717,X
  1677:          DEX
  1678:          BPL @loop
  1679:          RTS
  1680:  ;
  1681:  ;*********************************************************************
  1682:  ; READ-ONLY DATA
  1683:  CAGEDATA:       ; knowledge cycle time
  1684:          .byte   $00, $33, $76, $F9
  1685:                  ; right, up, left, right
  1686:          .byte   $00, $03, $02, $00
  1687:                  ; coordinate to consider going to upon release or demo
  1688:          .byte   $A0, $28, $00, $28, $A0, $88, $00, $88
  1689:  GOTEXT:         ; GAME OVER
  1690:          .byte   $87, $81, $8D, $85, $A0, $8F, $96, $85, $92
  1691:  INERTIA:        ; maintain direction
  1692:          .byte   $01, $00, $00, $01, $FF, $00, $00, $FF
  1693:  PEEKAHEAD:      ;
  1694:          .byte   $01, $15
  1695:  SNDBIT:         ; yummy sound effect
  1696:          .byte   $00, $00, $C0, $B8, $B0, $A8, $B0, $B8, $C0, $C8
  1697:  STARTPOS:       ;
  1698:          .byte   $50, $88, $50, $48, $50, $58, $60, $58, $40, $58
  1699:  SPRITEMASK:     ; really?
  1700:          .byte   $01, $02, $04, $08, $10
  1701:  ;
  1702:  ;*********************************************************************
  1703:  ; Maze data (copied to RAM: $1A00 - $1BFF)
  1704:  ; Screen size: 24-rows by 21-columns
  1705:          .res $AC00 - *
  1706:  MAZEDATA:
  1707:  SCORE   = * + $06
  1708:          .byte   $93, $83, $8F, $92, $85, $BA, $B0, $B0, $B0, $B0, $B0, $B0, $A0, $A0, $A0, $B0, $B2, $B0, $B0, $B0, $B0
  1709:          .byte   $37, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3D, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $38
  1710:          .byte   $39, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $39
  1711:          .byte   $39, $1E, $2F, $30, $1E, $2F, $2B, $2B, $30, $1E, $39, $1E, $2F, $2B, $2B, $30, $1E, $2F, $30, $1E, $39
  1712:          .byte   $39, $1F, $2D, $2E, $1E, $2D, $2C, $2C, $2E, $1E, $32, $1E, $2D, $2C, $2C, $2E, $1E, $2D, $2E, $1F, $39
  1713:          .byte   $39, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $39
  1714:          .byte   $39, $1E, $33, $34, $1E, $31, $1E, $33, $3A, $3A, $3D, $3A, $3A, $34, $1E, $31, $1E, $33, $34, $1E, $39
  1715:          .byte   $39, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $39
  1716:          .byte   $35, $3A, $3A, $38, $1E, $3B, $3A, $3A, $34, $20, $32, $20, $33, $3A, $3A, $3C, $1E, $37, $3A, $3A, $36
  1717:          .byte   $20, $20, $20, $39, $1E, $39, $20, $20, $20, $20, $20, $20, $20, $20, $20, $39, $1E, $39, $20, $20, $20
  1718:          .byte   $3A, $3A, $3A, $36, $1E, $32, $20, $37, $3A, $29, $C5, $2A, $3A, $38, $20, $32, $1E, $35, $3A, $3A, $3A
  1719:          .byte   $20, $20, $20, $20, $1E, $20, $20, $39, $20, $20, $20, $20, $20, $39, $20, $20, $1E, $20, $20, $20, $20
  1720:          .byte   $3A, $3A, $3A, $38, $1E, $31, $20, $35, $3A, $3A, $3A, $3A, $3A, $36, $20, $31, $1E, $37, $3A, $3A, $3A
  1721:          .byte   $20, $20, $20, $39, $1E, $39, $20, $20, $20, $20, $20, $20, $20, $20, $20, $39, $1E, $39, $20, $20, $20
  1722:          .byte   $37, $3A, $3A, $36, $1E, $32, $20, $33, $3A, $3A, $3D, $3A, $3A, $34, $20, $32, $1E, $35, $3A, $3A, $38
  1723:          .byte   $39, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $39
  1724:          .byte   $39, $1E, $33, $38, $1E, $33, $3A, $3A, $34, $1E, $32, $1E, $33, $3A, $3A, $34, $1E, $37, $34, $1E, $39
  1725:          .byte   $39, $1F, $1E, $39, $1E, $1E, $1E, $1E, $1E, $1E, $20, $1E, $1E, $1E, $1E, $1E, $1E, $39, $1E, $1F, $39
  1726:          .byte   $3B, $34, $1E, $32, $1E, $31, $1E, $33, $3A, $3A, $3D, $3A, $3A, $34, $1E, $31, $1E, $32, $1E, $33, $3C
  1727:          .byte   $39, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $39, $1E, $1E, $1E, $1E, $39
  1728:          .byte   $39, $1E, $33, $3A, $3A, $3E, $3A, $3A, $34, $1E, $32, $1E, $33, $3A, $3A, $3E, $3A, $3A, $34, $1E, $39
  1729:          .byte   $39, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $1E, $39
  1730:          .byte   $35, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $3A, $36
  1731:  BANNERMSG:      ; ©2008 RHURST  F1START
  1732:          .byte   $3F, $B2, $B0, $B0, $B8, $A0, $92, $88, $95, $92, $93, $94, $A0, $A0, $00, $01, $93, $94, $81, $92, $94
  1733:  FRUITSCORE:
  1734:          .byte   $01, $03, $05, $07, $0A, $14, $1E, $32
  1735:  ;
  1736:  ;*********************************************************************
  1737:  ; Custom character data (copied to RAM: $1C00 - $1DFF)
  1738:          .assert * = $AE00, error, "Graphics not at $AE00"
  1739:          .byte   $FF, $EA, $EF, $EF, $EB, $EF, $EF, $FF  ; @ [F - then sprite #0
  1740:          .byte   $FC, $EC, $EC, $EC, $EC, $EC, $EC, $FC  ; A  1] - then sprite #0
  1741:          .byte   $38, $7C, $FE, $92, $FE, $FE, $FE, $AA  ; B sprite #1 - red
  1742:          .byte   $00, $00, $00, $00, $00, $00, $00, $00  ; C
  1743:          .byte   $38, $7C, $FE, $92, $FE, $FE, $FE, $AA  ; D sprite #2 - green
  1744:          .byte   $00, $00, $00, $00, $00, $00, $00, $00  ; E
  1745:          .byte   $38, $7C, $FE, $92, $FE, $FE, $FE, $AA  ; F sprite #3 - cyan
  1746:          .byte   $00, $00, $00, $00, $00, $00, $00, $00  ; G
  1747:          .byte   $38, $7C, $FE, $92, $FE, $FE, $FE, $AA  ; H sprite #4 - yellow
  1748:          .byte   $00, $00, $00, $00, $00, $00, $00, $00  ; I
  1749:  ;
  1750:  QUIKMANCLR:     ; yellow
  1751:          .byte   $07
  1752:  MONSTERCLR:     ; red, green, cyan, yellow
  1753:          .byte   $02, $05, $03, $07
  1754:  FRUIT:          ; cherry, strawberry, 2-peach, 2-apple, 2-pineapple, 2-tbird, 2-bell, key
  1755:          .byte   $21, $22, $23, $23, $24, $24, $25, $25, $26, $26, $27, $27, $28
  1756:  FRUITCLR:       ; red, red, 2-yellow, 2-red, 2-green, 2-magenta, 2-yellow, cyan
  1757:          .byte   $02, $02, $07, $07, $02, $02, $05, $05, $04, $04, $07, $07, $03
  1758:  ;
  1759:  ; resume graphic character data
  1760:          .res $AE70 - *
  1761:          .byte   $00, $38, $7C, $54, $7C, $7C, $54, $00  ; N small ghost
  1762:          .byte   $1C, $3E, $7F, $64, $7F, $7F, $7F, $55  ; O ghost right
  1763:          .byte   $1C, $3E, $7F, $7F, $49, $7F, $7F, $55  ; P ghost down
  1764:          .byte   $38, $7C, $FE, $26, $FE, $FE, $FE, $AA  ; Q ghost left
  1765:          .byte   $38, $7C, $FE, $FE, $FE, $FE, $FE, $AA  ; R ghost up
  1766:          .byte   $38, $7C, $FE, $92, $FE, $82, $FE, $AA  ; S ghost caged
  1767:          .byte   $38, $7C, $FE, $92, $FE, $82, $FE, $54  ; T ghost fleeing
  1768:          .byte   $3C, $7E, $BD, $FF, $BD, $C3, $7E, $3C  ; U smiley
  1769:          .byte   $3C, $7E, $FF, $FF, $FF, $FF, $7E, $3C  ; V pacman closed
  1770:          .byte   $3E, $7C, $F8, $F0, $F0, $F8, $7C, $3E  ; W pacman right
  1771:          .byte   $3C, $7E, $FF, $FF, $E7, $C3, $81, $00  ; X pacman down
  1772:          .byte   $7C, $3E, $1F, $0F, $0F, $1F, $3E, $7C  ; Y pacman left
  1773:          .byte   $00, $81, $C3, $E7, $FF, $FF, $7E, $3C  ; Z pacman up
  1774:          .byte   $00, $10, $10, $6C, $10, $10, $00, $00  ; [ explosion
  1775:          .byte   $10, $44, $28, $C6, $28, $44, $10, $00  ; # smoke
  1776:          .byte   $92, $44, $00, $82, $00, $44, $92, $00  ; ] dust
  1777:          .byte   $00, $00, $00, $18, $18, $00, $00, $00  ; ^ dot
  1778:          .byte   $00, $3C, $7E, $7E, $7E, $7E, $3C, $00  ; <- powerpill (animated)
  1779:          .byte   $00, $00, $00, $00, $00, $00, $00, $00  ;$20 empty space
  1780:          .byte   $04, $08, $18, $24, $62, $F7, $F2, $60  ; ! cherry
  1781:          .byte   $10, $7C, $FE, $AA, $D6, $AA, $54, $28  ; " strawberry
  1782:          .byte   $20, $10, $7C, $FE, $FE, $FE, $7C, $38  ; # peach
  1783:          .byte   $08, $10, $7C, $FE, $FE, $FE, $7C, $28  ; $ apple
  1784:          .byte   $08, $10, $38, $38, $7C, $FE, $FE, $6C  ; % pear
  1785:          .byte   $10, $30, $92, $FE, $7C, $38, $10, $28  ; & tbird
  1786:          .byte   $10, $38, $7C, $7C, $7C, $7C, $FE, $10  ; ' bell
  1787:          .byte   $18, $24, $18, $08, $08, $18, $08, $18  ; ( key
  1788:          .byte   $00, $FF, $01, $01, $01, $01, $FE, $00  ; ) doorway east
  1789:          .byte   $00, $FF, $80, $80, $80, $80, $7F, $00  ; * doorway west
  1790:          .byte   $00, $FF, $00, $00, $00, $00, $00, $00  ; + maze wall h-top
  1791:          .byte   $00, $00, $00, $00, $00, $00, $FF, $00  ; , maze wall h-bottom
  1792:          .byte   $40, $40, $40, $40, $40, $20, $1F, $00  ; - maze wall s-w corner
  1793:          .byte   $02, $02, $02, $02, $02, $04, $F8, $00  ; . maze wall s-e corner
  1794:          .byte   $00, $1F, $20, $40, $40, $40, $40, $40  ; / maze wall n-w corner
  1795:          .byte   $00, $F8, $04, $02, $02, $02, $02, $02  ; 0 maze wall n-e corner
  1796:          .byte   $00, $18, $24, $42, $42, $42, $42, $42  ; 1 maze wall north
  1797:          .byte   $42, $42, $42, $42, $42, $24, $18, $00  ; 2 maze wall south
  1798:          .byte   $00, $1F, $20, $40, $40, $20, $1F, $00  ; 3 maze wall west
  1799:          .byte   $00, $F8, $04, $02, $02, $04, $F8, $00  ; 4 maze wall east
  1800:          .byte   $42, $41, $40, $40, $40, $20, $1F, $00  ; 5 maze wall s-w elbow
  1801:          .byte   $42, $82, $02, $02, $02, $04, $F8, $00  ; 6 maze wall s-e elbow
  1802:          .byte   $00, $1F, $20, $40, $40, $40, $41, $42  ; 7 maze wall n-w elbow
  1803:          .byte   $00, $F8, $04, $02, $02, $02, $82, $42  ; 8 maze wall n-e elbow
  1804:          .byte   $42, $42, $42, $42, $42, $42, $42, $42  ; 9 maze wall vertical
  1805:          .byte   $00, $FF, $00, $00, $00, $00, $FF, $00  ; : maze wall horizontal
  1806:          .byte   $42, $41, $40, $40, $40, $40, $41, $42  ; ; maze wall west tee
  1807:          .byte   $42, $82, $02, $02, $02, $02, $82, $42  ; < maze wall east tee
  1808:          .byte   $00, $FF, $00, $00, $00, $00, $81, $42  ; = maze wall north tee
  1809:          .byte   $42, $81, $00, $00, $00, $00, $FF, $00  ; > maze wall south tee
  1810:          .byte   $3C, $42, $99, $A1, $A1, $99, $42, $3C  ; ? (C)copyright symbol
Valid XHTML 1.0 Strict
quikman-rom.html; generated on Fri Dec 19 21:02:30 2008 by ca65html
uz@cc65.org