I have a problem in detecting whether I just got a plain ESC key (just code 27) or whether it was another special key such as an Arrow Up which sends me three bytes: ESC [ A (27 91 65).
Now, I understand escape sequences, what I don't understand is how can I possibly know that the user actually typed ESC instead of a special key since both start with 27 and ESC is only 27?
Note that I use the wgetch()
function from ncurses as in:
// initialization not shown initscr() should be enough for this test
while(!f_should_exit)
{
int c(wgetch(f_win_input));
// show codes of what the user types
//
printf("got [%d] ", c);
// prints 27 when I hit ESC
// prints 27 91 65 when I hit Arrow Up
}
I use the ESC and arrow keys all the time in vim so I would imagine that there is an easy way to specifically detect which key was pressed?!
This is a standard feature of X/Open Curses. The manual page for wgetch
discusses it in keypad
mode:
When a character that could be the beginning of a function key is received (which, on modern terminals, means an escape character), curses
sets a timer. If the remainder of the sequence does not come in within
the designated time, the character is passed through; otherwise, the
function key value is returned. For this reason, many terminals experience a delay between the time a user presses the escape key and the escape is returned to the program.
By default, keypad
is not set to true for a given window, i.e., the library does not do this (your program must, if you want function-keys):
keypad(win, TRUE);
The timeouts are described in ncurses' input-options manual page. To distinguish an escape character from a function (or cursor, or keypad key), you could use notimeout
, as mentioned in the discussion of nodelay
:
While interpreting an input escape sequence, wgetch(3x) sets a timer
while waiting for the next character. If notimeout(win, TRUE)
is
called, then wgetch does not set a timer. The purpose of the timeout
is to differentiate between sequences received from a function key and
those typed by a user.