A custom table should consist of 89 values in matrix code order. Refer to Tables 9-1-9-5 for a listing of the default ta- bles. The final value in the table should be 255/$FF, and you should be sure to include the shift key codes in the proper lo- cations. The following program sets up a Dvorak-style
keyboard:
100 FOR 1=0 TO 88:READ K:POKE 691.2 + 1 ,K:NEXT 110 POKE 830,0:POKE S31,27:END
120 DATA 2 0 , 1 3 , 2 9 , 1 3 6 , 1 3 3 , 1 3 4 , 1 3 5 , 1 7 , 5 1 , 4 4 130 DATA 6 5 , 5 2 , 5 9 , 7 9 , 4 6 , I , 5 3 , 8 0 , 6 9 , 5 4 140 DATA 7 4 , 8 5 , 8 9 , 8 1 , 5 5 , 7 0 , 7 3 , 5 6 , 8 8 , 6 8 150 DATA 7 1 , 7 5 , 5 7 , 6 7 , 7 2 , 4 8 , 7 7 , 8 4 , 8 2 , 6 6 160 DATA 4 3 , 7 6 , 7 8 , 4 5 , 8 6 , 8 3 , 4 7 , 8 7 , 9 2 , 4 2 170 DATA 5 9 , 1 9 , 1 , 6 1 , 9 4 , 9 0 , 4 9 , 9 5 , 4 , 5 0 180 DATA 3 2 , 2 , 3 9 , 3 , 1 3 2 , 5 6 , 5 3 , 9 , 5 0 , 5 2 190 DATA 5 5 , 4 9 , 2 7 , 4 3 , 4 5 , 1 0 , 1 3 , 5 4 , 5 7 , 5 1 200 DATA 8 , 4 8 , 4 6 , 1 4 5 , 1 7 , 1 5 7 , 2 9 , 2 5 5 , 255 842-851 $034A-$0353 KEYBUF Keyboard buffer
This ten-byte area is the keyboard buffer. When the SCNKEY routine [$C55D] detects a valid keypress, it generates a cor- responding character code. The character code is then stored in this buffer to await processing. (The Kernal GETIN and BA- SIN routines are normally used to retrieve characters from this buffer.) Location 208/$D0 holds the number of characters cur- rently waiting in the buffer. The maximum number of charac- ters that can be held in the buffer is determined by the value in location 2592/$0A20. If the value there is greater than 10, the keyboard buffer will overwrite the following memory areas such as the tab stop bitmap. When the value in 208/$DO equals the value in 2592/$0A20, the buffer is full; any further
830-841 $033E-$0349 $034A-$0353 842-851
830-841 $033E-$0349 DECODE
Keyboard table pointers
These six 2-byte pointers hold the starting addresses of the 89- byte tables used to translate the matrix code for the current keypress into a character code:
Pointer Shift pattern 830-831/$033E-$033F Unshifted SHIFT Commodore CONTROL ALT 832-833/$0340-$0341 834-835/$0342-$0343 836-837/$0344-$0345 838-839/$0346-$0347 840-841/$0348-$0349
Default table address 64128/$FA80 64217/$FAD9 64306/SFB32 64395/$FB8B 64128/$FA80 (same as unshifted) 64484/$FBE4 CAPS LOCK
The status of the five shift keys, recorded in 211/$D3, is used to select one of the table addresses from this area. If no shift key is pressed, the unshifted table is used. If one shift key is pressed, the appropriate decoding table is selected. If more than one shift key is pressed simultaneously, the table is se- lected as follows: CONTROL has the highest priority; when it is pressed in combination with any other shift keys, the CON- TROL table is used. The SHIFT and Commodore keys are next in priority; however, when they are pressed simultaneously, no decoding table is selected (although the combination may cause character set switching). ALT and CAPS LOCK have the lowest priority. They are effective in selecting the decoding ta- ble only if no other shift keys are being pressed. If pressed simultaneously, both are ignored and the unshifted table is used. Once a table is selected, its address is loaded into 204-205/$CC-$CD, and the current matrix code in 212/$D4 is used as an offset to the specific character code to be re- trieved from the table.
The default decoding table addresses are copied here from a table at 49263/$C06F in screen editor ROM by the CINT screen editor initialization routine [$C07B] during the reset se- quence. CINT is also part of the RUN/STOP-RESTORE se- quence, but it includes a flag that normally prevents the vectors from being reinitialized in that case. To redefine the 128 keyboard, you need only set up a new decoding table in RAM and change one of the address values here to point to the new table. For example, if you've used the CAPS LOCK key, you've probably discovered that it doesn't appear to af- fect the Q key. Actually, the problem is that whoever prepared
the CAPS LOCK decoding table used the wrong value for the Q key entry. The following shows how to fix the CAPS-Q bug by setting up a new copy of the decoding table for that shift pattern:
100 REM ** COPY CAPS LOCK TABLE TO RAM 110 FOR 1 = 0 TO 88:POKE 6912 + I,PEEK(64484 + I):NEXT
120 REM ** CHANGE INCORRECT CHARACTER CODE FOR Q 130 POKE 6912 + 62,209
140 REM ** REDIRECT POINTER TO NEW TABLE 150 POKE 840,0:POKE 841,27
A custom table should consist of 89 values in matrix code order. Refer to Tables 9-1-9-5 for a listing of the default ta- bles. The final value in the table should be 255/$FF, and you should be sure to include the shift key codes in the proper lo- cations. The following program sets up a Dvorak-style
keyboard:
100 FOR 1=0 TO 88:READ K:POKE 691.2 + 1 ,K:NEXT 110 POKE 830,0:POKE S31,27:END
120 DATA 2 0 , 1 3 , 2 9 , 1 3 6 , 1 3 3 , 1 3 4 , 1 3 5 , 1 7 , 5 1 , 4 4 130 DATA 6 5 , 5 2 , 5 9 , 7 9 , 4 6 , I , 5 3 , 8 0 , 6 9 , 5 4 140 DATA 7 4 , 8 5 , 8 9 , 8 1 , 5 5 , 7 0 , 7 3 , 5 6 , 8 8 , 6 8 150 DATA 7 1 , 7 5 , 5 7 , 6 7 , 7 2 , 4 8 , 7 7 , 8 4 , 8 2 , 6 6 160 DATA 4 3 , 7 6 , 7 8 , 4 5 , 8 6 , 8 3 , 4 7 , 8 7 , 9 2 , 4 2 170 DATA 5 9 , 1 9 , 1 , 6 1 , 9 4 , 9 0 , 4 9 , 9 5 , 4 , 5 0 180 DATA 3 2 , 2 , 3 9 , 3 , 1 3 2 , 5 6 , 5 3 , 9 , 5 0 , 5 2 190 DATA 5 5 , 4 9 , 2 7 , 4 3 , 4 5 , 1 0 , 1 3 , 5 4 , 5 7 , 5 1 200 DATA 8 , 4 8 , 4 6 , 1 4 5 , 1 7 , 1 5 7 , 2 9 , 2 5 5 , 255 842-851 $034A-$0353 KEYBUF Keyboard buffer
This ten-byte area is the keyboard buffer. When the SCNKEY routine [$C55D] detects a valid keypress, it generates a cor- responding character code. The character code is then stored in this buffer to await processing. (The Kernal GETIN and BA- SIN routines are normally used to retrieve characters from this buffer.) Location 208/$D0 holds the number of characters cur- rently waiting in the buffer. The maximum number of charac- ters that can be held in the buffer is determined by the value in location 2592/$0A20. If the value there is greater than 10, the keyboard buffer will overwrite the following memory areas such as the tab stop bitmap. When the value in 208/$DO equals the value in 2592/$0A20, the buffer is full; any further
842-851 $034A-$0353 $035E-$0361 862-865
keypresses will be ignored until one or more characters are re- moved from the buffer.
This key buffering system allows for a powerful program- ming technique known as the dynamic keyboard. By storing character code values in the buffer and storing the number of characters in 208/$D0, a program can appear to type on the keyboard. For example, the following lines add a default an- swer to the INPUT prompt:
200 POKE 842,89: POKE 208,1: REM PLACE Y IN BUFFER 210 INPUT'ARE YOU SURE";A$
When the INPUT statement begins to look for characters, it will find the Y already in the buffer.
An even more powerful use of the dynamic keyboard technique is to allow a program to execute a series of com- mands after it ends. When a program is finished executing, BASIC looks to the keyboard buffer for the characters of the next command. Thus, any characters placed in the buffer while a program is running will effectively be typed if the pro- gram ends. Since the buffer can hold only ten characters, the common practice is to print commands at carefully planned places on the screen, then fill the buffer with cursor move- ment and RETURN characters to execute the commands. The following program illustrates this technique. It creates DATA statements for one of the sprite patterns. You can adapt the program for your own needs by changing the values in line 10. AD is the starting address of the data, NI is the number of DATA items to be generated, and LN is the line number of the first DATA statement to be generated. The program prints a DATA line and a GOTO statement on the screen, then places {HOME} {RETURN} {RETURN} in the buffer and ends. The buffered characters are executed, entering the DATA line and restarting the program.
10 AD=3584:NI=64:LN=100!l=0 20 IF I=>NI THEN END
30 PRINT"[CLR}";LN;"DATA";:LN=LN+I0:J=0 40 PRINT P E E K ( A D + I ) ; : I = I + 1 : I P I=>NI THEN 60 50 J = J + 1 ; I F J < 8 THEN PRINT"{LEFT},";:GOTO 40 60 PRINT:PRINT"GOTO 20"
70 POKE 8 4 2 , I 9 : P O K E 843,13:POKE 844,.13:POKE 2 0 3 , 3 : E ND
104
A.
852-861 $0354-$035D TABMAP
Tab stop bitmap
These ten bytes provide an 80-bit map of the display's hori- zontal character positions. Each horizontal position in the cur- rently active display has a corresponding bit in the map. For the VIC chip's 40-column display, only the first five bytes (40 bits) are used. When a bit is set to % 1 , a tab stop is estab- lished at the corresponding screen column. Printing the TAB character, code 9/$09, or pressing the TAB key will move the cursor rightward to the next tab stop (or the right window margin if no tab stops are set between the current cursor posi- tion and the right margin).
During the CINT screen editor initialization sequence, all locations in the map are set to 128/$80, which establishes a tab stop every eighth column. Printing character code 24/$18 (or pressing SHIFT-TAB) toggles the map bit corresponding to the current cursor column, setting a tab stop if the bit was pre- viously %0 or clearing the tab stop if the bit was previously % 1 . The ESC Z sequence can be used to clear all tab stops (all locations in the map will be filled with 0/$00), and the ESC Y sequence can be used to restore default tab stops (all locations in the map will be filled with 128/S80).
When the active display is switched, screen editor SWAP- PER routine [$CD2E] exchanges the contents of this area with the contents of locations 2656-2665/$0A60-$0A69, the stor- age area for the inactive display tab stop bitmap. Thus, tab stop settings are preserved while the screen is inactive,
862-865 $035E-$0361 LNKMAP
Line link bitmap
These four bytes are used to provide a 25-bit map of the 25 rows of the active screen display (bits 0-6 of location 865/$361 are unused). Each row of the currently active dis- play has a corresponding bit in the map. When a bit is set to % 1 , the corresponding row is linked to the row above as part of a logical line. Bits set to %0 indicate unlinked lines (or rows that are the first physical line of a logical line). These locations are cleared to 0/$00, unlinking all lines, whenever the output window is cleared or reset to full screen size, or whenever the screen editor WINDOW routine is used to change the size of the output window. A screen line is normally linked to the one above when the cursor moves onto the line by wrapping
842-851 $034A-$0353 $035E-$0361 862-865
keypresses will be ignored until one or more characters are re- moved from the buffer.
This key buffering system allows for a powerful program- ming technique known as the dynamic keyboard. By storing character code values in the buffer and storing the number of characters in 208/$D0, a program can appear to type on the keyboard. For example, the following lines add a default an- swer to the INPUT prompt:
200 POKE 842,89: POKE 208,1: REM PLACE Y IN BUFFER 210 INPUT'ARE YOU SURE";A$
When the INPUT statement begins to look for characters, it will find the Y already in the buffer.
An even more powerful use of the dynamic keyboard technique is to allow a program to execute a series of com- mands after it ends. When a program is finished executing, BASIC looks to the keyboard buffer for the characters of the next command. Thus, any characters placed in the buffer while a program is running will effectively be typed if the pro- gram ends. Since the buffer can hold only ten characters, the common practice is to print commands at carefully planned places on the screen, then fill the buffer with cursor move- ment and RETURN characters to execute the commands. The following program illustrates this technique. It creates DATA statements for one of the sprite patterns. You can adapt the program for your own needs by changing the values in line 10. AD is the starting address of the data, NI is the number of DATA items to be generated, and LN is the line number of the first DATA statement to be generated. The program prints a DATA line and a GOTO statement on the screen, then places {HOME} {RETURN} {RETURN} in the buffer and ends. The buffered characters are executed, entering the DATA line and restarting the program.
10 AD=3584:NI=64:LN=100!l=0 20 IF I=>NI THEN END
30 PRINT"[CLR}";LN;"DATA";:LN=LN+I0:J=0 40 PRINT P E E K ( A D + I ) ; : I = I + 1 : I P I=>NI THEN 60 50 J = J + 1 ; I F J < 8 THEN PRINT"{LEFT},";:GOTO 40 60 PRINT:PRINT"GOTO 20"
70 POKE 8 4 2 , I 9 : P O K E 843,13:POKE 844,.13:POKE 2 0 3 , 3 : E ND
104
A.
852-861 $0354-$035D TABMAP
Tab stop bitmap
These ten bytes provide an 80-bit map of the display's hori- zontal character positions. Each horizontal position in the cur- rently active display has a corresponding bit in the map. For the VIC chip's 40-column display, only the first five bytes (40 bits) are used. When a bit is set to % 1 , a tab stop is estab- lished at the corresponding screen column. Printing the TAB character, code 9/$09, or pressing the TAB key will move the cursor rightward to the next tab stop (or the right window margin if no tab stops are set between the current cursor posi- tion and the right margin).
During the CINT screen editor initialization sequence, all locations in the map are set to 128/$80, which establishes a tab stop every eighth column. Printing character code 24/$18 (or pressing SHIFT-TAB) toggles the map bit corresponding to the current cursor column, setting a tab stop if the bit was pre- viously %0 or clearing the tab stop if the bit was previously % 1 . The ESC Z sequence can be used to clear all tab stops (all locations in the map will be filled with 0/$00), and the ESC Y sequence can be used to restore default tab stops (all locations in the map will be filled with 128/S80).
When the active display is switched, screen editor SWAP- PER routine [$CD2E] exchanges the contents of this area with the contents of locations 2656-2665/$0A60-$0A69, the stor- age area for the inactive display tab stop bitmap. Thus, tab stop settings are preserved while the screen is inactive,
862-865 $035E-$0361 LNKMAP
Line link bitmap
These four bytes are used to provide a 25-bit map of the 25 rows of the active screen display (bits 0-6 of location 865/$361 are unused). Each row of the currently active dis- play has a corresponding bit in the map. When a bit is set to % 1 , the corresponding row is linked to the row above as part of a logical line. Bits set to %0 indicate unlinked lines (or rows that are the first physical line of a logical line). These locations are cleared to 0/$00, unlinking all lines, whenever the output window is cleared or reset to full screen size, or whenever the screen editor WINDOW routine is used to change the size of the output window. A screen line is normally linked to the one above when the cursor moves onto the line by wrapping
866-875 S0362-S036B
from the right margin of the line above. Line linking can be disabled by setting the flag bit in location 248/$F8.
When the active display is switched, the screen editor SWAPPER routine [$CD2E] exchanges the contents of this area with the contents of locations 2666-2669/$0A6A-$0A6D, the storage area for the inactive display line link bitmap. Thus, the line link status is preserved when the screen is inactive.
Kernal File Tables
The following three ten-byte tables hold information on any currently open logical files. The three tables are parallel; the entry for a particular file will appear at the same position in all three tables. Location 152/$98 serves as an index to the next available entry in the tables. The fact that there are only ten bytes per table means that no more than ten logical files may be opened simultaneously.
866-875 $0362-$036B LATBL
Logical file number table for currently open files
When a logical file is opened, the OPEN routine [$EFBD] ex- amines the contents of this table. A FILE OPEN error occurs if an existing file already uses the specified logical file number, and a TOO MANY FILES error occurs if ten files are already open. Otherwise, the logical file number for the file is stored in the next available entry in this table. When the Kernal CHKIN [$F106] or CKOUT [$F14C] routines are used to select a logical file for input or output, this table is searched for the specified logical file number. A FILE NOT OPEN error occurs if the file number is not found in the table. Otherwise, the cor- responding device number and secondary address will be read from the respective tables. When a file is closed, the Kernal CLOSE routine [$F188] removes the file's entry from this table.
The Kernal includes a routine [LKUPLA, $F79D] to search for a particular file number in this table.
876-885 $036C-$0375 DNTBL
Device number table for currently open files
When a logical file is opened, the OPEN routine [$EFBD] stores the device number for the file in the next available en- try in this table. When the Kernal CHKIN [$F106] or CKOUT [$F14C] routines are used to select a logical file for input or
106
$0380-$039E 896-926
output, the device number for the selected file will be read from this table. When a file is closed, the Kernal CLOSE rou- tine [$F188] removes the file's entry from this table.
886-895 $0376-$037F SATBL
Secondary address table for currently open files
When a logical file is opened, the OPEN routine [$EFBD] will OR the specified secondary address for the file with the value 96/$60, then store the result in the next available entry in this table. When the Kernal CHKIN [$F106] or CKOUT [$F14C] routines are used to select a logical file for input or output, the secondary address for the selected file will be read from this table. When a file is closed, the Kernal CLOSE routine [$F188] removes the file's entry from this table.
The Kernal includes a routine [LKUPSA, $F786] to search for a particular secondary address in this table.