[SCM] WebKit Debian packaging branch, webkit-1.1, updated. upstream/1.1.15.1-1414-gc69ee75

timothy at apple.com timothy at apple.com
Thu Oct 29 20:32:36 UTC 2009


The following commit has been merged in the webkit-1.1 branch:
commit e640aff6260956971030e8f207cf7e5328f8663d
Author: timothy at apple.com <timothy at apple.com@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date:   Wed Sep 23 19:43:40 2009 +0000

    WebCore: Prevent scrolling multiple elements during latched wheel events.
    
    Reviewed by Anders Carlsson.
    
    * page/EventHandler.cpp:
    (WebCore::scrollAndAcceptEvent):
    (WebCore::EventHandler::clear):
    (WebCore::EventHandler::handleWheelEvent):
    * page/EventHandler.h:
    * rendering/RenderBox.cpp:
    (WebCore::RenderBox::scroll):
    * rendering/RenderBox.h:
    
    WebKit/mac: Prevent scrolling multiple frames during latched wheel events.
    
    Reviewed by Anders Carlsson.
    
    * WebView/WebDynamicScrollBarsView.h:
    * WebView/WebDynamicScrollBarsView.mm:
    (-[WebDynamicScrollBarsView scrollWheel:]):
    
    git-svn-id: http://svn.webkit.org/repository/webkit/trunk@48683 268f45cc-cd09-0410-ab3c-d52691b4dbfc

diff --git a/WebCore/ChangeLog b/WebCore/ChangeLog
index 965c5df..2c6ef3e 100644
--- a/WebCore/ChangeLog
+++ b/WebCore/ChangeLog
@@ -1,3 +1,18 @@
+2009-09-22  Timothy Hatcher  <timothy at apple.com>
+
+        Prevent scrolling multiple elements during latched wheel events.
+
+        Reviewed by Anders Carlsson.
+
+        * page/EventHandler.cpp:
+        (WebCore::scrollAndAcceptEvent):
+        (WebCore::EventHandler::clear):
+        (WebCore::EventHandler::handleWheelEvent):
+        * page/EventHandler.h:
+        * rendering/RenderBox.cpp:
+        (WebCore::RenderBox::scroll):
+        * rendering/RenderBox.h:
+
 2009-09-23  Daniel Bates  <dbates at webkit.org>
 
         Reviewed by Adam Barth.
diff --git a/WebCore/page/EventHandler.cpp b/WebCore/page/EventHandler.cpp
index abe40c7..1fe01b9 100644
--- a/WebCore/page/EventHandler.cpp
+++ b/WebCore/page/EventHandler.cpp
@@ -101,7 +101,7 @@ const double autoscrollInterval = 0.05;
 
 static Frame* subframeForHitTestResult(const MouseEventWithHitTestResults&);
 
-static inline void scrollAndAcceptEvent(float delta, ScrollDirection positiveDirection, ScrollDirection negativeDirection, PlatformWheelEvent& e, Node* node)
+static inline void scrollAndAcceptEvent(float delta, ScrollDirection positiveDirection, ScrollDirection negativeDirection, PlatformWheelEvent& e, Node* node, Node** stopNode)
 {
     if (!delta)
         return;
@@ -110,12 +110,13 @@ static inline void scrollAndAcceptEvent(float delta, ScrollDirection positiveDir
     RenderBox* enclosingBox = node->renderer()->enclosingBox();
 
     if (e.granularity() == ScrollByPageWheelEvent) {
-        if (enclosingBox->scroll(delta < 0 ? negativeDirection : positiveDirection, ScrollByPage, 1))
+        if (enclosingBox->scroll(delta < 0 ? negativeDirection : positiveDirection, ScrollByPage, 1, stopNode))
             e.accept();
         return;
-    } 
+    }
+
     float pixelsToScroll = delta > 0 ? delta : -delta;
-    if (enclosingBox->scroll(delta < 0 ? negativeDirection : positiveDirection, ScrollByPixel, pixelsToScroll))
+    if (enclosingBox->scroll(delta < 0 ? negativeDirection : positiveDirection, ScrollByPixel, pixelsToScroll, stopNode))
         e.accept();
 }
 
@@ -205,6 +206,7 @@ void EventHandler::clear()
     m_capturesDragging = false;
     m_capturingMouseEventsNode = 0;
     m_latchedWheelEventNode = 0;
+    m_previousWheelScrolledNode = 0;
 }
 
 void EventHandler::selectClosestWordFromMouseEvent(const MouseEventWithHitTestResults& result)
@@ -1774,7 +1776,7 @@ bool EventHandler::handleWheelEvent(PlatformWheelEvent& e)
     Node* node;
     bool isOverWidget;
     bool didSetLatchedNode = false;
