From 0c6fa477897e3bcda46fde6382a0eb4c640a5213 Mon Sep 17 00:00:00 2001 From: Kovid Goyal Date: Sun, 31 Mar 2024 09:41:04 +0530 Subject: [PATCH] Wayland IME: Fix a bug with handling synthetic keypresses generated by ZMK keyboard + fcitx5 Fixes #7283 --- docs/changelog.rst | 2 ++ glfw/wl_text_input.c | 12 ++++++------ kitty/keys.c | 3 ++- 3 files changed, 10 insertions(+), 7 deletions(-) diff --git a/docs/changelog.rst b/docs/changelog.rst index cfd2ab5a2..01af6061e 100644 --- a/docs/changelog.rst +++ b/docs/changelog.rst @@ -64,6 +64,8 @@ Detailed list of changes - Wayland KDE: Fix mouse cursor hiding not working in Plasma 6 (:iss:`7265`) +- Wayland IME: Fix a bug with handling synthetic keypresses generated by ZMK keyboard + fcitx (:pull:`7283`) + - A new option :opt:`terminfo_type` to allow passing the terminfo database embedded into the :envvar:`TERMINFO` env var directly instead of via a file - Mouse reporting: Fix drag release event outside the window not being reported in legacy mouse reporting modes (:iss:`7244`) diff --git a/glfw/wl_text_input.c b/glfw/wl_text_input.c index 4a9502e78..0a33fe71c 100644 --- a/glfw/wl_text_input.c +++ b/glfw/wl_text_input.c @@ -89,11 +89,11 @@ text_input_delete_surrounding_text( static void text_input_done(void *data UNUSED, struct zwp_text_input_v3 *txt_input UNUSED, uint32_t serial) { debug("text-input: done event: serial: %u current_commit_serial: %u\n", serial, commit_serial); - if (serial != commit_serial) { - if (serial > commit_serial) _glfwInputError(GLFW_PLATFORM_ERROR, "Wayland: text_input_done serial mismatch, expected=%u got=%u\n", commit_serial, serial); - return; - } - + const bool bad_event = serial != commit_serial; + // See https://wayland.app/protocols/text-input-unstable-v3#zwp_text_input_v3:event:done + // for handling of bad events. As best as I can tell spec says we perform all client side actions as usual + // but send nothing back to the compositor, aka no cursor position update. + // See https://github.com/kovidgoyal/kitty/pull/7283 for discussion if ((pending_pre_edit == NULL && current_pre_edit == NULL) || (pending_pre_edit && current_pre_edit && strcmp(pending_pre_edit, current_pre_edit) == 0)) { free(pending_pre_edit); pending_pre_edit = NULL; @@ -102,7 +102,7 @@ text_input_done(void *data UNUSED, struct zwp_text_input_v3 *txt_input UNUSED, u current_pre_edit = pending_pre_edit; pending_pre_edit = NULL; if (current_pre_edit) { - send_text(current_pre_edit, GLFW_IME_PREEDIT_CHANGED); + send_text(current_pre_edit, bad_event ? GLFW_IME_WAYLAND_DONE_EVENT : GLFW_IME_PREEDIT_CHANGED); } else { // Clear pre-edit text send_text(NULL, GLFW_IME_WAYLAND_DONE_EVENT); diff --git a/kitty/keys.c b/kitty/keys.c index b31ec8ed3..2b06d5cd8 100644 --- a/kitty/keys.c +++ b/kitty/keys.c @@ -165,7 +165,8 @@ on_key_input(GLFWkeyevent *ev) { case GLFW_IME_WAYLAND_DONE_EVENT: // If we update IME position here it sends GNOME's text input system into // an infinite loop. See https://github.com/kovidgoyal/kitty/issues/5105 - screen_update_overlay_text(screen, NULL); + // and also: https://github.com/kovidgoyal/kitty/pull/7283 + screen_update_overlay_text(screen, text); debug("handled wayland IME done event\n"); return; case GLFW_IME_PREEDIT_CHANGED: