--- rxvt-unicode/src/keyboard.C 2014/05/02 20:35:00 1.67 +++ rxvt-unicode/src/keyboard.C 2015/10/13 08:10:43 1.73 @@ -5,10 +5,11 @@ * All portions of code are copyright by their respective author/s. * Copyright (c) 2005 WU Fengguang * Copyright (c) 2005-2006 Marc Lehmann + * Copyright (c) 2015 Emanuele Giaquinta * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2 of the License, or + * the Free Software Foundation; either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, @@ -91,22 +92,42 @@ } void +keyboard_manager::unregister_action (KeySym keysym, unsigned int state) +{ + for (unsigned int i = 0; i < keymap.size (); ++i) + if (keymap [i]->keysym == keysym + && keymap [i]->state == state) + { + free (keymap [i]->str); + delete keymap [i]; + + if (i < keymap.size () - 1) + keymap [i] = keymap [keymap.size () - 1]; + keymap.pop_back (); + + break; + } +} + +void keyboard_manager::register_action (KeySym keysym, unsigned int state, const wchar_t *ws) { - char *translation = rxvt_wcstoutf8 (ws); + char *action = rxvt_wcstoutf8 (ws); keysym_t *key = new keysym_t; key->keysym = keysym; key->state = state; - key->str = translation; + key->str = action; key->type = keysym_t::STRING; - if (strncmp (translation, "builtin:", 8) == 0) + if (strncmp (action, "builtin:", 8) == 0) key->type = keysym_t::BUILTIN; - else if (strncmp (translation, "builtin-string:", 15) == 0) + else if (strncmp (action, "builtin-string:", 15) == 0) key->type = keysym_t::BUILTIN_STRING; + unregister_action (keysym, state); + if (keymap.size () == keymap.capacity ()) keymap.reserve (keymap.size () * 2); @@ -114,8 +135,8 @@ hash[0] = 3; } -bool -keyboard_manager::dispatch (rxvt_term *term, KeySym keysym, unsigned int state, const char *kbuf, int len) +keysym_t * +keyboard_manager::lookup_keysym (rxvt_term *term, KeySym keysym, unsigned int state) { assert (("register_done() need to be called", hash[0] == 0)); @@ -130,10 +151,16 @@ int index = find_keysym (keysym, state); - if (index >= 0) - { - keysym_t *key = keymap [index]; + return index >= 0 ? keymap [index] : 0; +} + +bool +keyboard_manager::dispatch (rxvt_term *term, KeySym keysym, unsigned int state, const char *kbuf, int len) +{ + keysym_t *key = lookup_keysym (term, keysym, state); + if (key) + { if (key->type == keysym_t::BUILTIN_STRING) { term->tt_write_user_input (kbuf, len); @@ -155,7 +182,7 @@ else if (strncmp (str, "perl:", 5) == 0) HOOK_INVOKE ((term, HOOK_USER_COMMAND, DT_STR, colon + 1, DT_END)); else - HOOK_INVOKE ((term, HOOK_KEYBOARD_DISPATCH, DT_STR_LEN, str, colon - str, DT_STR, colon + 1, DT_END)); + HOOK_INVOKE ((term, HOOK_ACTION, DT_STR_LEN, str, colon - str, DT_STR, colon + 1, DT_INT, 0, DT_STR_LEN, kbuf, len, DT_END)); } else term->tt_write_user_input (str, strlen (str));