-    
+
     if (m_useLatchedWheelEventNode) {
         if (!m_latchedWheelEventNode) {
             HitTestRequest request(HitTestRequest::ReadOnly);
@@ -1784,20 +1786,22 @@ bool EventHandler::handleWheelEvent(PlatformWheelEvent& e)
             m_widgetIsLatched = result.isOverWidget();
             didSetLatchedNode = true;
         }
-        
+
         node = m_latchedWheelEventNode.get();
         isOverWidget = m_widgetIsLatched;
     } else {
         if (m_latchedWheelEventNode)
             m_latchedWheelEventNode = 0;
-        
+        if (m_previousWheelScrolledNode)
+            m_previousWheelScrolledNode = 0;
+
         HitTestRequest request(HitTestRequest::ReadOnly);
         HitTestResult result(vPoint);
         doc->renderView()->layer()->hitTest(request, result);
         node = result.innerNode();
         isOverWidget = result.isOverWidget();
     }
-    
+
     if (node) {
         // Figure out which view to send the event to.
         RenderObject* target = node->renderer();
@@ -1814,17 +1818,20 @@ bool EventHandler::handleWheelEvent(PlatformWheelEvent& e)
         node->dispatchWheelEvent(e);
         if (e.isAccepted())
             return true;
-        
+
         // If we don't have a renderer, send the wheel event to the first node we find with a renderer.
         // This is needed for <option> and <optgroup> elements so that <select>s get a wheel scroll.
         while (node && !node->renderer())
             node = node->parent();
-        
+
         if (node && node->renderer()) {
             // Just break up into two scrolls if we need to.  Diagonal movement on 
             // a MacBook pro is an example of a 2-dimensional mouse wheel event (where both deltaX and deltaY can be set).
-            scrollAndAcceptEvent(e.deltaX(), ScrollLeft, ScrollRight, e, node);
-            scrollAndAcceptEvent(e.deltaY(), ScrollUp, ScrollDown, e, node);
+            Node* stopNode = m_previousWheelScrolledNode.get();
+            scrollAndAcceptEvent(e.deltaX(), ScrollLeft, ScrollRight, e, node, &stopNode);
+            scrollAndAcceptEvent(e.deltaY(), ScrollUp, ScrollDown, e, node, &stopNode);
+            if (!m_useLatchedWheelEventNode)
+                m_previousWheelScrolledNode = stopNode;
         }
     }
 
diff --git a/WebCore/page/EventHandler.h b/WebCore/page/EventHandler.h
index b390457..7066252 100644
--- a/WebCore/page/EventHandler.h
+++ b/WebCore/page/EventHandler.h
@@ -378,7 +378,9 @@ private:
     bool m_useLatchedWheelEventNode;
     RefPtr<Node> m_latchedWheelEventNode;
     bool m_widgetIsLatched;
-    
+
+    RefPtr<Node> m_previousWheelScrolledNode;
+
 #if PLATFORM(MAC)
     NSView *m_mouseDownView;
     bool m_sendingEventToSubview;
diff --git a/WebCore/rendering/RenderBox.cpp b/WebCore/rendering/RenderBox.cpp
index 8a38769..cea226e 100644
--- a/WebCore/rendering/RenderBox.cpp
+++ b/WebCore/rendering/RenderBox.cpp
@@ -400,14 +400,21 @@ int RenderBox::horizontalScrollbarHeight() const
     return includeHorizontalScrollbarSize() ? layer()->horizontalScrollbarHeight() : 0;
 }
 
-bool RenderBox::scroll(ScrollDirection direction, ScrollGranularity granularity, float multiplier)
+bool RenderBox::scroll(ScrollDirection direction, ScrollGranularity granularity, float multiplier, Node** stopNode)
 {
     RenderLayer* l = layer();
-    if (l && l->scroll(direction, granularity, multiplier))
+    if (l && l->scroll(direction, granularity, multiplier)) {
+        if (stopNode)
+            *stopNode = node();
         return true;
+    }
+
+    if (stopNode && *stopNode && *stopNode == node())
+        return true;
+
     RenderBlock* b = containingBlock();
     if (b && !b->isRenderView())
-        return b->scroll(direction, granularity, multiplier);
+        return b->scroll(direction, granularity, multiplier, stopNode);
     return false;
 }
 
diff --git a/WebCore/rendering/RenderBox.h b/WebCore/rendering/RenderBox.h
index b493ae9..41c5622 100644
--- a/WebCore/rendering/RenderBox.h
+++ b/WebCore/rendering/RenderBox.h
@@ -245,7 +245,7 @@ public:
 
     virtual int verticalScrollbarWidth() const;
     int horizontalScrollbarHeight() const;
