|
CALL L1363 ; Call Speech Routine (phrase)
LD HL,0BE03h ; Get MODE Register
SET 2,(HL) ; Enter COMBINE MODE
LD B,006h ; Loop = 6
LD HL,0BE31h ; Point to combine work area
XOR A ; Clear COMBINE ITEMS first
L0EC3: LD (HL),A ; Clear work area
INC HL ; Point to next location
DJNZ L0EC3 ; Loop until work area cleared
;----------------------------------------------------
; Clear keyboard buffer then return
;----------------------------------------------------
L0EC7: LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
RET ; Return
;----------------------------------------------------
; Combining Items
;----------------------------------------------------
L0ECD: LD HL,0BE0Bh ; Check Keyboard Buffer
RES 0,(HL) ; Clear keyboard buffer
CALL L0F50 ; Point to row based on scene (C9A5)
INC HL ; HL = C9A5+8*x
LD A,(HL) ;
LD (0BE30h),A ;
INC HL ; HL =
LD B,001h ;
L0EDD: LD A,(0BE0Ah) ; Get Keyboard Character
AND 01Fh ; Get item number
CP (HL) ; Is item in table?
JR Z,L0F04 ; No, so skip ahead
LD A,(0BE30h) ;
CP B ;
JR Z,L0EEF ;
INC HL ;
INC B ;
JR L0EDD ;
L0EEF: CALL L0F50 ; Get HL pointer to row (C9A5)
LD A,(HL) ; HL = C9A5+8*x
LD (0BC81h),A ;
LD HL,0BE03h ; Get MODE Register
SET 0,(HL) ; Reset Main Loop
RES 2,(HL) ; Cancel COMBINE MODE
LD DE,00032h ; Phrase="You Don't Have That Choice Here (%)"
CALL L1363 ; Call Speech Routine (phrase)
RET ; Return
;----------------------------------------------------
; Speak KeyPress Item
;----------------------------------------------------
L0F04: LD A,(0BE0Ah) ; Get Keyboard Character
SUB 041h ; Subtract 65d
LD E,A ; DE = Character Value
LD D,000h ; DE = Character Value
LD HL,08001h ; HL = Voice Message Table
ADD HL,DE ; Index to Key Message
EX DE,HL ; DE = Phrase for KeyPress
CALL L1363 ; Call Speech Routine (phrase)
LD HL,0BE31h
LD A,B
DEC A
JR Z,L0F20 ;
ADD A,L
LD L,A
JR NC,L0F20 ;
INC H
L0F20: LD A,(HL)
CP 001h ; Has Item been picked up?
RET Z
INC (HL)
LD HL,0BE31h
LD A,(0BE30h)
LD B,A
XOR A
L0F2D: CP (HL)
RET Z
INC HL
DJNZ L0F2D
LD HL,0BE03h
RES 2,(HL)
LD A,(IX+00Bh)
AND 007h
ADD A,01Ah
ADD A,040h
LD (0BE0Ah),A
SUB 040h
CALL L11DF ; Point to Item in Inventory
SET 1,(HL)
LD HL,0BE0Bh ; Get Keyboard Buffer
SET 0,(HL)
RET
;----------------------------------------------------
; Unknown
;----------------------------------------------------
; IX+0Bh = Scene Index + something
; Return HL = Address to row of 8 zeros
;----------------------------------------------------
L0F50: LD HL,LC9A5 ; Point to start of table
LD A,(IX+00Bh) ;
AND 007h ;
CP 001h ;
RET Z ;
DEC A ;
LD B,A ; B = Loop
LD DE,00008h ; Point to next row
L0F60: ADD HL,DE ; Add to pointer
DJNZ L0F60 ; Loop until correct row is found
RET ; Return
;----------------------------------------------------
; Check if player has item
;----------------------------------------------------
L0F64: LD A,(0BE0Ah) ; Get Keyboard Character
AND 01Fh ; Get item number
LD (0BE26h),A ; Save item selected
CALL L11DF ; Point to Item in Inventory
BIT 1,(HL) ; Check if item is in inventory
JR NZ,L0F79 ; Item is held so jump ahead
CALL L120F ; Tell Player they don't have said item
JP L0FF8 ; Skip to end
;----------------------------------------------------
; Check if Item can be Swapped
;----------------------------------------------------
L0F79: CALL L11E7 ; Go to last byte of swap data
LD A,00Bh ; Point to last byte
ADD A,L ; Point to last byte
LD L,A ; Point to last byte
JR NC,L0F83 ; Point to last byte
INC H ; Adjust pointer to end of row
L0F83: LD B,006h ; Loop = 6 possible swap senarios
L0F85: LD A,(HL) ; Check byte for swap data
CP 000h ; Is there swap data here?
DEC HL ; Data empty so skip next byte
PUSH HL ; Save swap pointer
JR Z,L0F95 ; No data, so jump ahead and continue loop
;----------------------------------------------------
; Swap is possible, check if correct item was used
;----------------------------------------------------
LD A,(HL) ; Get required item data
AND 01Fh ; Get required item value
LD HL,0BE26h ; Point to item selected
CP (HL) ; Is selected item the reqired item needed?
JR Z,L0F9F ; Yes, so jump ahead and allow swap
L0F95: POP HL ; Get swap pointer
DEC HL ; Go to next swap senario
DJNZ L0F85 ; Loop until all 6 swap senarios are checked
;----------------------------------------------------
; Incorrect item, item has no use here
;----------------------------------------------------
CALL L11FA ; Tell player that item won't work here
JP L0FF8 ; Clear keyboard buffer and return
;----------------------------------------------------
; Prepare to swap Items
;----------------------------------------------------
L0F9F: POP HL ; Get swap pointer
BIT 6,(HL)
JR Z,L0FD5
BIT 7,(HL)
PUSH HL ; Save swap pointer
JR Z,L0FB6
LD A,(0BE26h) ; Get item selected
CP 01Bh ; Is it one of 26 items
JR C,L0FC8 ; No, it's more than 26
CALL L102A ; Drop combined items
POP HL ; Get swap pointer
JR L0FD5
L0FB6: LD A,(0BE26h) ; Get item selected
CP 01Bh
JR C,L0FC3 ; Item is only dropped
CALL L0FFE
POP HL
JR L0FD5
L0FC3: CALL L11C7 ; Remove item from inventory
JR L0FCB
L0FC8: CALL L11D2 ; Mark item as used
L0FCB: LD A,(0BE26h) ; Get item selected
CALL L1224 ; Get Item's Weight
CALL L1230 ; Decrease Strength with item weight
POP HL
L0FD5: BIT 5,(HL)
PUSH HL
JR Z,L0FEB
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Isolate item number
LD HL,0BCC0h
ADD A,L
LD L,A
JR NC,L0FE7
INC H
L0FE7: RES 0,(HL)
SET 1,(HL)
L0FEB: POP HL
INC HL
LD A,(HL)
LD (0BC81h),A
LD HL,0BE03h
SET 4,(HL) ; Set Audio Track 2
SET 0,(HL)
L0FF8: LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
RET ; Return
;----------------------------------------------------
; Unknown
;----------------------------------------------------
L0FFE: LD HL,0C99Eh ;
LD A,(IX+00Bh) ;
AND 007h ;
SLA A ;
SLA A
SLA A
ADD A,L
LD L,A
JR NC,L1011
INC H
L1011: LD A,(HL)
LD B,A
INC HL
L1014: LD A,(HL)
PUSH HL
PUSH AF
CALL L11DF ; Point to Item in Inventory
RES 1,(HL)
SET 0,(HL)
POP AF
CALL L1224 ; Get Item's Weight
CALL L1230 ; Decrease Strength with item weight
POP HL
INC HL
DJNZ L1014
RET
;----------------------------------------------------
; Drop Multiple Items that are combined
;----------------------------------------------------
L102A: LD HL,0C99Eh ; Point to Item Table
LD A,(IX+00Bh) ; Get row, 8 bytes per row
AND 007h ; Row Number between 0-7
SLA A ; multiply by 2 (*2)
SLA A ; multiply by 2 (*4)
SLA A ; multiply by 2 (*8)
ADD A,L ; Index into table
LD L,A ; Index into correct row
JR NC,L103D ; Check carry
INC H ; Index into row
;----------------------------------------------------
; Drop all Items that are in table
;----------------------------------------------------
L103D: LD A,(HL) ; Get Number of items from table
LD B,A ; B = Number of items to drop
INC HL ; Point to item in table
L1040: LD A,(HL) ; Get item number from table
PUSH HL
PUSH AF
CALL L11DF ; Point to Item in Inventory
RES 0,(HL)
RES 1,(HL) ; Drop item from inventory
SET 2,(HL)
POP AF
CALL L1224 ; Get Item's Weight
CALL L1230 ; Decrease Strength with item weight
POP HL
INC HL ; Next item in table
DJNZ 01040h ; Loop until all items dropped
RET ; Return
;----------------------------------------------------
; Using or Picking up Items
;----------------------------------------------------
L1058: LD A,(0BE0Ah) ; Get Keyboard Character
AND 01Fh ; Isolate item number
LD HL,0BE26h ; Temp save location
LD (HL),A ; Save item selected
LD A,(IX+00Ah) ; Check item located in room
AND 01Fh ; Isolate item number
CP (HL) ; Is item in room to be picked up?
JR NZ,L109E ; No, so check if item is being used
;----------------------------------------------------
; Picking up an item from a room
;----------------------------------------------------
BIT 0,(IX+00Dh) ; Can we pick up items here?
JR Z,L1095 ; No, so skip ahead
CALL L123C ; HL = Health Pointer
PUSH HL ; Save Health Pointer
;----------------------------------------------------
; Check if player is strong enough to take item
;----------------------------------------------------
LD A,(0BE26h) ; Get item selected
CALL L1224 ; Get Item's Weight
LD HL,0BCE1h ; Get Strength
ADD A,(HL) ; Decrease player's strength
LD (0BE18h),A ; Save new strength temporarily
POP HL ; Point to Health
LD A,(HL) ; Get Health
LD HL,0BE18h ; Point to new strength
CP (HL) ; Are they strong enough to pick up item?
JP C,L11A6 ; No, the player must drop something
LD A,(0BE18h) ; Get new stregth
LD (0BCE1h),A ; Save player's adjusted strength
LD A,(0BE26h) ; Get item selected
CALL L11BF ; Put item in inventory
L1095: LD A,(IX+00Ch) ; Get next scene
LD (0BC81h),A ; Store Scene Index
JP L1199 ; Update then return
;----------------------------------------------------
; Use an Item to get another Item
;----------------------------------------------------
L109E: LD A,(0BE26h) ; Get item selected
CALL L11DF ; Point to Item in Inventory
BIT 1,(HL) ; Is item in inventory?
JR NZ,L10AE ; Yes, so skip ahead
CALL L120F ; Tell Player they don't have said item
JP L11A0 ; Clear Keyboard Buffer and Return
;----------------------------------------------------
; Get Item Swap Properties from table
;----------------------------------------------------
L10AE: LD HL,LC743 ; Start of Item Swap table
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Get item number
CP 001h ; Is it the first item?
JR Z,L10C2 ; Yes, so row is set
DEC A ; Subtract 1
LD B,A ; Loop = Item row
LD DE,00006h ; Skip row (6 bytes)
L10BF: ADD HL,DE ; Point to next row
L10C0: DJNZ L10BF ; Loop until Item Use row found
;----------------------------------------------------
; Check if Item can be Swapped
;----------------------------------------------------
L10C2: LD A,005h ; Go to last byte of swap data
ADD A,L ; Point to last byte
LD L,A ; Point to last byte
JR NC,L10C9 ; Point to last byte
INC H ; Point to last byte
L10C9: LD B,003h ; Loop = 3 possible swap senarios
L10CB: LD A,(HL) ; Check byte for swap data
CP 000h ; Is there swap data here?
JR NZ,L10D4 ; Yes, so skip ahead and check for item match
DEC HL ; Data empty so skip next byte
PUSH HL ; Save swap pointer
JR L10DF ; Jump ahead and continue loop
;----------------------------------------------------
; Swap is possible, check if correct item was used
;----------------------------------------------------
L10D4: DEC HL ; Point to required item data
LD A,(HL) ; Get required item data
AND 01Fh ; Get required item value
PUSH HL ; Save swap pointer
LD HL,0BE26h ; Point to item selected
CP (HL) ; Is selected item the reqired item needed?
JR Z,L10E9 ; Yes, so jump ahead and allow swap
L10DF: POP HL ; Get swap pointer
DEC HL ; Go to next swap senario
DJNZ L10CB ; Loop until all 3 swap senarios are checked
;----------------------------------------------------
; Incorrect item, item has no use here
;----------------------------------------------------
CALL L11FA ; Tell player that item won't work here
JP L11A0 ; Clear Keyboard Buffer and Return
;----------------------------------------------------
; Prepare to swap Items
;----------------------------------------------------
L10E9: POP HL ; Get swap pointer
BIT 6,(HL) ; Is it a 1-for-1 swap?
JP Z,L115E ; Yes, so jump ahead
BIT 5,(HL) ; Is it a 2-for-1 swap?
JR NZ,L110E ; Yes, so jump ahead
PUSH HL ; Save swap pointer
CALL L11C7 ; Remove item from inventory
LD A,(0BE26h) ; Get item selected
CALL L1224 ; Get Item's Weight
CALL L1230 ; Decrease Strength with item weight
POP HL ; Get swap pointer
BIT 7,(HL) ; Does the item expire after use?
JP Z,L1194 ; No, so skip ahead and play successful swap scene
;----------------------------------------------------
; Mark item as used, play successful scene
;----------------------------------------------------
PUSH HL ; Save swap pointer
CALL L11D2 ; Mark item as used
POP HL ; Get swap pointer
JP L1194 ; Play successful swap scene
;----------------------------------------------------
;
;----------------------------------------------------
L110E: PUSH HL ; Save swap pointer
LD A,(0BE26h) ; Get item selected
CALL L1224 ; Get Item's Weight
LD (0BE18h),A
LD A,(0BCE1h)
LD HL,0BE18h
SBC A,(HL)
LD (0BE18h),A
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Isolate item number
CALL L1224 ; Get Item's Weight
LD HL,0BE18h ; Point to player strength
ADD A,(HL) ; Add weight to player's strength
LD (0BE18h),A ; Save player's strength temporarily
CALL L123C ; HL = Health Pointer
LD A,(HL) ; Get Health
LD HL,0BE18h ; Point to new strength
CP (HL) ; Are they strong enough to pick up item?
JR NC,L113F ; Yes, so skip ahead
POP HL ; Get swap pointer
JP L11A6 ; Tell player to drop something before picking up
L113F: LD A,(0BE18h)
LD (0BCE1h),A
CALL L11C7 ; Remove item from inventory
POP HL
BIT 7,(HL)
JR Z,L1152
PUSH HL
CALL L11D2 ; Mark item as used
POP HL ; Get swap pointer
;----------------------------------------------------
; Put new item into inventory
;----------------------------------------------------
L1152: PUSH HL ; Save swap pointer
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Isolate item number
CALL L11BF ; Put item in inventory
POP HL ; Get swap pointer
JR L1194 ; Play successful swap scene
;----------------------------------------------------
;
;----------------------------------------------------
L115E: BIT 5,(HL)
JR Z,L1194
PUSH HL ; Save swap pointer
LD A,(0BCE1h) ; Get Strength
LD (0BE18h),A ; Save Strength temporarily
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Isolate item number
CALL L1224 ; Get Item's Weight
LD HL,0BE18h ; Point to temporary strength
ADD A,(HL) ; Add to player's strength
LD (0BE18h),A ; Save calculated strength
CALL L123C ; HL = Health Pointer
LD A,(HL)
LD HL,0BE18h
CP (HL)
JR NC,L1185
POP HL
JR L11A6 ; Tell player to drop something before picking up
L1185: LD A,(0BE18h)
LD (0BCE1h),A
LD A,(IX+00Ah)
AND 01Fh
CALL L11BF ; Put item in inventory
POP HL ; Get swap pointer
;----------------------------------------------------
; Play successful swap scene
;----------------------------------------------------
L1194: INC HL ; Point to swap scene byte
LD A,(HL) ; Get swap scene
LD (0BC81h),A ; Store new Scene Index
L1199: LD HL,0BE03h ; Get MODE Register
SET 0,(HL) ;
SET 4,(HL) ; Set Audio Track 2
L11A0: LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
RET ; Return
;----------------------------------------------------
; Tell player to drop something before picking up
;----------------------------------------------------
L11A6: CALL L136C ; Clear Speech Buffer
LD DE,00039h ; Phrase = "(%) You Must Drop Something To Get"
CALL L1383 ; Get Phrase from Table
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Get item number
LD E,A ; Turn item number into phrase
LD D,080h ; Phrase = Item Name
CALL L1383 ; Get Phrase from Table
CALL L21C1 ; Command Speech Chip to speak buffer
JR L11A0 ; Clear Keyboard Buffer and Return
;----------------------------------------------------
; Put item in inventory
;----------------------------------------------------
L11BF: CALL L11DF ; Point to Item in Inventory
SET 1,(HL) ; Put item into inventory
RES 0,(HL) ; ??
RET ; Return
;----------------------------------------------------
; Remove item from inventory
;----------------------------------------------------
L11C7: LD A,(0BE26h) ; Get item selected
CALL L11DF ; Point to Item in Inventory
RES 1,(HL) ; Remove item from inventory
SET 0,(HL) ; ??
RET ; Return
;----------------------------------------------------
; Mark item as used
;----------------------------------------------------
L11D2: LD A,(0BE26h) ; Get item selected
CALL L11DF ; Point to Item in Inventory
SET 2,(HL) ; Mark item as used
RES 0,(HL) ; ??
RES 1,(HL) ; Remove item from inventory
RET ; Return
;----------------------------------------------------
; Point to Item in Inventory
;----------------------------------------------------
; A = Item Number
; Return: HL = BC9F + A
;----------------------------------------------------
L11DF: LD HL,0BC9Fh ;
ADD A,L ;
LD L,A ;
RET NC ;
INC H ;
RET ;
;----------------------------------------------------
; Get row data from C7DF ROM
;----------------------------------------------------
; Return HL = Pointer to row data
;----------------------------------------------------
L11E7: LD HL,LC7DF ; Get start of table
LD A,(IX+00Ah) ; Get item located in room
AND 01Fh ; Get item number
CP 000h ; Is there an item in the room?
RET Z ; No item in room so leave
LD B,A ; Loop = Item row number
LD DE,0000Ch ; Skip one row of data
L11F6: ADD HL,DE ; Go to next row
DJNZ L11F6 ; Loop until correct row is reached
RET ; Return
;----------------------------------------------------
; Tell player that item won't work here
;----------------------------------------------------
L11FA: CALL L136C ; Clear Speech Buffer
LD A,(0BE26h) ; Get item trying to be used
L1200: LD E,A ; Make item into word
LD D,080h ; Setup word to speak
CALL L1383 ; Get Phrase from Table
LD DE,00031h ; Phrase = "Won't Work Here (%)"
CALL L1383 ; Get Phrase from Table
JP L21C1 ; Command Speech Chip to speak buffer
;----------------------------------------------------
; Tell player they don't have said item
;----------------------------------------------------
L120F: CALL L136C ; Clear Speech Buffer
LD DE,00030h ; Phrase = "Sorry (%) You Don't Have"
CALL L1383 ; Get Phrase from Table
LD A,(0BE26h) ; Get Item trying to be used
LD E,A ; Make item into word
LD D,080h ; Set up Word to speak
CALL L1383 ; Get Phrase from Table
JP L21C1 ; Command Speech Chip to speak buffer
;----------------------------------------------------
; Get Item's Weight
;----------------------------------------------------
; A = Item Number (1-26)
;----------------------------------------------------
; Return A = Item Weight (0-7)
;----------------------------------------------------
L1224: LD HL,0C95Eh ; Point to Item Property Table
ADD A,L ; Add item pointer
LD L,A ; Add item pointer
JR NC,L122C ; Jump on overflow
INC H ; Add item pointer
L122C: LD A,(HL) ; Get item property
AND 007h ; Get item's weight
RET ; Return
;----------------------------------------------------
; Decrease Strength with item weight
;----------------------------------------------------
; A = Item Weight (0-7)
;----------------------------------------------------
L1230: LD HL,0BE18h ; Item Weight
LD (HL),A ; Store Item Weight
LD A,(0BCE1h) ; Get Strength
SBC A,(HL) ; Subtract Weight from Strength
LD (0BCE1h),A ; Save Strength
RET ; Return
;----------------------------------------------------
; Unknown
;----------------------------------------------------
; (BCE0) Health index
; Return HL Pointer to Health Value
;----------------------------------------------------
L123C: LD HL,0C97Eh ; Point to Health Table
LD A,(0BCE0h) ; A = Health setting
ADD A,L ; Add to pointer
LD L,A ; Point to table
RET NC ; Check carry
INC H ; Point to table
RET ; Return
org 01247h
;----------------------------------------------------
; Initialize Speech Chip
;----------------------------------------------------
L1247: LD (0A60Ah),HL ; Erase any pending data
LD (0A608h),HL ; Erase any pending data
LD A,080h ; Control Code 80?
OUT (003h),A ; Set Speech Chip Register3
LD A,0C0h ; Control Code C0?
OUT (000h),A ; Set Speech Chip Register0
LD A,07Bh ; Control Code 7B?
OUT (003h),A ; Set Speech Chip Register3
LD A,0E6h ; Initial Filter Frequency (0E6h)
OUT (004h),A ; Set Speech Chip Register4
LD A,090h ; Control Code 90?
OUT (002h),A ; Set Speech Chip Register2
LD A,046h ; Initial Inflection (046h)
OUT (001h),A ; Set Speech Chip Register1
XOR A ; Control Code = PAUSE (00h)
OUT (000h),A ; Set Speech Chip Register0
RET ; Return
;----------------------------------------------------
; Interrupt function to send data to Speech Chip
;----------------------------------------------------
; A60A is incremented here in the interrupt
; Once A60A is equal to A608 then we're finished
;----------------------------------------------------
L1269: LD A,(0A608h) ; Get number of Control Codes to be sent
LD HL,(0A60Ah) ; Get number of codes that have already been sent
CP L ; Are there more control codes to send?
JR C,L1288 ; No control codes remaining, skip ahead
JR Z,L1288 ; No control codes remaining, skip ahead
;----------------------------------------------------
; Send bytes to Speech Chip registers
;----------------------------------------------------
; OUT (004h) <- (A000) Filter Frequency (ie E7h)
; OUT (003h) <- (A100) <AA> Punctuation Control Codes (ie 54h,74h)
; OUT (002h) <- (A200) <RI> Character Control Codes (ie A8h)
; OUT (001h) <- (A300) <IO> (ie 68h)
; OUT (000h) <- (A400) <OUT> Phoneme Codes (ie D,AH1,UH1)
;----------------------------------------------------
LD C,004h ; Output to Speech Registers 4,3,2,1,0
LD B,005h ; Loop = 5 registers
L1278: LD A,(HL) ; Get character/code from message
OUT (C),A ; Send character/code to Speech register
INC H ; Next character/code (A000,A100,A200,...)
DEC C ; Next register (port)
DJNZ L1278 ; Loop until all registers are written
LD A,H ; Get register
SUB 005h ; Go back to first register (A0xx)
LD H,A ; Point to byte just sent
INC HL ; Increment to next byte
LD (0A60Ah),HL ; Save number of bytes sent
RET ; Return
;----------------------------------------------------
; Data packet sent so turn off Speech Chip interrupt
;----------------------------------------------------
L1288: LD A,080h ; Raise Control bit in Register3
OUT (003h),A ; Send to Speech Chip Register3
XOR A ; Control Code 00?
OUT (000h),A ; Send to Speech Chip Register0
LD A,070h ; Lower Control bit in Register3
OUT (003h),A ; Send to Speech Chip Register3
XOR A ; Control Code 00?
OUT (000h),A ; Send to Speech Chip Register0
RET ; Return
;----------------------------------------------------
; Phrase and Word Indexes
;----------------------------------------------------
L1297: .word 0686Bh ; Phrase Index
L1299: .word 05C7Bh ; Word Index
;----------------------------------------------------
; Table of 1 of 4 Random Phrases
;----------------------------------------------------
L129B: DB 000h, 001h, 002h, 003h ; Type in Name
L129F: DB 004h, 005h, 006h, 007h ; Name Too Long
L12A3: DB 008h, 009h, 00Ah, 00Bh ; Did I Say Your Name Right?
L12A7: DB 00Ch, 00Dh, 00Dh, 00Fh ; Just Letters
L12AB: DB 010h, 011h, 012h, 013h ; Enter Yes or No
L12AF: DB 014h, 017h, 016h, 015h ; Act lively
L12B3: DB 018h, 019h, 01Ah, 01Bh ; Retype in Name
L12B7: DB 01Ch, 01Dh, 01Eh, 01Fh ; Empty-Handed
L12BB: DB 02Ah, 02Bh, 02Ch, 02Ch ; No Pointer
L12BF: DB 02Dh, 02Dh, 02Eh, 02Fh ; Try A Different Spelling
L12C3: DB 032h, 03Dh, 03Eh, 01Bh ; Bad Choice
L12C7: DB 066h, 067h, 068h, 08Fh ; Name sounds French
L12CB: DB 05Eh, 09Ah, 09Bh, 09Ch ; Nice To Have You Here Again (#)
;----------------------------------------------------
; Subtract values for Speaking Score
;----------------------------------------------------
L12CF: DB 098h, 096h, 080h ; 10,000,000
DB
00Fh, 042h, 040h ; 1,000,000
DB
001h, 086h, 0A0h ; 100,000
DB
000h, 027h, 010h ; 10,000
DB
000h, 003h, 0E8h ; 1,000
DB
000h, 000h, 064h ; 100
DB
000h, 000h, 00Ah ; 10
DB
000h, 000h, 001h ; 1
;----------------------------------------------------
; Speak Score "Teen" Word Pointer Table
;----------------------------------------------------
L12E7: DB 02Bh ; "Thir-"
DB
004h ; "Four-"
DB
02Ch ; "Fif-"
DB
006h ; "Six-"
DB
007h ; "Seven-"
DB
008h ; "Eight-"
DB
009h ; "Nine-"
;----------------------------------------------------
; Speak Score "Tens" Word Pointer Table
;----------------------------------------------------
L12EE: DB 02Eh ; "Twen-"
DB
02Bh ; "Thir-"
DB
004h ; "Four-"
DB
02Ch ; "Fif-"
DB
006h ; "Six-"
DB
007h ; "Seven-"
DB
008h ; "Eight-"
DB
009h ; "Nine-"
;----------------------------------------------------
; Speak Inventory
;----------------------------------------------------
; Count number of items in inventory
;----------------------------------------------------
L12F6: PUSH HL ; Save start of inventory
LD B,01Ah ; B = 26 items
LD DE,00000h ; DE = Number of items held (zero)
L12FC: BIT 1,(HL) ; Is item being held?
JR Z,L1302 ; Not held, so skip ahead
INC D ; D = D + 1, Count items
LD E,B ; E = Item Index
L1302: INC HL ; Check next item
DJNZ L12FC ; Loop until all items checked
POP HL ; Restore start of inventory
LD A,D ; A = Number of items held
OR A ; Is player empty-handed?
JR NZ,L1313 ; No, player has items so jump ahead
;----------------------------------------------------
; There are no items in inventory
;----------------------------------------------------
LD IY,012B7h ; Random Phrase = "Empty-Handed"
CALL L15EE ; Speak Random Phrase
JR L1362 ; Jump to end
L1313: CP 002h ; Does player have more than 1 item?
JR NC,L132F ; Yes, more than 1 item so jump ahead
;----------------------------------------------------
; Handle only one item in inventory
;----------------------------------------------------
CALL L136C ; Clear Speech Buffer
LD C,E ;
LD DE,00020h ; Phrase="(%) You Only Have"
CALL L1383 ; Get Phrase from Table
LD A,01Bh
SUB C
LD E,A
LD D,080h
CALL L1383 ; Get Phrase from Table
CALL L21C1 ; Command Speech Chip to speak buffer
JR L1362 ; Jump to end
;----------------------------------------------------
; Handle multiple items in inventory
;----------------------------------------------------
L132F: CALL L136C ; Clear Speech Buffer
LD C,D
LD DE,00021h ; Phrase="(%) You Now Have"
CALL L1363 ; Call Speech Routine (phrase)
LD B,01Ah ; Loop = 26 items
L133B: CALL L136C ; Clear Speech Buffer
BIT 1,(HL) ; Check if item is being held
JR Z,L135F ; Item not held so skip ahead
DEC C
JR NZ,L134B ; Skip the word AND if it's not the last item
LD DE,00059h ; Word="And"
CALL L13CF ; Speak One Word
L134B: LD A,01Bh ; Get item pointer
SUB B ; Point to correct item
LD E,A ; DE = item word
LD D,080h ; DE = item word (08001-0801B)
CALL L1383 ; Get Phrase from Table
LD DE,(0A641h) ; Get End of Speech Buffer
DEC DE ; Subtract last character
LD A,02Ch ; Character = ","
LD (DE),A ; Add comma
CALL L21C1 ; Command Speech Chip to speak buffer
L135F: INC HL ;
DJNZ L133B ;
L1362: RET ;
;----------------------------------------------------
; Speech Routine (Phrase)
;----------------------------------------------------
; DE = Phrase #
;----------------------------------------------------
L1363: CALL L136C ; Clear Speech Buffer
CALL L1383 ; Get Phrase from Table
JP L21C1 ; Command Speech Chip to speak buffer
;----------------------------------------------------
; Clear Speech Buffer
;----------------------------------------------------
L136C: PUSH IY ; Save IY (Random Number 0-3)
LD IY,0A001h ; Set End of Speech Buffer Pointer
LD (0A641h),IY ; Save End of Speech Buffer Pointer
LD A,020h ; First character is <space>
LD (0A000h),A ; Save first character in buffer
LD A,001h ; Set number of characters in buffer to 1
LD (0A614h),A ; Save number of characters in buffer
POP IY ; Restore IY (Random Number 0-3)
RET ; Return
;----------------------------------------------------
; Find Speech Phrase from table
;----------------------------------------------------
; DE = Phrase #
;----------------------------------------------------
L1383: PUSH HL ; Save HL Register
PUSH DE ; Save DE Register
PUSH BC ; Save BC Register
BIT 7,D ; Is DE > 8000h
LD HL,(01297h) ; Get Phrase Table 1
JR Z,L1390 ; No, so use Table 1
LD HL,(0C01Fh) ; DE > 8000h so get Phrase Table 2
L1390: CALL L1455 ; Check if Phrase # exists
JR C,L13C2 ; Phrase doesn't exist, jump to end
LD A,D ; A = D
AND 030h
SRL A
SRL A
SRL A
SRL A
LD C,A
;----------------------------------------------------
; HL = DE * 2 Add Phrase Index to Table
;----------------------------------------------------
ADD HL,DE ; Add Index to table
ADD HL,DE ; Add Index to table again
LD A,(HL)
INC HL
LD H,(HL)
LD L,A
;----------------------------------------------------
; Speak all words in the phrase
;----------------------------------------------------
LD B,(HL) ; B = Number of words in phrase
L13A8: INC HL
LD E,(HL)
INC HL
LD D,(HL)
CALL L13CF ; Speak One word
JR C,L13C2 ; Character Buffer Overflow error, so skip to end
DJNZ L13A8 ; Loop until all words spoken
LD A,C ; Get exclamation point
OR A ; Was there an exclamation point?
JR Z,L13C2 ; No, so skip to end
LD HL,01451h ; Point to inflection level codes
ADD HL,BC ; Index to proper level code
LD A,(HL) ; Get inflection level code
LD HL,(0A641h) ; Find end of speech buffer
DEC HL ; Subract one from end of speech buffer
LD (HL),A ; Put code on end of speech buffer
OR A ; C = Set
L13C2: POP BC ; Restore BC Register
POP DE ; Restore DE Register
POP HL ; Restore HL Register
RET ; Return
;----------------------------------------------------
; Speech Routine (Word)
;----------------------------------------------------
L13C6: CALL L136C ; Clear Speech Buffer
CALL L13CF ; Speak One Word
JP L21C1 ; Command Speech Chip to speak buffer
;----------------------------------------------------
; Speak One Word
; DE = Index to Word & Word Properties
;----------------------------------------------------
L13CF: PUSH HL ; Save HL Register
PUSH DE ; Save DE Register
PUSH BC ; Save BC Register
;----------------------------------------------------
; Check for Word Properties by looking at
; the bits in the Index to Word, DE
; DE = 0XXXX000
; ||||
; |||-
; |--- Inflection Level 0-3
; |
; ---- Plural
;----------------------------------------------------
LD A,D ; A = D
AND 078h ; Strip bits 01111000
SRL A ; Shift bits left -->
SRL A ; Shift bits left -->
SRL A ; Shift bits left -->
LD (0A6CFh),A ; Save Word Properties
BIT 7,D ; Determine whether to use Word Table 1 or 2
LD HL,(01299h) ; Get Pointer to Word Table 1 (HL)
JR Z,L13E8 ; Word Table 1 is selected so skip ahead
LD HL,(0C021h) ; Get Pointer to Word Table 2 (HL)
L13E8: CALL L1455 ; Check if word exists
JR C,L144A ; If word doesn't exist, jump ahead
;----------------------------------------------------
; Setup Indexes to the word
;----------------------------------------------------
ADD HL,DE ; Add Index to Table
ADD HL,DE ; Add Index to Table again
LD A,(HL) ; Pointer to start of word in table
INC HL ; Pointer to start of word in table
LD H,(HL) ; Pointer to start of word in table
LD L,A ; HL = Pointer to start of word
LD C,(HL) ; C = number of characters in word
LD A,(0A614h) ; Number of characters already in buffer
ADD A,014h ; Check for extra room (20 spaces)
JR C,L144E ; Character buffer overflow, skip ahead
ADD A,C ; Check for room to add word
JR C,L144E ; Character buffer overflow, skip ahead
LD B,000h ; BC = Number of characters
INC HL ; HL = Point to word characters
LD DE,(0A641h) ; Get Speech Character Buffer start
SCF ; Set carry
LD A,(0A6CFh) ; Get Word Properties
BIT 0,A ; Check for Inflection1
JR NZ,L1411 ; Yes, do Inflection1
LDIR ; Copy all characters into Buffer
JR L141F ; Check if word is plural (suffixes)
;----------------------------------------------------
; Process Word Properties
;----------------------------------------------------
L1411: LDI ; LDI Load and Increment [DE]=[HL],HL=HL+1,#
DEC DE ;
PUSH AF ;
LD A,(DE) ;
CP 02Fh ; Check for ending marker "/"
JR Z,L141B ;
INC DE ;
L141B: POP AF ;
JP PE,L1411 ;
;----------------------------------------------------
; Check for plural
;----------------------------------------------------
L141F: EX DE,HL ;
LD A,(0A6CFh) ; Get Word Properties
SRL A ; Shift bits left --->
LD (0A6CFh),A ; Save Word Properties
BIT 2,A ; Should word be plural?
JR Z,L1432 ; No, so skip ahead
;----------------------------------------------------
; Make Word Plural
;----------------------------------------------------
LD (HL),027h ; Add an "'" before making plural
INC HL ; Add character
LD (HL),053h ; Add an "S" on the end to make plural
INC HL ; Add character
;----------------------------------------------------
; Check for Inflection Level?
;----------------------------------------------------
L1432: LD A,(0A6CFh) ; Get Word Properties
AND 003h ; Check for Inflection Level
LD C,A ; C = Inflection Level (0-3)
PUSH HL
LD HL,01451h ; Get Inflection Table Start
ADD HL,BC ; Point to Inflection Data
LD A,(HL) ; Get Inflection Data Byte
POP HL ; Get End of Word buffer p
LD (HL),A ; Put Inflection byte on the end of word
INC HL ; Add Inflection character
LD (0A641h),HL ; Save End of Word buffer
LD A,L
DEC A
LD (0A614h),A ; Save number of characters in Speech buffer
OR A ; Clear Character Buffer Overflow flag
L144A: POP BC
POP DE
POP HL
RET ; Return with no error
;----------------------------------------------------
; Too many characters in speech buffer causes error
;----------------------------------------------------
L144E: SCF ; Set Character Buffer Overflow error flag
JR L144A ; Restore registers and return
;----------------------------------------------------
; Inflection Level
;----------------------------------------------------
L1451: DB 020h ; " "
DB 02Dh ; "-"
DB 02Ch ; ","
DB 03Fh ; "?"
;----------------------------------------------------
; Check if Speech Phrase exists
; HL = Phrase Table Size
; DE = Phrase Number
; C = 1, phrase doesn't exist
; C = 0, phrase exists
;----------------------------------------------------
L1455: LD A,D ; A = D
AND 007h ; Change to Table 1
LD D,A ; D = A
LD A,(HL) ; A = Table Pointer
SUB E ; Subtract E
INC HL ; Next byte
LD A,(HL) ; A = Table Pointer
SBC A,D ; Subtract D
INC HL ; Next byte
RET ; Return
;----------------------------------------------------
; Speak Score
;----------------------------------------------------
L1464: LD DE,00038h ; Phrase = "(%) Your Score is (n)"
CALL L1363 ; Call Speech Routine (phrase)
CALL L136C ; Clear Speech Buffer
CALL L146F ; Speak Score
JP L21C1 ; Command Speech Chip to speak buffer
;----------------------------------------------------
; Speak SCORE (number)
; HL = Pointer to Player Score
;----------------------------------------------------
L146F: LD B,004h ; Loop = 4 bytes
LD DE,0A646h ; DE = Temp holding area
LD IY,0A6CBh ; IY = Copy of Score
;----------------------------------------------------
; Test Player Score to see if it's zero
;----------------------------------------------------
LD A,(HL) ; A = First Score byte
INC HL ; Point to next score byte
OR (HL) ; Test for zero
INC HL ; Point to next score byte
OR (HL) ; Test for zero
DEC HL ; Go back to last score byte
DEC HL ; Go back to last score byte
JR NZ,L1487 ; Not zero so skip ahead
LD DE,L0000 ; Word = "Zero"
JP L13CF ; Speak One Word, then return
;----------------------------------------------------
; Clear Out A646-A64A, Copy Score to A6CB-A6CF
;----------------------------------------------------
L1487: XOR A ; A = 0
LD (DE),A ; Clear out A646-A64A
LD A,(HL) ; Get Score
LD (IY+000h),A ; Make copy of score
INC HL ; Next byte
INC IY ; Next byte
INC DE ; Next byte
DJNZ L1487 ; Loop back B=4
;----------------------------------------------------
; Setup Score loop
;----------------------------------------------------
LD DE,0A6CBh ; Copy of Score
LD HL,0A646h ; Temp spot
LD IY,012CFh ; Place Holder Value table
LD B,004h ; Loop = 4 bytes
;----------------------------------------------------
; Check all values 1,000,000 - 1
;----------------------------------------------------
L149F: CALL L15A7 ; Check Place Holder 1,000,000..1
JR C,L14A7 ;
INC (HL) ;
JR L149F ; Loop until finished
L14A7: INC IY ;
INC IY ;
INC IY ;
BIT 7,B ;
JR NZ,L14BD ;
SET 7,B ;
SLA (HL) ;
SLA (HL) ;
SLA (HL) ;
SLA (HL) ;
JR L149F ;
L14BD: RES 7,B
INC HL
DJNZ L149F
;----------------------------------------------------
; Speak Score Millions XXX,000,000
;----------------------------------------------------
LD HL,0A6CBh
LD DE,0A646h
LD A,(DE) ; Get Millions score
OR A ; Test if zero
JR Z,L14DC ; Millions zero so do Thousands
LD (HL),000h
INC HL
LD (HL),A
DEC HL
CALL L1520
RET C
LD DE,02032h ; Word = "Million"
CALL L13CF ; Speak One Word
RET C ; Character Buffer Overflow error, so return
;----------------------------------------------------
; Speak Score Thousands 000,XXX,000
;----------------------------------------------------
L14DC: LD DE,0A647h
LD A,(DE)
LD B,A
INC DE
LD A,(DE)
AND 0F0h
OR B
JR Z,L1515
DEC DE
LD A,(DE)
SRL A
SRL A
SRL A
SRL A
LD (HL),A
INC HL
LD A,(DE)
SLA A
SLA A
SLA A
SLA A
LD B,A
INC DE
LD A,(DE)
SRL A
SRL A
SRL A
SRL A
OR B
LD (HL),A
CALL L1520
RET C
LD DE,02031h ; Word = "Thousand"
CALL L13CF ; Speak One Word
RET C
;----------------------------------------------------
; Speak Score Hundreds 0,000,XXX
;----------------------------------------------------
L1515: LD HL,0A648h
LD DE,0A6CBh
LD BC,00002h
LDIR
L1520: PUSH HL
PUSH DE
PUSH BC
LD HL,0A6CBh
LD A,(HL)
AND 00Fh
JR Z,L153B
LD E,A
LD D,008h
CALL L13CF ; Speak One Word
JR C,L15A3
LD DE,00030h ; Word = "Hundred"
CALL L13CF ; Speak One Word
JR C,L15A3
L153B: INC HL
LD A,(HL)
SRL A
SRL A
SRL A
SRL A
JR Z,L1598
CP 001h
JR Z,L156A
LD E,A
LD D,000h
DEC DE
DEC DE
LD IY,012EEh ; Get start of Score Tens Table
ADD IY,DE
LD E,(IY+000h)
LD D,018h ; DE = Tens word
CALL L13CF ; Speak One Word
JR C,L15A3
LD DE,0082Fh ; Word = "-ty"
CALL L13CF ; Speak One Word
JR C,L15A3
JR L1598 ; Goto Speak Score One's
L156A: LD A,(HL)
AND 00Fh
CP 003h
JR NC,L157B
ADD A,028h
LD E,A
LD D,008h
CALL L13CF ; Speak One Word
JR L15A3
L157B: SUB 003h
LD E,A
LD D,000h
LD IY,012E7h ; Point to Teens Word Table
ADD IY,DE ; Add DE to table
LD E,(IY+000h) ; DE = Word
LD D,018h ; DE = 1800 + Word
CALL L13CF ; Speak One Word
JR C,L15A3
LD DE,0082Dh ; Word = "Teen"
CALL L13CF ; Speak One Word
JR L15A3
;----------------------------------------------------
; Speak Score: One's place
;----------------------------------------------------
L1598: LD A,(HL) ; Get Score byte 1
AND 00Fh ; Isolate One's place
JR Z,L15A3 ; If zero then skip ahead
LD E,A ; Setup word pointer
LD D,008h ; Word = Score Ones
CALL L13CF ; Speak One Word
;----------------------------------------------------
; Finished with Speak Score
;----------------------------------------------------
L15A3: POP BC ; Restore BC Register
POP DE ; Restore DE Register
POP HL ; Restore HL Register
RET ; Return from Speak Score
;----------------------------------------------------
; Subtract value from temp Score 1,000,000 etc.
; IY = Pointer to Place Holder (1,000,000 - 1)
; DE = Temp Score
;----------------------------------------------------
L15A7: INC DE ; Point to score byte
INC DE ; Point to score byte
LD A,(DE) ; Get score byte
SUB (IY+002h) ; Subtract set value
LD (0A645h),A ; Store result
DEC DE ; Point to next score byte
LD A,(DE) ; Get score byte
SBC A,(IY+001h) ; Subtract set value
LD (0A644h),A ; Store result
DEC DE ; Point to next score byte
LD A,(DE) ; Get score byte
SBC A,(IY+000h) ; Subtract set value
LD (0A643h),A ; Store result
RET C ; Return if Carry is set
LD A,(0A643h)
LD (DE),A
INC DE
LD A,(0A644h)
LD (DE),A
INC DE
LD A,(0A645h)
LD (DE),A
DEC DE
DEC DE
RET
;----------------------------------------------------
; Subtract the Price of Hint after Purchase
;----------------------------------------------------
; A = Cost of Hint
; HL = Pointer to Score
;----------------------------------------------------
L15D2: LD C,A ; C = Amount to subtract
INC HL ;
INC HL ;
LD A,(HL) ;
SUB C ; Subtract Cost
LD (HL),A ;
DEC HL ;
LD A,(HL) ;
SBC A,000h ;
LD (HL),A ;
DEC HL ;
LD A,(HL) ;
SBC A,000h ;
LD (HL),A ;
RET NC ; Score still positive so return
;----------------------------------------------------
; Score is negative so set it to zero
;----------------------------------------------------
LD (HL),000h ; Store zero in score
INC HL
LD (HL),000h
INC HL
LD (HL),000h
DEC HL
DEC HL
RET ; Return
;----------------------------------------------------
; Speak 1 of 4 Random Phrases
; IY = Phrase Number
;----------------------------------------------------
L15EE: PUSH DE ; Save DE Register
LD A,R ; Get Random Number
AND 003h ; Number between 0 and 3
LD D,000h ; DE = 0000
LD E,A ; DE = Random Number
ADD IY,DE ; Add Random Number
LD E,(IY+000) ; Store Phrase Pointer
CALL L1363 ; Call Speech Routine (phrase)
POP DE ; Restore DE Register
RET ; Return
;----------------------------------------------------
; Speak Ordered Phrase (not random)
;----------------------------------------------------
; Routine will speak 1 of 4 phrases in order like:
;
; -> 1 -> 2 -> 3 -> 4 -> back to 1
;
; This is to avoid saying the same phrase over
; and over again. Only increment to the next
; phrase if the same phrase is repeated consecutively.
;----------------------------------------------------
; HL = Ordered Phrase to speak
;----------------------------------------------------
L1600: PUSH HL ; Save HL Register
PUSH DE ; Save DE Register
LD DE,(0A6D4h) ; What was the previous phrase spoken?
PUSH HL ; Save current phrase
OR A ; Clear carry for subtraction
SBC HL,DE ; Compare current phrase with previous phrase
POP HL ; Get current phrase
JR Z,L1615 ; Are we repeating the same phrase again?
LD A,003h ; Initialize ring buffer to 3
LD (0A6D6h),A ; Save ring buffer
LD (0A6D4h),HL ; Save ordered phrase pointer
L1615: LD A,(0A6D6h) ; Get ring buffer (0-3)
INC A ; Increment ring buffer
AND 003h ; Constrain value between 0 and 3
LD (0A6D6h),A ; Save ring buffer
LD E,A ; DE = Ringer buffer
LD D,000h ; set ring buffer value
ADD HL,DE ; Add ring buffer value to HL pointer
LD E,(HL) ; Get the ordered phrase (DE = phrase)
CALL L1363 ; Call Speech Routine (phrase)
POP DE ; Restore DE Register
POP HL ; Restore HL Register
RET ; Return
;----------------------------------------------------
; Hint Request Processing
;----------------------------------------------------
; B=Scene Index C=Hint RAM Carry = Table #
;----------------------------------------------------
L1629: LD HL,(0C023h) ; Use Hint Table (Audio Track 1)
JR NC,L1631 ; skip ahead
LD HL,(0C025h) ; Use Hint Table (Audio Track 2)
L1631: LD E,(HL) ; E = Number of Hints in table
INC HL ; Point to Table
L1633: LD A,B ; A = Scene Index
CP (HL) ; Find hint that goes with Scene
JR Z,L1640 ; Scene found in table, so skip ahead
INC HL ; Go to next Hint
INC HL ; skip byte
INC HL ; skip byte
INC HL ; skip byte
INC HL ; skip byte
DEC E ; Check if any Hints left?
JR NZ,L1633 ; Yes, so keep looping
RET ; No match so return
;----------------------------------------------------
; Scene found in Hint Table
;----------------------------------------------------
L1640: INC HL ; Point to Hint RAM
LD A,C ; A = Hint RAM
CP (HL) ; Second byte must match RAM
JR Z,L164D ; Match found, do hint
INC HL ; skip byte
INC HL ; skip byte
INC HL ; skip byte
INC HL ; HL = Next Hint
DEC E ; Decrement Hint Loop
JR NZ,L1633 ; More hints remain so loop
RET ; All hints checked so return
;----------------------------------------------------
; Hint found, and is available
;----------------------------------------------------
L164D: INC HL ; Point to hint cost
LD C,(HL) ; C = Cost of Pointer
INC HL ; Point to Hint Phrase
LD E,(HL) ; DE = Hint Phrase
INC HL ; Point to Hint Phrase
LD D,(HL) ; DE = Hint Phrase
LD HL,0BCE2h ; HL = Pointer to Score
LD A,C ; A = Cost of hint
OR A ; Check if Hint is free
JR Z,L1683 ; Yes, it's free so skip ahead
;----------------------------------------------------
; Purchasing A Hint
;----------------------------------------------------
PUSH DE ; Save DE Hint Phrase
PUSH HL ; Save HL Pointer to Score
LD DE,00026h ; Phrase="I Have A Pointer For You (%)"
CALL L1363 ; Call Speech Routine (phrase)
LD DE,00028h ; Phrase="But It Will Cost You"
CALL L1363 ; Call Speech Routine (phrase)
LD HL,0A6D0h ; Setup Speakable Number
LD (HL),000 ; Number = 00
INC HL ; Next byte
LD (HL),000 ; Number = 0000
INC HL ; Next byte
LD (HL),C ; Number = Cost of Pointer
DEC HL ; Previous byte
DEC HL ; HL points to Speakable Number
;----------------------------------------------------
; Ask if player wants to purchase a hint
;----------------------------------------------------
LD DE,00029h ; Phrase="(n) Points Do You Want It"
CALL L1363 ; Call Speech Routine (phrase)
CALL L19E7 ; Check for "YES" or "NO"
POP HL ; Restore HL Pointer to Score
POP DE ; Restore DE Hint Phrase
JR C,L168A ; Timed out, so skip ahead
JR NZ,L1691 ; Hint declined, skip ahead
L1683: CALL L1363 ; Speak Hint to player
LD A,C ; A = Cost of Hint
JP L15D2 ; Subtract Cost of hint from score
;----------------------------------------------------
; Player did not answer to purchase hint
;----------------------------------------------------
L168A: LD IY,012BBh ; Random Phrase = "No Pointer"
CALL L15EE ; Speak Random Phrase
L1691: RET ; Return
;----------------------------------------------------
; Unknown Data
;----------------------------------------------------
L1692: DB 01Fh, 01Ch, 01Fh, 01Eh, 01Fh, 01Eh
DB 01Fh, 01Fh, 01Eh, 01Fh, 01Eh, 01Fh
;----------------------------------------------------
; Unknown
;----------------------------------------------------
L169E: LD HL,0BE01h ; Get GAME STATUS Register
SET 2,(HL) ; Set LOOP CHECK
LD B,006h ; Loop = 6
LD HL,0BE2Ch ;
L16A8: LD A,(0BE0Ch) ;
AND 01Fh
OR
040h
LD (0BE0Ch),A
OUT (020h),A
PUSH HL
L16B5: LD HL,0BE17h
BIT 0,(HL)
JR Z,L16B5
RES 0,(HL)
POP HL
LD A,(0BE26h)
LD (HL),A
DEC HL
DJNZ L16A8 ; Loop until all checked
LD A,(0BE0Ch) ;
AND 01Fh ;
OR
000h ;
LD (0BE0Ch),A ;
OUT (020h),A ;
LD HL,0BE01h ; Get GAME STATUS Register
RES 2,(HL) ; Clear LOOP CHECK
RET ; Return
;----------------------------------------------------
; Send Important bytes (BE27) to Keyboard Interface
;----------------------------------------------------
L16D8: LD HL,0BE01h ; Get GAME STATUS Register
SET 2,(HL) ;
LD B,006h ; Loop = 6
LD HL,0BE27h ;
L16E2: LD A,(HL) ;
PUSH HL ;
OUT (080h),A ; Write to Keyboard Interface (COP421L)
LD A,(0BE0Ch)
AND 01Fh
OR
080h
LD (0BE0Ch),A
OUT (020h),A
L16F2: LD HL,0BE17h
BIT 0,(HL)
JR Z,L16F2
RES 0,(HL)
POP HL
INC HL
DJNZ L16E2
LD A,(0BE0Ch)
AND 01Fh
OR
000h
LD (0BE0Ch),A
OUT (020h),A
LD HL,0BE01h
RES 2,(HL)
RET
;----------------------------------------------------
; Cycle Routine #3: Check if First Name Basis is okay
;----------------------------------------------------
; Find spaces in Player's Name
;----------------------------------------------------
L1711: LD A,(0A64Ah) ; Get Length of Name
LD C,A ; C = length of name
LD B,000h ; BC = Length of Name
LD HL,0A64Bh ; Point to start of name
LD A,' ' ; Load up the ' '(space) character
LD DE,00000h ; Initialize number of spaces in name to 0
L171F: CPI ; Is location empty or at end of name?
JR NZ,L1724 ; Location not empty, more spots to check so skip ahead
INC DE ; Increment number of spaces
L1724: JP PE,L171F ; Loop back until end of name is reached
XOR A ; Length = 0
LD (0A68Bh),A ; Clear length of first name
LD A,E ; Get number of spaces
OR A ; Are there any spaces?
RET Z ; No spaces so return
;----------------------------------------------------
; Strip off all characters after the first space
;----------------------------------------------------
LD HL,0A64Bh ; Set pointer to Start of Name
LD A,(0A64Ah) ; Get Length of Name
LD C,A ; Loop = Length of name
LD A,' ' ; Check for space character
CPIR ; Loop until first space or end of name
LD DE,0A64Bh ; Set DE = Start of Name
OR A ; Clear carry for subtraction
SBC HL,DE ; Calculate location of first space in name
DEC L ; L becomes the length up until the first space
RET Z ; Return if the length of name is zero
;----------------------------------------------------
; Copy First name to a buffer (A68C)
;----------------------------------------------------
LD C,L ; Loop = Length of Name (until first SPACE)
LD HL,0A64Bh ; Set pointer to Start of Name
LD DE,0A68Ch ; Set pointer to First name buffer
LD A,C ; A = Length of First Name
LD (0A68Bh),A ; Save the length of the First name
LDIR ; Copy first name to new location
LD A,(0A68Bh) ; Check length of First name
OR A ; Test if the length is zero
JR Z,L176B ; If length of first name is zero then just return
;----------------------------------------------------
; Verify that first name basis is okay
;----------------------------------------------------
L1754: LD DE,00071h ; Phrase="Can I Call You (*)"
CALL L1363 ; Call Speech Routine (phrase)
CALL L19E7 ; Check for "YES" or "NO"
JR C,L1754 ; Timed out, so repeat question
JR Z,L1765 ; "YES", so skip ahead
XOR A ; Length = 0
LD (0A68Bh),A ; Clear Length of First Name
L1765: LD DE,00072h ; Phrase="O K (*)"
CALL L1363 ; Call Speech Routine (phrase)
L176B: RET ; Return
;----------------------------------------------------
; Cycle Routine #2 Enter Name in Keyboard
;----------------------------------------------------
L176C: LD HL,(0BE05h) ; Get Game Timer
LD (0A6D9h),HL ; Save Game Timer before starting
;----------------------------------------------------
; Give extra time for entering name
;----------------------------------------------------
LD BC,00726h ; Give 1 additional minute
ADD HL,BC ; Add to Timer
LD (0BE05h),HL ; Store Game Timer
LD HL,0BE04h ; Get Game Timer Control Register
SET 0,(HL) ; Start Game Timer
;----------------------------------------------------
; Clear name area before beginning
;----------------------------------------------------
L177E: XOR A ; A = 0
LD HL,0A64Ah ; Point to Name Area
LD B,041h ; Loop = 65 spots to clear
L1784: LD (HL),A ; Clear name location
INC HL ; Go to next location
DJNZ L1784 ; Loop until all of name is erased
LD (0A68Bh),A ; Clear Length of First Name
LD HL,0A64Bh ; Setup pointer to Player's Name
;----------------------------------------------------
; Check if the time to enter name has expired
;----------------------------------------------------
LD A,(0BE48h) ; Get Timer Register
BIT 7,A ; Check if timer has expired
RET NZ ; Timer has expired so simply return
LD IY,0129Bh ; Random Phrase = "Type in Name"
CALL L15EE ; Speak Random Phrase
;----------------------------------------------------
; Get name from keyboard
;----------------------------------------------------
L179B: CALL L193C ; Get keyboard character for name
JR C,L177E ; CLEAR was pressed so re-enter name
CP 082h ; Has F3/ENTER been pressed?
JR Z,L17B5 ; Yes, so user is finished
CP 030h ; Is key a number?
JR C,L179B ; No, so get next key input
CP 041h ; Is key between A - Z?
JR NC,L179B ; Yes, so get next key input
;----------------------------------------------------
; Reject invalid key input
;----------------------------------------------------
LD IY,012A7h ; Random Phrase = "Just Letters"
CALL L15EE ; Speak Random Phrase
JR L177E ; Start entering again
;----------------------------------------------------
; ENTER pressed, user finished entering name
;----------------------------------------------------
L17B5: LD A,(0A64Ah) ; Get length of name
OR A ; Check if name left empty
JR NZ,L17C4 ; Name not empty so jump ahead
L17BB: LD IY,012B3h ; Random Phrase = "Retype in Name"
CALL L15EE ; Speak Random Phrase
JR L177E ; Do over again
;----------------------------------------------------
; Check name for single letter
;----------------------------------------------------
L17C4: DEC A ; Is name length greater that 1?
JR Z,L17BB ; No, so retype in name
;----------------------------------------------------
; Check name for vulgarities
;----------------------------------------------------
CALL L180E ; Check if name is in bad words list
JR NC,L17DE ; Name is not offensive, so skip ahead
XOR A ; Length = 0
LD (0A64Ah),A ; Clear length of full name
LD (0A68Bh),A ; Clear length of first name
LD IY,L12C7 ; Random Phrase = "Name Sounds French"
CALL L15EE ; Speak Random Phrase
OR
0FFh ; Set error flag
JR L17F2 ; Re-enter name
;----------------------------------------------------
; Verify that the name sounds correct
;----------------------------------------------------
L17DE: LD IY,L12A3 ; Random Phrase = "Did I Say Your Name Right?"
CALL L15EE ; Speak Random Phrase
CALL L19E7 ; Check for "YES" or "NO"
JR NC,L17F2 ; User responded so check the response
LD HL,L12AF ; Ordered Phrase = "Act Lively"
CALL L1600 ; Speak Ordered Phrase
JR L17C4 ; Ask the player the question again
L17F2: JR NZ,L1804 ; "NO" pressed, so skip ahead
;----------------------------------------------------
; Name is fine, expire the timer and return
;----------------------------------------------------
LD HL,(0BE05h) ; Get Game Timer
LD DE,(0A6D9h) ; Get timer value before name was entered
OR A ; Clear carry for subtraction
SBC HL,DE ; Check to see if all extra time was used
RET C ; All the time was already used so return
LD (0BE05h),DE ; Restore the Game Timer to its original value
RET ; Return
;----------------------------------------------------
; Name does not sound right so re-enter
;----------------------------------------------------
L1804: LD IY,L12BF ; Random Phrase = "Try A Different Spelling"
CALL L15EE ; Speak Random Phrase
JP L177E ; Re-enter name
;----------------------------------------------------
; Call Routine to check for offensive name
;----------------------------------------------------
; C = SET Name is offensive
;----------------------------------------------------
L180E: CALL L1812 ; Check if name is in list of bad words
RET ; Return
;----------------------------------------------------
; Check if name is in list of Bad Words
;----------------------------------------------------
; The player's name cannot be a bad word and it
; cannot contain a bad word in it anywhere.
;----------------------------------------------------
; C = SET Name is offensive
;----------------------------------------------------
L1812: LD A,(0A64Ah) ; A = Length of Name
OR A ; Is length of name zero?
RET Z ; Yes, so return
;----------------------------------------------------
; Get Bad Words and setup loop
;----------------------------------------------------
LD IY,BadWords ; Set pointer to Bad Words (1864h)
LD E,(IY+000h) ; E = Number of Bad Words in list
INC IY ; Point to Bad Word List
LD B,000h ; BC = 0
L1822: LD A,(0A64Ah) ; Get Length of Name
LD C,A ; BC = Length of Name (Loop)
LD HL,0A64Bh ; HL = Pointer to Name
LD D,(IY+000h) ; D = Length of Bad Word
INC IY ; Point to start of Bad Word
LD (0A6D7h),IY ; Save Pointer to Bad Word
LD (0A6D9h),DE ; Save Length of Bad Word and # of Bad Words
;----------------------------------------------------
; Check if bad word occurs anywhere in name
;----------------------------------------------------
L1836: LD A,(IY+000h) ; A = First character of Bad Word
CPIR ; Check the whole name for character
INC BC ; Increment loop
JR NZ,L1859 ; No occurance of character, so skip ahead
L183E: DEC D ; Subtract 1 from loop of Bad Word
JR Z,L1857 ; All letters were found, jump ahead
DEC C ; Subtract 1 from loop of Name
INC IY ; Go to next character in bad word
JR Z,L1859 ; Whole name was checked without match
LD A,(IY+000h) ; Get character in bad word
CP (HL) ; Compare characters in both words
INC HL ; Point to next character in Name
JR Z,L183E ; Characters match so check next character
LD IY,(0A6D7h) ; Restore Pointer to Bad Word
LD DE,(0A6D9h) ; Restore Length of Bad Word and # of Bad Words
JR L1836 ; Continue looking for occurrence of bad word
;----------------------------------------------------
; Bad Word was found so set error
;----------------------------------------------------
L1857: SCF ; Set Carry Flag
RET ; Return
;----------------------------------------------------
; Setup loop to point to next word
;----------------------------------------------------
L1859: INC IY ; Move bad word pointer
DEC D ; Count down number of characters in bad word
JR NZ,L1859 ; Loop until we reach the next bad word
DEC E ; Decrement # of bad words checked
XOR A ; A = 0
OR E ; Have we checked all the bad words?
RET Z ; Yes, so return
JR L1822 ; More Bad Words so check next word
;----------------------------------------------------
; This is a list of Bad Words that are not accepted
;----------------------------------------------------
BadWords:
DB 39 ; Number of bad words in list
DB 4
.STRING "FART"
DB 4
.STRING "CUNT"
DB 4
.STRING "PISS"
DB 4
.STRING "SHIT"
DB 4
.STRING "CRAP"
DB 4
.STRING "TURD"
DB 4
.STRING "DAMN"
DB 5
.STRING "PUSSY"
DB 6
.STRING "NIGGER"
DB 4
.STRING "SPIC"
DB 4
.STRING "SPIK"
DB 4
.STRING "KIKE"
DB 4
.STRING "KYKE"
DB 5
.STRING "QUEER"
DB 5
.STRING "KWEER"
DB 7
.STRING "SCROTUM"
DB 7
.STRING "SCROTEM"
DB 5
.STRING "KOTEX"
DB 5
.STRING "COTEX"
DB 5
.STRING "PENIS"
DB 5
.STRING "PEENI"
DB 6
.STRING "TAMPON"
DB 6
.STRING "TAMPAX"
DB 4
.STRING "ANUS"
DB 4
.STRING "ANIS"
DB 3
.STRING "ASS"
DB 5
.STRING "PRICK"
DB 3
.STRING "FAG"
DB 5
.STRING "WHORE"
DB 5
.STRING "BITCH"
DB 7
.STRING "BASTARD"
DB 4
.STRING "SUCK"
DB 4
.STRING "COCK"
DB 3
.STRING "FUQ"
DB 3
.STRING "FUC"
DB 3
.STRING "FUK"
DB 4
.STRING "PHUC"
DB 4
.STRING "PHUQ"
DB 4
.STRING "PHUK"
;----------------------------------------------------
; Get Keyboard Character for Name
;----------------------------------------------------
; C = 1, Clear Name (CLEAR, too long, timeout)
; 0, No Errors
;----------------------------------------------------
L193C: CALL L1989 ; Wait for a Keypress with timeout
JR NC,L1954 ; Keypress did not time out so skip ahead
XOR A ; A = 0
LD (0A64Ah),A ; Set Length of Name to zero
LD A,(0BE48h) ; Get Timer Register
BIT 7,A ; Check if enter name timer has expired
JR NZ,L1952 ; Timer has expired, so note error and return
LD HL,L12AF ; Ordered Phrase = "Act Lively"
CALL L1600 ; Speak Ordered Phrase
L1952: SCF ; Set carry flag to clear name and re-enter
RET ; Return
L1954: CALL L19B0 ; Speak keypress
;----------------------------------------------------
; Check for Function Keys F1,F2,F3,F4
;----------------------------------------------------
BIT 7,A ; Check if key was a Function Key
JR Z,L196E ; Not a function key so skip ahead
;----------------------------------------------------
; F1 = CLEAR
;----------------------------------------------------
CP 080h ; Check key "F1 = CLEAR"
JR NZ,L1961 ; Not F1 so check for F3
SCF ; Set the carry bit to signal re-entering name
RET ; Return
;----------------------------------------------------
; F3 = ENTER
;----------------------------------------------------
L1961: CP 082h ; Check key "F3 = ENTER"
RET Z ; ENTER was pressed so return
;----------------------------------------------------
; F2 = PAUSE
;----------------------------------------------------
CP 081h ; Check key "F2"
JR NZ,L196C ; Not F2 so must be F4
LD A,02Fh ; Add slash character "/"
JR L196E ; Skip ahead to length check
;----------------------------------------------------
; F4 = SPACE
;----------------------------------------------------
L196C: LD A,020h ; Character = SPACE
;----------------------------------------------------
; Check if name is too long already
;----------------------------------------------------
L196E: LD B,A ; B = Keyboard Character
LD A,(0A64Ah) ; Get Length of Name
INC A ; Add 1 to Length of Name
LD (0A64Ah),A ; Save new length
CP 041h ; Is Name too long?
JR C,L1983 ; No, length is fine, skip ahead
LD IY,0129Fh ; Random Phrase = "Name Too Long"
CALL L15EE ; Speak Random Phrase
SCF ; Set carry flag to clear name and re-enter
RET ; Return
;----------------------------------------------------
; Add keyboard character to end of name
;----------------------------------------------------
L1983: LD C,(HL) ; Get old name character before replacing new one
LD (HL),B ; Append keyboard character to name
INC HL ; Point to next name spot
LD A,B ; A = keyboard character
OR A ; Clear carry, no errors
RET ; Return
;----------------------------------------------------
; Wait for a Keypress with timeout
;----------------------------------------------------
; Z = 1, key pressed
; C = 1, timed out
; A = Keyboard Character
;----------------------------------------------------
L1989: PUSH HL ; Save HL Register
PUSH DE ; Save DE Register
;----------------------------------------------------
; Setup timeout period
;----------------------------------------------------
LD DE,001D5h ; Programmable Timer = 1D5
CALL L21A7 ; Set Programmable Timer
LD HL,0BE0Bh ; Get Keyboard Buffer
L1994: BIT 0,(HL) ; Has a key been pressed?
JR NZ,L19A7 ; Yes, so go get keypress
LD A,(0BE48h) ; Check Timer register
BIT 7,A ; Has timer expired?
JR NZ,L19A4 ; Yes, timer expired so jump ahead
CALL L21B3 ; Check if Programmable Timer expired
JR Z,L1994 ; Timer not expired so wait for keypress
L19A4: SCF ; Set carry flag
JR L19AD ; Jump to end of routine
L19A7: LD A,(0BE0Ah) ; Get Keyboard Character
RES 0,(HL) ; Clear Keyboard Buffer
OR A ; Z = 1
L19AD: POP DE ; Restore DE Register
POP HL ; Restore HL Register
RET ; Return
;----------------------------------------------------
; Speak Key?
; A = key
;----------------------------------------------------
L19B0: PUSH AF ; Save AF Register
PUSH DE ; Save DE Register
PUSH HL ; Save HL Register
BIT 7,A ;
JR Z,L19C3 ;
LD HL,019E3h ; HL = Pointer to table
AND 003h ;
LD E,A ; DE = A
LD D,000h ; DE = 0000 + A
ADD HL,DE ; Point to correct byte
LD E,(HL) ; E = byte from table
JR L19DC ;
L19C3: CP 041h ;
JR NC,L19D7 ;
SUB 012h ;
CP 01Eh ;
JR NZ,L19CF ;
ADD A,00Ah ;
L19CF: LD E,A ; Get word
LD D,080h ; Get word ($8000 + A) second table
CALL L1363 ; Call Speech Routine (phrase)
JR L19DF ; Goto end of subroutine
L19D7: SUB 037h ; ..else subtract 37h from word
LD E,A ; Get word
LD D,000h ; Get word ($0000 + A) first table
L19DC: CALL L13C6 ; Call Speech Routine (word)
L19DF: POP HL ;
POP DE
POP AF
RET
;----------------------------------------------------
; Unknown Table
;----------------------------------------------------
L19E3: .byte 25h ; "Clear"
.byte 02h ; "Two"
.byte 24h ; "Enter"
.byte 4Dh ; "Space"
;----------------------------------------------------
; Check for "YES" or "NO"
;----------------------------------------------------
; Carry set = Operation timed out
; Z = YES pressed
; NZ = NO pressed
;----------------------------------------------------
L19E7: PUSH IY ; Save IY Register
PUSH HL ; Save HL Register
PUSH DE ; Save DE Register
L19EB: LD DE,001D5h ; Programmable Timer = 001D5h
CALL L21A7 ; Set Programmable Timer
L19F1: CALL L2190 ; Keyboard Check routine
JR NC,L1A09
LD A,(0BE48h)
BIT 7,A
JR Z,L1A01
LD A,031h
JR L1A09
L1A01: CALL L21B3 ; Check if Programmable Timer expired
JR Z,L19F1
SCF
JR L1A35
L1A09: LD B,A
LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL)
CP '1' ; Character = '1'?
JR NZ,L1A1B ; No, so skip ahead
LD DE,00026h ; Get word ("Yes")
CALL L13C6 ; Call Speech Routine (word)
JR L1A30 ; Key pressed so leave
L1A1B: CP '0' ; Character = '0'?
JR NZ,L1A27 ; No, so skip ahead
LD DE,00027h ; Get word ("No")
CALL L13C6 ; Call Speech Routine (word)
JR L1A30 ; Key pressed so leave
L1A27: LD IY,012ABh
CALL L15EE
JR L19EB ; No answer so continue looping
L1A30: LD A,B ; A =
CP 031h ; Character = '1'?
SCF ; Carry = 1
CCF ; Negate Carry
L1A35: POP DE ; Restore DE Register
POP HL ; Restore HL Register
POP IY ; Restore IY Register
RET ; Return
;----------------------------------------------------
; Check for user choice at decision points
;----------------------------------------------------
L1A3A: LD HL,0BE0Bh ; Check Keyboard Buffer
BIT 0,(HL) ; Has a key been pressed?
RET Z ; No, so return
LD A,(IX+002h) ; Get available choice from scene
AND 00Fh ; Check only lower nibble
JP Z,L1A54 ; No choices restricted, so jump ahead
CP 005h ; Check if 0101
JR C,L1A9D ;
CP 00Ah ; Check if 1010
JP C,L1AD3 ;
JP L1B0E ;
;----------------------------------------------------
; Check user choice of "F1","F2","F3", or "F4"
;----------------------------------------------------
L1A54: LD A,(0BE0Ah) ; Get Keyboard Character
CP 080h ; Check key "F1"
LD B,(IX+003h) ; Get Scene choice 1
JR Z,L1A72 ; Go set scene pointer
CP 081h ; Check key "F2"
LD B,(IX+004h) ; Get Scene Choice 2
JR Z,L1A72 ; Go set scene pointer
CP 082h ; Check key "F3"
LD B,(IX+005h) ; Get Scene Choice 3
JR Z,L1A72 ; Go set scene pointer
CP 083h ; Check key "F4"
LD B,(IX+006h) ; Get Scene Choice 4
RET NZ ; Not a valid choice so leave
;----------------------------------------------------
; Check for valid scene
;----------------------------------------------------
L1A72: LD A,B ; Get Next scene
CP 000h ; Is that a valid choice?
JR NZ,L1A81 ; Yes, so skip ahead
;----------------------------------------------------
; Not a valid user keyboard choice
;----------------------------------------------------
L1A77: RES 0,(HL)
LD IY,012C3h ; Random Phrase = "Won't Work"
CALL L15EE ; Speak Random Phrase
RET ; Return
;----------------------------------------------------
; User keyboard choice has been made
;----------------------------------------------------
L1A81: LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
LD (0BC81h),A
LD HL,0BE03h
SET 0,(HL) ;
RES 4,(HL) ; Set Audio Track 1
LD A,(0BE0Ah) ; Get Keyboard Character
RES 7,A ; Remove MSB
INC A ; A = Keyboard word
LD E,A ; DE = A, Word
LD D,000h ; DE = A, Word
CALL L13C6 ; Call Speech Routine (word)
RET ; Return
;----------------------------------------------------
; Check user choice of "F1","F2","F3", or "F4"
;----------------------------------------------------
L1A9D: LD A,(0BE0Ah) ; Get Keyboard Character
CP 080h ; Check key "F1"
LD B,(IX+003h)
JR Z,L1A72
CP 081h ; Check key "F2"
LD B,(IX+004h)
JR Z,L1A72
CP 083h ; Check key "F4"
JR Z,L1A77
CP 082h ; Check key "F3"
RET NZ
LD B,004h
LD A,001h
LD HL,0BE18h
LD (HL),A
LD A,(IX+002h)
AND 00Fh
L1AC2: CP (HL)
JR NZ,L1AD0
LD A,R ; Get Random Number
AND 007h ; Random number between 0 - 7
CP (HL)
JP C,L1B84
JP L1B8A
L1AD0: INC (HL)
DJNZ L1AC2
;----------------------------------------------------
; Check user choice of "F1","F2","F3", or "F4"
;----------------------------------------------------
L1AD3: LD A,(0BE0Ah) ; Get Keyboard Character
CP 080h ; Check key "F1"
LD B,(IX+003h)
RET C
JR Z,L1A72
CP 081h ; Check key "F2"
JR NZ,L1A77
LD HL,0BE18h
LD A,(IX+002h)
AND 00Fh
CP 005h
JR NZ,L1AF2
LD (HL),002h
JR L1B56
L1AF2: CP 006h
JR NZ,L1AFA
LD (HL),003h
JR L1B56
L1AFA: CP 007h
JR NZ,L1B02
LD (HL),004h
JR L1B56
L1B02: CP 008h
JR NZ,L1B0A
LD (HL),004h
JR L1B46
L1B0A: LD (HL),005h
JR L1B46
L1B0E: LD A,(0BE0Ah) ; Get Keyboard Character
CP 080h
RET C
JP NZ,L1A77
LD HL,0BE18h
LD DE,0BE19h
LD A,(IX+002h)
AND 00Fh
CP 00Ah
JR NZ,L1B2C
LD (HL),002h
LD A,003h
JR L1B64
L1B2C: CP 00Bh
JR NZ,L1B36
LD A,004h
LD (HL),002h
JR L1B64
L1B36: CP 00Ch
JR NZ,L1B40
LD (HL),002h
LD A,005h
JR L1B64
L1B40: LD (HL),003h
LD A,005h
JR L1B64
L1B46: LD A,R ; Get Random Number
AND 007h
CP 002h
JP C,L1B7E
CP (HL)
JP C,L1B84
JP L1B8A
L1B56: LD A,R ; Get Random Number
AND 007h ; Make number between 0-7
JP Z,L1B7E ; Do Scene Choice 2
CP (HL)
JP C,L1B84 ; Do Scene Choice 3
JP L1B8A ; Else do Scene Choice 4
L1B64: LD (DE),A
LD A,R ; Get Random Number
AND 007h ; Make number between 0-7
JP Z,L1B78 ; if zero, do Scene Choice 1
CP (HL)
JP C,L1B7E ; Do Scene Choice 2
EX DE,HL
CP (HL)
JP C,L1B84 ; Do Scene Choice 3
JP L1B8A ; else do Scene Choice 4
L1B78: LD A,(IX+003h) ; Get Scene Choice 1
JP L1A81 ; Go set scene pointer
L1B7E: LD A,(IX+004h) ; Get Scene Choice 2
JP L1A81 ; Go set scene pointer
L1B84: LD A,(IX+005h) ; Get Scene Choice 3
JP L1A81 ; Go set scene pointer
L1B8A: LD A,(IX+006h) ; Get Scene Choice 4
JP L1A81 ; Go set scene pointer
;----------------------------------------------------
; Attract Mode Loop: Routine #1
;----------------------------------------------------
L1B90: IN A,(0F2h) ; Get DIP Switch A
LD (0BE0Fh),A ; Store DIP Switch A in BE0F
LD HL,0BE48h
SET 6,(HL)
RES 7,(HL)
CALL L1D54 ; Perform Attract Mode AUDIO Check
LD DE,(0C015h) ; DE = Starting Frame Number for Attract Mode
LD BC,(0C017h) ; BC = Scene Play Time for Attract Mode
CALL L1C11 ; Call Attract Mode Start
JR C,L1BBD ; Skip ahead if coin was inserted
LD DE,(0C019h) ; Get Frame Number, "Insert 1 Token for 3 Units..."
CALL L1C57 ; PAUSE on Frame Number
LD DE,0009Bh ; Load Timer Value = 9B
CALL L1C1F ; Wait for Timer or Coins
JR C,L1BBD ; Enough coins for 1 credit so skip ahead
JR L1B90 ; Loop back to Attract Mode
;----------------------------------------------------
; Show "Additional Coins" until timeout or keypress
;----------------------------------------------------
L1BBD: LD DE,(0C01Bh) ; Get Frame Number , "Insert additional quarters..."
CALL L1C57 ; PAUSE on Frame Number
LD HL,0BE0Bh ; Check Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
L1BC9: LD DE,00090h ; Phrase="Press Any Key To Continue"
CALL L1363 ; Call Speech Routine (phrase)
LD DE,0009Bh ; Programmable Timer = 09Bh
CALL L21A7 ; Set Programmable Timer
;----------------------------------------------------
; Pause until Programmable Timer expires or Keypress
;----------------------------------------------------
L1BD5: BIT 0,(HL) ; Check for key press
JR NZ,L1BE0 ; Key pressed, so jump ahead
CALL L1C4B ; Check Programmable Timer expiration
JR Z,L1BD5 ; Wait until Programmable Timer expires
JR L1BC9 ; Loop back and Speak again
L1BE0: RES 0,(HL) ; Clear Keyboard Buffer
RET ; Return
;----------------------------------------------------
; SEARCH then PLAY Frame Number, Setup Timer
;----------------------------------------------------
; DE = Starting Frame Number
; BC = Time of Scene
;----------------------------------------------------
; Return Z =
; NZ =
;----------------------------------------------------
L1BE3: PUSH BC ; Save BC Register
PUSH DE ; Save DE Register
CALL L1CC1 ; Setup AUDIO Channel(s)
POP DE ; Get Frame Number
CALL L1C57 ; PAUSE on Frame Number
POP BC ; Get Time of Scene
LD A,B ; Check if time is zero
OR C ; Check if time is zero
JR Z,L1C0F ; If time is zero then just return
PUSH BC
CALL L1F1E ; Send PLAY command
POP DE ; Get Programmable Timer Value
L1BF6: CALL L21A7 ; Set Programmable Timer
LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
L1BFE: CALL L1C4B ; Check Programmable Timer expiration
JR Z,L1BFE ; Wait until Programmable Timer expires
CALL L1F15 ; Send PAUSE Command
LD HL,0BE48h
BIT 1,(HL)
JR NZ,L1C0F ; Return (1)
LD A,000h ; Return (0)
L1C0F: OR A ; Setup return value
RET ; Return
;----------------------------------------------------
; SEARCH then PLAY Frame Number (Attract Mode)
; DE = Frame Number
; BC = Time of Scene
; Return: 1 = Timer expired
; 0 = Timer running
;----------------------------------------------------
L1C11: PUSH BC ; Save BC Register temporarily
CALL L1C57 ; PAUSE on Frame Number
POP BC ; Restore BC Register
LD A,B ; Test Programmable Timer Value
OR C ; Programmable Timer Value = 00000?
JR Z,L1C0F ; Yes, Timer = 0 so return(1)
PUSH BC ; Save Programmable Timer Value
CALL L1F1E ; Send PLAY command
POP DE ; Restore Programmable Timer Value
L1C1F: CALL L21A7 ; Set Programmable Timer
LD HL,0BE0Bh ; Get Keyboard Buffer
RES 0,(HL) ; Clear Keyboard Buffer
L1C27: CALL L1C4B ; Check Programmable Timer expiration
JR NZ,L1C46 ; Programmable Timer expired, jump to PAUSE
LD A,(0BE0Fh) ; Get DIP Switch A
LD B,A ; B = DIP Switch A
AND 007 ; Check for Free Play
JR NZ,L1C36 ; Not Free Play so skip ahead
SCF ; Free Play set so Return (1)
RET ; Return
L1C36: LD A,(0BE0Dh) ; Get number of Credits
LD C,003h ; C = 3
BIT 3,B ; Test A4, Coins per Credit
JR NZ,L1C41 ; One coin per coin game, so skip ahead
LD C,006h ; C = 6
L1C41: CP C ; Are there 3 or 6 coins?
JR C,L1C27 ; No, so loop back
SCF ; Return (1)
RET ; Return (1)
L1C46: CALL L1F15 ; Send PAUSE Command
OR A ; Return (0)
RET ; Return (0)
;----------------------------------------------------
; Check Programmable Timer Expiration
;----------------------------------------------------
; Return Z = Timer still running
; NZ = Timer expired
;----------------------------------------------------
L1C4B: PUSH HL ; Save HL Register
LD HL,0BE07h ; Check Programmable Timer Control Register
BIT 1,(HL) ; Has Timer expired?
JR Z,L1C55 ; No, Timer is still running so skip ahead
RES 1,(HL) ; Mark Timer as unexpired
L1C55: POP HL ; Restore HL Register
RET ; Return
;----------------------------------------------------
; SEARCH and PAUSE
;----------------------------------------------------
; DE = Frame Number
;----------------------------------------------------
L1C57: LD (0A794h),DE ; Store Frame Number for setup
LD HL,0A791h
RES 0,(HL)
CALL L1D9B ; SEARCH to frame
CALL L1F15 ; Send PAUSE Command
RET ; Return
;----------------------------------------------------
; Initialize System
;----------------------------------------------------
; Send PLAY command and wait for disc to spin up
;----------------------------------------------------
; C = set ???
;----------------------------------------------------
L1C67: CALL L1F27 ; Send REJECT Command to LDPlayer
LD DE,0003Fh ; Phrase="Thank You (%)"
CALL L1363 ; Call Speech Routine (phrase)
CALL L1F27 ; Send REJECT Command to LDPlayer
LD DE,000B3h ; Phrase="Initializing System"
CALL L1363 ; Call Speech Routine (phrase)
LD HL,0BE01h ;
SET 6,(HL) ; Enable both AUDIO Channels
CALL L1CA3 ; Check LDPLAYER type by checking the DIPs
LD DE,00174h ; Set Timer = 174h
CALL L2163 ; Wait until Timer Expires
CALL L1F1E ; Send PLAY command
LD DE,000B2h ; Phrase="Disc Spinning Up Please Wait"
CALL L1363 ; Call Speech Routine (phrase)
CALL L1F1E ; Send PLAY command
LD DE,001D1h ; Set Timer = 1D1h
CALL L2163 ; Wait until Timer Expires
CALL L1F30 ; Send DISPLAY DISABLE to LDPlayer
LD DE,L02B8 ; Get Frame Number, "Thayer's Quest" first scene
CALL L1C57 ; PAUSE on Frame Number
RET ; Return
;----------------------------------------------------
; Check LDPLAYER type by checking the DIPs
;----------------------------------------------------
; A79A bit3 = 0 LD-V1000
; bit3 = 1 PR-7820
;----------------------------------------------------
L1CA3: LD HL,0A79Ah ; Get LDPlayer Status bit
RES 3,(HL) ; Clear LDPLAYER bit
IN A,(0F1h) ; Get DIP Switch B
BIT 3,A ; Test B4, LDPlayer
RET Z ; PR-7820 so return
SET 3,(HL) ; Else set the LDPLAYER bit
RET ; Return
;----------------------------------------------------
; Send 2 Play Commands
;----------------------------------------------------
L1CB0: PUSH BC ; Save Timer Value
CALL L1CC1 ; Setup AUDIO Channel(s)
CALL L1F1E ; Send PLAY command
CALL L1F1E ; Send PLAY command
POP BC ; Restore Timer Value
LD D,B ; Get Programmable Timer Value
LD E,C ; Get Programmable Timer Value
JP L1BF6 ; Jump back and set timer
RET ; Return
;----------------------------------------------------
; Setup AUDIO Channel(s)
;----------------------------------------------------
L1CC1: LD A,(0BE01h) ; Get Control Status Byte
BIT 6,A ; Do we need just one audio channel?
JR Z,L1CE1 ; Yes, so determine which channel
;----------------------------------------------------
; Turn ON both AUDIO 1 and AUDIO 2
;----------------------------------------------------
L1CC8: CALL L1D4E ; Check LDPlayer type
JR Z,L1CD8 ; PR-7820 selected so skip ahead
;----------------------------------------------------
; LD-V1000: AUDIO 1 and AUDIO 2 ON
;----------------------------------------------------
LD A,001h ; Set AUDIO 1 to ON
CALL L1D30 ; Send AUDIO 1 Command
LD A,001h ; Set AUDIO 2 to ON
CALL L1D3F ; Send AUDIO 2 Command
RET ; Return
;----------------------------------------------------
; PR-7820: AUDIO 1 and AUDIO 2 ON
;----------------------------------------------------
L1CD8: LD A,012h ; Command = BOTH AUDIO SELECT (PR-7820)
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
RET ; Return
;----------------------------------------------------
; Determine which AUDIO channel 1 or 2
;----------------------------------------------------
L1CE1: BIT 7,A ; Test which channel to turn on
JR Z,L1CFE ; Skip ahead and turn AUDIO 1 ON
;----------------------------------------------------
; Turn just AUDIO 2 ON
;----------------------------------------------------
CALL L1D4E ; Check LDPlayer type
JR Z,L1CF5 ; PR-7820 selected so skip ahead
;----------------------------------------------------
; LD-V1000: AUDIO 2 ON
;----------------------------------------------------
LD A,001h ; Set AUDIO 2 to ON
CALL L1D3F ; Send AUDIO 2 Command
LD A,000h ; Set AUDIO 1 to OFF
CALL L1D30 ; Send AUDIO 1 Command
RET ; Return
;----------------------------------------------------
; PR-7820: AUDIO 2 ON
;----------------------------------------------------
L1CF5: LD A,01Ah ; Command = AUDIO 2 SELECT (PR-7820)
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
RET ; Return
;----------------------------------------------------
; Turn just AUDIO 1 ON
;----------------------------------------------------
L1CFE: CALL L1D4E ; Check LDPlayer type
JR Z,L1D0E ; PR-7820 selected so skip ahead
;----------------------------------------------------
; LD-V1000: AUDIO 1 ON
;----------------------------------------------------
LD A,001h ; Set AUDIO 1 to ON
CALL L1D30 ; Send AUDIO 1 Command
LD A,000h ; Set AUDIO 2 to OFF
CALL L1D3F ; Send AUDIO 2 Command
RET ; Return
;----------------------------------------------------
; PR-7820: AUDIO 1 ON
;----------------------------------------------------
L1D0E: LD A,019h ; Command = AUDIO 1 SELECT (PR-7820 A1)
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
RET ; Return
;----------------------------------------------------
; MUTE AUDIO
;----------------------------------------------------
L1D17: CALL L1D4E ; Check LDPlayer type
JR Z,L1D27 ; PR-7820 selected so skip ahead
;----------------------------------------------------
; LD-V1000: ALL AUDIO OFF
;----------------------------------------------------
LD A,000h ; Set AUDIO 1 to OFF
CALL L1D30 ; Send AUDIO 1 Command
LD A,000h ; Set AUDIO 2 to OFF
CALL L1D3F ; Send AUDIO 2 Command
RET ; Return
;----------------------------------------------------
; PR-7820: ALL AUDIO OFF
;----------------------------------------------------
L1D27: LD A,013h ; Command = ALL AUDIO OFF (PR-7820 A0)
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
RET ; Return
;----------------------------------------------------
; Send AUDIO 1 command to LDPlayer
; A = 00, OFF A= 01, ON
;----------------------------------------------------
L1D30: CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
LD A,010h ; Command = AUDIO 1
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
RET ; Return
;----------------------------------------------------
; Send AUDIO 2 command to LDPlayer
; A = 00, OFF A= 01, ON
;----------------------------------------------------
L1D3F: CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
LD A,011h ; Command = AUDIO 2
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
RET
;----------------------------------------------------
; Check LDPLAYER TYPE
;----------------------------------------------------
; Return Z PR-7820
; NZ LD-V1000
;----------------------------------------------------
L1D4E: LD HL,0A79Ah ; Get LDPlayer Status Byte
BIT 3,(HL) ; Check LDPLAYER TYPE
RET ; Return
;----------------------------------------------------
; Perform Attract Mode AUDIO Check
;----------------------------------------------------
L1D54: LD A,(0BE0Fh) ; Get DIP Switch A
BIT 5,A ; Test A6, Attract Mode Audio
JR NZ,L1D60 ; Attract Mode Audio ON, so skip ahead
L1D5B: CALL L1D17 ; MUTE audio
JR L1D70 ; Skip Attract Mode Count
L1D60: BIT 6,A ; Test A7, Attact Mode Count
JR NZ,L1D6D ; Audio Always ON, so skip ahead
LD HL,0A788h ; Point to Attract Mode Count
INC (HL) ; Increment Attract Mode Count
LD A,(HL) ; Get Attract Mode Count
AND 007h ; Test if it is equal to 8
JR NZ,L1D5B ; Not equal to 8 so loop back
L1D6D: CALL L1CC8 ; Enable AUDIO
L1D70: RET ; Return
;----------------------------------------------------
; Convert number (frame number or score) to BCD
; BCD is Binary-Coded Decimal
; A794-A796 Number awaiting conversion to BCD
; A7B5-A7B7 BCD, Number after converted to BCD
;----------------------------------------------------
L1D71:
MakeBCD:
;----------------------------------------------------
; Clear out BCD area A7B5 - A7B7
;----------------------------------------------------
LD HL,0A7B5h ; Setup BCD location to A7B5
LD B,004h ; B = 4, set Loop
L1D76: LD (HL),000h ; Store a zeros in BCD location
INC HL ; Increment byte pointer
DJNZ L1D76 ; B = B - 1, Loop until B = 0
;----------------------------------------------------
; Begin BCD conversion
;----------------------------------------------------
LD B,018h ; B = 24, set Loop
L1D7D: LD HL,0A794h ; Number to convert starts at A794
LD C,003h ; C = 3, set Loop
XOR A ; Clear carry
L1D83: RL (HL) ; Roll BCD bits to the left
INC HL ; Increment byte pointer
DEC C ; C = C - 1
JP NZ,L1D83 ; Loop until C = 0
LD HL,0A7B5h ; Set beginning of BCD area
LD C,004h ; C = 4, set Loop
L1D8F: LD A,(HL) ; Get BCD byte
ADC A,(HL) ; BCD = BCD * 2 + Carry
DAA
LD (HL),A ; Store calculation in BCD
INC HL ; Go to next BCD byte
DEC C ; C = C - 1
JP NZ,L1D8F ; Loop until C = 0, all BCD bytes
DJNZ L1D7D ; B = B - 1, Get next bit until B = 0
RET ; Return
;----------------------------------------------------
; SEARCH to Frame
;----------------------------------------------------
; A7B7h hold Frame Number in BCD
;----------------------------------------------------
L1D9B: CALL MakeBCD ; Convert number to BCD
LD HL,0A787h ; Point to Number of SEARCH Retries
LD (HL),000h ; Clear Number of SEARCH Retries to zero
;----------------------------------------------------
; Send Frame Number to LDPlayer
;----------------------------------------------------
; Send the 5 numbers that make up the frame number
; as separate commmands.
;----------------------------------------------------
L1DA3: LD HL,0A7B7h ; Point to Frame Number
LD A,(HL) ; Get Frame Number
AND 00Fh ; Isolate lower nibble digit
CALL GetCommand ; Convert data to LDPlayer Command Code
CALL L1E80 ; Send $FF then Command byte to LDPlayer
DEC HL ; Point to next digit
LD A,(HL) ; Get next digit
SRL A ; Shift right, Isolate upper nibble
SRL A ; Shift right
SRL A ; Shift right
SRL A ; Shift right
CALL GetCommand ; Convert data to LDPlayer Command Code
CALL L1E80 ; Send $FF then Command byte to LDPlayer
LD A,(HL) ; Get Frame Number
AND 00Fh ; Isolate lower nibble digit
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
DEC HL ; Send $FF then Command byte to LDPlayer
LD A,(HL) ; Get next digit
SRL A ; Shift right, Isolate upper nibble
SRL A ; Shift right
SRL A ; Shift right
SRL A ; Shift right
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
LD A,(HL) ; Get Frame Number
AND 00Fh ; Command = DISPLAY
CALL GetCommand ; Get LDPlayer Command Byte
CALL L1E80 ; Send $FF then Command byte to LDPlayer
NEXT PAGE
|