I decided I needed to learn to check for console key presses before moving onto to what I imagine will be much more difficult subjects like graphics and sound. So here it is. I wrote a smallish program to check for presses of the common console keys (OPTION, SELECT, START), and combinations there of. In doing so I also added a check for the BREAK key, though it’s not technically a console key. In addition, for XL/XE systems, it will check for the added console key HELP.
Library Code
To support this program I added a few lines to my A8 Assembly library. Here is the updated library.
A8DEFS.LIB Code
01 ; ------------------------------ 02 ; Lib.: A8DEFS.LIB 03 ; Desc: Definitions Library 09 ; ------------------------------ 99 ; I/O 0100 CIOV = $E456 0110 ICHID = $0340 ;IOCB 0 S: 0120 ICCOM = $0342 ;IOCB Command 0130 ICBAL = $0344 ;Xfer Buffer Adr 0140 ICBAH = $0345 0150 ICBLL = $0348 ;Buffer Len 0160 ICBLH = $0349 0162 ICAX1 = $0350 ;AUX byte 1 0164 ICAX2 = $0351 ;AUX byte 2 0499 ; Cursor 0500 LMARG = $52 ;82 0510 ROWCRS = $54 ;84 0520 COLCRS = $55 ;85 0530 CRSINH = $02F0 ;752 699 ; Console 700 CONSOL = $D01F ;53279 702 CONALL = $00 704 CONOSE = $01 706 CONOST = $02 708 CONO = $03 710 CONSST = $04 712 CONSE = $05 714 CONST = $06 716 CONNO = $07 720 BRKKEY = $11 ;17 730 HELPFG = $02DC ;732 0799 ; Character 0800 EOL = $9B ;155 0810 EOS = $00 0820 CLS = $7D ;125 0830 CIX = $F2 ;Index to INBUFF 0832 INBUFF = $F3 ;2 byte InBuf Ptr 0840 LBUFF = $0580 ;128 bytes 0899 ; Floating Point 0901 FPTEMP = $0482 ; User Mem 126 bytes 0902 ASCFP = $D800 ; ATASCII to FP 0904 FPASC = $D8E6 ; FP to ATASCII 0906 INTFP = $D9AA ; INT to FP 0908 FPINT = $D9D2 ; FP to INT 0910 FPSUB = $DA60 ; FR0-FR1 0912 FPADD = $DA66 ; FR0+FR1 0914 FPMUL = $DADB ; FR0*FR1 0916 FPDIV = $DB28 ; FR0/FR1 0918 FPLD0R = $DD89 ; Load using X,Y 0920 FPLD0P = $DD8D ; Load using FLPTR 0922 FPLD1R = $DD98 ; Load using X,Y 0924 FPLD1P = $DD9C ; Load using FLPTR 0926 FPSTOR = $DDA7 ; Store using X,Y 0928 FPSTOP = $DDA8 ; Store using FLPTR 0930 FPMOVE = $DDB6 ; FR0 to FR1 0940 FPZFR0 = $DA44 ; FR0 = 0 0942 FPZAF1 = $DA46 ; Reg in X = 0 0944 FPPTR1 = $FC ; 2 byte ptr User FP1 0946 FPPTR2 = $FE ; 2 byte ptr User FP2 1000 ; Misc 1010 RANDM = $D20A 1020 POKMSK = $10 ;16 1022 IRQEN = $D20E ;53774
Additions
And these are the additions:
- 720: Break key register
- 730: Help key register
- 1020,1022: Added initially as I was going to write a custom BREAK handler, but ultimately didn’t need to. I left them in anyway since they may come in handy later.
Source Code
This is the source code for “Console Keys”. I used ASCII line drawing characters instead of ATASCII drawing characters to simply code listing on the blog. I named it “CONSOLE.M65”.
01 ; ------------------------------ 02 ; App.: CONSOLE.M65 03 ; Desc: Console Keys 04 ; ------------------------------ 10 .TITLE "Console Keys, Version 1.0" 15 .OPT OBJ,NO EJECT 20 *= $3600 25 .INCLUDE #D2:A8DEFS.LIB 0200 ; ------------------------------ 0201 ; Setup App 0202 ; ------------------------------ 0204 APPST 0210 ; Set Margin 0212 LDA #0 0214 STA LMARG 0220 ; Cursor Off 0222 LDA #1 0224 STA CRSINH 0319 ; Setup Screen 0320 ; Position 0,0 0322 LDX #0 0324 LDY #0 0326 JSR CURXY 0330 ; Print Title 0332 LDA #STITLE/256 0334 LDY #STITLE&255 0336 JSR PRTLN 0340 ; Position 0,2 0342 LDX #0 0344 LDY #2 0346 JSR CURXY 0350 ; Print statement 0352 LDA #SEXIT/256 0354 LDY #SEXIT&255 0356 JSR PRTLN 0400 ; Position 0,4 0402 LDX #0 0404 LDY #4 0406 JSR CURXY 0410 ; Print statement 0412 LDA #SMSG/256 0414 LDY #SMSG&255 0416 JSR PRTLN 0500 ; ------------------------------ 0501 ; Pressed Loop 0502 ; ------------------------------ 0510 PRLOOP 0520 ; Check Break Key 0525 LDA BRKKEY 0530 CMP #0 0535 BEQ RKBRK 0540 ; Check Help Key 0545 LDA HELPFG 0550 CMP #17 0555 BEQ RKHELP 0560 ; Check Console Keys 0565 LDA CONSOL 0568 STA IKEY 0570 CMP #CONNO 0575 BNE PRESSD 0580 JMP PRLOOP 0600 PRESSD 0610 ; Clear text 0612 JSR RCLEAR 0830 ; Which key? 0832 LDA IKEY 0838 CMP #CONOSE ; 1-Option+Select 0840 BEQ RKOSE 0842 CMP #CONOST ; 2-Option+Start 0844 BEQ RKOST 0846 CMP #CONO ; 3-Option 0848 BEQ RKO 0850 CMP #CONSST ; 4-Select+Start 0852 BEQ RKSST 0854 CMP #CONSE ; 5-Select 0856 BEQ RKSE 0858 CMP #CONST ; 6-Start 0860 BEQ RKST 0870 CMP #CONALL ; 0-All keys 0872 BEQ RKALL 0960 ; Loop for next press check 0965 JMP PRLOOP 1000 ; ------------------------------ 1001 ; Break 1002 ; ------------------------------ 1010 RKBRK 1012 JSR RCLEAR 1019 ; Print BREAK 1020 LDA #SKBRK/256 1022 LDY #SKBRK&255 1024 JSR PRTLN 1029 ; Goto APPDON (exit) 1030 JMP APPDON 1050 ; ------------------------------ 1051 ; Help 1052 ; ------------------------------ 1060 RKHELP 1062 JSR RCLEAR 1063 ; Print HELP 1064 LDA #SKHELP/256 1065 LDX #SKHELP&255 1068 JSR PRTCH 1069 ; Reset Help flag 1070 LDA #0 1072 STA HELPFG 1079 ; Goto PRLOOP (next) 1080 JMP PRLOOP 1100 ; ------------------------------ 1101 ; Option + Select 1102 ; ------------------------------ 1110 RKOSE 1119 ; Print OPTION 1120 LDA #SKO/256 1122 LDX #SKO&255 1124 JSR PRTCH 1129 ; Print SELECT 1130 LDA #SKSE/256 1132 LDX #SKSE&255 1134 JSR PRTCH 1139 ; Goto PRLOOP (next) 1140 JMP PRLOOP 1200 ; ------------------------------ 1201 ; Option + Start 1202 ; ------------------------------ 1210 RKOST 1219 ; Print OPTION 1220 LDA #SKO/256 1222 LDX #SKO&255 1224 JSR PRTCH 1229 ; Print START 1230 LDA #SKST/256 1232 LDX #SKST&255 1234 JSR PRTCH 1239 ; Goto PRLOOP (next) 1240 JMP PRLOOP 1350 ; ------------------------------ 1351 ; Option 1352 ; ------------------------------ 1360 RKO 1361 ; Print OPTION 1362 LDA #SKO/256 1364 LDX #SKO&255 1366 JSR PRTCH 1367 ; Goto PRLOOP (next) 1368 JMP PRLOOP 1400 ; ------------------------------ 1401 ; Select + Start 1402 ; ------------------------------ 1410 RKSST 1419 ; Print SELECT 1420 LDA #SKSE/256 1422 LDX #SKSE&255 1424 JSR PRTCH 1429 ; Print START 1430 LDA #SKST/256 1432 LDX #SKST&255 1434 JSR PRTCH 1439 ; Goto PRLOOP (next) 1440 JMP PRLOOP 1500 ; ------------------------------ 1501 ; Select 1502 ; ------------------------------ 1510 RKSE 1519 ; Print SELECT 1520 LDA #SKSE/256 1522 LDX #SKSE&255 1524 JSR PRTCH 1529 ; Goto PRLOOP (next) 1530 JMP PRLOOP 1600 ; ------------------------------ 1601 ; Start 1602 ; ------------------------------ 1610 RKST 1619 ; Print START 1620 LDA #SKST/256 1622 LDX #SKST&255 1624 JSR PRTCH 1629 ; Goto PRLOOP (next) 1630 JMP PRLOOP 1700 ; ------------------------------ 1701 ; Option + Select + Start 1702 ; ------------------------------ 1710 RKALL 1719 ; Print OPTION 1720 LDA #SKO/256 1722 LDX #SKO&255 1724 JSR PRTCH 1729 ; Print SELECT 1730 LDA #SKSE/256 1732 LDX #SKSE&255 1734 JSR PRTCH 1739 ; Print START 1740 LDA #SKST/256 1742 LDX #SKST&255 1744 JSR PRTCH 1746 ; Goto PRLOOP (next) 1748 JMP PRLOOP 2500 ; ------------------------------ 2501 ; Clear Key Pressed Text 2502 ; ------------------------------ 2510 RCLEAR 2512 ; Position 13,4 2514 LDX #13 2516 LDY #4 2518 JSR CURXY 2520 ; Print blank 2522 LDA #SKNONE/256 2524 LDX #SKNONE&255 2526 JSR PRTCH 2530 ; Position 13,4 2532 LDX #13 2534 LDY #4 2536 JSR CURXY 2539 ; Return 2540 RTS 2900 ; ------------------------------ 2901 ; End of program 2902 ; ------------------------------ 2910 APPDON 2995 RTS 30000 ; ----- String Data ----- 30002 STITLE .BYTE CLS,"-|Console Keys|-------------------------",EOL 30004 SEXIT .BYTE "Press BREAK to exit.",EOL 30006 SMSG .BYTE "You pressed: ",EOL 30010 SKO .BYTE "OPTION ",EOS 30015 SKSE .BYTE "SELECT ",EOS 30020 SKST .BYTE "START ",EOS 30025 SKBRK .BYTE "BREAK",EOL 30026 SKHELP .BYTE "HELP",EOS 30030 SKNONE .BYTE " ",EOS 31000 ; ----- Variables ----- 31005 IKEY .BYTE 0 50000 ; ----- Function Includes ----- 50010 .INCLUDE #D2:A8FUNCS.LIB 64000 ; ---------- E N D ---------- 64001 .END
Breakdown
The code is documented pretty well. I will break down the pieces that are important for this program, which is mainly the press loop (PRLOOP).
- 20: Location to load program in memory
- 200-416: Set margin, turn the cursor off, print the display text in the right spots.
- 510: Start of the loop
- 525: Load the break key register into the accumulator
- 530: Compare the accumulator with value 0 (0 means break was pressed)
- 535: If the comparison is equal, branch to program location RKBRK
- 545: Load the help key register into the accumulator
- 550: Compare the accumulator with value 17 (17 means help key was pressed)
- 555: If the comparison is equal, branch to program location RKHELP
- 565: Load the console key register into the accumulator
- 568: Store the value into location IKEY. This is because the value in the accumulator will be changed by the time we actually need to check which key was pressed.
- 570: Compare the accumulator with value CONNO or 7 (7 means no key was pressed).
- 575: If the comparison is not equal (a key was pressed), branch to program location PRESSD
- 580: Goto the start of the loop to check again. No keys were pressed of any kind.
- 600: Start of which console key was pressed decision tree. This is only executed if a console key has been pressed (OPTION, SELECT, or START)
- 612: Call the clear text subroutine to remove what was on the screen before this press.
- 832: Load the value from location IKEY (the saved value) into the accumulator
- 838: Compare the accumulator with value CONOSE or 1 (1 means OPTION and SELECT were pressed)
- 840: If the comparison is equal, branch to program location RKOSE
- 842: Compare the accumulator with value CONOST or 2 (2 means OPTION and START were pressed)
- 844: If the comparison is equal, branch to program location RKOST
- 846: Compare the accumulator with value CONO or 3 (3 means OPTION was pressed)
- 848: If the comparison is equal, branch to program location RKO
- 850: Compare the accumulator with value CONSST or 4 (4 means SELECT and START were pressed)
- 852: If the comparison is equal, branch to program location RKSST
- 854: Compare the accumulator with value CONSE or 5 (5 means SELECT was pressed)
- 856: If the comparison is equal, branch to program location RKSE
- 858: Compare the accumulator with value CONST or 6 (6 means START was pressed)
- 860: If the comparison is equal, branch to program location RKST
- 870: Compare the accumulator with value CONALL or 0 (0 means OPTION, SELECT, and START were pressed)
- 872: If the comparison is equal, branch to program location RKALL
- 965: Goto PRLOOP to check for a key. Technically this should never be reached since all possible values of the CONSOL register were checked and conditioned for.
- 1000-1748: The subroutines for each key press and key press combination.
- 2500-2540: Clear output text subroutine. Positions the cursors, prints the blank space, then repositions the cursor for output.
- 2910-2995: The exit routine
- 30000-30030: String storage
- 31000-31005: Variable storage
Results
Program start up waiting for initial input:
Pressing OPTION key:
Pressing OPTION, SELECT, and START:
Pressing HELP (for XL/XE machines):
Pressing Break:
The source code is just about 5K in size, but it assembles down nicely to 547 bytes: