diff --git a/src/wayland/dispatcher.rs b/src/wayland/dispatcher.rs index 33e9927..cebe8c2 100644 --- a/src/wayland/dispatcher.rs +++ b/src/wayland/dispatcher.rs @@ -58,11 +58,16 @@ impl Dispatcher { .expect("Compositor must implement wl_seat"); let layer_shell = globals.bind(&queue, 3..=4, ()) .expect("Compositor must implement zwlr_layer_shell_v1"); - let vk_man = globals.bind(&queue, 1..=1, ()) - .expect("Compositor must implement zwp_virtual_keyboard_manager_v1"); - let im_man = globals.bind(&queue, 1..=1, ()) - .expect("Compositor must implement zwp_input_method_manager_v2"); + let vk_man = match globals.bind(&queue, 1..=1, ()) { + Ok(g) => Some(g), + Err(_) => None, + }; + + let im_man = match globals.bind(&queue, 1..=1, ()) { + Ok(g) => Some(g), + Err(_) => None, + }; let frac_scale_man = match globals.bind(&queue, 1..=1, ()) { Ok(g) => Some(g), diff --git a/src/wayland/keyboard.rs b/src/wayland/keyboard.rs index 1b30f95..37bc6c8 100644 --- a/src/wayland/keyboard.rs +++ b/src/wayland/keyboard.rs @@ -24,11 +24,11 @@ use wayland_client::protocol::wl_keyboard::KeymapFormat; use xkeysym::Keysym; pub struct VirtualKeyboard { - vk: ZwpVirtualKeyboardV1, + vk: Option, keymap: File, keymap_id: u8, - im: ZwpInputMethodV2, + im: Option, im_serial: u32, keycodes: HashMap, @@ -40,13 +40,13 @@ impl VirtualKeyboard { pub fn new + Dispatch + 'static>(queue: &QueueHandle, - vk_man: &ZwpVirtualKeyboardManagerV1, - im_man: &ZwpInputMethodManagerV2, + vk_man: &Option, + im_man: &Option, seat: &WlSeat) -> VirtualKeyboard { - let vk = vk_man.create_virtual_keyboard(seat, queue, ()); - let im = im_man.get_input_method(&seat, &queue, ()); + let vk = vk_man.as_ref().map(|m| m.create_virtual_keyboard(seat, queue, ())); + let im = im_man.as_ref().map(|m| m.get_input_method(&seat, &queue, ())); let path = format!("/tmp/ufkbd-keymap-pid{}-1", process::id()); let keymap = File::create(path).unwrap(); @@ -98,6 +98,10 @@ impl VirtualKeyboard { impl Keyboard for VirtualKeyboard { fn key_supported(&self, sym: Keysym) -> bool { + if self.vk.is_none() { + return false; + } + match sym.name() { Some(n) => n.starts_with("XK_"), None => false, @@ -106,6 +110,8 @@ impl Keyboard for VirtualKeyboard { fn press(&mut self, sym: Keysym) { + let vk = self.vk.as_ref().unwrap(); + if sym == Keysym::NoSymbol || sym == Keysym::XF86_Fn { return; } @@ -113,26 +119,28 @@ impl Keyboard for VirtualKeyboard { match sym { Keysym::Shift_L => { self.mod_state |= 0x1; - self.vk.modifiers(self.mod_state, 0, 0, 0); + vk.modifiers(self.mod_state, 0, 0, 0); }, Keysym::Control_L => { self.mod_state |= 0x4; - self.vk.modifiers(self.mod_state, 0, 0, 0); + vk.modifiers(self.mod_state, 0, 0, 0); }, Keysym::Alt_L => { self.mod_state |= 0x8; - self.vk.modifiers(self.mod_state, 0, 0, 0); + vk.modifiers(self.mod_state, 0, 0, 0); }, _ => (), } let keycode = *self.keycodes.get(&sym).unwrap(); self.pressed[keycode as usize] = sym; - self.vk.key(0, keycode as u32, 1); + vk.key(0, keycode as u32, 1); } fn release(&mut self, sym: Keysym) { + let vk = self.vk.as_ref().unwrap(); + if sym == Keysym::NoSymbol || sym == Keysym::XF86_Fn { return; } @@ -140,28 +148,29 @@ impl Keyboard for VirtualKeyboard { match sym { Keysym::Shift_L => { self.mod_state &= !0x1; - self.vk.modifiers(self.mod_state, 0, 0, 0); + vk.modifiers(self.mod_state, 0, 0, 0); }, Keysym::Control_L => { self.mod_state &= !0x4; - self.vk.modifiers(self.mod_state, 0, 0, 0); + vk.modifiers(self.mod_state, 0, 0, 0); }, Keysym::Alt_L => { self.mod_state &= !0x8; - self.vk.modifiers(self.mod_state, 0, 0, 0); + vk.modifiers(self.mod_state, 0, 0, 0); }, _ => (), } let keycode = *self.keycodes.get(&sym).unwrap(); self.pressed[keycode as usize] = Keysym::NoSymbol; - self.vk.key(0, keycode as u32, 0); + vk.key(0, keycode as u32, 0); } fn text(&mut self, text: &str) { - self.im.commit_string(text.to_string()); - self.im.commit(self.im_serial); + let im = self.im.as_ref().unwrap(); + im.commit_string(text.to_string()); + im.commit(self.im_serial); } fn change_layout(&mut self, layout: &Layout) @@ -229,27 +238,29 @@ impl Keyboard for VirtualKeyboard { self.keymap.write_all(b" };\n").unwrap(); self.keymap.write_all(b"};\n").unwrap(); - if self.mod_state != 0 { - self.vk.modifiers(0, 0, 0, 0); - } - - for (code, sym) in self.pressed.iter().enumerate() { - if *sym != Keysym::NoSymbol { - self.vk.key(0, code as u32, 0); + if let Some(vk) = self.vk.as_ref() { + if self.mod_state != 0 { + vk.modifiers(0, 0, 0, 0); } - } - let len = self.keymap.stream_position().unwrap() as u32; - self.vk.keymap(KeymapFormat::XkbV1 as u32, self.keymap.as_fd(), len); + for (code, sym) in self.pressed.iter().enumerate() { + if *sym != Keysym::NoSymbol { + vk.key(0, code as u32, 0); + } + } - if self.mod_state != 0 { - self.vk.modifiers(self.mod_state, 0, 0, 0); - } + let len = self.keymap.stream_position().unwrap() as u32; + vk.keymap(KeymapFormat::XkbV1 as u32, self.keymap.as_fd(), len); - for sym in &self.pressed { - if *sym != Keysym::NoSymbol { - let code = *self.keycodes.get(sym).unwrap(); - self.vk.key(0, code as u32, 1); + if self.mod_state != 0 { + vk.modifiers(self.mod_state, 0, 0, 0); + } + + for sym in &self.pressed { + if *sym != Keysym::NoSymbol { + let code = *self.keycodes.get(sym).unwrap(); + vk.key(0, code as u32, 1); + } } } }