Title: [286411] trunk/Source/WebCore
Revision
286411
Author
simon.fra...@apple.com
Date
2021-12-01 20:58:54 -0800 (Wed, 01 Dec 2021)

Log Message

Scrolling complex websites can stutter: scrolling thread frame can fail to process wheel events
https://bugs.webkit.org/show_bug.cgi?id=233739
rdar://85946176

Reviewed by Tim Horton.

While the scrolling thread is chilling in
ThreadedScrollingTree::waitForRenderingUpdateCompletionOrTimeout(), waiting up to half a
frame to allow the main thread to handle the commit (for scroll synchronization), wheel
events may have been dispatched to the scrolling thread.

If we blow the timeout and commit anyway, we need to make sure we've handled these wheel
events first, so that the current frame can commit some layer movement. We can achieve this
by dispatching the applyLayerPositions(), which will enqueue it behind any waiting wheel
event dispatch from EventDispatcher::internalWheelEvent().

* page/scrolling/ScrollingTree.cpp:
(WebCore::ScrollingTree::applyLayerPositions):
* page/scrolling/ThreadedScrollingTree.cpp:
(WebCore::ThreadedScrollingTree::waitForRenderingUpdateCompletionOrTimeout):

Modified Paths

Diff

Modified: trunk/Source/WebCore/ChangeLog (286410 => 286411)


--- trunk/Source/WebCore/ChangeLog	2021-12-02 04:58:49 UTC (rev 286410)
+++ trunk/Source/WebCore/ChangeLog	2021-12-02 04:58:54 UTC (rev 286411)
@@ -1,5 +1,28 @@
 2021-12-01  Simon Fraser  <simon.fra...@apple.com>
 
+        Scrolling complex websites can stutter: scrolling thread frame can fail to process wheel events
+        https://bugs.webkit.org/show_bug.cgi?id=233739
+        rdar://85946176
+
+        Reviewed by Tim Horton.
+
+        While the scrolling thread is chilling in
+        ThreadedScrollingTree::waitForRenderingUpdateCompletionOrTimeout(), waiting up to half a
+        frame to allow the main thread to handle the commit (for scroll synchronization), wheel
+        events may have been dispatched to the scrolling thread.
+
+        If we blow the timeout and commit anyway, we need to make sure we've handled these wheel
+        events first, so that the current frame can commit some layer movement. We can achieve this
+        by dispatching the applyLayerPositions(), which will enqueue it behind any waiting wheel
+        event dispatch from EventDispatcher::internalWheelEvent().
+
+        * page/scrolling/ScrollingTree.cpp:
+        (WebCore::ScrollingTree::applyLayerPositions):
+        * page/scrolling/ThreadedScrollingTree.cpp:
+        (WebCore::ThreadedScrollingTree::waitForRenderingUpdateCompletionOrTimeout):
+
+2021-12-01  Simon Fraser  <simon.fra...@apple.com>
+
         Scrolling complex websites can stutter: scrolling thread commit can get blocked on scroll synchronization
         https://bugs.webkit.org/show_bug.cgi?id=233738
         rdar://85880147

Modified: trunk/Source/WebCore/page/scrolling/ScrollingTree.cpp (286410 => 286411)


--- trunk/Source/WebCore/page/scrolling/ScrollingTree.cpp	2021-12-02 04:58:49 UTC (rev 286410)
+++ trunk/Source/WebCore/page/scrolling/ScrollingTree.cpp	2021-12-02 04:58:54 UTC (rev 286411)
@@ -437,7 +437,6 @@
 
 void ScrollingTree::applyLayerPositions()
 {
-    ASSERT(isMainThread());
     Locker locker { m_treeLock };
 
     applyLayerPositionsInternal();

Modified: trunk/Source/WebCore/page/scrolling/ThreadedScrollingTree.cpp (286410 => 286411)


--- trunk/Source/WebCore/page/scrolling/ThreadedScrollingTree.cpp	2021-12-02 04:58:49 UTC (rev 286410)
+++ trunk/Source/WebCore/page/scrolling/ThreadedScrollingTree.cpp	2021-12-02 04:58:54 UTC (rev 286411)
@@ -417,8 +417,12 @@
         m_state = SynchronizationState::Desynchronized;
         // At this point we know the main thread is taking too long in the rendering update,
         // so we give up trying to sync with the main thread and update layers here on the scrolling thread.
-        if (canUpdateLayersOnScrollingThread())
-            applyLayerPositionsInternal();
+        if (canUpdateLayersOnScrollingThread()) {
+            // Dispatch to allow for the scrolling thread to handle any outstanding wheel events before we commit layers.
+            ScrollingThread::dispatch([protectedThis = Ref { *this }]() {
+                protectedThis->applyLayerPositions();
+            });
+        }
         tracePoint(ScrollingThreadRenderUpdateSyncEnd, 1);
     } else
         tracePoint(ScrollingThreadRenderUpdateSyncEnd);
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to