Diff
Modified: trunk/LayoutTests/ChangeLog (269505 => 269506)
--- trunk/LayoutTests/ChangeLog 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/ChangeLog 2020-11-06 09:44:54 UTC (rev 269506)
@@ -1,3 +1,29 @@
+2020-11-06 Martin Robinson <[email protected]>
+
+ Scroll snap specified on :root doesn't work
+ https://bugs.webkit.org/show_bug.cgi?id=210469
+ <rdar://problem/61746676>
+
+ Reviewed by Simon Fraser.
+
+ Modified main frame scroll snap tests to reflect the specification and add a
+ few more tests to test the legacy behavior which this change maintains for
+ backwards compatibility.
+
+ * css3/scroll-snap/scroll-snap-positions-mainframe.html:
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy-expected.txt: Added.
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy.html: Copied from LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal.html.
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal.html:
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-horizontal.html:
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-vertical.html:
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy-expected.txt: Added.
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy.html: Copied from LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical.html.
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-then-horizontal.html:
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical.html:
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy-expected.txt: Added.
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy.html: Copied from LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe.html.
+ * tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe.html:
+
2020-11-05 Alex Christensen <[email protected]>
Align GBK and gb18030 encoder and decoder with specification and other browsers
Modified: trunk/LayoutTests/css3/scroll-snap/scroll-snap-positions-mainframe.html (269505 => 269506)
--- trunk/LayoutTests/css3/scroll-snap/scroll-snap-positions-mainframe.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/css3/scroll-snap/scroll-snap-positions-mainframe.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -1,11 +1,13 @@
<html>
<head>
<style>
- body {
+ html {
margin: 0;
scroll-snap-type: y mandatory;
}
-
+ body {
+ margin: 0;
+ }
.vertical {
width: 100%;
height: 600px;
Added: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy-expected.txt (0 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy-expected.txt (rev 0)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy-expected.txt 2020-11-06 09:44:54 UTC (rev 269506)
@@ -0,0 +1,6 @@
+PASS div scrolled to next window.
+PASS div honored snap points.
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
Copied: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy.html (from rev 269505, trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal.html) (0 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy.html (rev 0)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -0,0 +1,119 @@
+<!DOCTYPE HTML>
+<html>
+ <head>
+ <style>
+ .horizontalGallery {
+ width: 600vw;
+ height: 100vh;
+ margin: 0;
+ padding: 0;
+ scroll-snap-type: x mandatory;
+ }
+ .colorBox {
+ height: 100vh;
+ width: 100vw;
+ float: left;
+ scroll-snap-align: start;
+ }
+ #item0 { background-color: red; }
+ #item1 { background-color: green; }
+ #item2 { background-color: blue; }
+ #item3 { background-color: aqua; }
+ #item4 { background-color: yellow; }
+ #item5 { background-color: fuchsia; }
+ </style>
+ <script src=""
+ <script>
+ window.jsTestIsAsync = true;
+
+ var targetScroller;
+ var scrollPositionBeforeGlide;
+ var scrollPositionBeforeSnap;
+
+ function checkForScrollSnap()
+ {
+ // The div should have snapped back to the previous position
+ if (targetScroller.scrollLeft != scrollPositionBeforeSnap)
+ testFailed("div did not snap back to proper location. Expected " + scrollPositionBeforeSnap + ", but got " + targetScroller.scrollLeft);
+ else
+ testPassed("div honored snap points.");
+
+ finishJSTest();
+ }
+
+ function scrollSnapTest()
+ {
+ scrollPositionBeforeSnap = targetScroller.scrollLeft;
+
+ var startPosX = targetScroller.offsetLeft + 20;
+ var startPosY = targetScroller.offsetTop + 20;
+ eventSender.monitorWheelEvents();
+ eventSender.mouseMoveTo(startPosX, startPosY); // Make sure we are just outside the iFrame
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'began', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, 'ended', 'none');
+ eventSender.callAfterScrollingCompletes(checkForScrollSnap);
+ }
+
+ function checkForScrollGlide()
+ {
+ // The div should have scrolled (glided) to the next snap point.
+ if (targetScroller.scrollLeft == window.innerWidth)
+ testPassed("div scrolled to next window.");
+ else
+ testFailed("div did not honor snap points. Expected " + window.innerWidth + ", but got " + targetScroller.scrollLeft);
+
+ setTimeout(scrollSnapTest, 0);
+ }
+
+ function scrollGlideTest()
+ {
+ scrollPositionBeforeGlide = targetScroller.scrollLeft;
+
+ var startPosX = targetScroller.offsetLeft + 20;
+ var startPosY = targetScroller.offsetTop + 20;
+ eventSender.monitorWheelEvents();
+ eventSender.mouseMoveTo(startPosX, startPosY); // Make sure we are just outside the iFrame
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'began', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, 'ended', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'none', 'begin');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(-1, 0, 'none', 'continue');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, 'none', 'end');
+ eventSender.callAfterScrollingCompletes(checkForScrollGlide);
+ }
+
+ function onLoad()
+ {
+ targetScroller = document.scrollingElement;
+ if (window.eventSender) {
+ internals.setPlatformMomentumScrollingPredictionEnabled(false);
+ setTimeout(scrollGlideTest, 0);
+ } else {
+ var messageLocation = document.getElementById('item0');
+ var message = document.createElement('div');
+ message.innerHTML = "<p>This test is better run under DumpRenderTree. To manually test it, place the mouse pointer<br/>"
+ + "inside the red region at the top of the page, and then use the mouse wheel or a two-finger swipe to make a<br/>"
+ + "small swipe gesture with some momentum.<br/><br/>"
+ + "The region should scroll to show a green region.<br/><br/>"
+ + "Next, perform a small scroll gesture that does not involve momentum. You should begin to see one of the colors<br/>"
+ + "to the left (or right) of the current green box. When you release the wheel, the region should scroll back so<br/>"
+ + "that the region is a single color.<br/><br/>"
+ + "You should also be able to repeat these test steps for the vertical region below.</p>";
+ messageLocation.appendChild(message);
+ }
+ }
+ </script>
+ </head>
+ <body _onload_="onLoad();" class="horizontalGallery">
+ <div id="item0" class="colorBox"><div id="console"></div></div>
+ <div id="item1" class="colorBox"></div>
+ <div id="item2" class="colorBox"></div>
+ <div id="item3" class="colorBox"></div>
+ <div id="item4" class="colorBox"></div>
+ <div id="item5" class="colorBox"></div>
+ </body>
+</html>
Modified: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal.html (269505 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -2,12 +2,14 @@
<html>
<head>
<style>
+ html {
+ scroll-snap-type: x mandatory;
+ }
.horizontalGallery {
width: 600vw;
height: 100vh;
margin: 0;
padding: 0;
- scroll-snap-type: x mandatory;
}
.colorBox {
height: 100vh;
Modified: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-horizontal.html (269505 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-horizontal.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-horizontal.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -2,12 +2,14 @@
<html>
<head>
<style>
+ html {
+ scroll-snap-type: x mandatory;
+ }
.horizontalGallery {
width: 600vw;
height: 100vh;
margin: 0;
padding: 0;
- scroll-snap-type: x mandatory;
}
.colorBox {
height: 100vh;
Modified: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-vertical.html (269505 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-vertical.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-slow-vertical.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -2,12 +2,14 @@
<html>
<head>
<style>
+ html {
+ scroll-snap-type: y mandatory;
+ }
.verticalGallery {
width: 100vw;
height: 600vh;
margin: 0;
padding: 0;
- scroll-snap-type: y mandatory;
}
.colorBox {
height: 100vh;
Added: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy-expected.txt (0 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy-expected.txt (rev 0)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy-expected.txt 2020-11-06 09:44:54 UTC (rev 269506)
@@ -0,0 +1,6 @@
+PASS div scrolled to next window.
+PASS div honored snap points.
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
Copied: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy.html (from rev 269505, trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical.html) (0 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy.html (rev 0)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -0,0 +1,119 @@
+<!DOCTYPE HTML>
+<html>
+ <head>
+ <style>
+ .verticalGallery {
+ width: 100vw;
+ height: 600vh;
+ margin: 0;
+ padding: 0;
+ scroll-snap-type: y mandatory;
+ }
+ .colorBox {
+ height: 100vh;
+ width: 100vw;
+ float: left;
+ scroll-snap-align: start;
+ }
+ #item0 { background-color: red; }
+ #item1 { background-color: green; }
+ #item2 { background-color: blue; }
+ #item3 { background-color: aqua; }
+ #item4 { background-color: yellow; }
+ #item5 { background-color: fuchsia; }
+ </style>
+ <script src=""
+ <script>
+ window.jsTestIsAsync = true;
+
+ var scrollingTarget;
+ var scrollPositionBeforeGlide;
+ var scrollPositionBeforeSnap;
+
+ function checkForScrollSnap()
+ {
+ // The div should have snapped back to the previous position
+ if (scrollingTarget.scrollTop != scrollPositionBeforeSnap)
+ testFailed(`div did not snap back to proper location. (${scrollingTarget.scrollTop} vs. ${scrollPositionBeforeSnap})`);
+ else
+ testPassed("div honored snap points.");
+
+ finishJSTest();
+ }
+
+ function scrollSnapTest()
+ {
+ scrollPositionBeforeSnap = scrollingTarget.scrollTop;
+
+ var startPosX = scrollingTarget.offsetLeft + 20;
+ var startPosY = scrollingTarget.offsetTop + 20;
+ eventSender.monitorWheelEvents();
+ eventSender.mouseMoveTo(startPosX, startPosY); // Make sure we are just outside the iFrame
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'began', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, 'ended', 'none');
+ eventSender.callAfterScrollingCompletes(checkForScrollSnap);
+ }
+
+ function checkForScrollGlide()
+ {
+ // The div should have scrolled (glided) to the next snap point.
+ if (scrollingTarget.scrollTop == window.innerHeight)
+ testPassed("div scrolled to next window.");
+ else
+ testFailed(`div did not honor snap points. (${scrollingTarget.scrollTop} vs. ${window.innerHeight})`);
+
+ setTimeout(scrollSnapTest, 0);
+ }
+
+ function scrollGlideTest()
+ {
+ scrollPositionBeforeGlide = scrollingTarget.scrollTop;
+
+ var startPosX = scrollingTarget.offsetLeft + 20;
+ var startPosY = scrollingTarget.offsetTop + 20;
+ eventSender.monitorWheelEvents();
+ eventSender.mouseMoveTo(startPosX, startPosY); // Make sure we are just outside the iFrame
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'began', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'changed', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, 'ended', 'none');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -1, 'none', 'begin');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, -4, 'none', 'continue');
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, 'none', 'end');
+ eventSender.callAfterScrollingCompletes(checkForScrollGlide);
+ }
+
+ function onLoad()
+ {
+ scrollingTarget = document.scrollingElement;
+ if (window.eventSender) {
+ internals.setPlatformMomentumScrollingPredictionEnabled(false);
+ setTimeout(scrollGlideTest, 0);
+ } else {
+ var messageLocation = document.getElementById('item0');
+ var message = document.createElement('div');
+ message.innerHTML = "<p>This test is better run under DumpRenderTree. To manually test it, place the mouse pointer<br/>"
+ + "inside the red region at the top of the page, and then use the mouse wheel or a two-finger swipe to make a<br/>"
+ + "small swipe gesture with some momentum.<br/><br/>"
+ + "The region should scroll to show a green region.<br/><br/>"
+ + "Next, perform a small scroll gesture that does not involve momentum. You should begin to see one of the colors<br/>"
+ + "to the left (or right) of the current green box. When you release the wheel, the region should scroll back so<br/>"
+ + "that the region is a single color.<br/><br/>"
+ + "You should also be able to repeat these test steps for the vertical region below.</p>";
+ messageLocation.appendChild(message);
+ }
+ }
+ </script>
+ </head>
+ <body _onload_="onLoad();" class="verticalGallery">
+ <div id="item0" class="colorBox"><div id="console"></div></div>
+ <div id="item1" class="colorBox"></div>
+ <div id="item2" class="colorBox"></div>
+ <div id="item3" class="colorBox"></div>
+ <div id="item4" class="colorBox"></div>
+ <div id="item5" class="colorBox"></div>
+ </body>
+</html>
Modified: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-then-horizontal.html (269505 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-then-horizontal.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-then-horizontal.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -2,12 +2,14 @@
<html>
<head>
<style>
+ html {
+ scroll-snap-type: y mandatory;
+ }
.verticalGallery {
width: 100vw;
height: 600vh;
margin: 0;
padding: 0;
- scroll-snap-type: y mandatory;
}
.colorBox {
height: 100vh;
Modified: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical.html (269505 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -2,12 +2,14 @@
<html>
<head>
<style>
+ html {
+ scroll-snap-type: y mandatory;
+ }
.verticalGallery {
width: 100vw;
height: 600vh;
margin: 0;
padding: 0;
- scroll-snap-type: y mandatory;
}
.colorBox {
height: 100vh;
Added: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy-expected.txt (0 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy-expected.txt (rev 0)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy-expected.txt 2020-11-06 09:44:54 UTC (rev 269506)
@@ -0,0 +1,10 @@
+Scrolling body with 2 drag ticks
+- Did the scrolling snap to the top? YES
+- Did scrolling snap to the second box? NO
+Scrolling body with 30 drag ticks
+- Did the scrolling snap to the top? NO
+- Did scrolling snap to the second box? NO
+Scrolling body with 60 drag ticks
+- Did the scrolling snap to the top? NO
+- Did scrolling snap to the second box? YES
+
Copied: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy.html (from rev 269505, trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe.html) (0 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy.html (rev 0)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -0,0 +1,78 @@
+<!DOCTYPE HTML>
+<html>
+ <head>
+ <style>
+ body {
+ margin: 0;
+ width: 100%;
+ height: 100%;
+ overflow-x: none;
+ overflow-y: scroll;
+ position: absolute;
+ scroll-snap-type: y proximity;
+ }
+
+ .area {
+ width: 100%;
+ height: 100%;
+ float: left;
+ opacity: 0.5;
+ scroll-snap-align: start;
+ }
+
+ #output {
+ position: fixed;
+ }
+ </style>
+ <script>
+ let write = s => output.innerHTML += s + "<br>";
+ if (window.testRunner) {
+ testRunner.dumpAsText();
+ testRunner.waitUntilDone();
+ }
+
+ function verticalScrollInBody(dragDeltas)
+ {
+ return new Promise(resolve => {
+ write(`Scrolling body with ${dragDeltas.length} drag ticks`);
+ eventSender.monitorWheelEvents();
+ internals.setPlatformMomentumScrollingPredictionEnabled(false);
+ eventSender.mouseMoveTo(window.innerWidth / 2, window.innerHeight / 2);
+ dragDeltas.forEach((delta, i) => eventSender.mouseScrollByWithWheelAndMomentumPhases(0, delta, i == 0 ? "began" : "changed", "none"));
+ eventSender.mouseScrollByWithWheelAndMomentumPhases(0, 0, "ended", "none");
+ eventSender.callAfterScrollingCompletes(() => {
+ let areaHeight = document.querySelector(".area").clientHeight;
+ write(`- Did the scrolling snap to the top? ${document.scrollingElement.scrollTop == 0 ? "YES" : "NO"}`);
+ write(`- Did scrolling snap to the second box? ${document.scrollingElement.scrollTop == areaHeight ? "YES" : "NO"}`);
+ document.scrollingElement.scrollTop = 0;
+ setTimeout(resolve, 0);
+ });
+ });
+ }
+
+ function run() {
+ if (!window.testRunner || !window.eventSender) {
+ write("To manually test, verify that scrolling near one of the boundaries between the colored boxes");
+ write("snaps to the edge of the nearest colored box, but scrolling somewhere near the middle of two");
+ write("boxes does not cause the scroll offset to snap.");
+ return;
+ }
+
+ let areaHeight = document.querySelector(".area").clientHeight;
+ verticalScrollInBody(new Array(2).fill(-1))
+ .then(() => verticalScrollInBody(new Array(Math.round(areaHeight / 20)).fill(-1)))
+ .then(() => verticalScrollInBody(new Array(Math.round(areaHeight / 10)).fill(-1)))
+ .then(() => testRunner.notifyDone());
+ }
+ </script>
+ </head>
+ <body _onload_=run()>
+ <div class="area" style="background-color: red;"></div>
+ <div class="area" style="background-color: green;"></div>
+ <div class="area" style="background-color: blue;"></div>
+ <div class="area" style="background-color: aqua;"></div>
+ <div class="area" style="background-color: yellow;"></div>
+ <div class="area" style="background-color: fuchsia;"></div>
+ </body>
+ <div id="output"></div>
+</html>
Modified: trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe.html (269505 => 269506)
--- trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe.html 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/LayoutTests/tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe.html 2020-11-06 09:44:54 UTC (rev 269506)
@@ -2,6 +2,9 @@
<html>
<head>
<style>
+ html {
+ scroll-snap-type: y proximity;
+ }
body {
margin: 0;
width: 100%;
@@ -9,9 +12,6 @@
overflow-x: none;
overflow-y: scroll;
position: absolute;
- scroll-snap-type: y proximity;
- -webkit-scroll-snap-type: proximity;
- scroll-snap-type: proximity;
}
.area {
@@ -20,8 +20,6 @@
float: left;
opacity: 0.5;
scroll-snap-align: start;
- -webkit-scroll-snap-coordinate: 0 0;
- scroll-snap-coordinate: 0 0;
}
#output {
Modified: trunk/Source/WebCore/ChangeLog (269505 => 269506)
--- trunk/Source/WebCore/ChangeLog 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/ChangeLog 2020-11-06 09:44:54 UTC (rev 269506)
@@ -1,3 +1,43 @@
+2020-11-06 Martin Robinson <[email protected]>
+
+ Scroll snap specified on :root doesn't work
+ https://bugs.webkit.org/show_bug.cgi?id=210469
+ <rdar://problem/61746676>
+
+ Properly handle scroll-snap-type on the root element.
+
+ This change is originally based on a patch by Simon Fraser.
+
+ Reviewed by Simon Fraser.
+
+ Tests: tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-horizontal-legacy.html
+ tiled-drawing/scrolling/scroll-snap/scroll-snap-mandatory-mainframe-vertical-legacy.html
+ tiled-drawing/scrolling/scroll-snap/scroll-snap-proximity-mainframe-legacy.html
+
+ * page/FrameView.cpp:
+ (WebCore::FrameView::updateSnapOffsets): Send the body or root element style depending
+ on where the scroll-snap properties are set, but always use the FrameView viewport
+ when calculating geometry for scroll snap.
+ * page/scrolling/AxisScrollSnapOffsets.cpp:
+ (WebCore::updateSnapOffsetsForScrollableArea): Accept a viewport rectangle from the
+ caller and also eliminate redundant argument that was causing a bit of confusion.
+ * page/scrolling/AxisScrollSnapOffsets.h: Update the function declaration.
+ * platform/ScrollableArea.cpp:
+ (WebCore::ScrollableArea::clearSnapOffsets): Added a helper to clear both vertical and horizontal snap info.
+ * platform/ScrollableArea.h:
+ * rendering/RenderBox.cpp:
+ (WebCore::RenderBox::findEnclosingScrollableContainerForSnapping const): Renamed findEnclosingScrollableContainer
+ to this because now it is only useful for scroll snapping. The only preexisting caller was
+ the scroll snap code.
+ (WebCore::RenderBox::findEnclosingScrollableContainer const): Deleted.
+ * rendering/RenderBox.h: Updated method name.
+ * rendering/RenderLayer.cpp:
+ (WebCore::RenderLayer::updateSnapOffsets): Update to reflect changes to updateSnapOffsetsForScrollableArea.
+ * rendering/RenderObject.cpp:
+ (WebCore::RenderObject::enclosingScrollableContainerForSnapping const): Always return the
+ document root as the container instead of the body. The body never captures scroll
+ snap points.
+
2020-11-05 Said Abou-Hallawa <[email protected]>
[GPU Process] Use the Ref counting of ImageBuffer to control its life cycle in Web Process and GPU Process
Modified: trunk/Source/WebCore/page/FrameView.cpp (269505 => 269506)
--- trunk/Source/WebCore/page/FrameView.cpp 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/page/FrameView.cpp 2020-11-06 09:44:54 UTC (rev 269506)
@@ -919,12 +919,30 @@
if (!frame().document())
return;
- // FIXME: Should we allow specifying snap points through <html> tags too?
- HTMLElement* body = frame().document()->bodyOrFrameset();
- if (!renderView() || !body || !body->renderer())
+ auto& document = *frame().document();
+ auto* documentElement = document.documentElement();
+ RenderBox* bodyRenderer = document.bodyOrFrameset() ? document.bodyOrFrameset()->renderBox() : nullptr;
+ RenderBox* rootRenderer = documentElement ? documentElement->renderBox() : nullptr;
+ auto rendererSyleHasScrollSnap = [](const RenderObject* renderer) {
+ return renderer && renderer->style().scrollSnapType().strictness != ScrollSnapStrictness::None;
+ };
+
+ const RenderStyle* styleToUse = nullptr;
+ if (rendererSyleHasScrollSnap(bodyRenderer)) {
+ // The specification doesn't allow setting scroll-snap-type on the body, but
+ // we do this to ensure backwards compatibility with an earlier version of the
+ // specification: See webkit.org/b/200643.
+ styleToUse = &bodyRenderer->style();
+ } else if (rendererSyleHasScrollSnap(rootRenderer))
+ styleToUse = &rootRenderer->style();
+
+ if (!styleToUse || !documentElement) {
+ clearSnapOffsets();
return;
-
- updateSnapOffsetsForScrollableArea(*this, *body, *renderView(), body->renderer()->style());
+ }
+
+ LayoutRect viewport = LayoutRect(IntPoint(), baseLayoutViewportSize());
+ updateSnapOffsetsForScrollableArea(*this, *rootRenderer, *styleToUse, viewport);
}
bool FrameView::isScrollSnapInProgress() const
Modified: trunk/Source/WebCore/page/scrolling/AxisScrollSnapOffsets.cpp (269505 => 269506)
--- trunk/Source/WebCore/page/scrolling/AxisScrollSnapOffsets.cpp 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/page/scrolling/AxisScrollSnapOffsets.cpp 2020-11-06 09:44:54 UTC (rev 269506)
@@ -160,13 +160,12 @@
}
}
-void updateSnapOffsetsForScrollableArea(ScrollableArea& scrollableArea, HTMLElement& scrollingElement, const RenderBox& scrollingElementBox, const RenderStyle& scrollingElementStyle)
+void updateSnapOffsetsForScrollableArea(ScrollableArea& scrollableArea, const RenderBox& scrollingElementBox, const RenderStyle& scrollingElementStyle, LayoutRect viewportRectInBorderBoxCoordinates)
{
- auto* scrollContainer = scrollingElement.renderer();
auto scrollSnapType = scrollingElementStyle.scrollSnapType();
- if (!scrollContainer || scrollSnapType.strictness == ScrollSnapStrictness::None || scrollContainer->view().boxesWithScrollSnapPositions().isEmpty()) {
- scrollableArea.clearHorizontalSnapOffsets();
- scrollableArea.clearVerticalSnapOffsets();
+ const auto& boxesWithScrollSnapPositions = scrollingElementBox.view().boxesWithScrollSnapPositions();
+ if (scrollSnapType.strictness == ScrollSnapStrictness::None || boxesWithScrollSnapPositions.isEmpty()) {
+ scrollableArea.clearSnapOffsets();
return;
}
@@ -184,16 +183,16 @@
bool scrollerIsRTL = !scrollingElementBox.style().isLeftToRightDirection();
// The bounds of the scrolling container's snap port, where the top left of the scrolling container's border box is the origin.
- auto scrollSnapPort = computeScrollSnapPortOrAreaRect(scrollingElementBox.paddingBoxRect(), scrollingElementStyle.scrollPadding(), InsetOrOutset::Inset);
+ auto scrollSnapPort = computeScrollSnapPortOrAreaRect(viewportRectInBorderBoxCoordinates, scrollingElementStyle.scrollPadding(), InsetOrOutset::Inset);
LOG_WITH_STREAM(ScrollSnap, stream << "Computing scroll snap offsets for " << scrollableArea << " in snap port " << scrollSnapPort);
- for (auto* child : scrollContainer->view().boxesWithScrollSnapPositions()) {
- if (child->enclosingScrollableContainerForSnapping() != scrollContainer)
+ for (auto* child : boxesWithScrollSnapPositions) {
+ if (child->enclosingScrollableContainerForSnapping() != &scrollingElementBox)
continue;
// The bounds of the child element's snap area, where the top left of the scrolling container's border box is the origin.
// The snap area is the bounding box of the child element's border box, after applying transformations.
// FIXME: For now, just consider whether the scroller is RTL. The behavior of LTR boxes inside a RTL scroller is poorly defined: https://github.com/w3c/csswg-drafts/issues/5361.
- auto scrollSnapArea = LayoutRect(child->localToContainerQuad(FloatQuad(child->borderBoundingBox()), scrollingElement.renderBox()).boundingBox());
+ auto scrollSnapArea = LayoutRect(child->localToContainerQuad(FloatQuad(child->borderBoundingBox()), &scrollingElementBox).boundingBox());
// localToContainerQuad will transform the scroll snap area by the scroll position, except in the case that this position is
// coming from a ScrollView. We want the transformed area, but without scroll position taken into account.
Modified: trunk/Source/WebCore/page/scrolling/AxisScrollSnapOffsets.h (269505 => 269506)
--- trunk/Source/WebCore/page/scrolling/AxisScrollSnapOffsets.h 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/page/scrolling/AxisScrollSnapOffsets.h 2020-11-06 09:44:54 UTC (rev 269506)
@@ -27,6 +27,7 @@
#if ENABLE(CSS_SCROLL_SNAP)
+#include "LayoutRect.h"
#include "LayoutUnit.h"
#include "ScrollSnapOffsetsInfo.h"
#include "ScrollTypes.h"
@@ -39,7 +40,10 @@
class RenderStyle;
class ScrollableArea;
-void updateSnapOffsetsForScrollableArea(ScrollableArea&, HTMLElement& scrollingElement, const RenderBox& scrollingElementBox, const RenderStyle& scrollingElementStyle);
+// Update the snap offsets for this scrollable area, given the RenderBox of the scroll container, the RenderStyle
+// which defines the scroll-snap properties, and the viewport rectangle with the origin at the top left of
+// the scrolling container's border box.
+void updateSnapOffsetsForScrollableArea(ScrollableArea&, const RenderBox& scrollingElementBox, const RenderStyle& scrollingElementStyle, LayoutRect viewportRectInBorderBoxCoordinates);
const unsigned invalidSnapOffsetIndex = UINT_MAX;
WEBCORE_EXPORT LayoutUnit closestSnapOffset(const Vector<LayoutUnit>& snapOffsets, const Vector<ScrollOffsetRange<LayoutUnit>>& snapOffsetRanges, LayoutUnit scrollDestination, float velocity, unsigned& activeSnapIndex);
Modified: trunk/Source/WebCore/platform/ScrollableArea.cpp (269505 => 269506)
--- trunk/Source/WebCore/platform/ScrollableArea.cpp 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/platform/ScrollableArea.cpp 2020-11-06 09:44:54 UTC (rev 269506)
@@ -530,6 +530,12 @@
ensureSnapOffsetsInfo().verticalSnapOffsetRanges = verticalRanges;
}
+void ScrollableArea::clearSnapOffsets()
+{
+ clearHorizontalSnapOffsets();
+ clearVerticalSnapOffsets();
+}
+
void ScrollableArea::clearHorizontalSnapOffsets()
{
if (!m_snapOffsetsInfo)
Modified: trunk/Source/WebCore/platform/ScrollableArea.h (269505 => 269506)
--- trunk/Source/WebCore/platform/ScrollableArea.h 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/platform/ScrollableArea.h 2020-11-06 09:44:54 UTC (rev 269506)
@@ -96,6 +96,7 @@
void setVerticalSnapOffsets(const Vector<LayoutUnit>&);
void setHorizontalSnapOffsetRanges(const Vector<ScrollOffsetRange<LayoutUnit>>&);
void setVerticalSnapOffsetRanges(const Vector<ScrollOffsetRange<LayoutUnit>>&);
+ void clearSnapOffsets();
void clearHorizontalSnapOffsets();
void clearVerticalSnapOffsets();
unsigned currentHorizontalSnapPointIndex() const { return m_currentHorizontalSnapPointIndex; }
Modified: trunk/Source/WebCore/rendering/RenderBox.cpp (269505 => 269506)
--- trunk/Source/WebCore/rendering/RenderBox.cpp 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/rendering/RenderBox.cpp 2020-11-06 09:44:54 UTC (rev 269506)
@@ -5033,17 +5033,18 @@
return containerBlock->offsetFromLogicalTopOfFirstPage() + logicalTop();
}
-const RenderBox* RenderBox::findEnclosingScrollableContainer() const
+const RenderBox* RenderBox::findEnclosingScrollableContainerForSnapping() const
{
for (auto& candidate : lineageOfType<RenderBox>(*this)) {
if (candidate.hasOverflowClip())
return &candidate;
}
- // If all parent elements are not overflow scrollable, check the body.
- // FIXME: We should not treat the body as the scrollable element (see webkit.org/b/210469).
- if (document().body() && frame().view() && frame().view()->isScrollable())
- return document().body()->renderBox();
-
+
+ // If all parent elements are not overflow scrollable and the frame is, then return
+ // the root element.
+ if (document().documentElement() && frame().view() && frame().view()->isScrollable())
+ return document().documentElement()->renderBox();
+
return nullptr;
}
Modified: trunk/Source/WebCore/rendering/RenderBox.h (269505 => 269506)
--- trunk/Source/WebCore/rendering/RenderBox.h 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/rendering/RenderBox.h 2020-11-06 09:44:54 UTC (rev 269506)
@@ -637,7 +637,7 @@
bool canHaveOutsideFragmentRange() const { return !isInFlowRenderFragmentedFlow(); }
virtual bool needsLayoutAfterFragmentRangeChange() const { return false; }
- const RenderBox* findEnclosingScrollableContainer() const;
+ const RenderBox* findEnclosingScrollableContainerForSnapping() const;
bool isGridItem() const { return parent() && parent()->isRenderGrid() && !isExcludedFromNormalLayout(); }
bool isFlexItem() const { return parent() && parent()->isFlexibleBox() && !isExcludedFromNormalLayout(); }
Modified: trunk/Source/WebCore/rendering/RenderLayer.cpp (269505 => 269506)
--- trunk/Source/WebCore/rendering/RenderLayer.cpp 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/rendering/RenderLayer.cpp 2020-11-06 09:44:54 UTC (rev 269506)
@@ -3592,7 +3592,7 @@
return;
RenderBox* box = enclosingElement()->renderBox();
- updateSnapOffsetsForScrollableArea(*this, *downcast<HTMLElement>(enclosingElement()), *box, box->style());
+ updateSnapOffsetsForScrollableArea(*this, *box, box->style(), box->paddingBoxRect());
}
bool RenderLayer::isScrollSnapInProgress() const
Modified: trunk/Source/WebCore/rendering/RenderObject.cpp (269505 => 269506)
--- trunk/Source/WebCore/rendering/RenderObject.cpp 2020-11-06 09:09:31 UTC (rev 269505)
+++ trunk/Source/WebCore/rendering/RenderObject.cpp 2020-11-06 09:44:54 UTC (rev 269506)
@@ -455,12 +455,12 @@
const RenderBox* RenderObject::enclosingScrollableContainerForSnapping() const
{
auto& renderBox = enclosingBox();
- if (auto* scrollableContainer = renderBox.findEnclosingScrollableContainer()) {
+ if (auto* scrollableContainer = renderBox.findEnclosingScrollableContainerForSnapping()) {
// The scrollable container for snapping cannot be the node itself.
if (scrollableContainer != this)
return scrollableContainer;
if (renderBox.parentBox())
- return renderBox.parentBox()->findEnclosingScrollableContainer();
+ return renderBox.parentBox()->findEnclosingScrollableContainerForSnapping();
}
return nullptr;
}