wok-4.x annotate lxpanel/stuff/Fix-failure-to-react-to-keyboard-map-changes-initiat.patch @ rev 7710

merge
author fireflyoo <lufeng369@gmail.com>
date Sun Dec 19 23:29:00 2010 +0800 (2010-12-19)
parents
children
rev   line source
slaxemulator@6394 1 From 438d9fdbd3e0be04de933705917d508a02b7c04b Mon Sep 17 00:00:00 2001
slaxemulator@6394 2 From: Marty Jack <martyj@linux.local>
slaxemulator@6394 3 Date: Sat, 20 Feb 2010 16:23:57 -0500
slaxemulator@6394 4 Subject: [PATCH 4/5] Fix failure to react to keyboard map changes initiated outside the plugin
slaxemulator@6394 5 - Occurred when setxkbmap was run, or when HAL configured the keyboard at X startup
slaxemulator@6394 6 - Caused by failure to process the NewKeyboard event
slaxemulator@6394 7 - Caused by dropping events due to faulty code to read them
slaxemulator@6394 8 - Cosmetic change, the tooltip now the Xkb Group name rather than Xkb Symbol name
slaxemulator@6394 9
slaxemulator@6394 10 ---
slaxemulator@6394 11 src/plugins/xkb/xkb-plugin.c | 92 +++++++++--------
slaxemulator@6394 12 src/plugins/xkb/xkb.c | 236 +++++++++++++++++++++--------------------
slaxemulator@6394 13 src/plugins/xkb/xkb.h | 7 +-
slaxemulator@6394 14 3 files changed, 173 insertions(+), 162 deletions(-)
slaxemulator@6394 15
slaxemulator@6394 16 diff --git a/src/plugins/xkb/xkb-plugin.c b/src/plugins/xkb/xkb-plugin.c
slaxemulator@6394 17 index f49a77d..80a14ba 100644
slaxemulator@6394 18 --- a/src/plugins/xkb/xkb-plugin.c
slaxemulator@6394 19 +++ b/src/plugins/xkb/xkb-plugin.c
slaxemulator@6394 20 @@ -1,18 +1,23 @@
slaxemulator@6394 21 -/*
slaxemulator@6394 22 -//====================================================================
slaxemulator@6394 23 -// xfce4-xkb-plugin - XFCE4 Xkb Layout Indicator panel plugin
slaxemulator@6394 24 -// -------------------------------------------------------------------
slaxemulator@6394 25 -// Alexander Iliev <sasoiliev@mamul.org>
slaxemulator@6394 26 -// 20-Feb-04
slaxemulator@6394 27 -// -------------------------------------------------------------------
slaxemulator@6394 28 -// Parts of this code belong to Michael Glickman <wmalms@yahooo.com>
slaxemulator@6394 29 -// and his program wmxkb.
slaxemulator@6394 30 -// WARNING: DO NOT BOTHER Michael Glickman WITH QUESTIONS ABOUT THIS
slaxemulator@6394 31 -// PROGRAM!!! SEND INSTEAD EMAILS TO <sasoiliev@mamul.org>
slaxemulator@6394 32 -//====================================================================
slaxemulator@6394 33 -*/
slaxemulator@6394 34 -
slaxemulator@6394 35 -/* Modified by Hong Jen Yee (PCMan) <pcman.tw@gmail.com> on 2008-04-06 for lxpanel */
slaxemulator@6394 36 +/**
slaxemulator@6394 37 + * Copyright (c) 2010 LxDE Developers, see the file AUTHORS for details.
slaxemulator@6394 38 + *
slaxemulator@6394 39 + * This program is free software; you can redistribute it and/or modify
slaxemulator@6394 40 + * it under the terms of the GNU General Public License as published by
slaxemulator@6394 41 + * the Free Software Foundation; either version 2 of the License, or
slaxemulator@6394 42 + * (at your option) any later version.
slaxemulator@6394 43 + *
slaxemulator@6394 44 + * This program is distributed in the hope that it will be useful,
slaxemulator@6394 45 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
slaxemulator@6394 46 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
slaxemulator@6394 47 + * GNU General Public License for more details.
slaxemulator@6394 48 + *
slaxemulator@6394 49 + * You should have received a copy of the GNU General Public License
slaxemulator@6394 50 + * along with this program; if not, write to the Free Software Foundation,
slaxemulator@6394 51 + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
slaxemulator@6394 52 + */
slaxemulator@6394 53 +
slaxemulator@6394 54 +/* Originally derived from xfce4-xkb-plugin, Copyright 2004 Alexander Iliev,
slaxemulator@6394 55 + * which credits Michael Glickman. */
slaxemulator@6394 56
slaxemulator@6394 57 #ifdef HAVE_CONFIG_H
slaxemulator@6394 58 #include <config.h>
slaxemulator@6394 59 @@ -49,38 +54,45 @@ void xkb_redraw(XkbPlugin * xkb)
slaxemulator@6394 60 if (xkb->display_type == IMAGE)
slaxemulator@6394 61 {
slaxemulator@6394 62 int size = xkb->plugin->panel->icon_size;
slaxemulator@6394 63 - char * group_name = (char *) xkb_get_current_group_name_lowercase(xkb);
slaxemulator@6394 64 - char * filename = g_strdup_printf("%s/%s.png", FLAGSDIR, group_name);
slaxemulator@6394 65 - GdkPixbuf * unscaled_pixbuf = gdk_pixbuf_new_from_file(filename, NULL);
slaxemulator@6394 66 - g_free(filename);
slaxemulator@6394 67 - g_free(group_name);
slaxemulator@6394 68 -
slaxemulator@6394 69 - if (unscaled_pixbuf != NULL)
slaxemulator@6394 70 + char * group_name = (char *) xkb_get_current_symbol_name_lowercase(xkb);
slaxemulator@6394 71 + if (group_name != NULL)
slaxemulator@6394 72 {
slaxemulator@6394 73 - /* Loaded successfully. */
slaxemulator@6394 74 - int width = gdk_pixbuf_get_width(unscaled_pixbuf);
slaxemulator@6394 75 - int height = gdk_pixbuf_get_height(unscaled_pixbuf);
slaxemulator@6394 76 - GdkPixbuf * pixbuf = gdk_pixbuf_scale_simple(unscaled_pixbuf, size * width / height, size, GDK_INTERP_BILINEAR);
slaxemulator@6394 77 - if (pixbuf != NULL)
slaxemulator@6394 78 + char * filename = g_strdup_printf("%s/%s.png", FLAGSDIR, group_name);
slaxemulator@6394 79 + GdkPixbuf * unscaled_pixbuf = gdk_pixbuf_new_from_file(filename, NULL);
slaxemulator@6394 80 + g_free(filename);
slaxemulator@6394 81 + g_free(group_name);
slaxemulator@6394 82 +
slaxemulator@6394 83 + if (unscaled_pixbuf != NULL)
slaxemulator@6394 84 {
slaxemulator@6394 85 - gtk_image_set_from_pixbuf(GTK_IMAGE(xkb->image), pixbuf);
slaxemulator@6394 86 - g_object_unref(G_OBJECT(pixbuf));
slaxemulator@6394 87 - gtk_widget_hide(xkb->label);
slaxemulator@6394 88 - gtk_widget_show(xkb->image);
slaxemulator@6394 89 - gtk_widget_set_tooltip_text(xkb->btn, xkb_get_current_group_name(xkb));
slaxemulator@6394 90 - valid_image = TRUE;
slaxemulator@6394 91 + /* Loaded successfully. */
slaxemulator@6394 92 + int width = gdk_pixbuf_get_width(unscaled_pixbuf);
slaxemulator@6394 93 + int height = gdk_pixbuf_get_height(unscaled_pixbuf);
slaxemulator@6394 94 + GdkPixbuf * pixbuf = gdk_pixbuf_scale_simple(unscaled_pixbuf, size * width / height, size, GDK_INTERP_BILINEAR);
slaxemulator@6394 95 + if (pixbuf != NULL)
slaxemulator@6394 96 + {
slaxemulator@6394 97 + gtk_image_set_from_pixbuf(GTK_IMAGE(xkb->image), pixbuf);
slaxemulator@6394 98 + g_object_unref(G_OBJECT(pixbuf));
slaxemulator@6394 99 + gtk_widget_hide(xkb->label);
slaxemulator@6394 100 + gtk_widget_show(xkb->image);
slaxemulator@6394 101 + gtk_widget_set_tooltip_text(xkb->btn, xkb_get_current_group_name(xkb));
slaxemulator@6394 102 + valid_image = TRUE;
slaxemulator@6394 103 + }
slaxemulator@6394 104 + g_object_unref(unscaled_pixbuf);
slaxemulator@6394 105 }
slaxemulator@6394 106 - g_object_unref(unscaled_pixbuf);
slaxemulator@6394 107 }
slaxemulator@6394 108 }
slaxemulator@6394 109
slaxemulator@6394 110 /* Set the label. */
slaxemulator@6394 111 if ((xkb->display_type == TEXT) || ( ! valid_image))
slaxemulator@6394 112 {
slaxemulator@6394 113 - panel_draw_label_text(xkb->plugin->panel, xkb->label, (char *) xkb_get_current_group_name(xkb), TRUE, TRUE);
slaxemulator@6394 114 - gtk_widget_hide(xkb->image);
slaxemulator@6394 115 - gtk_widget_show(xkb->label);
slaxemulator@6394 116 - gtk_widget_set_tooltip_text(xkb->btn, NULL);
slaxemulator@6394 117 + char * group_name = (char *) xkb_get_current_symbol_name(xkb);
slaxemulator@6394 118 + if (group_name != NULL)
slaxemulator@6394 119 + {
slaxemulator@6394 120 + panel_draw_label_text(xkb->plugin->panel, xkb->label, (char *) group_name, TRUE, TRUE);
slaxemulator@6394 121 + gtk_widget_hide(xkb->image);
slaxemulator@6394 122 + gtk_widget_show(xkb->label);
slaxemulator@6394 123 + gtk_widget_set_tooltip_text(xkb->btn, xkb_get_current_group_name(xkb));
slaxemulator@6394 124 + }
slaxemulator@6394 125 }
slaxemulator@6394 126 }
slaxemulator@6394 127
slaxemulator@6394 128 @@ -196,10 +208,6 @@ static int xkb_constructor(Plugin * plugin, char ** fp)
slaxemulator@6394 129 /* Initialize the XKB interface. */
slaxemulator@6394 130 xkb_mechanism_constructor(xkb);
slaxemulator@6394 131
slaxemulator@6394 132 - /* Initialize a channel to listen for XKB events. */
slaxemulator@6394 133 - GIOChannel * channel = g_io_channel_unix_new(xkb_get_connection_number(xkb));
slaxemulator@6394 134 - xkb->source_id = g_io_add_watch(channel, G_IO_IN | G_IO_PRI, (GIOFunc) xkb_gio_callback, (gpointer) xkb);
slaxemulator@6394 135 -
slaxemulator@6394 136 /* Connect signals. */
slaxemulator@6394 137 g_signal_connect(xkb->btn, "button-press-event", G_CALLBACK(xkb_button_press_event), xkb);
slaxemulator@6394 138 g_signal_connect(xkb->btn, "scroll-event", G_CALLBACK(xkb_scroll_event), xkb);
slaxemulator@6394 139 diff --git a/src/plugins/xkb/xkb.c b/src/plugins/xkb/xkb.c
slaxemulator@6394 140 index 5bb0c39..898a931 100644
slaxemulator@6394 141 --- a/src/plugins/xkb/xkb.c
slaxemulator@6394 142 +++ b/src/plugins/xkb/xkb.c
slaxemulator@6394 143 @@ -1,18 +1,23 @@
slaxemulator@6394 144 -/*
slaxemulator@6394 145 -// ====================================================================
slaxemulator@6394 146 -// xfce4-xkb-plugin - XFCE4 Xkb Layout Indicator panel plugin
slaxemulator@6394 147 -// -------------------------------------------------------------------
slaxemulator@6394 148 -// Alexander Iliev <sasoiliev@mamul.org>
slaxemulator@6394 149 -// 20-Feb-04
slaxemulator@6394 150 -// -------------------------------------------------------------------
slaxemulator@6394 151 -// Parts of this code belong to Michael Glickman <wmalms@yahooo.com>
slaxemulator@6394 152 -// and his program wmxkb.
slaxemulator@6394 153 -// WARNING: DO NOT BOTHER Michael Glickman WITH QUESTIONS ABOUT THIS
slaxemulator@6394 154 -// PROGRAM!!! SEND INSTEAD EMAILS TO <sasoiliev@mamul.org>
slaxemulator@6394 155 -//====================================================================
slaxemulator@6394 156 -*/
slaxemulator@6394 157 -
slaxemulator@6394 158 -/* Modified by Hong Jen Yee (PCMan) <pcman.tw@gmail.com> on 2008-04-06 for lxpanel */
slaxemulator@6394 159 +/**
slaxemulator@6394 160 + * Copyright (c) 2010 LxDE Developers, see the file AUTHORS for details.
slaxemulator@6394 161 + *
slaxemulator@6394 162 + * This program is free software; you can redistribute it and/or modify
slaxemulator@6394 163 + * it under the terms of the GNU General Public License as published by
slaxemulator@6394 164 + * the Free Software Foundation; either version 2 of the License, or
slaxemulator@6394 165 + * (at your option) any later version.
slaxemulator@6394 166 + *
slaxemulator@6394 167 + * This program is distributed in the hope that it will be useful,
slaxemulator@6394 168 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
slaxemulator@6394 169 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
slaxemulator@6394 170 + * GNU General Public License for more details.
slaxemulator@6394 171 + *
slaxemulator@6394 172 + * You should have received a copy of the GNU General Public License
slaxemulator@6394 173 + * along with this program; if not, write to the Free Software Foundation,
slaxemulator@6394 174 + * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
slaxemulator@6394 175 + */
slaxemulator@6394 176 +
slaxemulator@6394 177 +/* Originally derived from xfce4-xkb-plugin, Copyright 2004 Alexander Iliev,
slaxemulator@6394 178 + * which credits Michael Glickman. */
slaxemulator@6394 179
slaxemulator@6394 180 #include "xkb.h"
slaxemulator@6394 181
slaxemulator@6394 182 @@ -26,9 +31,13 @@
slaxemulator@6394 183 #include <gdk-pixbuf/gdk-pixbuf.h>
slaxemulator@6394 184 #include <glib.h>
slaxemulator@6394 185
slaxemulator@6394 186 +/* The X Keyboard Extension: Library Specification
slaxemulator@6394 187 + * http://www.xfree86.org/current/XKBlib.pdf */
slaxemulator@6394 188 +
slaxemulator@6394 189 static void xkb_enter_locale_by_process(XkbPlugin * xkb);
slaxemulator@6394 190 static void refresh_group_xkb(XkbPlugin * xkb);
slaxemulator@6394 191 -static int do_init_xkb(XkbPlugin * xkb);
slaxemulator@6394 192 +static int initialize_keyboard_description(XkbPlugin * xkb);
slaxemulator@6394 193 +static GdkFilterReturn xkb_event_filter(GdkXEvent * xevent, GdkEvent * event, XkbPlugin * xkb);
slaxemulator@6394 194
slaxemulator@6394 195 /* Insert a process and its layout into the hash table. */
slaxemulator@6394 196 static void xkb_enter_locale_by_process(XkbPlugin * xkb)
slaxemulator@6394 197 @@ -56,60 +65,65 @@ int xkb_get_group_count(XkbPlugin * xkb)
slaxemulator@6394 198 return xkb->group_count;
slaxemulator@6394 199 }
slaxemulator@6394 200
slaxemulator@6394 201 +/* Get the current group name. */
slaxemulator@6394 202 +const char * xkb_get_current_group_name(XkbPlugin * xkb)
slaxemulator@6394 203 +{
slaxemulator@6394 204 + return xkb->group_names[xkb->current_group_xkb_no];
slaxemulator@6394 205 +}
slaxemulator@6394 206 +
slaxemulator@6394 207 /* Convert a group number to a symbol name. */
slaxemulator@6394 208 const char * xkb_get_symbol_name_by_res_no(XkbPlugin * xkb, int n)
slaxemulator@6394 209 {
slaxemulator@6394 210 return xkb->symbol_names[n];
slaxemulator@6394 211 }
slaxemulator@6394 212
slaxemulator@6394 213 -/* Get the current group name. */
slaxemulator@6394 214 -const char * xkb_get_current_group_name(XkbPlugin * xkb)
slaxemulator@6394 215 +/* Get the current symbol name. */
slaxemulator@6394 216 +const char * xkb_get_current_symbol_name(XkbPlugin * xkb)
slaxemulator@6394 217 {
slaxemulator@6394 218 return xkb_get_symbol_name_by_res_no(xkb, xkb->current_group_xkb_no);
slaxemulator@6394 219 }
slaxemulator@6394 220
slaxemulator@6394 221 -/* Get the current group name converted to lowercase. */
slaxemulator@6394 222 -const char * xkb_get_current_group_name_lowercase(XkbPlugin * xkb)
slaxemulator@6394 223 +/* Get the current symbol name converted to lowercase. */
slaxemulator@6394 224 +const char * xkb_get_current_symbol_name_lowercase(XkbPlugin * xkb)
slaxemulator@6394 225 {
slaxemulator@6394 226 - const char * tmp = xkb_get_current_group_name(xkb);
slaxemulator@6394 227 - return g_utf8_strdown(tmp, -1);
slaxemulator@6394 228 + const char * tmp = xkb_get_current_symbol_name(xkb);
slaxemulator@6394 229 + return ((tmp != NULL) ? g_utf8_strdown(tmp, -1) : NULL);
slaxemulator@6394 230 }
slaxemulator@6394 231
slaxemulator@6394 232 /* Refresh current group number from Xkb state. */
slaxemulator@6394 233 static void refresh_group_xkb(XkbPlugin * xkb)
slaxemulator@6394 234 {
slaxemulator@6394 235 XkbStateRec xkb_state;
slaxemulator@6394 236 - XkbGetState(xkb->dsp, xkb->device_id, &xkb_state);
slaxemulator@6394 237 + XkbGetState(GDK_DISPLAY(), XkbUseCoreKbd, &xkb_state);
slaxemulator@6394 238 xkb->current_group_xkb_no = xkb_state.group;
slaxemulator@6394 239 }
slaxemulator@6394 240
slaxemulator@6394 241 -/* Initialize the Xkb structures. */
slaxemulator@6394 242 -static int do_init_xkb(XkbPlugin * xkb)
slaxemulator@6394 243 +/* Initialize the keyboard description initially or after a NewKeyboard event. */
slaxemulator@6394 244 +static int initialize_keyboard_description(XkbPlugin * xkb)
slaxemulator@6394 245 {
slaxemulator@6394 246 - /* Create hash table. */
slaxemulator@6394 247 - xkb->group_hash_table = g_hash_table_new(g_direct_hash, NULL);
slaxemulator@6394 248 -
slaxemulator@6394 249 - /* Initialize the Xkb extension. */
slaxemulator@6394 250 - int major, minor, opcode;
slaxemulator@6394 251 - Bool status = XkbQueryExtension(xkb->dsp, &opcode,
slaxemulator@6394 252 - &xkb->base_event_code, &xkb->base_error_code, &major, &minor);
slaxemulator@6394 253 -
slaxemulator@6394 254 - /* Use the core keyboard. */
slaxemulator@6394 255 - xkb->device_id = XkbUseCoreKbd;
slaxemulator@6394 256 + /* Free the strings. */
slaxemulator@6394 257 + int i;
slaxemulator@6394 258 + for (i = 0; i < XkbNumKbdGroups; i += 1)
slaxemulator@6394 259 + {
slaxemulator@6394 260 + g_free(xkb->group_names[i]);
slaxemulator@6394 261 + g_free(xkb->symbol_names[i]);
slaxemulator@6394 262 + xkb->group_names[i] = NULL;
slaxemulator@6394 263 + xkb->symbol_names[i] = NULL;
slaxemulator@6394 264 + }
slaxemulator@6394 265
slaxemulator@6394 266 /* Allocate a keyboard description structure. */
slaxemulator@6394 267 + int status = False;
slaxemulator@6394 268 XkbDescRec * kbd_desc_ptr = XkbAllocKeyboard();
slaxemulator@6394 269 if (kbd_desc_ptr == NULL)
slaxemulator@6394 270 {
slaxemulator@6394 271 ERR("Failed to get keyboard description\n");
slaxemulator@6394 272 goto HastaLaVista;
slaxemulator@6394 273 }
slaxemulator@6394 274 - kbd_desc_ptr->dpy = xkb->dsp;
slaxemulator@6394 275
slaxemulator@6394 276 /* Fetch information into the keyboard description. */
slaxemulator@6394 277 - XkbGetControls(xkb->dsp, XkbAllControlsMask, kbd_desc_ptr);
slaxemulator@6394 278 - XkbGetNames(xkb->dsp, XkbSymbolsNameMask, kbd_desc_ptr);
slaxemulator@6394 279 - XkbGetNames(xkb->dsp, XkbGroupNamesMask, kbd_desc_ptr);
slaxemulator@6394 280 + XkbGetControls(GDK_DISPLAY(), XkbAllControlsMask, kbd_desc_ptr);
slaxemulator@6394 281 + XkbGetNames(GDK_DISPLAY(), XkbSymbolsNameMask, kbd_desc_ptr);
slaxemulator@6394 282 + XkbGetNames(GDK_DISPLAY(), XkbGroupNamesMask, kbd_desc_ptr);
slaxemulator@6394 283
slaxemulator@6394 284 if (kbd_desc_ptr->names == NULL)
slaxemulator@6394 285 {
slaxemulator@6394 286 @@ -137,12 +151,11 @@ static int do_init_xkb(XkbPlugin * xkb)
slaxemulator@6394 287
slaxemulator@6394 288 /* Determine the group names. Trim off text beginning at a '('. */
slaxemulator@6394 289 const Atom * tmp_group_source = kbd_desc_ptr->names->groups;
slaxemulator@6394 290 - int i;
slaxemulator@6394 291 for (i = 0; i < xkb->group_count; i++)
slaxemulator@6394 292 {
slaxemulator@6394 293 if (tmp_group_source[i] != None)
slaxemulator@6394 294 {
slaxemulator@6394 295 - char * ptr = XGetAtomName(xkb->dsp, tmp_group_source[i]);
slaxemulator@6394 296 + char * ptr = XGetAtomName(GDK_DISPLAY(), tmp_group_source[i]);
slaxemulator@6394 297 xkb->group_names[i] = ptr;
slaxemulator@6394 298 if ((ptr != NULL) && ((ptr = strchr(ptr, '('))) != NULL)
slaxemulator@6394 299 *ptr = '\0';
slaxemulator@6394 300 @@ -153,7 +166,7 @@ static int do_init_xkb(XkbPlugin * xkb)
slaxemulator@6394 301 Atom sym_name_atom = kbd_desc_ptr->names->symbols;
slaxemulator@6394 302 char * sym_name;
slaxemulator@6394 303 if ((sym_name_atom == None)
slaxemulator@6394 304 - || ((sym_name = XGetAtomName(xkb->dsp, sym_name_atom)) == NULL))
slaxemulator@6394 305 + || ((sym_name = XGetAtomName(GDK_DISPLAY(), sym_name_atom)) == NULL))
slaxemulator@6394 306 goto HastaLaVista;
slaxemulator@6394 307
slaxemulator@6394 308 /* Parse and store symbol names. */
slaxemulator@6394 309 @@ -190,83 +203,106 @@ static int do_init_xkb(XkbPlugin * xkb)
slaxemulator@6394 310 {
slaxemulator@6394 311 xkb->group_count = 2;
slaxemulator@6394 312 xkb->symbol_names[1] = xkb->symbol_names[0];
slaxemulator@6394 313 - xkb->symbol_names[0] = strdup("us");
slaxemulator@6394 314 - xkb->group_names[0] = strdup("US/ASCII");
slaxemulator@6394 315 - xkb->group_names[1] = strdup("Japanese");
slaxemulator@6394 316 + xkb->symbol_names[0] = g_strdup("us");
slaxemulator@6394 317 + xkb->group_names[0] = g_strdup("US/ASCII");
slaxemulator@6394 318 + xkb->group_names[1] = g_strdup("Japanese");
slaxemulator@6394 319 }
slaxemulator@6394 320 else if (count < xkb->group_count)
slaxemulator@6394 321 {
slaxemulator@6394 322 /* Ensure that the names are fully initialized. */
slaxemulator@6394 323 int j = count, k = xkb->group_count;
slaxemulator@6394 324 while(--j >= 0) xkb->symbol_names[--k] = xkb->symbol_names[j];
slaxemulator@6394 325 - while(--k >= 0) xkb->symbol_names[k] = strdup("en_US");
slaxemulator@6394 326 + while(--k >= 0) xkb->symbol_names[k] = g_strdup("en_US");
slaxemulator@6394 327 }
slaxemulator@6394 328
slaxemulator@6394 329 - /* Enxure that the names are fully initialized. */
slaxemulator@6394 330 + /* Ensure that the names are fully initialized. */
slaxemulator@6394 331 for (i = 0; i < xkb->group_count; i++)
slaxemulator@6394 332 {
slaxemulator@6394 333 if (xkb->symbol_names[i] == NULL)
slaxemulator@6394 334 {
slaxemulator@6394 335 ERR("\nGroup Symbol %i is undefined, set to 'U/A' !\n", i+1);
slaxemulator@6394 336 - xkb->symbol_names[i] = strdup("U/A");
slaxemulator@6394 337 + xkb->symbol_names[i] = g_strdup("U/A");
slaxemulator@6394 338 }
slaxemulator@6394 339 }
slaxemulator@6394 340
slaxemulator@6394 341 + /* Create or recreate hash table.
slaxemulator@6394 342 + * The layout that was associated to the windows may or may not be at the same group number,
slaxemulator@6394 343 + * and worse, may no longer exist, which there is no meaningful way to deal with. */
slaxemulator@6394 344 + if (xkb->group_hash_table != NULL)
slaxemulator@6394 345 + g_hash_table_destroy(xkb->group_hash_table);
slaxemulator@6394 346 + xkb->group_hash_table = g_hash_table_new(g_direct_hash, NULL);
slaxemulator@6394 347 +
slaxemulator@6394 348 status = True;
slaxemulator@6394 349
slaxemulator@6394 350 HastaLaVista:
slaxemulator@6394 351 if (kbd_desc_ptr != NULL)
slaxemulator@6394 352 XkbFreeKeyboard(kbd_desc_ptr, 0, True);
slaxemulator@6394 353 +
slaxemulator@6394 354 return status;
slaxemulator@6394 355 }
slaxemulator@6394 356
slaxemulator@6394 357 +/* GDK event filter that receives events from all windows and the Xkb extension. */
slaxemulator@6394 358 +static GdkFilterReturn xkb_event_filter(GdkXEvent * xevent, GdkEvent * event, XkbPlugin * xkb)
slaxemulator@6394 359 +{
slaxemulator@6394 360 + XEvent * ev = (XEvent *) xevent;
slaxemulator@6394 361 +
slaxemulator@6394 362 + if (ev->xany.type == xkb->base_event_code + XkbEventCode)
slaxemulator@6394 363 + {
slaxemulator@6394 364 + /* Xkb event. */
slaxemulator@6394 365 + XkbEvent * xkbev = (XkbEvent *) ev;
slaxemulator@6394 366 + if (xkbev->any.xkb_type == XkbNewKeyboardNotify)
slaxemulator@6394 367 + {
slaxemulator@6394 368 + initialize_keyboard_description(xkb);
slaxemulator@6394 369 + refresh_group_xkb(xkb);
slaxemulator@6394 370 + xkb_redraw(xkb);
slaxemulator@6394 371 + xkb_enter_locale_by_process(xkb);
slaxemulator@6394 372 + }
slaxemulator@6394 373 + else if (xkbev->any.xkb_type == XkbStateNotify)
slaxemulator@6394 374 + {
slaxemulator@6394 375 + if (xkbev->state.group != xkb->current_group_xkb_no)
slaxemulator@6394 376 + {
slaxemulator@6394 377 + /* Switch to the new group and redraw the display. */
slaxemulator@6394 378 + xkb->current_group_xkb_no = xkbev->state.group;
slaxemulator@6394 379 + refresh_group_xkb(xkb);
slaxemulator@6394 380 + xkb_redraw(xkb);
slaxemulator@6394 381 + xkb_enter_locale_by_process(xkb);
slaxemulator@6394 382 + }
slaxemulator@6394 383 + }
slaxemulator@6394 384 + }
slaxemulator@6394 385 + return GDK_FILTER_CONTINUE;
slaxemulator@6394 386 +}
slaxemulator@6394 387 +
slaxemulator@6394 388 /* Initialize the Xkb interface. */
slaxemulator@6394 389 void xkb_mechanism_constructor(XkbPlugin * xkb)
slaxemulator@6394 390 {
slaxemulator@6394 391 - /* Enable the Xkb extension on all clients. */
slaxemulator@6394 392 - XkbIgnoreExtension(False);
slaxemulator@6394 393 -
slaxemulator@6394 394 - /* Open the display. */
slaxemulator@6394 395 - int major = XkbMajorVersion;
slaxemulator@6394 396 - int minor = XkbMinorVersion;
slaxemulator@6394 397 - char * display_name = "";
slaxemulator@6394 398 - int event_code;
slaxemulator@6394 399 - int error_rtrn;
slaxemulator@6394 400 - int reason_rtrn;
slaxemulator@6394 401 - xkb->dsp = XkbOpenDisplay(display_name, &event_code, &error_rtrn, &major, &minor, &reason_rtrn);
slaxemulator@6394 402 -
slaxemulator@6394 403 - switch (reason_rtrn)
slaxemulator@6394 404 + /* Initialize Xkb extension. */
slaxemulator@6394 405 + int opcode;
slaxemulator@6394 406 + int maj = XkbMajorVersion;
slaxemulator@6394 407 + int min = XkbMinorVersion;
slaxemulator@6394 408 + if ((XkbLibraryVersion(&maj, &min))
slaxemulator@6394 409 + && (XkbQueryExtension(GDK_DISPLAY(), &opcode, &xkb->base_event_code, &xkb->base_error_code, &maj, &min)))
slaxemulator@6394 410 {
slaxemulator@6394 411 - case XkbOD_BadLibraryVersion:
slaxemulator@6394 412 - ERR("Bad XKB library version.\n");
slaxemulator@6394 413 - return;
slaxemulator@6394 414 - case XkbOD_ConnectionRefused:
slaxemulator@6394 415 - ERR("Connection to X server refused.\n");
slaxemulator@6394 416 - return;
slaxemulator@6394 417 - case XkbOD_BadServerVersion:
slaxemulator@6394 418 - ERR("Bad X server version.\n");
slaxemulator@6394 419 - return;
slaxemulator@6394 420 - case XkbOD_NonXkbServer:
slaxemulator@6394 421 - ERR("XKB not present.\n");
slaxemulator@6394 422 - return;
slaxemulator@6394 423 - case XkbOD_Success:
slaxemulator@6394 424 - break;
slaxemulator@6394 425 - }
slaxemulator@6394 426 + /* Read the keyboard description. */
slaxemulator@6394 427 + initialize_keyboard_description(xkb);
slaxemulator@6394 428
slaxemulator@6394 429 - /* Initialize our mechanism. */
slaxemulator@6394 430 - if (do_init_xkb(xkb) != True)
slaxemulator@6394 431 - return;
slaxemulator@6394 432 + /* Establish GDK event filter. */
slaxemulator@6394 433 + gdk_window_add_filter(NULL, (GdkFilterFunc) xkb_event_filter, (gpointer) xkb);
slaxemulator@6394 434
slaxemulator@6394 435 - /* Specify events we will receive. */
slaxemulator@6394 436 - XkbSelectEventDetails(xkb->dsp, xkb->device_id, XkbStateNotify, XkbAllStateComponentsMask, XkbGroupStateMask);
slaxemulator@6394 437 + /* Specify events we will receive. */
slaxemulator@6394 438 + XkbSelectEvents(GDK_DISPLAY(), XkbUseCoreKbd, XkbNewKeyboardNotifyMask, XkbNewKeyboardNotifyMask);
slaxemulator@6394 439 + XkbSelectEventDetails(GDK_DISPLAY(), XkbUseCoreKbd, XkbStateNotify, XkbAllStateComponentsMask, XkbGroupStateMask);
slaxemulator@6394 440
slaxemulator@6394 441 - /* Get current state. */
slaxemulator@6394 442 - refresh_group_xkb(xkb);
slaxemulator@6394 443 + /* Get current state. */
slaxemulator@6394 444 + refresh_group_xkb(xkb);
slaxemulator@6394 445 + }
slaxemulator@6394 446 }
slaxemulator@6394 447
slaxemulator@6394 448 /* Deallocate resources associated with Xkb interface. */
slaxemulator@6394 449 void xkb_mechanism_destructor(XkbPlugin * xkb)
slaxemulator@6394 450 {
slaxemulator@6394 451 + /* Remove event filter. */
slaxemulator@6394 452 + gdk_window_remove_filter(NULL, (GdkFilterFunc) xkb_event_filter, xkb);
slaxemulator@6394 453 +
slaxemulator@6394 454 /* Free group and symbol name memory. */
slaxemulator@6394 455 int i;
slaxemulator@6394 456 for (i = 0; i < xkb->group_count; i++)
slaxemulator@6394 457 @@ -283,21 +319,11 @@ void xkb_mechanism_destructor(XkbPlugin * xkb)
slaxemulator@6394 458 }
slaxemulator@6394 459 }
slaxemulator@6394 460
slaxemulator@6394 461 - /* Close the display. */
slaxemulator@6394 462 - XCloseDisplay(xkb->dsp);
slaxemulator@6394 463 - xkb->dsp = NULL;
slaxemulator@6394 464 -
slaxemulator@6394 465 /* Destroy the hash table. */
slaxemulator@6394 466 g_hash_table_destroy(xkb->group_hash_table);
slaxemulator@6394 467 xkb->group_hash_table = NULL;
slaxemulator@6394 468 }
slaxemulator@6394 469
slaxemulator@6394 470 -/* Return the connection number for the display. */
slaxemulator@6394 471 -int xkb_get_connection_number(XkbPlugin * xkb)
slaxemulator@6394 472 -{
slaxemulator@6394 473 - return ConnectionNumber(xkb->dsp);
slaxemulator@6394 474 -}
slaxemulator@6394 475 -
slaxemulator@6394 476 /* Set the layout to the next layout. */
slaxemulator@6394 477 int xkb_change_group(XkbPlugin * xkb, int increment)
slaxemulator@6394 478 {
slaxemulator@6394 479 @@ -307,33 +333,13 @@ int xkb_change_group(XkbPlugin * xkb, int increment)
slaxemulator@6394 480 if (next_group >= xkb->group_count) next_group = 0;
slaxemulator@6394 481
slaxemulator@6394 482 /* Execute the change. */
slaxemulator@6394 483 - XkbLockGroup(xkb->dsp, xkb->device_id, next_group);
slaxemulator@6394 484 + XkbLockGroup(GDK_DISPLAY(), XkbUseCoreKbd, next_group);
slaxemulator@6394 485 refresh_group_xkb(xkb);
slaxemulator@6394 486 xkb_redraw(xkb);
slaxemulator@6394 487 xkb_enter_locale_by_process(xkb);
slaxemulator@6394 488 return 1;
slaxemulator@6394 489 }
slaxemulator@6394 490
slaxemulator@6394 491 -/* Callback when activity detected on the Xkb channel. */
slaxemulator@6394 492 -gboolean xkb_gio_callback(GIOChannel * source, GIOCondition condition, gpointer data)
slaxemulator@6394 493 -{
slaxemulator@6394 494 - XkbPlugin * xkb = (XkbPlugin *) data;
slaxemulator@6394 495 -
slaxemulator@6394 496 - XkbEvent evnt;
slaxemulator@6394 497 - XNextEvent(xkb->dsp, &evnt.core);
slaxemulator@6394 498 - if ((evnt.type == xkb->base_event_code)
slaxemulator@6394 499 - && (evnt.any.xkb_type == XkbStateNotify)
slaxemulator@6394 500 - && (evnt.state.group != xkb->current_group_xkb_no))
slaxemulator@6394 501 - {
slaxemulator@6394 502 - /* Switch to the new group and redraw the display. */
slaxemulator@6394 503 - xkb->current_group_xkb_no = evnt.state.group;
slaxemulator@6394 504 - refresh_group_xkb(xkb);
slaxemulator@6394 505 - xkb_redraw(xkb);
slaxemulator@6394 506 - xkb_enter_locale_by_process(xkb);
slaxemulator@6394 507 - }
slaxemulator@6394 508 - return TRUE;
slaxemulator@6394 509 -}
slaxemulator@6394 510 -
slaxemulator@6394 511 /* React to change of focus by switching to the application's layout or the default layout. */
slaxemulator@6394 512 void xkb_active_window_changed(XkbPlugin * xkb, gint pid)
slaxemulator@6394 513 {
slaxemulator@6394 514 @@ -345,7 +351,7 @@ void xkb_active_window_changed(XkbPlugin * xkb, gint pid)
slaxemulator@6394 515
slaxemulator@6394 516 if (new_group_xkb_no < xkb->group_count)
slaxemulator@6394 517 {
slaxemulator@6394 518 - XkbLockGroup(xkb->dsp, xkb->device_id, new_group_xkb_no);
slaxemulator@6394 519 + XkbLockGroup(GDK_DISPLAY(), XkbUseCoreKbd, new_group_xkb_no);
slaxemulator@6394 520 refresh_group_xkb(xkb);
slaxemulator@6394 521 }
slaxemulator@6394 522 }
slaxemulator@6394 523 diff --git a/src/plugins/xkb/xkb.h b/src/plugins/xkb/xkb.h
slaxemulator@6394 524 index 9265198..20c7ed3 100644
slaxemulator@6394 525 --- a/src/plugins/xkb/xkb.h
slaxemulator@6394 526 +++ b/src/plugins/xkb/xkb.h
slaxemulator@6394 527 @@ -49,10 +49,8 @@ typedef struct {
slaxemulator@6394 528 GtkWidget * per_app_default_layout_menu; /* Combo box of all available layouts */
slaxemulator@6394 529
slaxemulator@6394 530 /* Mechanism. */
slaxemulator@6394 531 - Display * dsp; /* Handle to X display */
slaxemulator@6394 532 int base_event_code; /* Result of initializing Xkb extension */
slaxemulator@6394 533 int base_error_code;
slaxemulator@6394 534 - int device_id; /* Keyboard device ID (always "core keyboard") */
slaxemulator@6394 535 int current_group_xkb_no; /* Current layout */
slaxemulator@6394 536 int group_count; /* Count of groups as returned by Xkb */
slaxemulator@6394 537 char * group_names[XkbNumKbdGroups]; /* Group names as returned by Xkb */
slaxemulator@6394 538 @@ -67,12 +65,11 @@ extern int xkb_get_current_group_xkb_no(XkbPlugin * xkb);
slaxemulator@6394 539 extern int xkb_get_group_count(XkbPlugin * xkb);
slaxemulator@6394 540 extern const char * xkb_get_symbol_name_by_res_no(XkbPlugin * xkb, int group_res_no);
slaxemulator@6394 541 extern const char * xkb_get_current_group_name(XkbPlugin * xkb);
slaxemulator@6394 542 -extern const char * xkb_get_current_group_name_lowercase(XkbPlugin * xkb);
slaxemulator@6394 543 +extern const char * xkb_get_current_symbol_name(XkbPlugin * xkb);
slaxemulator@6394 544 +extern const char * xkb_get_current_symbol_name_lowercase(XkbPlugin * xkb);
slaxemulator@6394 545 extern void xkb_mechanism_constructor(XkbPlugin * xkb);
slaxemulator@6394 546 extern void xkb_mechanism_destructor(XkbPlugin * xkb);
slaxemulator@6394 547 -extern int xkb_get_connection_number(XkbPlugin * xkb);
slaxemulator@6394 548 extern int xkb_change_group(XkbPlugin * xkb, int increment);
slaxemulator@6394 549 -extern gboolean xkb_gio_callback(GIOChannel * source, GIOCondition condition, gpointer data);
slaxemulator@6394 550 extern void xkb_active_window_changed(XkbPlugin * xkb, GPid pid);
slaxemulator@6394 551
slaxemulator@6394 552 #endif
slaxemulator@6394 553 --
slaxemulator@6394 554 1.7.0
slaxemulator@6394 555