1- use std:: os:: unix:: io:: OwnedFd ;
21use std:: {
32 fmt,
3+ fs:: File ,
4+ io:: Read ,
5+ os:: unix:: io:: OwnedFd ,
46 sync:: { Arc , Mutex } ,
57} ;
68
9+ use memmap2:: MmapOptions ;
710use tracing:: debug;
811use wayland_protocols_misc:: zwp_virtual_keyboard_v1:: server:: zwp_virtual_keyboard_v1:: Error :: NoKeymap ;
912use wayland_protocols_misc:: zwp_virtual_keyboard_v1:: server:: zwp_virtual_keyboard_v1:: {
1013 self , ZwpVirtualKeyboardV1 ,
1114} ;
12- use wayland_server:: {
13- backend:: ClientId , protocol:: wl_keyboard:: KeymapFormat , Client , DataInit , Dispatch , DisplayHandle ,
14- Resource ,
15- } ;
15+ use wayland_server:: protocol:: wl_keyboard:: KeymapFormat ;
16+ use wayland_server:: { backend:: ClientId , Client , DataInit , Dispatch , DisplayHandle , Resource } ;
1617use xkbcommon:: xkb;
1718
18- use crate :: input:: keyboard:: { KeyboardTarget , KeymapFile , ModifiersState } ;
19+ use crate :: input:: keyboard:: { KeyboardTarget , Keymap , ModifiersState } ;
1920use crate :: wayland:: input_method:: InputMethodSeat ;
2021use crate :: {
2122 input:: { Seat , SeatHandler } ,
@@ -33,15 +34,18 @@ pub(crate) struct VirtualKeyboard {
3334}
3435
3536struct VirtualKeyboardState {
36- keymap : KeymapFile ,
37+ keymap : Keymap ,
3738 mods : ModifiersState ,
3839 state : xkb:: State ,
3940}
4041
4142impl fmt:: Debug for VirtualKeyboardState {
4243 fn fmt ( & self , f : & mut fmt:: Formatter < ' _ > ) -> fmt:: Result {
4344 f. debug_struct ( "VirtualKeyboardState" )
44- . field ( "keymap" , & self . keymap . id ( ) )
45+ . field (
46+ "keymap" ,
47+ & self . keymap . inner . get_as_string ( xkb:: KEYMAP_FORMAT_USE_ORIGINAL ) ,
48+ )
4549 . field ( "mods" , & self . mods )
4650 . field ( "state" , & self . state . get_raw_ptr ( ) )
4751 . finish ( )
96100 } ;
97101 match request {
98102 zwp_virtual_keyboard_v1:: Request :: Keymap { format, fd, size } => {
99- update_keymap ( data, format, fd, size as usize ) ;
103+ update_keymap ( user_data , data, format, fd, size as usize ) ;
100104 }
101105
102106 zwp_virtual_keyboard_v1:: Request :: Key { time, key, state } => {
@@ -116,10 +120,11 @@ where
116120 . map ( |grab| grab. client ( ) . as_ref ( ) == Some ( client) )
117121 . unwrap_or ( false )
118122 {
123+ let old_keymap = keyboard_handle. get_keymap ( ) . clone ( ) ;
124+ let _ = keyboard_handle. set_keymap ( user_data, & vk_state. keymap ) ;
119125 use wayland_server:: protocol:: wl_keyboard:: KeyState ;
120126 let mut internal = keyboard_handle. arc . internal . lock ( ) . unwrap ( ) ;
121127 let focus = internal. focus . as_mut ( ) . map ( |( focus, _) | focus) ;
122- keyboard_handle. send_keymap ( user_data, & focus, & vk_state. keymap , vk_state. mods ) ;
123128 if let Some ( wl_surface) = focus. and_then ( |f| f. wl_surface ( ) ) {
124129 for_each_focused_kbds ( & data. seat , & wl_surface, |kbd| {
125130 // This should be wl_keyboard::KeyState, but the protocol does not state
@@ -133,18 +138,18 @@ where
133138 kbd. key ( SERIAL_COUNTER . next_serial ( ) . 0 , time, key, key_state) ;
134139 } ) ;
135140 }
141+ drop ( internal) ;
142+ keyboard_handle. set_keymap ( user_data, & old_keymap) ;
136143 } else {
137- {
138- let mut internal = keyboard_handle. arc . internal . lock ( ) . unwrap ( ) ;
139- let focus = internal. focus . as_mut ( ) . map ( |( focus, _) | focus) ;
140- keyboard_handle. send_keymap ( user_data, & focus, & vk_state. keymap , vk_state. mods ) ;
141- }
144+ let old_keymap = keyboard_handle. get_keymap ( ) . clone ( ) ;
145+ let _ = keyboard_handle. set_keymap ( user_data, & vk_state. keymap ) ;
142146 let key_state = if state == 1 {
143147 KeyState :: Pressed
144148 } else {
145149 KeyState :: Released
146150 } ;
147- user_data. on_keyboard_event ( ( key + 8 ) . into ( ) , key_state, time, keyboard_handle) ;
151+ user_data. on_keyboard_event ( ( key + 8 ) . into ( ) , key_state, time, keyboard_handle. clone ( ) ) ;
152+ keyboard_handle. set_keymap ( user_data, & old_keymap) ;
148153 }
149154 }
150155 zwp_virtual_keyboard_v1:: Request :: Modifiers {
@@ -171,15 +176,13 @@ where
171176
172177 // Ensure virtual keyboard's keymap is active.
173178 let keyboard_handle = data. seat . get_keyboard ( ) . unwrap ( ) ;
179+ let old_keymap = keyboard_handle. get_keymap ( ) . clone ( ) ;
180+ let _ = keyboard_handle. set_keymap ( user_data, & state. keymap ) ;
174181 {
175182 let mut internal = keyboard_handle. arc . internal . lock ( ) . unwrap ( ) ;
176183 let focus = internal. focus . as_mut ( ) . map ( |( focus, _) | focus) ;
177- let keymap_changed =
178- keyboard_handle. send_keymap ( user_data, & focus, & state. keymap , state. mods ) ;
179- if !keymap_changed {
180- if let Some ( focus) = focus {
181- focus. modifiers ( & data. seat , user_data, state. mods , SERIAL_COUNTER . next_serial ( ) ) ;
182- }
184+ if let Some ( focus) = focus {
185+ focus. modifiers ( & data. seat , user_data, state. mods , SERIAL_COUNTER . next_serial ( ) ) ;
183186 }
184187 }
185188 if ime_keyboard_grabbed. is_none ( )
@@ -189,9 +192,10 @@ where
189192 mods_depressed,
190193 mods_latched,
191194 mods_locked,
192- keyboard_handle,
195+ keyboard_handle. clone ( ) ,
193196 ) ;
194197 }
198+ keyboard_handle. set_keymap ( user_data, & old_keymap) ;
195199 }
196200 zwp_virtual_keyboard_v1:: Request :: Destroy => {
197201 // Nothing to do
@@ -212,8 +216,13 @@ where
212216/// Handle the zwp_virtual_keyboard_v1::keymap request.
213217///
214218/// The `true` returns when keymap was properly loaded.
215- fn update_keymap < D > ( data : & VirtualKeyboardUserData < D > , format : u32 , fd : OwnedFd , size : usize )
216- where
219+ fn update_keymap < D > (
220+ user_data : & mut D ,
221+ data : & VirtualKeyboardUserData < D > ,
222+ format : u32 ,
223+ fd : OwnedFd ,
224+ size : usize ,
225+ ) where
217226 D : SeatHandler + ' static ,
218227{
219228 // Only libxkbcommon compatible keymaps are supported.
@@ -222,34 +231,27 @@ where
222231 return ;
223232 }
224233
225- let context = xkb:: Context :: new ( xkb:: CONTEXT_NO_FLAGS ) ;
226- // SAFETY: we can map the keymap into the memory.
227- let new_keymap = match unsafe {
228- xkb:: Keymap :: new_from_fd (
229- & context,
230- fd,
231- size,
232- xkb:: KEYMAP_FORMAT_TEXT_V1 ,
233- xkb:: KEYMAP_COMPILE_NO_FLAGS ,
234- )
235- } {
236- Ok ( Some ( new_keymap) ) => new_keymap,
237- Ok ( None ) => {
238- debug ! ( "Invalid libxkbcommon keymap" ) ;
239- return ;
240- }
241- Err ( err) => {
242- debug ! ( "Could not map the keymap: {err:?}" ) ;
243- return ;
244- }
234+ let map = unsafe {
235+ MmapOptions :: new ( )
236+ . len ( size as usize )
237+ . map_copy_read_only ( & File :: from ( fd) )
238+ . unwrap ( )
245239 } ;
246-
240+ let keymap_string = String :: from_utf8_lossy ( & map [ .. ] ) . to_string ( ) ;
247241 // Store active virtual keyboard map.
248242 let mut inner = data. handle . inner . lock ( ) . unwrap ( ) ;
249243 let mods = inner. state . take ( ) . map ( |state| state. mods ) . unwrap_or_default ( ) ;
244+ let keyboard_handle = data. seat . get_keyboard ( ) . unwrap ( ) ;
245+ let old_keymap = keyboard_handle. get_keymap ( ) . clone ( ) ;
246+ let keymap = {
247+ let _ = keyboard_handle. set_keymap_from_string ( user_data, keymap_string) ;
248+ keyboard_handle. get_keymap ( ) . clone ( )
249+ } ;
250+ let state = xkb:: State :: new ( & keymap. inner ) ;
250251 inner. state = Some ( VirtualKeyboardState {
251252 mods,
252- keymap : KeymapFile :: new ( & new_keymap ) ,
253- state : xkb :: State :: new ( & new_keymap ) ,
253+ keymap : keymap . clone ( ) ,
254+ state,
254255 } ) ;
256+ keyboard_handle. set_keymap ( user_data, & old_keymap) ;
255257}
0 commit comments