Prev: 72CA Up: Map Next: 7337
72D4: Print a message (message bytecode interpreter)
Almost everything the game says is printed by this routine, which interprets a compact message 'bytecode' starting at the address in HL. Messages are not stored as ASCII; they are sequences of dictionary references and control codes, which is how The Hobbit fits so much text into 48K.
The entry at 72D4 saves DE, IX and A (restored at the end, 7352) so callers do not lose them. If the command is only being tried ($B5EB is 0) the flag B5EC is cleared.
The loop at 72EB fetches a byte and decides what it is:
  • $80-$FF: the first byte of a two-byte dictionary reference, high byte first. The low nibble of the first byte and all of the second give the word's offset from 6000; the three remaining flag bits (bits 4-6) choose an ending. Flag values 2, 3 and 6 mean 'this is the last word of the message': 2 just stops, 3 adds a full stop and a new line, 6 adds a new line (733F). Other values are passed on to 74B8 as printing flags (for example 'add an S').
  • $60-$7F: one of the 32 most common words, looked up in AC31 by 748A.
  • $20-$5F: a literal character, printed by 72BA.
  • $00-$1F: a control code, dispatched through the table at 728C.
Control codes below $14 are called as subroutines. A handler that returns with Z set lets the interpreter move on to the next byte; one that returns with Z reset asks it to print the dictionary word now in DE (so a handler can choose a word such as HIS or YOUR and have it printed). Codes $14 and above end the message.
Several control codes take an extra parameter from the stack: the caller pushes an object address or a word before calling the interpreter, and the handler removes it (see 735E).
The same interpreter runs the little scripts attached to rooms and objects, which is why the room and object tables contain what look like fragments of messages.
Input
HL Address of the message bytecode
72D4 LD ($70D4),DE Store DE at 70D4
72D8 LD ($70D7),IX Store IX at 70D7
72DC LD ($70D3),A Store A at 70D3
72DF LD A,($B5EB) A = the "really do it" flag
72E2 AND A Is A zero?
72E3 JR NZ,$72E8 If it is not zero, go to 72E8
72E5 LD ($B5EC),A Store A in the "it would work" flag
This entry point is used by the routine at 73D7.
72E8 PUSH HL Save HL
72E9 POP IX Restore IX
72EB LD A,(IX+$00) A = (IX+0)
72EE BIT 7,A Bit 7 set: a dictionary word reference
72F0 JR Z,$730F If the bit is clear, go to 730F
72F2 AND $7F Keep only the bits of $7F
72F4 LD D,A D = A
72F5 LD E,(IX+$01) E = (IX+1)
72F8 INC IX Increment IX
72FA AND $F0 Flag values 3, 2 and 6 end the message
72FC CP $30 Is it "0"?
72FE JR Z,$733F If yes, go to Print the last word of a message and finish (733F)
7300 CP $20 Is it " "?
7302 JR Z,$733F If yes, go to Print the last word of a message and finish (733F)
7304 CP $60 Is it "`"?
7306 JR Z,$733F If yes, go to Print the last word of a message and finish (733F)
This entry point is used by the routine at 748A.
7308 CALL $74B8 Print an ordinary dictionary word
730B INC IX Increment IX
730D JR $72EB Continue at 72EB
730F CP $20 Otherwise: control code, abbreviation or literal character
7311 JR C,$731D If A < 32, go to 731D
7313 CP $60 Is it "`"?
7315 JP NC,$748A $60-$7F: one-byte abbreviation
7318 CALL $72BA Call: Print a character from a message (72BA)
731B JR $730B Continue at 730B
731D PUSH DE Save DE
731E LD E,A E = A
731F LD D,$00 D = 0
7321 LD HL,$728C $00-$1F: index into the control-code jump table
7324 ADD HL,DE Add HL,DE
7325 ADD HL,DE Add HL,DE
7326 LD E,(HL) E = (HL)
7327 INC HL Increment HL
7328 LD D,(HL) D = (HL)
7329 EX DE,HL Swap DE and HL
732A POP DE Restore DE
732B CP $14 Codes $14 and above end the message
732D JR NC,$7336 If A >= 20, go to 7336
732F CALL $7336 Call the handler; Z set means carry on
7332 JR Z,$730B If the routine returned with Z set, go to 730B
7334 JR $7308 Z reset: print the word in DE, then carry on
7336 JP (HL) Jump to the address in HL
Prev: 72CA Up: Map Next: 7337