From 07c0de71ec05297123776f3ffbdb8fa37899e1fe Mon Sep 17 00:00:00 2001 From: Alexander Ljungberg Date: Wed, 23 Jul 2014 15:04:07 +0100 Subject: [PATCH] New: support line-by-line scrolling with old scroll wheel devices in Firefox. Without this change, using a traditional scroll wheel mouse with discrete steps would result in very slow scrolling in Firefox. With this fix we handle these events like in Cocoa: as "[im]preciseScrollingDeltas", which `CPScrollView` in turn knows to apply the configurable line scroll amount for. For backwards compatibility, [event deltaX] and [event deltaY] are premultiplied with a suitable constant, while [event scrollingDeltaX] and [event scrollingDeltaY] show the true values needed. Browsers other than Firefox seem to always send pixel scrolling information even for old style scrolling devices, at least on the Mac, so are not affected by this change. Fixes #2013. --- AppKit/CPScrollView.j | 11 +++++++- AppKit/Platform/DOM/CPPlatformWindow+DOM.j | 30 ++++++++++++++-------- 2 files changed, 30 insertions(+), 11 deletions(-) diff --git a/AppKit/CPScrollView.j b/AppKit/CPScrollView.j index 3ea8593b9..c93543315 100644 --- a/AppKit/CPScrollView.j +++ b/AppKit/CPScrollView.j @@ -1403,7 +1403,16 @@ Notifies the delegate when the scroll view has finished scrolling. if (![_horizontalScroller isHidden] || ![_verticalScroller isHidden]) _timerScrollersHide = [CPTimer scheduledTimerWithTimeInterval:CPScrollViewFadeOutTime target:self selector:@selector(_hideScrollers:) userInfo:nil repeats:NO]; - [self _respondToScrollWheelEventWithDeltaX:[anEvent deltaX] deltaY:[anEvent deltaY]]; + var deltaX = [anEvent scrollingDeltaX], + deltaY = [anEvent scrollingDeltaY]; + + if (![anEvent hasPreciseScrollingDeltas]) + { + deltaX *= (_horizontalLineScroll || 1.0); + deltaY *= (_verticalLineScroll || 1.0); + } + + [self _respondToScrollWheelEventWithDeltaX:deltaX deltaY:deltaY]; } - (void)scrollPageUp:(id)sender diff --git a/AppKit/Platform/DOM/CPPlatformWindow+DOM.j b/AppKit/Platform/DOM/CPPlatformWindow+DOM.j index ad288aae4..b0610b5f2 100644 --- a/AppKit/Platform/DOM/CPPlatformWindow+DOM.j +++ b/AppKit/Platform/DOM/CPPlatformWindow+DOM.j @@ -203,7 +203,9 @@ var ModifierKeyCodes = [ var resizeTimer = nil; var PreventScroll = true; -#define FIREFOX_SCROLLWHEEL_FACTOR 6 +// When scrolling with an old-style scroll wheel with discete steps ('clicks'), the scroll amount can indicate how many "lines" to +// scroll. +#define SCROLLWHEEL_LINE_PIXELS 6.0 #if PLATFORM(DOM) @@ -919,9 +921,22 @@ var PreventScroll = true; // We lag 1 event behind without this timeout. setTimeout(function() { - // Find the scroll delta - var deltaX = _DOMScrollingElement.scrollLeft - 150, - deltaY = (_DOMScrollingElement.scrollTop - 150) || (aDOMEvent.deltaY === undefined ? 0 : (aDOMEvent.deltaY * FIREFOX_SCROLLWHEEL_FACTOR)); + if (aDOMEvent.deltaMode !== undefined && aDOMEvent.deltaMode !== 0) + { + event._hasPreciseScrollingDeltas = NO; + event._scrollingDeltaX = aDOMEvent.deltaX; + event._scrollingDeltaY = aDOMEvent.deltaY; + event._deltaX = aDOMEvent.deltaX * SCROLLWHEEL_LINE_PIXELS; + event._deltaY = aDOMEvent.deltaY * SCROLLWHEEL_LINE_PIXELS; + } + else + { + event._hasPreciseScrollingDeltas = YES; + event._scrollingDeltaX = (_DOMScrollingElement.scrollLeft - 150) || aDOMEvent.deltaX || 0; + event._scrollingDeltaY = (_DOMScrollingElement.scrollTop - 150) || aDOMEvent.deltaY || 0; + event._deltaX = event._scrollingDeltaX; + event._deltaY = event._scrollingDeltaY; + } // If we scroll super with momentum, // there are so many events going off that @@ -932,13 +947,8 @@ var PreventScroll = true; // // We get free performance boost if we skip sending these events, // as sending a scroll event with no deltas doesn't do anything. - if (deltaX || deltaY) - { - event._deltaX = deltaX; - event._deltaY = deltaY; - + if (event._deltaX || event._deltaY) [CPApp sendEvent:event]; - } // We set StopDOMEventPropagation = NO on line 1008 //if (StopDOMEventPropagation)