RESOLVED FIXED136729
Latching in iframes is not working as expected
https://bugs.webkit.org/show_bug.cgi?id=136729
Summary Latching in iframes is not working as expected
Beth Dakin
Reported 2014-09-10 17:21:23 PDT
Latching in iframes seems to be a bit broken right now. In the attached test case, start a strong momentum scroll gesture in the iframe. The one single gesture will continue scrolling the main frame, which shouldn't happen. Non-momentum gestures work as expected.
Attachments
Test case (83 bytes, text/html)
2014-09-10 17:21 PDT, Beth Dakin
no flags
Counter-test case (704 bytes, text/html)
2014-09-11 15:52 PDT, Brent Fulgham
no flags
Patch (35.47 KB, patch)
2014-09-17 15:55 PDT, Brent Fulgham
no flags
Patch (35.38 KB, patch)
2014-09-17 17:42 PDT, Brent Fulgham
no flags
Updated to correct Windows build. (35.33 KB, patch)
2014-09-17 17:44 PDT, Brent Fulgham
no flags
Corrected Makefiles for GTK/EFL use. (35.77 KB, patch)
2014-09-18 09:26 PDT, Brent Fulgham
no flags
Fixed crash in destructor call (36.28 KB, patch)
2014-09-18 13:35 PDT, Brent Fulgham
no flags
Archive of layout-test-results from webkit-ews-03 for mac-mountainlion (511.81 KB, application/zip)
2014-09-18 15:21 PDT, Build Bot
no flags
Patch (42.64 KB, patch)
2014-09-19 11:42 PDT, Brent Fulgham
no flags
Patch (35.89 KB, patch)
2014-09-19 13:55 PDT, Brent Fulgham
no flags
Patch (35.98 KB, patch)
2014-09-19 16:46 PDT, Brent Fulgham
simon.fraser: review+
Beth Dakin
Comment 1 2014-09-10 17:21:44 PDT
Created attachment 237921 [details] Test case
Brent Fulgham
Comment 2 2014-09-11 09:45:20 PDT
Ugh!
Brent Fulgham
Comment 3 2014-09-11 11:18:47 PDT
The latching logic thinks that the <iframe> is at the maximum scroll position because the scroll position is 0, and the maximum scrolled position is -1094. It's like the scrollable area coordinates are flipped for this case.
Brent Fulgham
Comment 4 2014-09-11 11:35:13 PDT
Actually, it looks like the issue here is that this test case puts us into the RenderLayer logic for maximum scroll position (and current scroll position), while the other scroll latch test cases seem to stay in the "ScrollableArea" implementation.
Brent Fulgham
Comment 5 2014-09-11 15:52:28 PDT
Created attachment 237993 [details] Counter-test case A nearly identical page where the iframe content is defined by "data" instead of a URL does not suffer from this problem.
Brent Fulgham
Comment 6 2014-09-11 16:53:13 PDT
On page load, the contentSize of the ScrollView representing the content of the <iframe> is (768x150). The <iframe> element is 300x150. The calculated maximum scroll position y coordinate is therefore 0, and we believe the content is already scrolled to the bottom.
Brent Fulgham
Comment 7 2014-09-11 17:22:06 PDT
Latching seems to set itself up properly if I do the following: 1. Load page. 2. Scroll the iframe slightly down so I am not at the upper limit of the scroll. 3. Scroll up (causing a rubber-band). 4. Now if I scroll down it is latched properly. This causes the scroll dimensions to be recalculated internally and everything works properly. It might be that after the iframe loads, the scroll bounds are not calculated without this manual step?
Brent Fulgham
Comment 8 2014-09-15 17:30:44 PDT
The problem seems to be related to the apple.com page used in the test. The page markup is causing the viewSize of the iframe to match the size of the iframe (e.g., we give the iframe a 150px height in the test case, and the page markup explicitly sets the view size to also have a 150px height). This behavior causes our latching logic to fail, because it always thinks that we are starting wheel gestures at the edge of the iframe. Consequently, all events get propagated to the enclosing parent, causing the main page to scroll once the iframe has completed scrolling.
Radar WebKit Bug Importer
Comment 9 2014-09-17 13:41:01 PDT
Brent Fulgham
Comment 10 2014-09-17 15:55:04 PDT
Brent Fulgham
Comment 11 2014-09-17 17:42:41 PDT
Brent Fulgham
Comment 12 2014-09-17 17:44:38 PDT
Created attachment 238275 [details] Updated to correct Windows build.
Brent Fulgham
Comment 13 2014-09-17 17:46:02 PDT
Comment on attachment 238275 [details] Updated to correct Windows build. There's really no need to conditionalize the presence of a boolean and one smart pointer in the LatchedState class. Removing these conditionals and building on all platforms.
Brent Fulgham
Comment 14 2014-09-17 19:42:48 PDT
Looks like I need to update the CMake files!
Brent Fulgham
Comment 15 2014-09-18 09:26:38 PDT
Created attachment 238312 [details] Corrected Makefiles for GTK/EFL use.
Brent Fulgham
Comment 16 2014-09-18 13:16:18 PDT
Comment on attachment 238312 [details] Corrected Makefiles for GTK/EFL use. Pulling from review due to a crash when destroying the MainFrame.
Brent Fulgham
Comment 17 2014-09-18 13:35:55 PDT
Created attachment 238322 [details] Fixed crash in destructor call
Simon Fraser (smfr)
Comment 18 2014-09-18 14:12:50 PDT
Comment on attachment 238322 [details] Fixed crash in destructor call View in context: https://bugs.webkit.org/attachment.cgi?id=238322&action=review > Source/WebCore/page/LatchedState.h:38 > +class LatchedState { I think this should be called ScrollLatchingState. Out of context, it's hard to know what is being latched. You could also move it to page/scrolling. > Source/WebCore/page/MainFrame.cpp:38 > + , m_latchedState(std::make_unique<LatchedState>()) Should platforms without scroll events waste memory on a latched state? > Source/WebCore/page/MainFrame.cpp:46 > + m_latchedState = nullptr; > + m_recentWheelEventDeltaTracker = nullptr; Neither is necessary. > Source/WebCore/page/MainFrame.cpp:83 > + if (!m_latchedState) > + return; This should never happen, right? > Source/WebCore/page/MainFrame.h:48 > + bool hasLatchedState() { return m_latchedState.get(); } > + LatchedState& latchedState() { return *m_latchedState; } I don't see the advantage over just returning a pointer. > LayoutTests/platform/mac/fast/scrolling/scroll-iframe-100pct.html:16 > + // The IFrame should have scrolled, but not the main page. IFrame -> iframe everywhere. > LayoutTests/platform/mac/fast/scrolling/scroll-iframe-100pct.html:34 > + var iFrameBody = window.frames['target'].document.body; iFrame -> iframe
Brent Fulgham
Comment 19 2014-09-18 14:44:27 PDT
Comment on attachment 238322 [details] Fixed crash in destructor call View in context: https://bugs.webkit.org/attachment.cgi?id=238322&action=review >> Source/WebCore/page/LatchedState.h:38 >> +class LatchedState { > > I think this should be called ScrollLatchingState. Out of context, it's hard to know what is being latched. > > You could also move it to page/scrolling. Will do! >> Source/WebCore/page/MainFrame.cpp:38 >> + , m_latchedState(std::make_unique<LatchedState>()) > > Should platforms without scroll events waste memory on a latched state? Probably not. With this refactoring, it's actually a lot easier to skip the latching stuff on these platforms. I'll change this. >> Source/WebCore/page/MainFrame.cpp:46 >> + m_recentWheelEventDeltaTracker = nullptr; > > Neither is necessary. Will do! >> Source/WebCore/page/MainFrame.cpp:83 >> + return; > > This should never happen, right? It does happen in the destructor for Frame, which ends up triggering a call to EventHandler::clear() after it has destroyed part of the Frame. >> Source/WebCore/page/MainFrame.h:48 >> + LatchedState& latchedState() { return *m_latchedState; } > > I don't see the advantage over just returning a pointer. Agreed. Changing... >> LayoutTests/platform/mac/fast/scrolling/scroll-iframe-100pct.html:16 >> + // The IFrame should have scrolled, but not the main page. > > IFrame -> iframe everywhere. Done. >> LayoutTests/platform/mac/fast/scrolling/scroll-iframe-100pct.html:34 >> + var iFrameBody = window.frames['target'].document.body; > > iFrame -> iframe Done.
Build Bot
Comment 20 2014-09-18 15:21:53 PDT
Comment on attachment 238322 [details] Fixed crash in destructor call Attachment 238322 [details] did not pass mac-ews (mac): Output: http://webkit-queues.appspot.com/results/6080750784872448 New failing tests: platform/mac/fast/scrolling/scroll-iframe-latched-iframe.html
Build Bot
Comment 21 2014-09-18 15:21:57 PDT
Created attachment 238325 [details] Archive of layout-test-results from webkit-ews-03 for mac-mountainlion The attached test failures were seen while running run-webkit-tests on the mac-ews. Bot: webkit-ews-03 Port: mac-mountainlion Platform: Mac OS X 10.8.5
Brent Fulgham
Comment 22 2014-09-18 15:34:01 PDT
Looks like WK1 scrolling is broken. Working on a fix.
Brent Fulgham
Comment 23 2014-09-19 11:42:45 PDT
Simon Fraser (smfr)
Comment 24 2014-09-19 11:52:17 PDT
Comment on attachment 238381 [details] Patch View in context: https://bugs.webkit.org/attachment.cgi?id=238381&action=review > Source/WebCore/page/MainFrame.cpp:39 > +#if PLATFORM(COCOA) > + , m_latchedState(std::make_unique<ScrollLatchedState>()) > +#endif COCOA includes iOS, and I don't think you want that. > Source/WebCore/page/MainFrame.h:47 > +#if PLATFORM(COCOA) MAC? > Source/WebCore/page/mac/EventHandlerMac.mm:819 > +static bool isWK1EventForOtherPlatformFrame(const Frame& frame) We try really hard to avoid explicitly distinguishing between WK1 and WK2 in WebCore. The name of this function needs to communicate WHY WK1 needs different handling. > Source/WebCore/page/scrolling/ScrollLatchedState.h:37 > +class ScrollLatchedState { I'd prefer ScrollLatchingState
Brent Fulgham
Comment 25 2014-09-19 13:55:41 PDT
Brent Fulgham
Comment 26 2014-09-19 15:26:37 PDT
FYI - The patch builds locally on Windows. I'm not sure why EWS is failing.
Brent Fulgham
Comment 27 2014-09-19 16:46:00 PDT
Simon Fraser (smfr)
Comment 28 2014-09-19 18:01:10 PDT
Comment on attachment 238397 [details] Patch View in context: https://bugs.webkit.org/attachment.cgi?id=238397&action=review > Source/WebCore/ChangeLog:9 > + Test: platform/mac/fast/scrolling/scrolling-iframe-100pct.html I don't see this in the patch. I think the name could be improved to reflect what's being tested.
Brent Fulgham
Comment 29 2014-09-19 18:11:00 PDT
Note You need to log in before you can comment on or make changes to this bug.