This website uses cookies to ensure you get the best experience on our website More info

Keyboard Input

This section deatils replacing the keyboard interrupt for player input. Only basic programming knowledge is assumed. We recommend users to go through the tutorial in sequence and check all the examples.

The Theory

When a key is pressed or released, the keyboard sends the information about this key and the action (pressed or relased) to the CPU. This data is proccessed by the B.I.O.S. interrupt '9H' which sends the translated information to programs.

Just put your key detection function over the BIOS keyboard handler and your code will be called every time a key event occurs. The keyboard event can be read from port 60h. It's a byte size port and is divided in to the Scancode and the Key Event

| .7 |
.6 | .5 | .4 | .3 | .2 | .1 | .0 |
Key |
Scan Code

The Scancode is 7-bits and represents the key ID. The key event is the most significant bit (bit-7). When this is true the key was released, otherwise the key was pressed. You must control whether keys are pressed or relased by yourself.

The Code

Here is the new interrupt code. This is using the keys Q, A, O, P, M and ESCAPE. Change the case values to use different keys. Its also easy to add more or remove keys from this code.

void key_handler(void)
unsigned char al, ah;
asm("cli; pusha");
raw_key = inportb(0x60);
al = inportb(0x61);
al |= 0x82;
outportb(0x61, al);
al &= 0x7f;
outportb(0x61, al);
case 16: key_table[UP] = 1; break;//presses \/
case 30: key_table[DOWN] = 1; break;
case 50: key_table[FIRE] = 1; break;
case 24: key_table[LEFT] = 1; break;
case 25: key_table[RIGHT] = 1; break;
case 1: key_table[QUIT] = 1; break;
case 49: key_table[FIRE] = 1; break;
case 144: key_table[UP] = 0; break;//releases \/
case 158: key_table[DOWN] = 0; break;
case 178: key_table[FIRE] = 0; break;
case 152: key_table[LEFT] = 0; break;
case 153: key_table[RIGHT] = 0; break;
case 129: key_table[QUIT] = 0; break;
case 177: key_table[FIRE] = 0; break;
outportb(0x20, 0x20);
asm("popa; sti");

You will also need to install this code - not forgetting to put the old interrupt back at the end! See this example for a complete solution.