KASM-1871 Add smooth scrolling

Previously all scrolling relied on "clicking" the up/down or left/right scroll buttons
which made it unprecise and to always scroll at the same speed.

Now we pass the scroll delta directly to the xorg input driver so the scroll is more responsinve and adaptive.
pull/63/head
Mariusz Marciniak 4 years ago
parent 3f3d31312c
commit 0a45fcc700

2
.gitmodules vendored

@ -1,4 +1,4 @@
[submodule "kasmweb"] [submodule "kasmweb"]
path = kasmweb path = kasmweb
url = https://github.com/kasmtech/noVNC.git url = https://github.com/kasmtech/noVNC.git
branch = master branch = feature/KASM-1871_scroll_sensitivity

@ -38,7 +38,9 @@ namespace rfb {
virtual void pointerEvent(const Point& __unused_attr pos, virtual void pointerEvent(const Point& __unused_attr pos,
int __unused_attr buttonMask, int __unused_attr buttonMask,
const bool __unused_attr skipClick, const bool __unused_attr skipClick,
const bool __unused_attr skipRelease) { } const bool __unused_attr skipRelease,
int scrollX,
int scrollY) { }
virtual void clientCutText(const char* __unused_attr str, virtual void clientCutText(const char* __unused_attr str,
int __unused_attr len) { } int __unused_attr len) { }
}; };

@ -223,7 +223,9 @@ void SMsgReader::readPointerEvent()
int mask = is->readU8(); int mask = is->readU8();
int x = is->readU16(); int x = is->readU16();
int y = is->readU16(); int y = is->readU16();
handler->pointerEvent(Point(x, y), mask, false, false); int scrollX = is->readS16();
int scrollY = is->readS16();
handler->pointerEvent(Point(x, y), mask, false, false, scrollX, scrollY);
} }

@ -692,7 +692,7 @@ void VNCSConnectionST::setPixelFormat(const PixelFormat& pf)
setCursor(); setCursor();
} }
void VNCSConnectionST::pointerEvent(const Point& pos, int buttonMask, const bool skipClick, const bool skipRelease) void VNCSConnectionST::pointerEvent(const Point& pos, int buttonMask, const bool skipClick, const bool skipRelease, int scrollX, int scrollY)
{ {
pointerEventTime = lastEventTime = time(0); pointerEventTime = lastEventTime = time(0);
server->lastUserInputTime = lastEventTime; server->lastUserInputTime = lastEventTime;
@ -720,7 +720,7 @@ void VNCSConnectionST::pointerEvent(const Point& pos, int buttonMask, const bool
} }
} }
server->desktop->pointerEvent(pointerEventPos, buttonMask, skipclick, skiprelease); server->desktop->pointerEvent(pointerEventPos, buttonMask, skipclick, skiprelease, scrollX, scrollY);
} }
} }

