libuiohook
libuiohook copied to clipboard
Rotation value is always zero for mouse wheel events generated by a trackpad on Windows
So, on Windows when a mouse wheel event is generated by, well, a mouse wheel, then the rotation value helps distinguish the direction of the scroll. But on a trackpad rotation is always 0 so the direction is not known.
I suspect that the issue is in this code:
/* Delta HIWORD(mshook->mouseData)
* A positive value indicates that the wheel was rotated
* forward, away from the user; a negative value indicates that
* the wheel was rotated backward, toward the user. One wheel
* click is defined as WHEEL_DELTA, which is 120. */
event.data.wheel.rotation = (int16_t) HIWORD(mshook->mouseData) / WHEEL_DELTA;
I tried googling whether mouseData of MSLLHOOKSTRUCT has any problems with trackpads, but didn't find anything.
I do not have a Windows machine with a trackpad I am going to be able to test this on, but I suspect there is a different way of getting trackpad info. I suspect this sort of thing is also a problem on OS X.
I've decided to look more closely into this issue, and the problem is that the rotation value is divided by 120. A mouse generates rotation values which are multiples of 120, but a trackpad generates other values which are usually much smaller, and when these values are divided by 120, we get 0. I've replaced this: (int16_t) HIWORD(mshook->mouseData) / WHEEL_DELTA with this: (int16_t) HIWORD(mshook->mouseData) and now here's what I'm getting:
id=11,when=1659258447626,mask=0x0,type=1,amount=5,rotation=120
id=11,when=1659258450538,mask=0x0,type=1,amount=5,rotation=1
The first event was generated by a mouse, and the second one - by a trackpad. Problem is, a trackpad can generate much higher values if I scroll with it more intensely (I was able to generate values between 1 and 134), and as far as I understand, we can't determine whether it was a mouse scroll, or a trackpad scroll in the hook callback.
The question is, what should we do about it? Do we really need to divide the scroll rotation by 120?
So, on Windows when a mouse wheel event is generated by, well, a mouse wheel, then the rotation value helps distinguish the direction of the scroll. But on a trackpad rotation is always 0 so the direction is not known.
Use uiohook_event.data.wheel.direction value on the struct should be used to detect which direction the wheel is moving in.
Problem is, a trackpad can generate much higher values if I scroll with it more intensely ... we can't determine whether it was a mouse scroll, or a trackpad scroll in the hook callback.
This is the more interesting problem. You are correct, Windows does not provide a distinction between mouse and touchpad "wheel" events.
I was able to generate values between 1 and 134
You may have stumbled on the answer here without realizing it.
I think what maybe happening here is that the wheel is in WHEEL_BLOCK_SCROLL and the touchpad is in WHEEL_UNIT_SCROLL where only one of these type's should be divided by WHEEL_DELTA.
I've just run a sample app and tried scrolling with a mouse and a touchpad - both of them emit WHEEL_UNIT_SCROLL, so I don't think that's the case.
https://github.com/kwhat/libuiohook/pull/160/files Solves half the problem here by carrying over WHEEL_DELTA but this should probably change after I figure out what is going on with other platforms like OSX. I will probably end up back porting this fix back to 1.2 for windows.
https://github.com/kwhat/libuiohook/pull/160 solves this issue in a more intuitive way. I've redone how wheel events work on all platforms which should be more accurate and consistent across platforms.