From 2e610111b019da0eea953e998cad2dba2f7adc4f Mon Sep 17 00:00:00 2001 From: Kirill Chibisov Date: Sat, 30 Dec 2023 01:10:38 +0400 Subject: [PATCH] On X11, update keymap on XkbMapNotify This is required to handle xmodmap. Fixes #3338. --- CHANGELOG.md | 1 + src/platform_impl/linux/x11/event_processor.rs | 15 +++++++++++++++ src/platform_impl/linux/x11/mod.rs | 4 +++- 3 files changed, 19 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index bc5ba4abe7..0b315bc9d1 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -11,6 +11,7 @@ Unreleased` header. # Unreleased +- On X11, keymap not updated from xmodmap. - On X11, reduce the amount of time spent fetching screen resources. - On Wayland, fix `Window::request_inner_size` being overwritten by resize. - On Wayland, fix `Window::inner_size` not using the correct rounding. diff --git a/src/platform_impl/linux/x11/event_processor.rs b/src/platform_impl/linux/x11/event_processor.rs index ad031b28bc..2cf597f94d 100644 --- a/src/platform_impl/linux/x11/event_processor.rs +++ b/src/platform_impl/linux/x11/event_processor.rs @@ -1282,6 +1282,21 @@ impl EventProcessor { unsafe { self.kb_state.init_with_x11_keymap() }; } } + ffi::XkbMapNotify => { + let prev_mods = self.kb_state.mods_state(); + unsafe { self.kb_state.init_with_x11_keymap() }; + let new_mods = self.kb_state.mods_state(); + if prev_mods != new_mods { + if let Some(window) = self.active_window { + callback(Event::WindowEvent { + window_id: mkwid(window), + event: WindowEvent::ModifiersChanged( + Into::::into(new_mods).into(), + ), + }); + } + } + } ffi::XkbStateNotify => { let xev = unsafe { &*(xev as *const _ as *const ffi::XkbStateNotifyEvent) }; diff --git a/src/platform_impl/linux/x11/mod.rs b/src/platform_impl/linux/x11/mod.rs index fc3a6456a7..1632ade590 100644 --- a/src/platform_impl/linux/x11/mod.rs +++ b/src/platform_impl/linux/x11/mod.rs @@ -364,7 +364,9 @@ impl EventLoop { .xconn .select_xkb_events( 0x100, // Use the "core keyboard device" - xkb::EventType::NEW_KEYBOARD_NOTIFY | xkb::EventType::STATE_NOTIFY, + xkb::EventType::NEW_KEYBOARD_NOTIFY + | xkb::EventType::MAP_NOTIFY + | xkb::EventType::STATE_NOTIFY, ) .unwrap();