@ -204,7 +204,7 @@ namespace rfb {
virtual void queryConnection(const char* userName); virtual void queryConnection(const char* userName);
virtual void clientInit(bool shared); virtual void clientInit(bool shared);
virtual void setPixelFormat(const PixelFormat& pf); virtual void setPixelFormat(const PixelFormat& pf);
virtual void pointerEvent(const Point& pos, int buttonMask, const bool skipClick, const bool skipRelease); virtual void pointerEvent(const Point& pos, int buttonMask, const bool skipClick, const bool skipRelease, int scrollX, int scrollY);
virtual void keyEvent(rdr::U32 keysym, rdr::U32 keycode, bool down); virtual void keyEvent(rdr::U32 keysym, rdr::U32 keycode, bool down);
virtual void framebufferUpdateRequest(const Rect& r, bool incremental); virtual void framebufferUpdateRequest(const Rect& r, bool incremental);
virtual void setDesktopSize(int fb_width, int fb_height, virtual void setDesktopSize(int fb_width, int fb_height,

@ -1 +1 @@
Subproject commit a0907e9390e8a135a280f7e4157eced05b8ec687 Subproject commit d20e5d78fac5a8866dba5bff2585cd4bb75f7fc9

@ -234,6 +234,14 @@ void vncPointerMove(int x, int y)
cursorPosY = y; cursorPosY = y;
} }
void vncScroll(int x, int y) {
ValuatorMask mask;
valuator_mask_zero(&mask);
valuator_mask_set(&mask, 2, x);
valuator_mask_set(&mask, 3, y);
QueuePointerEvents(vncPointerDev, MotionNotify, 0, POINTER_RELATIVE, &mask);
}
void vncGetPointerPos(int *x, int *y) void vncGetPointerPos(int *x, int *y)
{ {
if (vncPointerDev != NULL) { if (vncPointerDev != NULL) {
@ -261,7 +269,7 @@ static int vncPointerProc(DeviceIntPtr pDevice, int onoff)
* is not a bug. * is not a bug.
*/ */
Atom btn_labels[BUTTONS]; Atom btn_labels[BUTTONS];
Atom axes_labels[2]; Atom axes_labels[4];
switch (onoff) { switch (onoff) {
case DEVICE_INIT: case DEVICE_INIT:
@ -278,11 +286,29 @@ static int vncPointerProc(DeviceIntPtr pDevice, int onoff)
axes_labels[0] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_X); axes_labels[0] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_X);
axes_labels[1] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_Y); axes_labels[1] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_Y);
axes_labels[2] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_HSCROLL);
axes_labels[3] = XIGetKnownProperty(AXIS_LABEL_PROP_REL_VSCROLL);
InitPointerDeviceStruct(pDev, map, BUTTONS, btn_labels, InitPointerDeviceStruct(pDev, map, BUTTONS, btn_labels,
(PtrCtrlProcPtr)NoopDDA, (PtrCtrlProcPtr)NoopDDA,
GetMotionHistorySize(), GetMotionHistorySize(),
2, axes_labels); 4, axes_labels);
InitValuatorAxisStruct(pDevice, 2, axes_labels[2], NO_AXIS_LIMITS, NO_AXIS_LIMITS, 0, 0, 0, Relative);
InitValuatorAxisStruct(pDevice, 3, axes_labels[3], NO_AXIS_LIMITS, NO_AXIS_LIMITS, 0, 0, 0, Relative);
char* envScrollFactorH = getenv("SCROLL_FACTOR_H");
char* envScrollFactorV = getenv("SCROLL_FACTOR_V");
float scrollFactorH = envScrollFactorH ? atof(envScrollFactorH) : 50.0;
float scrollFactorV = envScrollFactorV ? atof(envScrollFactorV) : 50.0;
LOG_INFO("Mouse horizonatl scroll factor: %f", scrollFactorH);
LOG_INFO("Mouse vertical scroll factor: %f", scrollFactorV);
SetScrollValuator(pDevice, 2, SCROLL_TYPE_HORIZONTAL, scrollFactorH, SCROLL_FLAG_NONE);
SetScrollValuator(pDevice, 3, SCROLL_TYPE_VERTICAL, scrollFactorV, SCROLL_FLAG_PREFERRED);
break; break;
case DEVICE_ON: case DEVICE_ON:
pDev->on = TRUE; pDev->on = TRUE;

@ -35,6 +35,7 @@ void vncInitInputDevice(void);
void vncPointerButtonAction(int buttonMask, const unsigned char skipclick, void vncPointerButtonAction(int buttonMask, const unsigned char skipclick,
const unsigned char skiprelease); const unsigned char skiprelease);
void vncPointerMove(int x, int y); void vncPointerMove(int x, int y);
void vncScroll(int x, int y);
void vncGetPointerPos(int *x, int *y); void vncGetPointerPos(int *x, int *y);
void vncKeyboardEvent(KeySym keysym, unsigned xtcode, int down); void vncKeyboardEvent(KeySym keysym, unsigned xtcode, int down);

@ -446,11 +446,14 @@ void XserverDesktop::approveConnection(uint32_t opaqueId, bool accept,
void XserverDesktop::pointerEvent(const Point& pos, int buttonMask, void XserverDesktop::pointerEvent(const Point& pos, int buttonMask,
const bool skipClick, const bool skipRelease) const bool skipClick, const bool skipRelease, int scrollX, int scrollY)
{ {
vncPointerMove(pos.x + vncGetScreenX(screenIndex), if (scrollX == 0 && scrollY == 0) {
pos.y + vncGetScreenY(screenIndex)); vncPointerMove(pos.x + vncGetScreenX(screenIndex), pos.y + vncGetScreenY(screenIndex));
vncPointerButtonAction(buttonMask, skipClick, skipRelease); vncPointerButtonAction(buttonMask, skipClick, skipRelease);
} else {
vncScroll(scrollX, scrollY);
}
} }
unsigned int XserverDesktop::setScreenLayout(int fb_width, int fb_height, unsigned int XserverDesktop::setScreenLayout(int fb_width, int fb_height,

@ -90,7 +90,7 @@ public:
// rfb::SDesktop callbacks // rfb::SDesktop callbacks
virtual void pointerEvent(const rfb::Point& pos, int buttonMask, virtual void pointerEvent(const rfb::Point& pos, int buttonMask,
const bool skipClick, const bool skipRelease); const bool skipClick, const bool skipRelease, int scrollX = 0, int scrollY = 0);
virtual void keyEvent(rdr::U32 keysym, rdr::U32 keycode, bool down); virtual void keyEvent(rdr::U32 keysym, rdr::U32 keycode, bool down);
virtual unsigned int setScreenLayout(int fb_width, int fb_height, virtual unsigned int setScreenLayout(int fb_width, int fb_height,
const rfb::ScreenSet& layout); const rfb::ScreenSet& layout);

Loading…
Cancel
Save