4) Input from keyboard
Input on the ZX81 can be obtained in 2 ways.
The easiest way is to use the systemvariable stored in LASTK.
The other way is to read parts of the keyboard or joysticks.
Each 1/50 sec the screen is displayed and the keyboard is read.
The result of reading the keyboard is stored in LASTK, a 2 byte address
containing information about the key that is pressed.
For now we will test IF a key is pressed, not what key.
So again open now GAME1-001.ASM and save as GAME1-002.ASM
We want to see what is displayed. In our earlier version the display was
raging fast. We can add a check if a key is pressed, if not the program will halt.
For this I need to explain the registers a bit
With the register A, B, C, D, E, H and L you can set values from 0 to 255
(negative numbers are also possible but just see it as 0-255)
However B and C, D and E, H and L together form a 16bit register.
This will give you values from 0-65535
You can read and write 16 bits registers
directly from a memorylocation.
For 8 bits that is only possible for the A-register, as we did with the writing
to the screen. To test a key press we need to read LASTK. We can do that with A but then
we don;t know what to write to the screen. So we use a pair to read LASTK. BC is the best
to use as we will find out later.
Place the following code UNDER the line with the label "showa"
Code: Select all
nokey ld bc,(lastk)
inc c
jr z,nokey
This routine reads the LASTK and test if ANY key is pressed.
If NOKEY is pressed C holds 255 and if you add 1 to it it becomes 0 again (overflow)
When that happens we wait in the loop for ANY KEY press.
Save the code and compile. Run the code.
Now you see that we need to press a key to go to the next display.
However the code is still running fast when we press a key.
Get GAME1-002.ASM again in edit, we add a few lines
Again UNDER SHOWA add the following code
Code: Select all
upkey ld bc,(lastk)
inc c
jr nz,upkey
Like before LASTK is read, but now the routine waits until a key is released.
If a key is pressed C is NOT 255 and will never get to 0.
Save and compile.... and try to figure out what you must do to show the character.
LASTK stores information about the key, but not the printable value of the key.
The keyboard of the ZX81 is defined in 40 keys and numeric value.
The table is:
Code: Select all
1 2 3 4 5 6 7 8 9 0
15 16 17 18 19 24 23 22 21 20
Q W E R T Y U I O P
10 11 12 13 14 29 28 27 26 25
A S D F G H J K L NEWL
5 6 7 8 9 34 33 32 31 30
SH Z X C V B N M SY SPACE
0 1 2 3 4 39 38 37 36 35
lucky for us the ROM is possible to do the translation for us.
And it even has a table to read from the keynumber the ASCII-character.
Let's edit GAME1-002.ASM and save it as GAME1-003.ASM.
We will alter the routine too much.
A CALL is like GOSUB in BASIC it goes to a subroutine and returns after the CALL with a RET(urn)
Replace the code between gamecode and dfile with this:
Code: Select all
gamecode ld bc,(lastk) ; get key information
ld a,c ; copy C in A to keep C
inc a ; Test if NOKEY pressed
jr z,gamecode ; NO KEY, wiat for key
call #7bd ; BC holds info about key, ROM can translated this here
ld a,(hl) ; After the CALL registerpair HL points to ASCII-character, get characer
ld (screen),a ; write character
jr gamecode ; JUMP back to start
Save and compile, see what happens when you press a key.