-    virtual bool scroll(ScrollDirection, ScrollGranularity, float multiplier = 1.0f);
+    virtual bool scroll(ScrollDirection, ScrollGranularity, float multiplier = 1.0f, Node** stopNode = 0);
     bool canBeScrolledAndHasScrollableArea() const;
     virtual bool canBeProgramaticallyScrolled(bool) const;
     virtual void autoscroll();
diff --git a/WebKit/mac/ChangeLog b/WebKit/mac/ChangeLog
index 733112a..8b4d539 100644
--- a/WebKit/mac/ChangeLog
+++ b/WebKit/mac/ChangeLog
@@ -1,3 +1,13 @@
+2009-09-22  Timothy Hatcher  <timothy at apple.com>
+
+        Prevent scrolling multiple frames during latched wheel events.
+
+        Reviewed by Anders Carlsson.
+
+        * WebView/WebDynamicScrollBarsView.h:
+        * WebView/WebDynamicScrollBarsView.mm:
+        (-[WebDynamicScrollBarsView scrollWheel:]):
+
 2009-09-22  Dan Bernstein  <mitz at apple.com>
 
         Reviewed by John Sullivan.
diff --git a/WebKit/mac/WebView/WebDynamicScrollBarsView.h b/WebKit/mac/WebView/WebDynamicScrollBarsView.h
index ce92b33..40aadc0 100644
--- a/WebKit/mac/WebView/WebDynamicScrollBarsView.h
+++ b/WebKit/mac/WebView/WebDynamicScrollBarsView.h
@@ -43,6 +43,8 @@ extern const int WebCoreScrollbarAlwaysOn;
     BOOL suppressLayout;
     BOOL suppressScrollers;
     BOOL inUpdateScrollers;
+    BOOL verticallyPinnedByPreviousWheelEvent;
+    BOOL horizontallyPinnedByPreviousWheelEvent;
     unsigned inUpdateScrollersLayoutPass;
 }
 - (void)setAllowsHorizontalScrolling:(BOOL)flag; // This method is used by Safari, so it cannot be removed.
diff --git a/WebKit/mac/WebView/WebDynamicScrollBarsView.mm b/WebKit/mac/WebView/WebDynamicScrollBarsView.mm
index 92e5123..3c28e3c 100644
--- a/WebKit/mac/WebView/WebDynamicScrollBarsView.mm
+++ b/WebKit/mac/WebView/WebDynamicScrollBarsView.mm
@@ -328,17 +328,41 @@ static const unsigned cMaxUpdateScrollbarsPass = 2;
     BOOL isContinuous;
     WKGetWheelEventDeltas(event, &deltaX, &deltaY, &isContinuous);
 
+    BOOL isLatchingEvent = WKIsLatchingWheelEvent(event);
+
     if (fabsf(deltaY) > fabsf(deltaX)) {
         if (![self allowsVerticalScrolling]) {
             [[self nextResponder] scrollWheel:event];
             return;
         }
-    } else if (![self allowsHorizontalScrolling]) {
-        [[self nextResponder] scrollWheel:event];
-        return;
+
+        if (isLatchingEvent && !verticallyPinnedByPreviousWheelEvent) {
+            double verticalPosition = [[self verticalScroller] doubleValue];
+            if ((deltaY >= 0.0 && verticalPosition == 0.0) || (deltaY <= 0.0 && verticalPosition == 1.0))
+                return;
+        }
+    } else {
+        if (![self allowsHorizontalScrolling]) {
+            [[self nextResponder] scrollWheel:event];
+            return;
+        }
+
+        if (isLatchingEvent && !horizontallyPinnedByPreviousWheelEvent) {
+            double horizontalPosition = [[self horizontalScroller] doubleValue];
+            if ((deltaX >= 0.0 && horizontalPosition == 0.0) || (deltaX <= 0.0 && horizontalPosition == 1.0))
+                return;
+        }
     }
 
     [super scrollWheel:event];
+
+    if (!isLatchingEvent) {
+        double verticalPosition = [[self verticalScroller] doubleValue];
+        double horizontalPosition = [[self horizontalScroller] doubleValue];
+
+        verticallyPinnedByPreviousWheelEvent = (verticalPosition == 0.0 || verticalPosition == 1.0);
+        horizontallyPinnedByPreviousWheelEvent = (horizontalPosition == 0.0 || horizontalPosition == 1.0);
+    }
 }
 
 - (BOOL)accessibilityIsIgnored 

-- 
WebKit Debian packaging



More information about the Pkg-webkit-commits mailing list