Commit 9d73b89a authored by Daiki Ueno's avatar Daiki Ueno
Browse files

Use libXtst directly instead of via libfakekey.

parent 606f3354
......@@ -8,7 +8,7 @@ tools to implement desktop virtual keyboards.
** Dependencies
REQUIRED: GLib2, GTK, PangoCairo, libxklavier, libcroco
OPTIONAL: fakekey, at-spi2-core, Clutter, Clutter-Gtk, Python, Vala, gobject-introspection
OPTIONAL: libXtst, at-spi2-core, Clutter, Clutter-Gtk, Python, Vala, gobject-introspection
** Build from git repo
......
......@@ -104,21 +104,24 @@ PKG_CHECK_MODULES([LIBXKLAVIER], [libxklavier x11], ,
PKG_CHECK_MODULES([LIBCROCO], [libcroco-0.6], ,
[AC_MSG_ERROR([libcroco not found])])
dnl use libfakekey to generate key events
AC_MSG_CHECKING([whether you enable fakekey])
AC_ARG_ENABLE(fakekey,
AS_HELP_STRING([--enable-fakekey=no/yes],
[Enable fakekey default=yes]),,
enable_fakekey=yes)
if test x$enable_fakekey = xyes; then
PKG_CHECK_MODULES([FAKEKEY], [libfakekey], , enable_fakekey=no)
if test x$enable_fakekey = xyes; then
AC_DEFINE([HAVE_FAKEKEY], [1], [Define if fakekey is found])
dnl use XTest to generate key events
AC_MSG_CHECKING([whether you enable XTest])
AC_ARG_ENABLE(xtest,
AS_HELP_STRING([--enable-xtest=no/yes],
[Enable XTest default=yes]),,
enable_xtest=yes)
if test x$enable_xtest = xyes; then
PKG_CHECK_MODULES([XTEST], [xtst], , enable_xtest=no)
if test x$enable_xtest = xyes; then
AC_DEFINE([HAVE_XTEST], [1], [Define if XTest is found])
fi
fi
AM_CONDITIONAL(ENABLE_FAKEKEY, [test x$enable_fakekey = xyes])
AC_MSG_RESULT($enable_fakekey)
AM_CONDITIONAL(ENABLE_XTEST, [test x$enable_xtest = xyes])
AC_MSG_RESULT($enable_xtest)
focus_listeners=""
keystroke_listeners=""
focus_listeners=""
keystroke_listeners=""
......
......@@ -41,11 +41,11 @@ eekboard_LDADD = \
$(XKB_LIBS) \
$(LIBXKLAVIER_LIBS)
if ENABLE_FAKEKEY
if ENABLE_XTEST
eekboard_CFLAGS += \
$(FAKEKEY_CFLAGS)
$(XTEST_CFLAGS)
eekboard_LDADD += \
$(FAKEKEY_LIBS)
$(XTEST_LIBS)
endif
if ENABLE_ATSPI
......
......@@ -277,12 +277,12 @@ main (int argc, char **argv)
g_free (file);
}
#ifdef HAVE_FAKEKEY
if (!eekboard_client_enable_fakekey (client)) {
g_printerr ("Can't init fakekey\n");
#ifdef HAVE_XTEST
if (!eekboard_client_enable_xtest (client)) {
g_printerr ("Can't init xtest\n");
exit (1);
}
#endif /* HAVE_FAKEKEY */
#endif /* HAVE_XTEST */
loop = g_main_loop_new (NULL, FALSE);
if (!opt_focus) {
......
......@@ -28,9 +28,9 @@
#include <gdk/gdkx.h>
#ifdef HAVE_FAKEKEY
#include <fakekey/fakekey.h>
#endif /* HAVE_FAKEKEY */
#ifdef HAVE_XTEST
#include <X11/extensions/XTest.h>
#endif /* HAVE_XTEST */
#ifdef HAVE_IBUS
#include <ibus.h>
......@@ -42,6 +42,8 @@
#include "client.h"
#include "xklutil.h"
#include <string.h>
#define CSW 640
#define CSH 480
......@@ -86,9 +88,9 @@ struct _EekboardClient {
guint ibus_focus_message_filter;
#endif /* HAVE_IBUS */
#ifdef HAVE_FAKEKEY
FakeKey *fakekey;
#endif /* HAVE_FAKEKEY */
#ifdef HAVE_XTEST
KeyCode modifier_keycodes[8];
#endif /* HAVE_XTEST */
};
struct _EekboardClientClass {
......@@ -124,6 +126,10 @@ static gboolean set_xkl_keyboard (EekboardClient *client,
const gchar *model,
const gchar *layouts,
const gchar *options);
#ifdef HAVE_XTEST
static void update_modifier_keycodes
(EekboardClient *client);
#endif /* HAVE_XTEST */
static void
eekboard_client_set_property (GObject *object,
......@@ -204,9 +210,9 @@ eekboard_client_dispose (GObject *object)
}
#endif /* HAVE_IBUS */
#ifdef HAVE_FAKEKEY
eekboard_client_disable_fakekey (client);
#endif /* HAVE_FAKEKEY */
#ifdef HAVE_XTEST
eekboard_client_disable_xtest (client);
#endif /* HAVE_XTEST */
if (client->context) {
if (client->eekboard) {
......@@ -227,12 +233,6 @@ eekboard_client_dispose (GObject *object)
client->keyboard = NULL;
}
#ifdef HAVE_FAKEKEY
if (client->fakekey) {
client->fakekey = NULL;
}
#endif /* HAVE_FAKEKEY */
if (client->display) {
gdk_display_close (client->display);
client->display = NULL;
......@@ -302,9 +302,6 @@ eekboard_client_init (EekboardClient *client)
client->ibus_bus = NULL;
client->ibus_focus_message_filter = 0;
#endif /* HAVE_IBUS */
#ifdef HAVE_FAKEKEY
client->fakekey = NULL;
#endif /* HAVE_FAKEKEY */
}
gboolean
......@@ -683,8 +680,7 @@ on_xkl_config_changed (XklEngine *xklengine,
g_return_if_fail (retval);
#ifdef HAVE_FAKEKEY
if (client->fakekey)
fakekey_reload_keysyms (client->fakekey);
update_modifier_keycodes (client);
#endif /* HAVE_FAKEKEY */
}
......@@ -789,22 +785,59 @@ on_xkl_state_changed (XklEngine *xklengine,
}
}
#ifdef HAVE_FAKEKEY
G_INLINE_FUNC FakeKeyModifier
get_fakekey_modifiers (EekModifierType modifiers)
#ifdef HAVE_XTEST
static void
send_fake_modifier_key_event (EekboardClient *client,
EekModifierType modifiers,
gboolean is_pressed)
{
FakeKeyModifier retval = 0;
gint i;
if (modifiers & EEK_SHIFT_MASK)
retval |= FAKEKEYMOD_SHIFT;
if (modifiers & EEK_CONTROL_MASK)
retval |= FAKEKEYMOD_CONTROL;
if (modifiers & EEK_MOD1_MASK)
retval |= FAKEKEYMOD_ALT;
if (modifiers & EEK_META_MASK)
retval |= FAKEKEYMOD_META;
for (i = 0; i < G_N_ELEMENTS(client->modifier_keycodes); i++) {
if (modifiers & (1 << i)) {
guint keycode = client->modifier_keycodes[i];
return retval;
g_return_if_fail (keycode > 0);
XTestFakeKeyEvent (GDK_DISPLAY_XDISPLAY (client->display),
keycode,
is_pressed,
CurrentTime);
}
}
}
static void
send_fake_key_event (EekboardClient *client,
EekKey *key,
gboolean is_pressed)
{
EekSymbol *symbol;
EekModifierType modifiers;
guint xkeysym;
guint keycode;
symbol = eek_key_get_symbol_with_fallback (key, 0, 0);
/* Ignore special keys and modifiers */
if (!EEK_IS_KEYSYM(symbol) || eek_symbol_is_modifier (symbol))
return;
xkeysym = eek_keysym_get_xkeysym (EEK_KEYSYM(symbol));
g_return_if_fail (xkeysym > 0);
keycode = XKeysymToKeycode (GDK_DISPLAY_XDISPLAY (client->display),
xkeysym);
g_return_if_fail (keycode > 0);
modifiers = eek_keyboard_get_modifiers (client->keyboard);
send_fake_modifier_key_event (client, modifiers, is_pressed);
XTestFakeKeyEvent (GDK_DISPLAY_XDISPLAY (client->display),
keycode,
is_pressed,
CurrentTime);
XSync (GDK_DISPLAY_XDISPLAY (client->display), False);
}
static void
......@@ -813,35 +846,7 @@ on_key_pressed (EekKeyboard *keyboard,
gpointer user_data)
{
EekboardClient *client = user_data;
EekSymbol *symbol;
g_assert (client->fakekey);
symbol = eek_key_get_symbol_with_fallback (key, 0, 0);
if (EEK_IS_KEYSYM(symbol) && !eek_symbol_is_modifier (symbol)) {
guint xkeysym;
guint keycode;
EekModifierType modifiers;
FakeKeyModifier fakekey_modifiers;
xkeysym = eek_keysym_get_xkeysym (EEK_KEYSYM(symbol));
g_return_if_fail (xkeysym > 0);
keycode = XKeysymToKeycode (GDK_DISPLAY_XDISPLAY (client->display),
xkeysym);
g_return_if_fail (keycode > 0);
modifiers = eek_keyboard_get_modifiers (client->keyboard);
fakekey_modifiers = get_fakekey_modifiers (modifiers);
fakekey_send_keyevent (client->fakekey,
keycode,
TRUE,
fakekey_modifiers);
fakekey_send_keyevent (client->fakekey,
keycode,
FALSE,
fakekey_modifiers);
}
send_fake_key_event (client, key, TRUE);
}
static void
......@@ -850,23 +855,37 @@ on_key_released (EekKeyboard *keyboard,
gpointer user_data)
{
EekboardClient *client = user_data;
send_fake_key_event (client, key, FALSE);
}
g_assert (client->fakekey);
fakekey_release (client->fakekey);
static void
update_modifier_keycodes (EekboardClient *client)
{
XModifierKeymap *mods;
gint i, j;
mods = XGetModifierMapping (GDK_DISPLAY_XDISPLAY (client->display));
for (i = 0; i < 8; i++) {
client->modifier_keycodes[i] = 0;
for (j = 0; j < mods->max_keypermod; j++) {
KeyCode keycode = mods->modifiermap[mods->max_keypermod * i + j];
if (keycode != 0) {
client->modifier_keycodes[i] = keycode;
break;
}
}
}
}
gboolean
eekboard_client_enable_fakekey (EekboardClient *client)
eekboard_client_enable_xtest (EekboardClient *client)
{
if (!client->display) {
client->display = gdk_display_get_default ();
}
g_assert (client->display);
if (!client->fakekey) {
client->fakekey = fakekey_init (GDK_DISPLAY_XDISPLAY (client->display));
}
g_assert (client->fakekey);
update_modifier_keycodes (client);
client->key_pressed_handler =
g_signal_connect (client->keyboard, "key-pressed",
......@@ -879,11 +898,8 @@ eekboard_client_enable_fakekey (EekboardClient *client)
}
void
eekboard_client_disable_fakekey (EekboardClient *client)
eekboard_client_disable_xtest (EekboardClient *client)
{
if (client->fakekey)
fakekey_release (client->fakekey);
if (g_signal_handler_is_connected (client->keyboard,
client->key_pressed_handler))
g_signal_handler_disconnect (client->keyboard,
......@@ -922,4 +938,4 @@ eekboard_client_load_keyboard_from_file (EekboardClient *client,
return retval;
}
#endif /* HAVE_FAKEKEY */
#endif /* HAVE_XTEST */
......@@ -31,36 +31,36 @@ G_BEGIN_DECLS
typedef struct _EekboardClient EekboardClient;
EekboardClient * eekboard_client_new (GDBusConnection *connection);
EekboardClient * eekboard_client_new (GDBusConnection *connection);
gboolean eekboard_client_load_keyboard_from_file
(EekboardClient *client,
const gchar *file);
gboolean eekboard_client_set_xkl_config (EekboardClient *client,
const gchar *model,
const gchar *layouts,
const gchar *options);
(EekboardClient *client,
const gchar *file);
gboolean eekboard_client_set_xkl_config (EekboardClient *client,
const gchar *model,
const gchar *layouts,
const gchar *options);
gboolean eekboard_client_enable_xkl (EekboardClient *client);
void eekboard_client_disable_xkl (EekboardClient *client);
gboolean eekboard_client_enable_xkl (EekboardClient *client);
void eekboard_client_disable_xkl (EekboardClient *client);
gboolean eekboard_client_enable_atspi_focus
(EekboardClient *client);
(EekboardClient *client);
void eekboard_client_disable_atspi_focus
(EekboardClient *client);
(EekboardClient *client);
gboolean eekboard_client_enable_atspi_keystroke
(EekboardClient *client);
(EekboardClient *client);
void eekboard_client_disable_atspi_keystroke
(EekboardClient *client);
(EekboardClient *client);
gboolean eekboard_client_enable_fakekey (EekboardClient *client);
void eekboard_client_disable_fakekey (EekboardClient *client);
gboolean eekboard_client_enable_xtest (EekboardClient *client);
void eekboard_client_disable_xtest (EekboardClient *client);
gboolean eekboard_client_enable_ibus_focus
(EekboardClient *client);
(EekboardClient *client);
void eekboard_client_disable_ibus_focus
(EekboardClient *client);
(EekboardClient *client);
G_END_DECLS
#endif /* EEKBOARD_CLIENT_H */
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment