From: Matteo Bruni <mbruni@codeweavers.com> --- dlls/winex11.drv/keyboard.c | 55 ++++++++++++++++++++----------------- 1 file changed, 30 insertions(+), 25 deletions(-) diff --git a/dlls/winex11.drv/keyboard.c b/dlls/winex11.drv/keyboard.c index 50bb613e1a5..a3cd2b01af3 100644 --- a/dlls/winex11.drv/keyboard.c +++ b/dlls/winex11.drv/keyboard.c @@ -1669,6 +1669,14 @@ static LANGID langid_from_xkb_layout( const char *layout ) return MAKELANGID(LANG_NEUTRAL, SUBLANG_CUSTOM_UNSPECIFIED); }; +static const char *xkb_layout_from_langid( LANGID langid ) +{ + for (int i = 0; i < ARRAY_SIZE(layout_ids); i++) + if (langid == layout_ids[i].langid) + return layout_ids[i].name; + return NULL; +} + static const struct klid_map_entry { const char *layout; @@ -2062,12 +2070,16 @@ static void init_keycode_mappings( Display *display ) } } -static BOOL find_xkb_layout_variant( const char *name, const char **layout, const char **variant ) +static void find_xkb_layout_variant( Display *display, XModifierKeymap *mmp, int group, const char *name, + const char **layout, const char **variant ) { + unsigned int index; #ifdef SONAME_LIBXKBREGISTRY struct rxkb_layout *iter; - if (rxkb_context) + if (!rxkb_context) WARN( "libxkbregistry not available, falling back to fuzzy layout detection\n" ); + else if (!name) WARN( "Xkb layout name not found, falling back to fuzzy layout detection\n" ); + else { for (iter = p_rxkb_layout_first( rxkb_context ); iter; iter = p_rxkb_layout_next( iter )) { @@ -2077,18 +2089,19 @@ static BOOL find_xkb_layout_variant( const char *name, const char **layout, cons { *layout = p_rxkb_layout_get_name( iter ); *variant = p_rxkb_layout_get_variant( iter ); - return TRUE; + return; } } WARN( "Unknown Xkb layout name %s\n", debugstr_a(name) ); } - else - WARN( "libxkbregistry not available, falling back to fuzzy layout detection\n" ); #else WARN( "libxkbregistry support not compiled in, falling back to fuzzy layout detection\n" ); #endif - return FALSE; + + index = detect_keyboard_layout( display, mmp, group ); + *layout = xkb_layout_from_langid( main_key_tab[index].lcid ); + if (strstr( main_key_tab[index].comment, "dvorak" )) *variant = "dvorak"; } /* initialize or update keyboard layouts */ @@ -2099,7 +2112,6 @@ void init_keyboard_layouts( Display *display ) XModifierKeymap *mmp; XkbDescRec *xkb_desc; struct layout *entry; - LANGID xkb_lang = 0; Status status; KeyCode *kcp; @@ -2147,7 +2159,8 @@ void init_keyboard_layouts( Display *display ) if (!xkb_desc->names->groups[count]) break; if (!XGetAtomNames( display, xkb_desc->names->groups, count, names )) count = 0; - TRACE("Found %u group names\n", count); + TRACE( "Found %u group names\n", count ); + for (int i = 0; i < count; i++) { const char *layout, *variant = NULL; @@ -2155,32 +2168,24 @@ void init_keyboard_layouts( Display *display ) DWORD klid; LANGID lang; - if (!names[i]) continue; - if (find_xkb_layout_variant( names[i], &layout, &variant )) - { - lang = langid_from_xkb_layout( layout ); - klid = klid_from_xkb_layout( layout, variant ); - if (i == xkb_group) xkb_lang = lang; + find_xkb_layout_variant( display, mmp, i, names[i], &layout, &variant ); + lang = langid_from_xkb_layout( layout ); + klid = klid_from_xkb_layout( layout, variant ); - TRACE( "Found group %u with name %s -> layout %s:%s, lang %04x, klid %08x\n", i, debugstr_a(names[i]), - debugstr_a(layout), debugstr_a(variant), lang, klid ); + TRACE( "Found group %u with name %s -> layout %s:%s, lang %04x, klid %08x\n", i, debugstr_a(names[i]), + debugstr_a(layout), debugstr_a(variant), lang, klid ); - snprintf( buffer, ARRAY_SIZE(buffer), "%s:%s", layout, variant ); - create_layout_from_xkb( i, buffer, lang, klid ); - } - XFree( names[i] ); + snprintf( buffer, ARRAY_SIZE(buffer), "%s:%s", layout, variant ); + create_layout_from_xkb( i, buffer, lang, klid ); + + if (names[i]) XFree( names[i] ); } XkbFreeKeyboard( xkb_desc, 0, True ); } - kbd_layout = detect_keyboard_layout( display, mmp, xkb_group ); XFreeModifiermap( mmp ); - if (xkb_lang && xkb_lang != main_key_tab[kbd_layout].lcid) - WARN( "Xkb langid %04x differs from detected langid %04x\n", - xkb_lang, main_key_tab[kbd_layout].lcid ); - init_keycode_mappings( display ); pthread_mutex_unlock( &kbd_mutex ); -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/11037