How to get Ctrl, Shift or Alt with getch()
ncurses ?
I cannot get it work to get Ctrl, Shift or Alt with getch()
using ncurses ? Do I miss something in the man ?
Ncurses uses the terminfo definition. If it says that KEY_ENTER is control/M, getch will return KEY_ENTER when you press control/M. When using getch, wgetch, mvgetch, or mvwgetch, nocbreak mode (nocbreak) and echo mode (echo) should not be used at the same time.
getch () returns an integer corresponding to the key pressed. If it is a normal character, the integer value will be equivalent to the character. Otherwise it returns a number which can be matched with the constants defined in curses.h.
If it says that KEY_ENTER is control/M, getch will return KEY_ENTER when you press control/M. When using getch, wgetch, mvgetch, or mvwgetch, nocbreak mode ( nocbreak) and echo mode ( echo) should not be used at the same time. Depending on the state of the tty driver when each character is typed, the program may produce undesirable results.
As you have seen in almost all of the above examples, it's very easy to get key input from the user. A simple way of getting key presses is to use getch () function.
Amazing how sometimes the right answer gets demoted, and answers that "authoritatively" give up get promoted... With a bit of creativity, key_name actually holds the right key to figuring this out, with one caveat - that SHIFT/ALT/CTRL are pressed with other keys at the same time:
First, for "normal keys" such as the printable ones, you can easily detect shift because it uppercases.
For special keys, e.g. KEY_LEFT, you will see that the code generated when SHIFT is selected is actually KEY_SLEFT. ditto for KEY_RIGHT. Unfortunately, no such luck for KEY_UP/KEY_DOWN , which seem unfazed by SHIFT. So you can distinguish by the returned char from getch() - the KEY_S.. implies shift was pressed.
For ALT (what's not trapped by X or the Aqua Windowmanager, at least), keyname will convert the key to an M... something.
For CTRL you'll get a "^" preceding the actual key name. E.g ^R for key 18
So you can now figure out the key codes for your switch(getch) statements, etc, by a simple snippet:
ch = getch(); endwin(); printf("KEY NAME : %s - %d\n", keyname(ch),ch);
and that's that. Think before definitively saying "can't". Maybe there's a way that's less obvious.
At least for the control modifier there is a simple solution. Curses had been derived from vi source code, in which you find the following (see https://github.com/n-t-roff/ex-1.1/blob/master/ex.h line 77 and https://github.com/n-t-roff/ex-1.1/blob/master/ex_vops.c line 445):
#ifndef CTRL
#define CTRL(c) ((c) & 037)
#endif
switch(getch()) {
case CTRL('r'):
/* key ctrl-r (i.e. ^R) pressed */
Dependend on used includes CTRL
may or may not already been defined in your code.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With