From c8cc03f8a7b13db01a71c4a597c05a7b94ba664c Mon Sep 17 00:00:00 2001 From: Emmanuele Bassi Date: Tue, 18 Jan 2011 13:08:09 +0000 Subject: [PATCH] event/x11: Epic clean up Event translation is now done where it belongs: we don't need a massive switch in a file with direct access to private structure members. So long, event_translate(); and thanks for all the fish. --- clutter/x11/clutter-event-x11.c | 869 -------------------------------- 1 file changed, 869 deletions(-) diff --git a/clutter/x11/clutter-event-x11.c b/clutter/x11/clutter-event-x11.c index b5bd31306..14653d6df 100644 --- a/clutter/x11/clutter-event-x11.c +++ b/clutter/x11/clutter-event-x11.c @@ -24,45 +24,21 @@ * Emmanuele Bassi */ -#ifdef HAVE_CONFIG_H #include "config.h" -#endif -#include "clutter-stage-x11.h" #include "clutter-backend-x11.h" -#include "clutter-keymap-x11.h" #include "clutter-x11.h" -#include "clutter-actor-private.h" #include "clutter-backend-private.h" #include "clutter-debug.h" -#include "clutter-device-manager-private.h" #include "clutter-event.h" #include "clutter-main.h" -#include "clutter-paint-volume-private.h" #include "clutter-private.h" -#include "clutter-stage-private.h" - -#include "cogl/cogl-internal.h" #include #include -#ifdef HAVE_XFIXES -#include -#endif - -#include - -#ifdef HAVE_XINPUT -#include -#endif - -#ifdef HAVE_XKB -#include -#endif - #if 0 /* XEMBED protocol support for toolkit embedding */ #define XEMBED_MAPPED (1 << 0) @@ -251,847 +227,6 @@ _clutter_backend_x11_events_uninit (ClutterBackend *backend) } } -#if 0 -static void -update_last_event_time (ClutterBackendX11 *backend_x11, - XEvent *xevent) -{ - Time current_time = CurrentTime; - Time last_time = backend_x11->last_event_time; - - switch (xevent->type) - { - case KeyPress: - case KeyRelease: - current_time = xevent->xkey.time; - break; - - case ButtonPress: - case ButtonRelease: - current_time = xevent->xbutton.time; - break; - - case MotionNotify: - current_time = xevent->xmotion.time; - break; - - case EnterNotify: - case LeaveNotify: - current_time = xevent->xcrossing.time; - break; - - case PropertyNotify: - current_time = xevent->xproperty.time; - break; - - default: - break; - } - - /* only change the current event time if it's after the previous event - * time, or if it is at least 30 seconds earlier - in case the system - * clock was changed - */ - if ((current_time != CurrentTime) && - (current_time > last_time || (last_time - current_time > (30 * 1000)))) - backend_x11->last_event_time = current_time; -} - -static void -set_user_time (ClutterBackendX11 *backend_x11, - Window *xwindow, - long timestamp) -{ - if (timestamp != CLUTTER_CURRENT_TIME) - { - XChangeProperty (backend_x11->xdpy, *xwindow, - backend_x11->atom_NET_WM_USER_TIME, - XA_CARDINAL, 32, PropModeReplace, - (unsigned char *) ×tamp, 1); - } -} - -#ifdef HAVE_XINPUT -static void -convert_xdevicekey_to_xkey (XDeviceKeyEvent *xkev, - XEvent *xevent) -{ - xevent->xany.type = xevent->xkey.type = xkev->type; - xevent->xkey.serial = xkev->serial; - xevent->xkey.display = xkev->display; - xevent->xkey.window = xkev->window; - xevent->xkey.root = xkev->root; - xevent->xkey.subwindow = xkev->subwindow; - xevent->xkey.time = xkev->time; - xevent->xkey.x = xkev->x; - xevent->xkey.y = xkev->y; - xevent->xkey.x_root = xkev->x_root; - xevent->xkey.y_root = xkev->y_root; - xevent->xkey.state = xkev->state; - xevent->xkey.keycode = xkev->keycode; - xevent->xkey.same_screen = xkev->same_screen; -} -#endif /* HAVE_XINPUT */ - -static inline void -translate_key_event (ClutterBackendX11 *backend_x11, - ClutterEvent *event, - XEvent *xevent) -{ - ClutterEventX11 *event_x11; - char buffer[256 + 1]; - int n; - - /* KeyEvents have platform specific data associated to them */ - event_x11 = _clutter_event_x11_new (); - _clutter_event_set_platform_data (event, event_x11); - - event->key.time = xevent->xkey.time; - event->key.modifier_state = (ClutterModifierType) xevent->xkey.state; - event->key.hardware_keycode = xevent->xkey.keycode; - - /* keyval is the key ignoring all modifiers ('1' vs. '!') */ - event->key.keyval = - _clutter_keymap_x11_translate_key_state (backend_x11->keymap, - event->key.hardware_keycode, - event->key.modifier_state, - NULL); - - event_x11->key_group = - _clutter_keymap_x11_get_key_group (backend_x11->keymap, - event->key.modifier_state); - event_x11->key_is_modifier = - _clutter_keymap_x11_get_is_modifier (backend_x11->keymap, - event->key.hardware_keycode); - event_x11->num_lock_set = - _clutter_keymap_x11_get_num_lock_state (backend_x11->keymap); - event_x11->caps_lock_set = - _clutter_keymap_x11_get_caps_lock_state (backend_x11->keymap); - - /* unicode_value is the printable representation */ - n = XLookupString (&xevent->xkey, buffer, sizeof (buffer) - 1, NULL, NULL); - - if (n != NoSymbol) - { - event->key.unicode_value = g_utf8_get_char_validated (buffer, n); - if ((event->key.unicode_value != -1) && - (event->key.unicode_value != -2)) - goto out; - } - else - event->key.unicode_value = (gunichar)'\0'; - -out: - return; -} - -static gboolean -handle_wm_protocols_event (ClutterBackendX11 *backend_x11, - Window window, - XEvent *xevent) -{ - Atom atom = (Atom) xevent->xclient.data.l[0]; - - if (atom == backend_x11->atom_WM_DELETE_WINDOW && - xevent->xany.window == window) - { - /* the WM_DELETE_WINDOW is a request: we do not destroy - * the window right away, as it might contain vital data; - * we relay the event to the application and we let it - * handle the request - */ - CLUTTER_NOTE (EVENT, "delete window:\txid: %ld", - xevent->xclient.window); - - set_user_time (backend_x11, - &window, - xevent->xclient.data.l[1]); - - return TRUE; - } - else if (atom == backend_x11->atom_NET_WM_PING && - xevent->xany.window == window) - { - XClientMessageEvent xclient = xevent->xclient; - - xclient.window = backend_x11->xwin_root; - XSendEvent (backend_x11->xdpy, xclient.window, - False, - SubstructureRedirectMask | SubstructureNotifyMask, - (XEvent *) &xclient); - return FALSE; - } - - /* do not send any of the WM_PROTOCOLS events to the queue */ - return FALSE; -} - -static gboolean -clipped_redraws_cool_off_cb (void *data) -{ - ClutterStageX11 *stage_x11 = data; - - stage_x11->clipped_redraws_cool_off = 0; - - return FALSE; -} - -static gboolean -event_translate (ClutterBackend *backend, - ClutterEvent *event, - XEvent *xevent) -{ - ClutterBackendX11 *backend_x11; - ClutterStageX11 *stage_x11; - ClutterStage *stage; - ClutterStageWindow *impl; - ClutterDeviceManager *manager; - gboolean res, not_yet_handled = FALSE; - Window xwindow, stage_xwindow; - ClutterInputDevice *device; - - backend_x11 = CLUTTER_BACKEND_X11 (backend); - - xwindow = xevent->xany.window; - - if (backend_x11->event_filters) - { - GSList *node; - - node = backend_x11->event_filters; - - while (node) - { - ClutterX11EventFilter *filter = node->data; - - switch (filter->func (xevent, event, filter->data)) - { - case CLUTTER_X11_FILTER_CONTINUE: - break; - case CLUTTER_X11_FILTER_TRANSLATE: - return TRUE; - case CLUTTER_X11_FILTER_REMOVE: - return FALSE; - default: - break; - } - - node = node->next; - } - } - - /* Pass the event through Cogl */ - if (_cogl_xlib_handle_event (xevent) == COGL_XLIB_FILTER_REMOVE) - return FALSE; - - /* Do further processing only on events for the stage window (the x11 - * filters might be getting events for other windows, so do not mess - * them about. - */ - stage = clutter_x11_get_stage_from_window (xwindow); - if (stage == NULL) - return FALSE; - - impl = _clutter_stage_get_window (stage); - stage_x11 = CLUTTER_STAGE_X11 (impl); - stage_xwindow = xwindow; /* clutter_x11_get_stage_window (stage); */ - - event->any.stage = stage; - - res = TRUE; - - update_last_event_time (backend_x11, xevent); - - manager = clutter_device_manager_get_default (); - - switch (xevent->type) - { - case ConfigureNotify: - if (!stage_x11->is_foreign_xwin) - { - CLUTTER_NOTE (BACKEND, "%s: ConfigureNotify[%x] (%d, %d)", - G_STRLOC, - (unsigned int) stage_x11->xwin, - xevent->xconfigure.width, - xevent->xconfigure.height); - - /* Queue a relayout - we want glViewport to be called - * with the correct values, and this is done in ClutterStage - * via _cogl_onscreen_clutter_backend_set_size (). - * - * We queue a relayout, because if this ConfigureNotify is - * in response to a size we set in the application, the - * set_size above is essentially a null-op. - * - * Make sure we do this only when the size has changed, - * otherwise we end up relayouting on window moves. - */ - if ((stage_x11->state & CLUTTER_STAGE_STATE_FULLSCREEN) || - (stage_x11->xwin_width != xevent->xconfigure.width) || - (stage_x11->xwin_height != xevent->xconfigure.height)) - { - clutter_actor_queue_relayout (CLUTTER_ACTOR (stage)); - } - - /* If we're fullscreened, we want these variables to - * represent the size of the window before it was set - * to fullscreen. - */ - if (!(stage_x11->state & CLUTTER_STAGE_STATE_FULLSCREEN)) - { - stage_x11->xwin_width = xevent->xconfigure.width; - stage_x11->xwin_height = xevent->xconfigure.height; - } - - clutter_actor_set_size (CLUTTER_ACTOR (stage), - xevent->xconfigure.width, - xevent->xconfigure.height); - - /* XXX: This is a workaround for a race condition when - * resizing windows while there are in-flight - * glXCopySubBuffer blits happening. - * - * The problem stems from the fact that rectangles for the - * blits are described relative to the bottom left of the - * window and because we can't guarantee control over the X - * window gravity used when resizing so the gravity is - * typically NorthWest not SouthWest. - * - * This means if you grow a window vertically the server - * will make sure to place the old contents of the window - * at the top-left/north-west of your new larger window, but - * that may happen asynchronous to GLX preparing to do a - * blit specified relative to the bottom-left/south-west of - * the window (based on the old smaller window geometry). - * - * When the GLX issued blit finally happens relative to the - * new bottom of your window, the destination will have - * shifted relative to the top-left where all the pixels you - * care about are so it will result in a nasty artefact - * making resizing look very ugly! - * - * We can't currently fix this completely, in-part because - * the window manager tends to trample any gravity we might - * set. This workaround instead simply disables blits for a - * while if we are notified of any resizes happening so if - * the user is resizing a window via the window manager then - * they may see an artefact for one frame but then we will - * fallback to redrawing the full stage until the cooling - * off period is over. - */ - if (stage_x11->clipped_redraws_cool_off) - g_source_remove (stage_x11->clipped_redraws_cool_off); - stage_x11->clipped_redraws_cool_off = - g_timeout_add_seconds (1, clipped_redraws_cool_off_cb, stage_x11); - - CLUTTER_UNSET_PRIVATE_FLAGS (stage_x11->wrapper, - CLUTTER_IN_RESIZE); - - /* the resize process is complete, so we can ask the stage - * to set up the GL viewport with the new size - */ - clutter_stage_ensure_viewport (stage); - } - res = FALSE; - break; - - case PropertyNotify: - if (xevent->xproperty.atom == backend_x11->atom_NET_WM_STATE && - xevent->xproperty.window == stage_xwindow && - !stage_x11->is_foreign_xwin) - { - Atom type; - gint format; - gulong n_items, bytes_after; - guchar *data = NULL; - gboolean fullscreen_set = FALSE; - - clutter_x11_trap_x_errors (); - XGetWindowProperty (backend_x11->xdpy, stage_xwindow, - backend_x11->atom_NET_WM_STATE, - 0, G_MAXLONG, - False, XA_ATOM, - &type, &format, &n_items, - &bytes_after, &data); - clutter_x11_untrap_x_errors (); - - if (type != None && data != NULL) - { - Atom *atoms = (Atom *) data; - gulong i; - gboolean is_fullscreen = FALSE; - - for (i = 0; i < n_items; i++) - { - if (atoms[i] == backend_x11->atom_NET_WM_STATE_FULLSCREEN) - fullscreen_set = TRUE; - } - - is_fullscreen = - (stage_x11->state & CLUTTER_STAGE_STATE_FULLSCREEN); - - if (fullscreen_set != is_fullscreen) - { - if (fullscreen_set) - stage_x11->state |= CLUTTER_STAGE_STATE_FULLSCREEN; - else - stage_x11->state &= ~CLUTTER_STAGE_STATE_FULLSCREEN; - - stage_x11->fullscreening = fullscreen_set; - - event->type = CLUTTER_STAGE_STATE; - event->stage_state.changed_mask = - CLUTTER_STAGE_STATE_FULLSCREEN; - event->stage_state.new_state = stage_x11->state; - } - else - res = FALSE; - - XFree (data); - } - else - res = FALSE; - } - else - res = FALSE; - break; - - case MapNotify: - res = FALSE; - break; - - case UnmapNotify: - res = FALSE; - break; - - case FocusIn: - if (!(stage_x11->state & CLUTTER_STAGE_STATE_ACTIVATED)) - { - /* TODO: check xevent->xfocus.detail ? */ - stage_x11->state |= CLUTTER_STAGE_STATE_ACTIVATED; - - event->type = CLUTTER_STAGE_STATE; - event->stage_state.changed_mask = CLUTTER_STAGE_STATE_ACTIVATED; - event->stage_state.new_state = stage_x11->state; - } - else - res = FALSE; - break; - - case FocusOut: - if (stage_x11->state & CLUTTER_STAGE_STATE_ACTIVATED) - { - stage_x11->state &= ~CLUTTER_STAGE_STATE_ACTIVATED; - - event->type = CLUTTER_STAGE_STATE; - event->stage_state.changed_mask = CLUTTER_STAGE_STATE_ACTIVATED; - event->stage_state.new_state = stage_x11->state; - } - else - res = FALSE; - break; - - case Expose: - { - XExposeEvent *expose = (XExposeEvent *)xevent; - ClutterPaintVolume clip; - ClutterVertex origin; - - CLUTTER_NOTE (MULTISTAGE, "expose for stage: %p, redrawing", stage); - CLUTTER_NOTE (MULTISTAGE, - "expose for stage: %p, " - "redrawing (x=%d, y=%d, width=%d, height=%d)", - stage, - expose->x, - expose->y, - expose->width, - expose->height); - - origin.x = expose->x; - origin.y = expose->y; - origin.z = 0; - - _clutter_paint_volume_init_static (CLUTTER_ACTOR (stage), &clip); - - clutter_paint_volume_set_origin (&clip, &origin); - clutter_paint_volume_set_width (&clip, expose->width); - clutter_paint_volume_set_height (&clip, expose->height); - - _clutter_actor_queue_redraw_with_clip (CLUTTER_ACTOR (stage), 0, &clip); - - clutter_paint_volume_free (&clip); - - res = FALSE; - } - break; - case DestroyNotify: - CLUTTER_NOTE (EVENT, "destroy notify:\txid: %ld", - xevent->xdestroywindow.window); - if (xevent->xdestroywindow.window == stage_xwindow && - !stage_x11->is_foreign_xwin) - event->type = event->any.type = CLUTTER_DESTROY_NOTIFY; - else - res = FALSE; - break; - - case ClientMessage: - CLUTTER_NOTE (EVENT, "client message"); - - event->type = event->any.type = CLUTTER_CLIENT_MESSAGE; - - if (xevent->xclient.message_type == backend_x11->atom_XEMBED) - res = handle_xembed_event (backend_x11, xevent); - else if (xevent->xclient.message_type == backend_x11->atom_WM_PROTOCOLS) - { - res = handle_wm_protocols_event (backend_x11, stage_xwindow, xevent); - event->type = event->any.type = CLUTTER_DELETE; - } - break; - - case KeyPress: - event->key.type = event->type = CLUTTER_KEY_PRESS; - event->key.device = - clutter_device_manager_get_core_device (manager, - CLUTTER_KEYBOARD_DEVICE); - - translate_key_event (backend_x11, event, xevent); - - set_user_time (backend_x11, &xwindow, xevent->xkey.time); - break; - - case KeyRelease: - /* old-style X11 terminals require that even modern X11 send - * KeyPress/KeyRelease pairs when auto-repeating. for this - * reason modern(-ish) API like XKB has a way to detect - * auto-repeat and do a single KeyRelease at the end of a - * KeyPress sequence. - * - * this check emulates XKB's detectable auto-repeat; we peek - * the next event and check if it's a KeyPress for the same key - * and timestamp - and then ignore it if it matches the - * KeyRelease - * - * if we have XKB, and autorepeat is enabled, then this becomes - * a no-op - */ - if (!backend_x11->have_xkb_autorepeat && XPending (xevent->xkey.display)) - { - XEvent next_event; - - XPeekEvent (xevent->xkey.display, &next_event); - - if (next_event.type == KeyPress && - next_event.xkey.keycode == xevent->xkey.keycode && - next_event.xkey.time == xevent->xkey.time) - { - res = FALSE; - break; - } - } - - event->key.type = event->type = CLUTTER_KEY_RELEASE; - event->key.device = - clutter_device_manager_get_core_device (manager, - CLUTTER_KEYBOARD_DEVICE); - - translate_key_event (backend_x11, event, xevent); - break; - - default: - /* ignore every other event */ - not_yet_handled = TRUE; - break; - } - - /* Input device event handling.. */ - if (not_yet_handled) - { - device = clutter_device_manager_get_core_device (manager, - CLUTTER_POINTER_DEVICE); - - /* Regular X event */ - switch (xevent->type) - { - case ButtonPress: - switch (xevent->xbutton.button) - { - case 4: /* up */ - case 5: /* down */ - case 6: /* left */ - case 7: /* right */ - event->scroll.type = event->type = CLUTTER_SCROLL; - - if (xevent->xbutton.button == 4) - event->scroll.direction = CLUTTER_SCROLL_UP; - else if (xevent->xbutton.button == 5) - event->scroll.direction = CLUTTER_SCROLL_DOWN; - else if (xevent->xbutton.button == 6) - event->scroll.direction = CLUTTER_SCROLL_LEFT; - else - event->scroll.direction = CLUTTER_SCROLL_RIGHT; - - event->scroll.time = xevent->xbutton.time; - event->scroll.x = xevent->xbutton.x; - event->scroll.y = xevent->xbutton.y; - event->scroll.modifier_state = xevent->xbutton.state; - event->scroll.device = device; - break; - - default: - event->button.type = event->type = CLUTTER_BUTTON_PRESS; - event->button.time = xevent->xbutton.time; - event->button.x = xevent->xbutton.x; - event->button.y = xevent->xbutton.y; - event->button.modifier_state = xevent->xbutton.state; - event->button.button = xevent->xbutton.button; - event->button.device = device; - break; - } - - set_user_time (backend_x11, &xwindow, event->button.time); - - res = TRUE; - break; - - case ButtonRelease: - /* scroll events don't have a corresponding release */ - if (xevent->xbutton.button == 4 || - xevent->xbutton.button == 5 || - xevent->xbutton.button == 6 || - xevent->xbutton.button == 7) - { - res = FALSE; - goto out; - } - - event->button.type = event->type = CLUTTER_BUTTON_RELEASE; - event->button.time = xevent->xbutton.time; - event->button.x = xevent->xbutton.x; - event->button.y = xevent->xbutton.y; - event->button.modifier_state = xevent->xbutton.state; - event->button.button = xevent->xbutton.button; - event->button.device = device; - - res = TRUE; - break; - - case MotionNotify: - event->motion.type = event->type = CLUTTER_MOTION; - event->motion.time = xevent->xmotion.time; - event->motion.x = xevent->xmotion.x; - event->motion.y = xevent->xmotion.y; - event->motion.modifier_state = xevent->xmotion.state; - event->motion.device = device; - - res = TRUE; - break; - - case EnterNotify: - /* we know that we are entering the stage here */ - _clutter_input_device_set_stage (device, stage); - CLUTTER_NOTE (EVENT, "Entering the stage"); - - /* Convert enter notifies to motion events because X - doesn't emit the corresponding motion notify */ - event->motion.type = event->type = CLUTTER_MOTION; - event->motion.time = xevent->xcrossing.time; - event->motion.x = xevent->xcrossing.x; - event->motion.y = xevent->xcrossing.y; - event->motion.modifier_state = xevent->xcrossing.state; - event->motion.source = CLUTTER_ACTOR (stage); - event->motion.device = device; - - res = TRUE; - break; - - case LeaveNotify: - if (device->stage == NULL) - { - CLUTTER_NOTE (EVENT, - "Discarding LeaveNotify for ButtonRelease " - "event off-stage"); - res = FALSE; - goto out; - } - - /* we know that we are leaving the stage here */ - _clutter_input_device_set_stage (device, NULL); - CLUTTER_NOTE (EVENT, "Leaving the stage (time:%u)", - event->crossing.time); - - event->crossing.type = event->type = CLUTTER_LEAVE; - event->crossing.time = xevent->xcrossing.time; - event->crossing.x = xevent->xcrossing.x; - event->crossing.y = xevent->xcrossing.y; - event->crossing.source = CLUTTER_ACTOR (stage); - event->crossing.device = device; - res = TRUE; - break; - - default: - res = FALSE; - break; - } - } - - /* XInput fun...*/ - if (!res && clutter_x11_has_xinput ()) - { -#ifdef HAVE_XINPUT - int *ev_types = backend_x11->event_types; - int button_press, button_release; - int key_press, key_release; - int motion_notify; - - button_press = ev_types[CLUTTER_X11_XINPUT_BUTTON_PRESS_EVENT]; - button_release = ev_types[CLUTTER_X11_XINPUT_BUTTON_RELEASE_EVENT]; - motion_notify = ev_types[CLUTTER_X11_XINPUT_MOTION_NOTIFY_EVENT]; - key_press = ev_types[CLUTTER_X11_XINPUT_KEY_PRESS_EVENT]; - key_release = ev_types[CLUTTER_X11_XINPUT_KEY_RELEASE_EVENT]; - - CLUTTER_NOTE (EVENT, "XInput event type: %d", xevent->type); - - if (xevent->type == button_press) - { - XDeviceButtonEvent *xbev = (XDeviceButtonEvent *) xevent; - - device = _clutter_x11_get_device_for_xid (xbev->deviceid); - _clutter_input_device_set_stage (device, stage); - - CLUTTER_NOTE (EVENT, - "XI ButtonPress for %li ('%s') at %d, %d", - xbev->deviceid, - device->device_name, - xbev->x, - xbev->y); - - switch (xbev->button) - { - case 4: - case 5: - case 6: - case 7: - event->scroll.type = event->type = CLUTTER_SCROLL; - - if (xbev->button == 4) - event->scroll.direction = CLUTTER_SCROLL_UP; - else if (xbev->button == 5) - event->scroll.direction = CLUTTER_SCROLL_DOWN; - else if (xbev->button == 6) - event->scroll.direction = CLUTTER_SCROLL_LEFT; - else - event->scroll.direction = CLUTTER_SCROLL_RIGHT; - - event->scroll.time = xbev->time; - event->scroll.x = xbev->x; - event->scroll.y = xbev->y; - event->scroll.modifier_state = xbev->state; - event->scroll.device = device; - break; - - default: - event->button.type = event->type = CLUTTER_BUTTON_PRESS; - event->button.time = xbev->time; - event->button.x = xbev->x; - event->button.y = xbev->y; - event->button.modifier_state = xbev->state; - event->button.button = xbev->button; - event->button.device = device; - break; - } - - set_user_time (backend_x11, &xwindow, xbev->time); - - res = TRUE; - } - else if (xevent->type == button_release) - { - XDeviceButtonEvent *xbev = (XDeviceButtonEvent *)xevent; - - device = _clutter_x11_get_device_for_xid (xbev->deviceid); - _clutter_input_device_set_stage (device, stage); - - CLUTTER_NOTE (EVENT, "XI ButtonRelease for %li ('%s') at %d, %d", - xbev->deviceid, - device->device_name, - xbev->x, - xbev->y); - - /* scroll events don't have a corresponding release */ - if (xbev->button == 4 || - xbev->button == 5 || - xbev->button == 6 || - xbev->button == 7) - { - res = FALSE; - goto out; - } - - event->button.type = event->type = CLUTTER_BUTTON_RELEASE; - event->button.time = xbev->time; - event->button.x = xbev->x; - event->button.y = xbev->y; - event->button.modifier_state = xbev->state; - event->button.button = xbev->button; - event->button.device = device; - - res = TRUE; - } - else if (xevent->type == motion_notify) - { - XDeviceMotionEvent *xmev = (XDeviceMotionEvent *)xevent; - - device = _clutter_x11_get_device_for_xid (xmev->deviceid); - _clutter_input_device_set_stage (device, stage); - - CLUTTER_NOTE (EVENT, "XI Motion for %li ('%s') at %d, %d", - xmev->deviceid, - device->device_name, - xmev->x, - xmev->y); - - event->motion.type = event->type = CLUTTER_MOTION; - event->motion.time = xmev->time; - event->motion.x = xmev->x; - event->motion.y = xmev->y; - event->motion.modifier_state = xmev->state; - event->motion.device = device; - - res = TRUE; - } - else if (xevent->type == key_press || xevent->type == key_release) - { - /* the XInput 1.x handling of key presses/releases is broken: - * it makes key repeat, key presses and releases outside the - * window not generate events even when the window has focus - */ - XDeviceKeyEvent *xkev = (XDeviceKeyEvent *) xevent; - XEvent xevent_converted; - - convert_xdevicekey_to_xkey (xkev, &xevent_converted); - - event->key.type = event->type = (xevent->type == key_press) - ? CLUTTER_KEY_PRESS - : CLUTTER_KEY_RELEASE; - - translate_key_event (backend_x11, event, &xevent_converted); - - if (xevent->type == key_press) - set_user_time (backend_x11, &xwindow, xkev->time); - } - else -#endif /* HAVE_XINPUT */ - { - CLUTTER_NOTE (EVENT, "Uknown Event"); - res = FALSE; - } - } - -out: - return res; -} -#endif - static void events_queue (ClutterBackend *backend) { @@ -1137,8 +272,6 @@ events_queue (ClutterBackend *backend) ClutterX11FilterReturn clutter_x11_handle_event (XEvent *xevent) { - ClutterBackendX11Class *backend_x11_class; - ClutterMainContext *clutter_context; ClutterX11FilterReturn result; ClutterBackend *backend; ClutterEvent *event; @@ -1157,9 +290,7 @@ clutter_x11_handle_event (XEvent *xevent) clutter_threads_enter (); - clutter_context = _clutter_context_get_default (); backend = clutter_get_default_backend (); - backend_x11_class = CLUTTER_BACKEND_X11_GET_CLASS (backend); event = clutter_event_new (CLUTTER_NOTHING);