summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Reveman <davidr@novell.com>2008-10-13 11:53:21 -0400
committerDavid Reveman <davidr@novell.com>2008-10-30 03:37:51 -0400
commit4c5cb82302beda6c76a23c7d2bfc71e4ad8bca91 (patch)
tree9c32b5a66626b6e5c54b3e8013c6684255882de7
parentf30d46a9b95430d1938c8842373eb9eb64c0d025 (diff)
Add more appropriate system for dealing with pointer motion when
forwarding XDND.
-rw-r--r--hw/dmx/dmxdnd.c61
-rw-r--r--hw/dmx/dmxgrab.c38
-rw-r--r--hw/dmx/dmxgrab.h4
-rw-r--r--hw/dmx/dmxinput.c84
-rw-r--r--hw/dmx/dmxinput.h9
5 files changed, 148 insertions, 48 deletions
diff --git a/hw/dmx/dmxdnd.c b/hw/dmx/dmxdnd.c
index dee70b934..6927e0435 100644
--- a/hw/dmx/dmxdnd.c
+++ b/hw/dmx/dmxdnd.c
@@ -81,6 +81,16 @@ dmxDnDUpdatePosition (DMXScreenInfo *dmxScreen,
event.u.clientMessage.u.l.longs0 = dmxScreens[0].selectionProxyWid[0];
+ if (pWin)
+ {
+ if (!dmxFakeMotion (&dmxScreen->input, x, y))
+ pWin = NullWindow;
+ }
+ else
+ {
+ dmxEndFakeMotion (&dmxScreen->input);
+ }
+
while (pWin)
{
if ((pWin->mapped) &&
@@ -246,50 +256,6 @@ dmxDnDUpdatePosition (DMXScreenInfo *dmxScreen,
}
}
-/* version 5 of the XDND protocol doesn't provide information about
- the pointer device that is used so we'll simply update all devices */
-static void
-dmxDnDUpdatePointerDevice (ScreenPtr pScreen,
- int x,
- int y)
-{
- DMXInputInfo *dmxInput = &dmxScreens[pScreen->myNum].input;
- int i;
-
- for (i = 0; i < dmxInput->numDevs; i++)
- {
- DeviceIntPtr pDevice = dmxInput->devs[i];
- dmxDevicePrivPtr pDevPriv = DMX_GET_DEVICE_PRIV (pDevice);
- xcb_generic_event_t xevent;
-
- /* extension device */
- if (pDevPriv->deviceId >= 0)
- {
- xcb_input_device_motion_notify_event_t *xmotion =
- (xcb_input_device_motion_notify_event_t *) &xevent;
-
- xmotion->response_type = dmxInput->eventBase +
- XCB_INPUT_DEVICE_MOTION_NOTIFY;
- xmotion->device_id = pDevPriv->deviceId;
-
- xmotion->event_x = x;
- xmotion->event_y = y;
- }
- else
- {
- xcb_motion_notify_event_t *xmotion =
- (xcb_motion_notify_event_t *) &xevent;
-
- xmotion->response_type = XCB_MOTION_NOTIFY;
-
- xmotion->event_x = x;
- xmotion->event_y = y;
- }
-
- (*pDevPriv->EventCheck) (pDevice, &xevent);
- }
-}
-
static void
dmxDnDTranslateCoordinatesReply (ScreenPtr pScreen,
unsigned int sequence,
@@ -312,8 +278,6 @@ dmxDnDTranslateCoordinatesReply (ScreenPtr pScreen,
WindowPtr pWin = WindowTable[pScreen->myNum];
xcb_client_message_event_t xevent;
- dmxDnDUpdatePointerDevice (pScreen, xcoord->dst_x, xcoord->dst_y);
-
#ifdef PANORAMIX
if (!noPanoramiXExtension)
pWin = WindowTable[0];
@@ -596,6 +560,8 @@ dmxDnDDropMessage (ScreenPtr pScreen,
{
DMXScreenInfo *dmxScreen = &dmxScreens[pScreen->myNum];
+ dmxEndFakeMotion (&dmxScreen->input);
+
if (dmxScreen->dndWindow)
{
WindowPtr pWin;
@@ -760,7 +726,8 @@ dmxDnDClientMessageEvent (xEvent *event)
if (dmxScreen->dndAcceptedAction &&
ValidAtom (dmxScreen->dndAcceptedAction))
xevent.data.data32[4] =
- dmxBEAtom (dmxScreen, dmxScreen->dndAcceptedAction);
+ dmxBEAtom (dmxScreen,
+ dmxScreen->dndAcceptedAction);
xcb_send_event (dmxScreen->connection,
FALSE,
diff --git a/hw/dmx/dmxgrab.c b/hw/dmx/dmxgrab.c
index 17f24f3ed..2cfb72a8f 100644
--- a/hw/dmx/dmxgrab.c
+++ b/hw/dmx/dmxgrab.c
@@ -285,6 +285,44 @@ dmxDeactivatePointerGrab (DeviceIntPtr pDev)
&pDev->deviceGrab);
}
+Bool
+dmxActivateFakePointerGrab (DeviceIntPtr pDev,
+ GrabPtr pGrab)
+{
+ dmxDevicePrivPtr pDevPriv = DMX_GET_DEVICE_PRIV (pDev);
+
+ if (pDevPriv->fakeGrab)
+ return TRUE;
+
+ if (pDev->deviceGrab.grab)
+ return FALSE;
+
+ pDevPriv->fakeGrab = TRUE;
+
+ DMX_UNWRAP (ActivateGrab, pDevPriv, &pDev->deviceGrab);
+ (*pDev->deviceGrab.ActivateGrab) (pDev, pGrab, currentTime, FALSE);
+ DMX_WRAP (ActivateGrab, dmxActivatePointerGrab, pDevPriv,
+ &pDev->deviceGrab);
+
+ return TRUE;
+}
+
+void
+dmxDeactivateFakePointerGrab (DeviceIntPtr pDev)
+{
+ dmxDevicePrivPtr pDevPriv = DMX_GET_DEVICE_PRIV (pDev);
+
+ if (!pDevPriv->fakeGrab)
+ return;
+
+ pDevPriv->fakeGrab = FALSE;
+
+ DMX_UNWRAP (DeactivateGrab, pDevPriv, &pDev->deviceGrab);
+ (*pDev->deviceGrab.DeactivateGrab) (pDev);
+ DMX_WRAP (DeactivateGrab, dmxDeactivatePointerGrab, pDevPriv,
+ &pDev->deviceGrab);
+}
+
static int
dmxProcGrabButton (ClientPtr client)
{
diff --git a/hw/dmx/dmxgrab.h b/hw/dmx/dmxgrab.h
index 4a2f96c3c..ed0de0a5a 100644
--- a/hw/dmx/dmxgrab.h
+++ b/hw/dmx/dmxgrab.h
@@ -37,6 +37,10 @@ extern void dmxActivatePointerGrab (DeviceIntPtr pDev,
Bool autoGrab);
extern void dmxDeactivatePointerGrab (DeviceIntPtr pDev);
+extern Bool dmxActivateFakePointerGrab (DeviceIntPtr pDev,
+ GrabPtr pGrab);
+extern void dmxDeactivateFakePointerGrab (DeviceIntPtr pDev);
+
extern void dmxInitGrabs (void);
extern void dmxResetGrabs (void);
diff --git a/hw/dmx/dmxinput.c b/hw/dmx/dmxinput.c
index 3b35a7525..f1ba3e00d 100644
--- a/hw/dmx/dmxinput.c
+++ b/hw/dmx/dmxinput.c
@@ -30,6 +30,7 @@
#include "dmx.h"
#include "dmxlog.h"
#include "dmxinput.h"
+#include "dmxgrab.h"
#include "dmxwindow.h"
#include "dmxcursor.h"
#include "dmxscrinit.h"
@@ -426,6 +427,82 @@ dmxUpdateSpritePosition (DeviceIntPtr pDevice,
return dmxButtonEvent (pDevice, 0, x, y, XCB_MOTION_NOTIFY);
}
+Bool
+dmxFakeMotion (DMXInputInfo *dmxInput,
+ int x,
+ int y)
+{
+ DMXScreenInfo *dmxScreen = (DMXScreenInfo *) dmxInput;
+ WindowPtr pWin = WindowTable[dmxScreen->index];
+ GrabRec newGrab;
+ int i;
+
+#ifdef PANORAMIX
+ if (!noPanoramiXExtension)
+ pWin = WindowTable[0];
+#endif
+
+ memset (&newGrab, 0, sizeof (GrabRec));
+
+ newGrab.window = pWin;
+ newGrab.resource = 0;
+ newGrab.ownerEvents = xFalse;
+ newGrab.cursor = NULL;
+ newGrab.confineTo = NullWindow;
+ newGrab.eventMask = NoEventMask;
+ newGrab.genericMasks = NULL;
+ newGrab.next = NULL;
+ newGrab.keyboardMode = GrabModeAsync;
+ newGrab.pointerMode = GrabModeAsync;
+
+ for (i = 0; i < dmxInput->numDevs; i++)
+ {
+ DeviceIntPtr pDevice = dmxInput->devs[i];
+
+ if (!pDevice->isMaster && pDevice->u.master)
+ pDevice = pDevice->u.master;
+
+ if (!pDevice->button)
+ continue;
+
+ newGrab.device = pDevice;
+
+ if (!dmxActivateFakePointerGrab (pDevice, &newGrab))
+ return FALSE;
+ }
+
+ for (i = 0; i < dmxInput->numDevs; i++)
+ {
+ DeviceIntPtr pDevice = dmxInput->devs[i];
+
+ if (!pDevice->button)
+ continue;
+
+ dmxUpdateSpritePosition (pDevice, x, y);
+ }
+
+ return TRUE;
+}
+
+void
+dmxEndFakeMotion (DMXInputInfo *dmxInput)
+{
+ int i;
+
+ for (i = 0; i < dmxInput->numDevs; i++)
+ {
+ DeviceIntPtr pDevice = dmxInput->devs[i];
+
+ if (!pDevice->isMaster && pDevice->u.master)
+ pDevice = pDevice->u.master;
+
+ if (!pDevice->button)
+ continue;
+
+ dmxDeactivateFakePointerGrab (pDevice);
+ }
+}
+
static Bool
dmxDevicePointerEventCheck (DeviceIntPtr pDevice,
xcb_generic_event_t *event)
@@ -440,7 +517,8 @@ dmxDevicePointerEventCheck (DeviceIntPtr pDevice,
case XCB_MOTION_NOTIFY: {
xcb_motion_notify_event_t *xmotion =
(xcb_motion_notify_event_t *) event;
-
+
+ dmxEndFakeMotion (dmxInput);
dmxUpdateSpritePosition (pButtonDev,
xmotion->event_x,
xmotion->event_y);
@@ -450,6 +528,7 @@ dmxDevicePointerEventCheck (DeviceIntPtr pDevice,
xcb_button_press_event_t *xbutton =
(xcb_button_press_event_t *) event;
+ dmxEndFakeMotion (dmxInput);
dmxUpdateSpritePosition (pButtonDev,
xbutton->event_x,
xbutton->event_y);
@@ -480,6 +559,7 @@ dmxDevicePointerEventCheck (DeviceIntPtr pDevice,
if (id != (xmotion->device_id & DEVICE_BITS))
return FALSE;
+ dmxEndFakeMotion (dmxInput);
dmxUpdateSpritePosition (pButtonDev,
xmotion->event_x,
xmotion->event_y);
@@ -492,6 +572,7 @@ dmxDevicePointerEventCheck (DeviceIntPtr pDevice,
if (id != (xbutton->device_id & DEVICE_BITS))
return FALSE;
+ dmxEndFakeMotion (dmxInput);
dmxUpdateSpritePosition (pButtonDev,
xbutton->event_x,
xbutton->event_y);
@@ -1466,6 +1547,7 @@ dmxAddInputDevice (DMXInputInfo *dmxInput,
pDevPriv->deviceId = deviceId;
pDevPriv->masterId = masterId;
pDevPriv->device = NULL;
+ pDevPriv->fakeGrab = xFalse;
pDevPriv->EventCheck = EventCheck;
pDevPriv->ReplyCheck = ReplyCheck;
diff --git a/hw/dmx/dmxinput.h b/hw/dmx/dmxinput.h
index f412224ed..9dd1385c0 100644
--- a/hw/dmx/dmxinput.h
+++ b/hw/dmx/dmxinput.h
@@ -39,6 +39,7 @@ typedef struct _dmxDevicePriv {
KeySymsRec keySyms;
KeyCode *keycode;
xcb_void_cookie_t grab;
+ Bool fakeGrab;
Bool (*EventCheck) (DeviceIntPtr, xcb_generic_event_t *);
Bool (*ReplyCheck) (DeviceIntPtr, unsigned int, xcb_generic_reply_t *);
@@ -91,6 +92,14 @@ dmxInputUngrabPointer (DMXInputInfo *dmxInput,
DeviceIntPtr pDevice,
WindowPtr pWindow);
+Bool
+dmxFakeMotion (DMXInputInfo *dmxInput,
+ int x,
+ int y);
+
+void
+dmxEndFakeMotion (DMXInputInfo *dmxInput);
+
int
dmxInputEnable (DMXInputInfo *dmxInput);