From 0aefc2c65de8cca39ddbf9d8c12f1a4d4206b42a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Daniel=20Ekl=C3=B6f?= Date: Tue, 6 Feb 2024 10:41:01 +0100 Subject: [PATCH] input: remove the concept of "significant" modifiers For the purpose of matching key bindings, "significant" modifiers are no more. We're really only interested in filtering out "locked" modifiers. We're already doing this, so there's no need to *also* match against a set of "significant" modifiers. Furthermore, we *never* want to consider locked keys (e.g. when emitting escapes to the client application), thus we can filter those out already when retrieving the set of active modifiers. The exception is the kitty keyboard protocol, which has support for CapsLock and NumLock. Since we're already re-retrieving the "consumed" modifiers (using the GTK style, rather than normal "XKB" style, to better match the kitty terminal), we might as well re-retrieve the effective modifiers as well. --- input.c | 52 +++++++++++++++++++++------------------------------- input.h | 2 +- search.c | 9 ++------- search.h | 1 - terminal.c | 2 +- url-mode.c | 12 +++--------- url-mode.h | 1 - wayland.h | 1 - 8 files changed, 28 insertions(+), 52 deletions(-) diff --git a/input.c b/input.c index 97c95a92..dc0eec93 100644 --- a/input.c +++ b/input.c @@ -597,15 +597,6 @@ keyboard_keymap(void *data, struct wl_keyboard *wl_keyboard, if (seat->kbd.mod_num != XKB_MOD_INVALID) seat->kbd.kitty_significant |= 1 << seat->kbd.mod_num; - /* Significant modifiers when handling shortcuts - use all available */ - seat->kbd.bind_significant = 0; - const xkb_mod_index_t mod_count = xkb_keymap_num_mods(seat->kbd.xkb_keymap); - for (xkb_mod_index_t i = 0; i < mod_count; i++) { - LOG_DBG("significant modifier: %s", - xkb_keymap_mod_get_name(seat->kbd.xkb_keymap, i)); - seat->kbd.bind_significant |= 1 << i; - } - seat->kbd.key_arrow_up = xkb_keymap_key_by_name(seat->kbd.xkb_keymap, "UP"); seat->kbd.key_arrow_down = xkb_keymap_key_by_name(seat->kbd.xkb_keymap, "DOWN"); } @@ -887,7 +878,8 @@ UNITTEST void get_current_modifiers(const struct seat *seat, xkb_mod_mask_t *effective, - xkb_mod_mask_t *consumed, uint32_t key) + xkb_mod_mask_t *consumed, uint32_t key, + bool filter_locked) { if (unlikely(seat->kbd.xkb_state == NULL)) { if (effective != NULL) @@ -897,24 +889,27 @@ get_current_modifiers(const struct seat *seat, } else { + const xkb_mod_mask_t locked = + xkb_state_serialize_mods(seat->kbd.xkb_state, XKB_STATE_MODS_LOCKED); + if (effective != NULL) { *effective = xkb_state_serialize_mods( seat->kbd.xkb_state, XKB_STATE_MODS_EFFECTIVE); + + if (filter_locked) + *effective &= ~locked; } if (consumed != NULL) { *consumed = xkb_state_key_get_consumed_mods2( seat->kbd.xkb_state, key, XKB_CONSUMED_MODE_XKB); + + if (filter_locked) + *consumed &= ~locked; } } } -static xkb_mod_mask_t -get_locked_modifiers(const struct seat *seat) -{ - return xkb_state_serialize_mods(seat->kbd.xkb_state, XKB_STATE_MODS_LOCKED); -} - struct kbd_ctx { xkb_layout_index_t layout; xkb_keycode_t key; @@ -1184,7 +1179,7 @@ kitty_kbd_protocol(struct seat *seat, struct terminal *term, xkb_state_update_key( seat->kbd.xkb_state, ctx->key, pressed ? XKB_KEY_DOWN : XKB_KEY_UP); - get_current_modifiers(seat, &mods, NULL, ctx->key); + get_current_modifiers(seat, &mods, NULL, ctx->key, false); consumed = xkb_state_key_get_consumed_mods2( seat->kbd.xkb_state, ctx->key, XKB_CONSUMED_MODE_GTK); @@ -1201,7 +1196,9 @@ kitty_kbd_protocol(struct seat *seat, struct terminal *term, seat->kbd.xkb_state, ctx->key, pressed ? XKB_KEY_UP : XKB_KEY_DOWN); #endif } else { - mods = ctx->mods; + /* Same as ctx->mods, but without locked modifiers being + filtered out */ + get_current_modifiers(seat, &mods, NULL, ctx->key, false); /* Re-retrieve the consumed modifiers using the GTK mode, to better match kitty. */ @@ -1490,13 +1487,7 @@ key_press_release(struct seat *seat, struct terminal *term, uint32_t serial, const bool composed = compose_status == XKB_COMPOSE_COMPOSED; xkb_mod_mask_t mods, consumed; - get_current_modifiers(seat, &mods, &consumed, key); - - const xkb_mod_mask_t locked = get_locked_modifiers(seat); - const xkb_mod_mask_t bind_mods - = mods & seat->kbd.bind_significant & ~locked; - const xkb_mod_mask_t bind_consumed = - consumed & seat->kbd.bind_significant & ~locked; + get_current_modifiers(seat, &mods, &consumed, key, true); xkb_layout_index_t layout_idx = xkb_state_key_get_layout(seat->kbd.xkb_state, key); @@ -1520,7 +1511,7 @@ key_press_release(struct seat *seat, struct terminal *term, uint32_t serial, start_repeater(seat, key); search_input( - seat, term, bindings, key, sym, mods, consumed, locked, + seat, term, bindings, key, sym, mods, consumed, raw_syms, raw_count, serial); return; } @@ -1530,7 +1521,7 @@ key_press_release(struct seat *seat, struct terminal *term, uint32_t serial, start_repeater(seat, key); urls_input( - seat, term, bindings, key, sym, mods, consumed, locked, + seat, term, bindings, key, sym, mods, consumed, raw_syms, raw_count, serial); return; } @@ -1563,14 +1554,14 @@ key_press_release(struct seat *seat, struct terminal *term, uint32_t serial, /* Match translated symbol */ if (bind->k.sym == sym && - bind->mods == (bind_mods & ~bind_consumed) && + bind->mods == (mods & ~consumed) && execute_binding(seat, term, bind, serial, 1)) { LOG_WARN("matched translated symbol"); goto maybe_repeat; } - if (bind->mods != bind_mods || bind_mods != (mods & ~locked)) + if (bind->mods != mods) continue; /* Match untranslated symbols */ @@ -2253,8 +2244,7 @@ static const struct key_binding * xassert(bindings != NULL); xkb_mod_mask_t mods; - get_current_modifiers(seat, &mods, NULL, 0); - mods &= seat->kbd.bind_significant; + get_current_modifiers(seat, &mods, NULL, 0, true); /* Ignore selection override modifiers when * matching modifiers */ diff --git a/input.h b/input.h index 906008d5..001d116f 100644 --- a/input.h +++ b/input.h @@ -33,6 +33,6 @@ void input_repeat(struct seat *seat, uint32_t key); void get_current_modifiers(const struct seat *seat, xkb_mod_mask_t *effective, xkb_mod_mask_t *consumed, - uint32_t key); + uint32_t key, bool filter_locked); enum cursor_shape xcursor_for_csd_border(struct terminal *term, int x, int y); diff --git a/search.c b/search.c index 55388577..10541884 100644 --- a/search.c +++ b/search.c @@ -1374,17 +1374,12 @@ void search_input(struct seat *seat, struct terminal *term, const struct key_binding_set *bindings, uint32_t key, xkb_keysym_t sym, xkb_mod_mask_t mods, xkb_mod_mask_t consumed, - xkb_mod_mask_t locked, const xkb_keysym_t *raw_syms, size_t raw_count, uint32_t serial) { LOG_DBG("search: input: sym=%d/0x%x, mods=0x%08x, consumed=0x%08x", sym, sym, mods, consumed); - const xkb_mod_mask_t bind_mods = - mods & seat->kbd.bind_significant & ~locked; - const xkb_mod_mask_t bind_consumed = - consumed & seat->kbd.bind_significant & ~locked; enum xkb_compose_status compose_status = seat->kbd.xkb_compose_state != NULL ? xkb_compose_state_get_status(seat->kbd.xkb_compose_state) : XKB_COMPOSE_NOTHING; @@ -1399,7 +1394,7 @@ search_input(struct seat *seat, struct terminal *term, /* Match translated symbol */ if (bind->k.sym == sym && - bind->mods == (bind_mods & ~bind_consumed)) { + bind->mods == (mods & ~consumed)) { if (execute_binding(seat, term, bind, serial, &update_search_result, &search_direction, @@ -1410,7 +1405,7 @@ search_input(struct seat *seat, struct terminal *term, return; } - if (bind->mods != bind_mods || bind_mods != (mods & ~locked)) + if (bind->mods != mods) continue; /* Match untranslated symbols */ diff --git a/search.h b/search.h index d5d4162b..ee8ecd76 100644 --- a/search.h +++ b/search.h @@ -11,7 +11,6 @@ void search_input( struct seat *seat, struct terminal *term, const struct key_binding_set *bindings, uint32_t key, xkb_keysym_t sym, xkb_mod_mask_t mods, xkb_mod_mask_t consumed, - xkb_mod_mask_t locked, const xkb_keysym_t *raw_syms, size_t raw_count, uint32_t serial); void search_add_chars(struct terminal *term, const char *text, size_t len); diff --git a/terminal.c b/terminal.c index b0120c6a..f63aaaa7 100644 --- a/terminal.c +++ b/terminal.c @@ -3039,7 +3039,7 @@ term_mouse_grabbed(const struct terminal *term, const struct seat *seat) */ xkb_mod_mask_t mods; - get_current_modifiers(seat, &mods, NULL, 0); + get_current_modifiers(seat, &mods, NULL, 0, true); const struct key_binding_set *bindings = key_binding_for(term->wl->key_binding_manager, term->conf, seat); diff --git a/url-mode.c b/url-mode.c index 1b28f8e0..07499794 100644 --- a/url-mode.c +++ b/url-mode.c @@ -145,28 +145,22 @@ void urls_input(struct seat *seat, struct terminal *term, const struct key_binding_set *bindings, uint32_t key, xkb_keysym_t sym, xkb_mod_mask_t mods, xkb_mod_mask_t consumed, - xkb_mod_mask_t locked, const xkb_keysym_t *raw_syms, size_t raw_count, uint32_t serial) { - const xkb_mod_mask_t bind_mods = - mods & seat->kbd.bind_significant & ~locked; - const xkb_mod_mask_t bind_consumed = - consumed & seat->kbd.bind_significant & ~locked; - /* Key bindings */ tll_foreach(bindings->url, it) { const struct key_binding *bind = &it->item; /* Match translated symbol */ if (bind->k.sym == sym && - bind->mods == (bind_mods & ~bind_consumed)) + bind->mods == (mods & ~consumed)) { execute_binding(seat, term, bind, serial); return; } - if (bind->mods != bind_mods || bind_mods != (mods & ~locked)) + if (bind->mods != mods) continue; for (size_t i = 0; i < raw_count; i++) { @@ -196,7 +190,7 @@ urls_input(struct seat *seat, struct terminal *term, return; } - if (mods & ~consumed & ~locked) + if (mods & ~consumed) return; char32_t wc = xkb_state_key_get_utf32(seat->kbd.xkb_state, key); diff --git a/url-mode.h b/url-mode.h index abfcb57b..eefe07c0 100644 --- a/url-mode.h +++ b/url-mode.h @@ -23,6 +23,5 @@ void urls_reset(struct terminal *term); void urls_input(struct seat *seat, struct terminal *term, const struct key_binding_set *bindings, uint32_t key, xkb_keysym_t sym, xkb_mod_mask_t mods, xkb_mod_mask_t consumed, - xkb_mod_mask_t locked, const xkb_keysym_t *raw_syms, size_t raw_count, uint32_t serial); diff --git a/wayland.h b/wayland.h index 3551dd60..733ebd3f 100644 --- a/wayland.h +++ b/wayland.h @@ -128,7 +128,6 @@ struct seat { xkb_mod_index_t mod_caps; xkb_mod_index_t mod_num; - xkb_mod_mask_t bind_significant; /* Significant modifiers for shortcut handling */ xkb_mod_mask_t legacy_significant; /* Significant modifiers for the legacy keyboard protocol */ xkb_mod_mask_t kitty_significant; /* Significant modifiers for the kitty keyboard protocol */