## ASCII and Extended Codes

[MS-DOS code page 437](http://en.wikipedia.org/wiki/Code_page_437)

[ASCII Control 0 to 31](http://ascii.cl/control-characters.htm)  \| ASCII Keyboard Character Codes 32 to 127

| Code | Character [key] | Code | Character | Code | Character | Code | Character |
| ---- | --------------- | ---- | --------- | ---- | --------- | ---- | --------- | 
|  0 |        (NUL)  | 32 |  \[[SPACE$](SPACE$)]| 64 |  @ |  96 |  ` |
|  1 |  ☺   (SOH) | 33 |  ! | 65 |  A |  97 |  a |
|  2 |  ☻   (STX) | 34 |  " | 66 |  B |  98 |  b |
|  3 |  ♥   (ETX) | 35 |  # | 67 |  C |  99 |  c |
|  4 |  ♦   (EOT) | 36 |  $ | 68 |  D | 100 |  d |
|  5 |  ♣   (ENQ) | 37 |  % | 69 |  E | 101 |  e |
|  6 |  ♠   (ACK) | 38 |  & | 70 |  F | 102 |  f |
|  7 |  •   (BEL)   \[BEEP](BEEP)| 39 |  ' | 71 |  G | 103 |  g |
|  8 |  ◘    \[BackSpace] `**`| 40 |  ( | 72 |  H | 104 |  h |
|  9 |  ○   (HT)    \[TAB] `**`| 41 |  ) | 73 |  I | 105 |   i |
| 10 |  ◙   (LineFeed)  `**`| 42 |  * | 74 |  J | 106 |  j |
| 11 |  ♂   (VT) `**`| 43 |  + | 75 |  K | 107 |  k |
| 12 |  ♀   (FormFeed) `**`| 44 |  , | 76 |  L | 108 |  l |
| 13 |  ♪   (CR) \[Enter] `**`| 45 |  - | 77 |  M | 109 |  m |
| 14 |  ♫   (SO) | 46 |  . | 78 |  N | 110 |  n |
| 15 |  ¤   (SI) | 47 |  / | 79 |  O | 111 |  o |
| 16 |  ►   (DLE) | 48 |  0 | 80 |  P | 112 |  p |
| 17 |  ◄   (DC1) | 49 |  1 | 81 |  Q | 113 |  q |
| 18 |  ↕   (DC2) | 50 |  2 | 82 |  R | 114 |  r |
| 19 |  ‼   (DC3) | 51 |  3 | 83 |  S | 115 |  s |
| 20 |  ¶   (DC4) | 52 |  4 | 84 |  T | 116 |  t |
| 21 |  §   (NAK) | 53 |  5 | 85 |  U | 117 |  u |
| 22 |  ▬   (SYN) | 54 |  6 | 86 |  V | 118 |  v |
| 23 |  ↨   (ETB) | 55 |  7 | 87 |  W | 119 |  w |
| 24 |  ↑   (CAN) | 56 |  8 | 88 |  X | 120 |  x |
| 25 |  ↓   (EM)  | 57 |  9 | 89 |  Y | 121 |  y |
| 26 |  →   (SUB)    [EOF](EOF) | 58 |  : | 90 |  Z | 122 |  z |
| 27 |  ←   (ESC)   \[Esc]| 59 |  ; | 91 |  [ | 123 |  { |
| 28 |  ∟   (FS) `**`| 60 |  < | 92 |  \ | 124 |  \| |
| 29 |  ↔   (GS) `**`| 61 |  = | 93 |  ] | 125 |  } |
| 30 |  ▲   (RS) `**`| 62 |  > | 94 |  ^ | 126 |  ~ |
| 31 |  ▼   (US) `**`| 63 |  ? | 95 |  _ | 127 |  ¦ (DEL) `*` |

IBM, International, graphical, mathematical and other characters

| Code | Character | Code | Character | Code | Character | Code | Character
| ---- | --------------- | ---- | --------- | ---- | --------- | ---- | --------- | 
| 128 |  Ç | 160 |  á | 192 |  + | 224 |  a | 
| 129 |  ü | 161 |  í | 193 |  - | 225 |  ß | 
| 130 |  é | 162 |  ó | 194 |  - | 226 |  G | 
| 131 |  â | 163 |  ú | 195 |  + | 227 |  p | 
| 132 |  ä | 164 |  ñ | 196 |  - | 228 |  S | 
| 133 |  à | 165 |  Ñ | 197 |  + | 229 |  s | 
| 134 |  å | 166 |  ª | 198 |  ¦ | 230 |  µ | 
| 135 |  ç | 167 |  º | 199 |  ¦ | 231 |  t | 
| 136 |  ê | 168 |  ¿ | 200 |  + | 232 |  F | 
| 137 |  ë | 169 |  ¬ | 201 |  + | 233 |  T | 
| 138 |  è | 170 |  ¬ | 202 |  - | 234 |  O | 
| 139 |  ï | 171 |  ½ | 203 |  - | 235 |  d | 
| 140 |  î | 172 |  ¼ | 204 |  ¦ | 236 |  8 | 
| 141 |  ì | 173 |  ¡ | 205 |  - | 237 |  f | 
| 142 |  Ä | 174 |  « | 206 |  + | 238 |  e | 
| 143 |  Å | 175 |  » | 207 |  - | 239 |  n | 
| 144 |  É | 176 |  ¦ | 208 |  - | 240 |  = | 
| 145 |  æ | 177 |  ¦ | 209 |  - | 241 |  ± | 
| 146 |  Æ | 178 |  ¦ | 210 |  - | 242 |  = | 
| 147 |  ô | 179 |  ¦ | 211 |  + | 243 |  = | 
| 148 |  ö | 180 |  ¦ | 212 |  + | 244 |  ( | 
| 149 |  ò | 181 |  ¦ | 213 |  + | 245 |  ) | 
| 150 |  û | 182 |  ¦ | 214 |  + | 246 |  ÷ | 
| 151 |  ù | 183 |  + | 215 |  + | 247 |  ˜ | 
| 152 |  ÿ | 184 |  + | 216 |  + | 248 |  ° | 
| 153 |  Ö | 185 |  ¦ | 217 |  + | 249 |  · | 
| 154 |  Ü | 186 |  ¦ | 218 |  + | 250 |  · | 
| 155 |  ¢ | 187 |  + | 219 |  ¦ | 251 |  v | 
| 156 |  £ | 188 |  + | 220 |  _ | 252 |  n | 
| 157 |  ¥ | 189 |  + | 221 |  ¦ | 253 |  ² | 
| 158 |  P | 190 |  + | 222 |  ¦ | 254 |  ¦ | 
| 159 |  ƒ | 191 |  + | 223 | ¯  | 255 |  *NBSP* `***`  | 

* `*` DEL was used to erase paper tape data by punching out all of the 7 holes.**
* `**` Control characters 8 to 13 and 28 to 31 can move text formatting when [PRINT](PRINT) and do not display
* `***` NBSP is a Non-breaking Space used to indent text. Some browsers may handle this character differently**

[More information about ASCII  Control Characters](http://www.lammertbies.nl/comm/info/ascii-characters.html) 

[Unicode](Unicode)

## Control Characters

* [INKEY$](INKEY$) will return Control + letter key press combinations as the equivalent control characters or bold **function keys** listed below:

Code | C | Description | Code | C | Description
--- | --- | --- | --- | --- | ---
CTRL + A = CHR$(1)  | ☺ | StartHeader (SOH)  | CTRL + B = CHR$(2)  | ☻ | StartText         (STX)
CTRL + C = CHR$(3)  | ♥ | EndText     (ETX)  | CTRL + D = CHR$(4)  | ♦ | EndOfTransmit     (EOT)
CTRL + E = CHR$(5)  | ♣ | Enquiry     (ENQ)  | CTRL + F = CHR$(6)  | ♠ | Acknowledge       (ACK)
CTRL + G = CHR$(7)  | `•` | Bell        (BEL)  | CTRL + H = CHR$(8)  | ◘ | [Backspace]       (BSP)
CTRL + I = CHR$(9)  | `○` | Horiz.Tab   [Tab]  | CTRL + J = CHR$(10) | `◙` | LineFeed(printer) (LF)
CTRL + K = CHR$(11) | `♂` | Vert. Tab   (VT)   | CTRL + L = CHR$(12) | `♀` | FormFeed(printer) (FF)
CTRL + M = CHR$(13) | `♪` | [Enter]     (CR)   | CTRL + N = CHR$(14) | ♫ | ShiftOut          (SO)
CTRL + O = CHR$(15) | ☼ | ShiftIn     (SI)   | CTRL + P = CHR$(16) | ► | DataLinkEscape    (DLE)
CTRL + Q = CHR$(17) | ◄ | DevControl1 (DC1)  | CTRL + R = CHR$(18) | ↕ | DeviceControl2    (DC2)
CTRL + S = CHR$(19) | ‼ | DevControl3 (DC3)  | CTRL + T = CHR$(20) | ¶ | DeviceControl4    (DC4)
CTRL + U = CHR$(21) | § | NegativeACK (NAK)  | CTRL + V = CHR$(22) | ▬ | Synchronous Idle  (SYN)
CTRL + W = CHR$(23) | ↨ | EndTXBlock  (ETB)  | CTRL + X = CHR$(24) | ↑ | Cancel            (CAN)
CTRL + Y = CHR$(25) | ↓ | EndMedium   (EM)   | CTRL + Z = CHR$(26) | → | End Of File(SUB)  (EOF)

**Highlighted items will format text and not [PRINT](PRINT) the symbol. [_PRINTSTRING](_PRINTSTRING) can print in QB64**

* Control characters **1 to 26** can be used to simulate *Ctrl + letter* key shortcuts in Windows programs using [_SCREENPRINT](_SCREENPRINT).
* [_CONTROLCHR](_CONTROLCHR) OFF can also be used in QB64 to allow control characters to be printed without formatting the text.

**ASCII in Text and Printing**

* Characters **0**(NULL) and **255**(NBSP) can also be used to print spaces(**32**). Useful for making file names harder to delete too.
* Character **7** will create a [BEEP](BEEP) sound when printed in **QB64** or an error sound in QBasic using a **SCREEN 0** window.
* Character **8** is returned when the **Backspace** key is pressed.
* Characters **9 thru 13** and **28 thru 31** can affect screen or file text placements and do not display the character when [PRINT](PRINT):
  * Character **9** will **Tab** space the cursor 8 column spaces when printed.
  * Character **10** moves the cursor or *"line feeds"* the printer head down one row.
  * Character **11** vertical tabs the cursor back to top left position of page or screen. Acts like [CLS](CLS).
  * Character **12** acts like [CLS](CLS) when printed. *"Form feeds"* the page out of printers.
  * Character **13** is the cursor or typing **"carriage return"** to the start of the line on left side. Returned when **Enter** key pressed.
  * Character **28** designates a File Separator. Moves the print cursor one space right. Combination Ctrl + \
  * Character **29** designates a Group Separator. Moves the print cursor one space left. Combination Ctrl + ]
  * Character **30** designates a Record Separator. Moves the print cursor one row up. Combination Ctrl + ^
  * Character **31** designates a Unit Separator. Moves the print cursor one row down. Combination Ctrl + _
* **QB64** can display all of the control characters without formatting the text using [_PRINTSTRING](_PRINTSTRING).
* Characters **13** and **10** can be combined to create the **CrLf** carriage return used in files or printing. crlf$ = CHR$(13) + CHR$(10).
* Character **16**, the data link escape(DLE) character, can designate that a control character is being sent from a [OPEN COM](OPEN-COM).
  Example(s)
  (DLE) \<XON> \<DATA PACKET> (DLE) \<XOFF> or (DLE) \<STX> \<DATA PACKET> (DLE) \<ETX>
* Character **17**, Device Control 1, is used with [OPEN COM](OPEN-COM) to mark the start of a transmission as "XON". The character is read.
* Character **19**, Device Control 3, is used with [OPEN COM](OPEN-COM) to mark the end of a transmission as "XOFF". The character is NOT read.
* Character **26** can be used to designate the end of a file. See [EOF](EOF).
* Character **27** **?** is returned when the **Escape** key is pressed.

**Control character [PRINT](PRINT) actions can be controlled using [_CONTROLCHR](_CONTROLCHR) OFF or ON in QB64.**

```vb

SCREEN 12
COLOR 14: PRINT "Press Control + letter key combinations."
DO
  K$ = INKEY$
  IF LEN(K$) THEN
    code = ASC(K$)
    IF code < 32 THEN _PRINTSTRING (220, 100), "Ctrl + " + CHR$(code + 64) + " = " + K$ + " "
  END IF
LOOP UNTIL K$ = CHR$(27)

END 

```

**ASCII Character Usage**

* Characters are one byte and take up one space(byte) in a [STRING](STRING) value or variable.
* Extended(non-keyboard) characters can be entered by holding down *Alt* key and entering the code number on the Number pad.
* [PRINT](PRINT)s text characters and symbols or formats the screen, printer or file.
* [BINARY](BINARY) files often store values below 256 in the one byte character. To read the value get the code with [ASC](ASC).
* Numerical values placed into a [BINARY](BINARY) or [RANDOM](RANDOM) file using a [GET](GET) or [PUT](PUT) variable, they will be stored in [_MK$](_MK$) format.
* Characters **176** to **223** can be used to create screen borders or boundaries in an ASCII game. See: [SCREEN (function)](SCREEN-(function))
* Character **253**(small 2) can be found as the first character byte of a [BSAVE](BSAVE)d image file opened in [BINARY](BINARY) mode.
* Character **255** can be used as the NBSP(non-breaking space) character on web pages to fill in extra spaces.
* Can be used to crudely encrypt a file so others cannot read it by shifting the code values. See [CHR$](CHR$) example 2.

## [ASC](ASC) Codes

**[ASC](ASC) cannot read empty [INKEY$](INKEY$) = "" loop reads! Check for them before reading [ASC](ASC) key press codes!**

```text

'                                **ASCII Keyboard Codes**
'
**' Esc  F1  F2  F3  F4  F5  F6  F7  F8  F9  F10  F11  F12  Sys ScL Pause**
'  27 +59 +60 +61 +62 +63 +64 +65 +66 +67 +68  +133 +134   -   -    -
**' `~  1!  2@  3#  4$  5%  6^  7&  8*  9(  0) -_ =+ BkSp   Ins Hme PUp   NumL  /   *    -**
' 126 33  64  35  36  37  94  38  42  40  41 95 43   8    +82 +71 +73    -    47  42   45
**  96 49  50  51  52  53  54  55  56  57  48 45 61*
**' Tab Q   W   E   R   T   Y   U   I   O   P  [{  ]}  \|   Del End PDn   7Hme 8/?  9PU  + **
'  9  81  87  69  82  84  89  85  73  79  80 123 125 124  +83 +79 +81   +71  +72  +73  43
**    113 119 101 114 116 121 117 105 111 112  91  93  92                 55   56   57 *
**' CapL  A   S   D   F   G   H   J   K   L   ;:  '" Enter                4/?-  5   6/-?
'   -   65  83  68  70  71  72  74  75  76  58  34  13                  +75  +76  +77  **E**
**       97 115 100 102 103 104 106 107 108  59  39                       52   53   54 * **n**
**' Shift  Z   X   C   V   B   N   M   ,<  .>  /?    Shift       ?        1End 2/?  3PD  t**
'   *    90  88  67  86  66  78  77  60  62  63      *        +72       +79  +80  +81  **e**
**       122 120  99 118  98 110 109  44  46  47                          49   50   51 * **r**
**' Ctrl Win Alt       Spacebar          Alt Win Menu Ctrl   ?-  ?   -?   0Ins     .Del **
'  *    -   *           32              *   -   -    *    +75 +80 +77   +82       +83  13
'                                                                   *     48        46*
'
' **    *Italics* = LCase/NumLock On  ____________  + = 2 Byte: CHR$(0) + CHR$(code)**
'<sub>NOTE: The above commented table can be copied and pasted directly into the QB64 IDE</sub>

```

Use **ASC(RIGHT$(key$, 1))** or **ASC(key$, 2)** in QB64 to read a two byte code when **ASC(key$) = 0**

*** See the Two Byte Ctrl, Alt and Shift + Function key combinations below**

```vb
'             Demo displays all ASCII codes and 2 byte code combinations
DO: K$ = INKEY$
  IF K$ <> "" THEN      'ASC will return an error if an empty string is read!
    IF ASC(K$) > 0 THEN
      PRINT "CHR$(" + LTRIM$(STR$(ASC(K$))) + ")"  'display normal keypress codes
    ELSE PRINT "CHR$(0) + CHR$(" + LTRIM$(STR$(ASC(K$, 2))) + ")"  'display 2 byte codes
    END IF
  END IF
LOOP UNTIL K$ = CHR$(27) 'escape key press exits 

```
> *Note:* In QB64 [ASC](ASC)(K$, 2) can read the second byte of the 2 byte code when [ASC](ASC)(K$) reads the first byte as 0.

## Two Byte Codes

**Two Byte ASCII Keyboard Return Values**

* [INKEY$](INKEY$) returns both bytes when two byte keys or key combinations are pressed. The second byte = [RIGHT$](RIGHT$)(keypress$, 1)
* If the character returned is a two byte code, [ASC](ASC) will return 0. **Warning:** ASC cannot read empty [INKEY$](INKEY$) string values!
* In **QB64** only, [ASC](ASC)(keypress$, 2) can return the second byte code. Don't read empty string values!
* String values returned can be compared in an [IF...THEN](IF...THEN) or [SELECT CASE](SELECT-CASE) routine by using the actual string definitions such as:

> IF INKEY$ = CHR$(0) + CHR$(80) THEN row = row + 1 **or** IF INKEY$ = CHR$(0) + "P" THEN row = row + 1

```text

                 **Two Byte Character Codes       Key                 CHR$(0) + "?" **

                    CHR$(0) + CHR$(16-50)      [Alt] + letter
                    CHR$(0) + CHR$(59)         [F1]                 ";"
                    CHR$(0) + CHR$(60)         [F2]                 "<"
                    CHR$(0) + CHR$(61)         [F3]                 "="
                    CHR$(0) + CHR$(62)         [F4]                 ">"
                    CHR$(0) + CHR$(63)         [F5]                 "?"
                    CHR$(0) + CHR$(64)         [F6]                 "@"
                    CHR$(0) + CHR$(65)         [F7]                 "A"
                    CHR$(0) + CHR$(66)         [F8]                 "B"
                    CHR$(0) + CHR$(67)         [F9]                 "C"
                    CHR$(0) + CHR$(68)         [F10]                "D"
                    CHR$(0) + CHR$(71)         [Home]               "G"
                    CHR$(0) + CHR$(72)         [?] Up Arrow         "H"
                    CHR$(0) + CHR$(73)         [Page Up]            "I"
                    CHR$(0) + CHR$(75)         [?] Left Arrow       "K"
                    CHR$(0) + CHR$(76)         [5 NumberPad]        "L" (NumLock off in QB64)
                    CHR$(0) + CHR$(77)         [?] Right Arrow      "M"
                    CHR$(0) + CHR$(79)         [End]                "O"
                    CHR$(0) + CHR$(80)         [?] Down Arrow       "P"
                    CHR$(0) + CHR$(81)         [Page Down]          "Q"
                    CHR$(0) + CHR$(82)         [Insert]             "R"
                    CHR$(0) + CHR$(83)         [Delete]             "S"
                    CHR$(0) + CHR$(84-93)      [Shift] + F1-10
                    CHR$(0) + CHR$(94-103)     [Ctrl] + F1-10
                    CHR$(0) + CHR$(104-113)    [Alt] + F1-10
                    CHR$(0) + CHR$(114-119)    [Ctrl] + keypad
                    CHR$(0) + CHR$(120-129)    [Alt] + number
                    CHR$(0) + CHR$(130 or 131) [Alt] + _/- or +/=   "é" or "â"
                    CHR$(0) + CHR$(133)        [F11]                "à"
                    CHR$(0) + CHR$(134)        [F12]                "å"
                    CHR$(0) + CHR$(135)        [Shift] + [F11]      "ç"
                    CHR$(0) + CHR$(136)        [Shift] + [F12]      "ê"
                    CHR$(0) + CHR$(137)        [Ctrl] + [F11]       "ë"
                    CHR$(0) + CHR$(138)        [Ctrl] + [F12]       "è"
                    CHR$(0) + CHR$(139)        [Alt] + [F11]        "ï"
                    CHR$(0) + CHR$(140)        [Alt] + [F12]        "î"

```

> In **QB64**, [CVI](CVI) can be used to get the [_KEYDOWN](_KEYDOWN) 2-byte code value. Example: **status = _KEYDOWN(CVI(CHR$(0) + "P"))**

**See [Scancodes](Scancodes) for other keyboard function keys.**


## Code Examples

Using arrow keys to move a text character. A change from a previous position tells program when to PRINT:

```vb
movey = 1: movex = 1 'text coordinates can never be 0
at$ = "@"  'text sprite could be almost any ASCII character
LOCATE movey, movex: PRINT at$;
DO
    px = movex: py = movey 'previous positions
    B$ = INKEY$
    IF B$ = CHR$(0) + CHR$(72) AND movey > 1 THEN movey = movey - 1 'rows 1 to 23 only
    IF B$ = CHR$(0) + CHR$(80) AND movey < 23 THEN movey = movey + 1
    IF B$ = CHR$(0) + CHR$(75) AND movex > 1 THEN movex = movex - 1 'columns 1 to 80 only
    IF B$ = CHR$(0) + CHR$(77) AND movex < 80 THEN movex = movex + 1

    IF px <> movex OR py <> movey THEN 'only changes when needed
        LOCATE py, px: PRINT SPACE$(1); 'erase old sprite
        LOCATE movey, movex: PRINT at$; 'show new position
    END IF
LOOP UNTIL B$ = CHR$(27) 'ESCape key exit
END

```

Routine displays all keypress codes including Ctrl, Alt and Shift combinations. Ctrl + letter = control codes 1 to 26.

```vb

 * *
 SCREEN 13
 tmp$ = "   CHR$(###),\\,\          \       "
 tmp2$ = "  CHR$(0) + CHR$(###) \           \"
 COLOR 14: LOCATE 3, 3: PRINT "The code can tell what key is pressed"
 COLOR 12: LOCATE 5, 14: PRINT CHR$(3); SPACE$(3);
 COLOR 13: PRINT CHR$(5); SPACE$(3);
 COLOR 12: PRINT CHR$(4); SPACE$(3);
 COLOR 13: PRINT CHR$(6)
 COLOR 10: LOCATE 7, 4: PRINT " Hit a key to find the ASCII Code"
 COLOR 5: LOCATE 13, 1: PRINT " Codes below 33 are called control keys"
 LOCATE 14, 1: PRINT " CHR$(0) + are 2 byte Extended key codes"
 COLOR 13: LOCATE 16, 1: PRINT " Extended: Press Alt + numberpad: Enter"
 LOCATE 18, 1: PRINT "  Try some Ctrl, Alt, or Shift Combo's"
 COLOR 5: LOCATE 20, 1: PRINT " INKEY$ is used to detect the key entry"
 COLOR 2: LOCATE 22, 15: PRINT CHR$(1); "       "; CHR$(2)
 COLOR 4: LOCATE 24, 10: PRINT "To Quit hit the TAB key";

 COLOR 9
 DO
     DO: SLEEP: A$ = INKEY$: LOOP UNTIL A$ <> ""  'legal ASC read keys
     IF ASC(A$) > 0 THEN  ' normal key codes
         code% = ASC(A$)
         SELECT CASE code%
           CASE 7: Key$ = "Beep"
           CASE 8: Key$ = "Backspace"
           CASE 9: Key$ = "Tab Key"
           CASE 10: Key$ = "Line Feed"
           CASE 12: Key$ = "Form Feed"
           CASE 13: Key$ = "Enter"
           CASE 27: Key$ = "Escape"
           CASE 32: Key$ = "Space Bar"
           CASE 48 TO 57: Key$ = "Number"
           CASE 65 TO 90: Key$ = "Uppercase"
           CASE 97 TO 122: Key$ = "Lowercase"
           CASE ELSE: Key$ = ""
         END SELECT
         SELECT CASE code%  'check for unprintable control combo characters
           CASE 10 TO 13: Kcode% = 32
           CASE ELSE: Kcode% = code%
         END SELECT
         COLOR 9: LOCATE 10, 5: PRINT USING tmp$; code%; CHR$(Kcode%); Key$;
     END IF
     IF ASC(A$) = 0 THEN  'two byte key codes
         code% = ASC(RIGHT$(A$, 1)) 'QBasic code
         'code% = ASC(A$, 2)        'QB64 code alternative
         SELECT CASE code%
            CASE 16 TO 50: Key$ = "Alt+ letter"
            CASE 72: Key$ = CHR$(24) + " Arrow"
            CASE 75: Key$ = CHR$(27) + " Arrow"
            CASE 77: Key$ = CHR$(26) + " Arrow"
            CASE 80: Key$ = CHR$(25) + " Arrow"
            CASE 83: Key$ = "Delete"
            CASE 59: Key$ = "F1"
            CASE 60: Key$ = "F2"
            CASE 61: Key$ = "F3"
            CASE 62: Key$ = "F4"
            CASE 63: Key$ = "F5"
            CASE 64: Key$ = "F6"
            CASE 65: Key$ = "F7"
            CASE 66: Key$ = "F8"
            CASE 67: Key$ = "F9"
            CASE 68: Key$ = "F10"
            CASE 71: Key$ = "Home"
            CASE 73: Key$ = "Page " + CHR$(24)
            CASE 79: Key$ = "End"
            CASE 81: Key$ = "Page " + CHR$(25)
            CASE 82: Key$ = "Insert"
            CASE 83: Key$ = "Delete"
            CASE 84 TO 93: Key$ = "Shift+ F"
            CASE 94 TO 103: Key$ = "Ctrl+ F"
            CASE 104 TO 113: Key$ = "Alt+ F"
            CASE 114 TO 119: Key$ = "Ctrl + pad"
            CASE 120 TO 129: Key$ = "Alt+ number"
            CASE 132: Key$ = "Ctrl + pad"
            CASE 133: Key$ = "F11"
            CASE 134: Key$ = "F12"
            CASE 135: Key$ = "Shift+ F11"
            CASE 136: Key$ = "Shift+ F12"
            CASE 137: Key$ = "Ctrl+ F11"
            CASE 138: Key$ = "Ctrl+ F12"
            CASE 139: Key$ = "Alt+ F11"
            CASE 140: Key$ = "Alt+ F12"
            CASE ELSE: Key$ = ""
         END SELECT
         LOCATE 10, 5: PRINT USING tmp2$; code%; Key$
     END IF
 LOOP UNTIL A$ = CHR$(9)
 SOUND 400, 4
 SLEEP 3
 SYSTEM 

```
<sub>Code by Ted Weissgerber</sub>

*Explanation:* The routine checks for a keypress and [SLEEP](SLEEP) guarantees that [ASC](ASC) will never read an empty string from INKEY$. When the keypress is determined to be two bytes ([ASC](ASC)(A$) = 0) the second SELECT CASE routine is used. You can even display non-keyboard extended characters. Just press Alt + numberpad code, release and press enter.

> Note: Ctrl + letter keys will list the contol keys as normal codes. EX: Ctrl + G will BEEP (CHR$(7)).

## References

*Printable ASCII Table:* [_PRINTIMAGE](_PRINTIMAGE) (see Example 2 on page)

## See Also

* [_KEYHIT](_KEYHIT), [_KEYDOWN](_KEYDOWN)
* [_MAPUNICODE](_MAPUNICODE), [_MAPUNICODE (function)](_MAPUNICODE-(function))
* [Code Pages](Code-Pages) (Various Unicode Languages)
* [ASC (statement)](ASC-(statement)) (QB64 only)
* [ASC](ASC), [INSTR](INSTR)
* [CHR$](CHR$), [INKEY$](INKEY$)
* [LEFT$](LEFT$), [MID$](MID$), [RIGHT$](RIGHT$)
* [PRINT](PRINT), [SCREEN](SCREEN)
* [MKI$](MKI$), [MKL$](MKL$), [MKS$](MKS$), [MKD$](MKD$), [_MK$](_MK$)
* [_PRINTSTRING](_PRINTSTRING), [_SCREENPRINT](_SCREENPRINT)
* [_CONTROLCHR](_CONTROLCHR) (turns control PRINT actions OFF/ON)
* [Scancodes](Scancodes)(keyboard), [Unicode](Unicode)(character table)
* [Text Using Graphics](Text-Using-Graphics)
