From 1cd5005d0675ad475a2daac6e77ef17357a93a41 Mon Sep 17 00:00:00 2001 From: Benno Schulenberg Date: Tue, 21 Jan 2020 12:31:34 +0100 Subject: [PATCH] bindings: allow to bind shifted Meta+letter combinations with Sh-M-X As long as the user does not define any Sh-M-X bindings in their nanorc, and will not have any effect on combos. But as soon as any Sh-M-X combination is bound, will be seen as different from the unshifted keystroke. This kind of fulfills https://savannah.gnu.org/bugs/?54659. Requested-by: Peter Passchier --- src/global.c | 11 ++++++++++- src/nano.c | 4 ++++ src/proto.h | 1 + src/winio.c | 6 +++--- 4 files changed, 18 insertions(+), 4 deletions(-) diff --git a/src/global.c b/src/global.c index a2aa09d7..318fb305 100644 --- a/src/global.c +++ b/src/global.c @@ -33,6 +33,8 @@ volatile sig_atomic_t the_window_resized = FALSE; bool on_a_vt = FALSE; /* Whether we're running on a Linux console (a VT). */ +bool shifted_metas = FALSE; + /* Whether any Sh-M- combo has been bound. */ bool meta_key; /* Whether the current keystroke is a Meta key. */ @@ -505,6 +507,13 @@ int keycode_from_string(const char *keystring) return (int)' '; else return -1; +#ifdef ENABLE_NANORC + } else if (strncasecmp(keystring, "Sh-M-", 5) == 0 && + 'a' <= (keystring[5] | 0x20) && (keystring[5] | 0x20) <= 'z' && + keystring[6] == '\0') { + shifted_metas = TRUE; + return (keystring[5] & 0x5F); +#endif } else if (keystring[0] == 'F') { int fn = atoi(&keystring[1]); if (fn < 1 || fn > 24) @@ -522,7 +531,7 @@ int keycode_from_string(const char *keystring) void assign_keyinfo(keystruct *s, const char *keystring, const int keycode) { s->keystr = keystring; - s->meta = (keystring[0] == 'M' && keycode < 0x7F); + s->meta = ((keystring[0] == 'M' || keystring[0] == 'S') && keycode < 0x7F); s->keycode = (keycode ? keycode : keycode_from_string(keystring)); } diff --git a/src/nano.c b/src/nano.c index 7bb9779e..dcbbc1fc 100644 --- a/src/nano.c +++ b/src/nano.c @@ -1359,6 +1359,10 @@ void unbound_key(int code) #ifndef NANO_TINY else if (code < 0x20) statusline(ALERT, _("Unbindable key: M-^%c"), code + 0x40); +#endif +#ifdef ENABLE_NANORC + else if (shifted_metas && 'A' <= code && code <= 'Z') + statusline(ALERT, _("Unbound key: Sh-M-%c"), code); #endif else statusline(ALERT, _("Unbound key: M-%c"), toupper(code)); diff --git a/src/proto.h b/src/proto.h index 89c48d57..3ed7f28e 100644 --- a/src/proto.h +++ b/src/proto.h @@ -27,6 +27,7 @@ extern volatile sig_atomic_t the_window_resized; #endif extern bool on_a_vt; +extern bool shifted_metas; extern bool meta_key; extern bool shift_held; diff --git a/src/winio.c b/src/winio.c index b5e25e11..a0cbbb08 100644 --- a/src/winio.c +++ b/src/winio.c @@ -391,7 +391,7 @@ int parse_kbinput(WINDOW *win) * meta key sequence mode. */ if (!solitary || (keycode >= 0x20 && keycode < 0x7F)) meta_key = TRUE; - retval = tolower(keycode); + retval = (shifted_metas) ? keycode : tolower(keycode); } else /* One escape followed by a non-escape, and there * are more codes waiting: escape sequence mode. */ @@ -466,7 +466,7 @@ int parse_kbinput(WINDOW *win) * or control character sequence mode. */ if (!solitary) { meta_key = TRUE; - retval = tolower(keycode); + retval = (shifted_metas) ? keycode : tolower(keycode); } else retval = get_control_kbinput(keycode); else { @@ -495,7 +495,7 @@ int parse_kbinput(WINDOW *win) if (key_buffer_len == 0) { if (!solitary) { meta_key = TRUE; - retval = tolower(keycode); + retval = (shifted_metas) ? keycode : tolower(keycode); } else /* Three escapes followed by a non-escape, and no * other codes are waiting: normal input mode. */