Hi all,
I have implemented a new feature for the mouse driver.
On the one side I like the copy and paste function with the middle mouse
button in X11. On the other side I like the scrolling capability using the
same middle mouse button and a trackpoint like it is built into most IBM
notebooks. But with the current mouse driver it is not possible to have both.
I wanted to have both and just implemented this into the mouse driver. Using
this patch there is a new mouse driver integer option called
EmulateWheelTimeout.
If the EmulateWheel button is pressed and released within this timout the
original button press/release event is emitted. If it is pressed longer than
this timeout you can use use the mouse axis like usual with EmulateWheel for
scrolling.
This is a very usefull feature for notebooks with trackpoints.
Attached is a patch to yesterdays cvs tree. Please apply!
Since I am not on any xfree list please cc me on reply.
Many thanks in advance
Mathias Fröhlich
--
Mathias Fröhlich, email: [EMAIL PROTECTED]
Index: programs/Xserver/hw/xfree86/input/mouse/mouse.c
===
RCS file: /cvs/xc/programs/Xserver/hw/xfree86/input/mouse/mouse.c,v
retrieving revision 1.76
diff -u -r1.76 mouse.c
--- programs/Xserver/hw/xfree86/input/mouse/mouse.c 17 Sep 2003 03:46:32 - 1.76
+++ programs/Xserver/hw/xfree86/input/mouse/mouse.c 24 Sep 2003 20:23:24 -
@@ -186,6 +186,7 @@
OPTION_EMULATE_WHEEL,
OPTION_EMU_WHEEL_BUTTON,
OPTION_EMU_WHEEL_INERTIA,
+OPTION_EMU_WHEEL_TIMEOUT,
OPTION_X_AXIS_MAPPING,
OPTION_Y_AXIS_MAPPING,
OPTION_AUTO_SOFT,
@@ -223,6 +224,7 @@
{ OPTION_EMULATE_WHEEL, "EmulateWheel", OPTV_BOOLEAN, {0}, FALSE },
{ OPTION_EMU_WHEEL_BUTTON, "EmulateWheelButton", OPTV_INTEGER, {0}, FALSE },
{ OPTION_EMU_WHEEL_INERTIA, "EmulateWheelInertia", OPTV_INTEGER, {0}, FALSE },
+{ OPTION_EMU_WHEEL_TIMEOUT, "EmulateWheelTimeout", OPTV_INTEGER, {0}, FALSE },
{ OPTION_X_AXIS_MAPPING, "XAxisMapping", OPTV_STRING, {0}, FALSE },
{ OPTION_Y_AXIS_MAPPING, "YAxisMapping", OPTV_STRING, {0}, FALSE },
{ OPTION_AUTO_SOFT, "AutoSoft", OPTV_BOOLEAN, {0}, FALSE },
@@ -581,7 +583,7 @@
pInfo->name, wheelButton);
wheelButton = 4;
}
- pMse->wheelButtonMask = 1 << (wheelButton - 1);
+ pMse->wheelButton = wheelButton;
pMse->wheelInertia = xf86SetIntOption(pInfo->options,
"EmulateWheelInertia", 10);
@@ -590,6 +592,8 @@
pInfo->name, pMse->wheelInertia);
pMse->wheelInertia = 50;
}
+ pMse->wheelButtonTimeout = xf86SetIntOption(pInfo->options,
+ "EmulateWheelButtonTimeout", 200);
pMse->negativeX = MSE_NOAXISMAP;
pMse->positiveX = MSE_NOAXISMAP;
@@ -1631,6 +1635,7 @@
pMse->lastButtons = 0;
pMse->emulateState = 0;
pMse->emulate3Pending = FALSE;
+ pMse->wheelButtonExpires = GetTimeInMillis ();
device->public.on = TRUE;
FlushButtons(pMse);
if (pMse->emulate3Buttons || pMse->emulate3ButtonsSoft)
@@ -1961,6 +1966,8 @@
int truebuttons, emulateButtons;
int id, change;
int emuWheelDelta, emuWheelButton, emuWheelButtonMask;
+int wheelButtonMask;
+int ms;
pMse = pInfo->private;
@@ -1970,64 +1977,102 @@
else
buttons = reverseBits(reverseMap, buttons);
-/* Intercept wheel emulation. */
-if (pMse->emulateWheel && (buttons & pMse->wheelButtonMask)) {
- /* Y axis movement */
- if (pMse->negativeY != MSE_NOAXISMAP) {
- pMse->wheelYDistance += dy;
- if (pMse->wheelYDistance < 0) {
- emuWheelDelta = -pMse->wheelInertia;
- emuWheelButton = pMse->negativeY;
+if (pMse->emulateWheel) {
+ /* Emulate wheel button handling */
+ wheelButtonMask = 1 << (pMse->wheelButton - 1);
+
+ if (pMse->protocolID == PROT_MMHIT)
+ change = buttons ^ reverseBits(hitachMap, pMse->lastButtons);
+ else
+ change = buttons ^ reverseBits(reverseMap, pMse->lastButtons);
+
+ if (change & wheelButtonMask) {
+ if (buttons & wheelButtonMask) {
+ /* Start timeout handling */
+ pMse->wheelButtonExpires = GetTimeInMillis () + pMse->wheelButtonTimeout;
+ ms = - pMse->wheelButtonTimeout;
} else {
- emuWheelDelta = pMse->wheelInertia;
- emuWheelButton = pMse->positiveY;
- }
- emuWheelButtonMask = 1 << (emuWheelButton - 1);
- while (abs(pMse->wheelYDistance) > pMse->wheelInertia) {
- pMse->wheelYDistance -= emuWheelDelta;
+ ms = pMse->wheelButtonExpires - GetTimeInMillis ();
- /*
- * Synthesize the press and release, but not when the button
- * to be synthesized is already pressed "for real".
- */
- if (!(emuWheelButtonMask & buttons) ||
- (emuWheelButtonMask & pMse->wheelButtonMask)) {
- xf86PostButtonEvent(pInfo->dev, 0, emuWheelButton, 1, 0, 0);
- xf86PostButtonEvent(pInfo->dev, 0, emuWheelButton, 0, 0, 0);
+ if (0 < ms) {
+ /*
+ * If the button is released early enough emit the button
+ * press/release events
+ */
+ xf86PostButtonEv