Title: [279714] trunk
Revision
279714
Author
commit-qu...@webkit.org
Date
2021-07-08 00:23:32 -0700 (Thu, 08 Jul 2021)

Log Message

[css-scroll-snap] scroll-snap-align should use the box's writing-mode when the box is larger than the snapport
https://bugs.webkit.org/show_bug.cgi?id=227743

Patch by Martin Robinson <mrobin...@igalia.com> on 2021-07-08
Reviewed by Simon Fraser.

Source/WebCore:

No new tests. This fixes an existing WPT test:
   - imported/w3c/web-platform-tests/css/css-scroll-snap/snap-after-initial-layout/scroll-snap-writing-mode-000.html

* page/scrolling/ScrollSnapOffsetsInfo.cpp:
(WebCore::axesFlippedForWritingModeAndDirection): Added this helper which abstracts the process of
determining if the x-axis and y-axis are flipped given the style's writing mode and text direction.
(WebCore::updateSnapOffsetsForScrollableArea): When the inline axis of the box defining the snap area
is larger than the snapport, we use the box's writing mode and text-direction to determine if the
x-axis and y-axis are flipped.

LayoutTests:

* TestExpectations: Unskip a test which is now passing.

Modified Paths

Diff

Modified: trunk/LayoutTests/ChangeLog (279713 => 279714)


--- trunk/LayoutTests/ChangeLog	2021-07-08 07:23:20 UTC (rev 279713)
+++ trunk/LayoutTests/ChangeLog	2021-07-08 07:23:32 UTC (rev 279714)
@@ -1,3 +1,12 @@
+2021-07-08  Martin Robinson  <mrobin...@igalia.com>
+
+        [css-scroll-snap] scroll-snap-align should use the box's writing-mode when the box is larger than the snapport
+        https://bugs.webkit.org/show_bug.cgi?id=227743
+
+        Reviewed by Simon Fraser.
+
+        * TestExpectations: Unskip a test which is now passing.
+
 2021-07-07  Chris Dumez  <cdu...@apple.com>
 
         Our structured cloning implementation does not encode all of RegExp's flags

Modified: trunk/LayoutTests/TestExpectations (279713 => 279714)


--- trunk/LayoutTests/TestExpectations	2021-07-08 07:23:20 UTC (rev 279713)
+++ trunk/LayoutTests/TestExpectations	2021-07-08 07:23:32 UTC (rev 279714)
@@ -4725,7 +4725,6 @@
 imported/w3c/web-platform-tests/css/css-scroll-snap/scroll-target-align-003.html [ ImageOnlyFailure ]
 imported/w3c/web-platform-tests/css/css-scroll-snap/scroll-target-snap-001.html [ ImageOnlyFailure ]
 imported/w3c/web-platform-tests/css/css-scroll-snap/scroll-target-snap-002.html [ ImageOnlyFailure ]
-imported/w3c/web-platform-tests/css/css-scroll-snap/snap-after-initial-layout/scroll-snap-writing-mode-000.html [ ImageOnlyFailure ]
 webkit.org/b/218325 imported/w3c/web-platform-tests/css/css-scroll-snap/scroll-target-margin-001.html [ Pass ImageOnlyFailure ]
 webkit.org/b/218325 imported/w3c/web-platform-tests/css/css-scroll-snap/scroll-target-margin-003.html [ Pass ImageOnlyFailure ]
 

Modified: trunk/Source/WebCore/ChangeLog (279713 => 279714)


--- trunk/Source/WebCore/ChangeLog	2021-07-08 07:23:20 UTC (rev 279713)
+++ trunk/Source/WebCore/ChangeLog	2021-07-08 07:23:32 UTC (rev 279714)
@@ -1,3 +1,20 @@
+2021-07-08  Martin Robinson  <mrobin...@igalia.com>
+
+        [css-scroll-snap] scroll-snap-align should use the box's writing-mode when the box is larger than the snapport
+        https://bugs.webkit.org/show_bug.cgi?id=227743
+
+        Reviewed by Simon Fraser.
+
+        No new tests. This fixes an existing WPT test:
+           - imported/w3c/web-platform-tests/css/css-scroll-snap/snap-after-initial-layout/scroll-snap-writing-mode-000.html
+
+        * page/scrolling/ScrollSnapOffsetsInfo.cpp:
+        (WebCore::axesFlippedForWritingModeAndDirection): Added this helper which abstracts the process of
+        determining if the x-axis and y-axis are flipped given the style's writing mode and text direction.
+        (WebCore::updateSnapOffsetsForScrollableArea): When the inline axis of the box defining the snap area
+        is larger than the snapport, we use the box's writing mode and text-direction to determine if the
+        x-axis and y-axis are flipped.
+
 2021-07-08  Fujii Hironori  <hironori.fu...@sony.com>
 
         Merge Cairo::save and Cairo::restore into GraphicsContextCairo's methods

Modified: trunk/Source/WebCore/page/scrolling/ScrollSnapOffsetsInfo.cpp (279713 => 279714)


--- trunk/Source/WebCore/page/scrolling/ScrollSnapOffsetsInfo.cpp	2021-07-08 07:23:20 UTC (rev 279713)
+++ trunk/Source/WebCore/page/scrolling/ScrollSnapOffsetsInfo.cpp	2021-07-08 07:23:32 UTC (rev 279714)
@@ -199,6 +199,16 @@
     }
 }
 
+static std::pair<bool, bool> axesFlippedForWritingModeAndDirection(WritingMode writingMode, TextDirection textDirection)
+{
+    // text-direction flips the inline axis and writing-mode can flip the block axis. Whether or
+    // not the writing-mode is vertical determines the physical orientation of the block and inline axes.
+    bool hasVerticalWritingMode = isVerticalWritingMode(writingMode);
+    bool blockAxisFlipped = isFlippedWritingMode(writingMode);
+    bool inlineAxisFlipped = textDirection == TextDirection::RTL;
+    return std::make_pair(hasVerticalWritingMode ? blockAxisFlipped : inlineAxisFlipped, hasVerticalWritingMode ? inlineAxisFlipped : blockAxisFlipped);
+}
+
 void updateSnapOffsetsForScrollableArea(ScrollableArea& scrollableArea, const RenderBox& scrollingElementBox, const RenderStyle& scrollingElementStyle, LayoutRect viewportRectInBorderBoxCoordinates, WritingMode writingMode, TextDirection textDirection)
 {
     auto scrollSnapType = scrollingElementStyle.scrollSnapType();
@@ -223,14 +233,8 @@
     auto maxScrollOffset = scrollableArea.maximumScrollOffset();
     auto scrollPosition = LayoutPoint { scrollableArea.scrollPosition() };
 
-    // text-direction flips the inline axis and writing-mode can flip the block axis. Whether or
-    // not the writing-mode is vertical determines the physical orientation of the block and inline axes.
+    auto [scrollerXAxisFlipped, scrollerYAxisFlipped] = axesFlippedForWritingModeAndDirection(writingMode, textDirection);
     bool scrollerHasVerticalWritingMode = isVerticalWritingMode(writingMode);
-    bool blockAxisFlipped = isFlippedWritingMode(writingMode);
-    bool inlineAxisFlipped = textDirection == TextDirection::RTL;
-    bool xAxisFlipped = scrollerHasVerticalWritingMode ? blockAxisFlipped : inlineAxisFlipped;
-    bool yAxisFlipped = scrollerHasVerticalWritingMode ? inlineAxisFlipped : blockAxisFlipped;
-
     bool hasHorizontalSnapOffsets = scrollSnapType.axis == ScrollSnapAxis::Both || scrollSnapType.axis == ScrollSnapAxis::XAxis;
     bool hasVerticalSnapOffsets = scrollSnapType.axis == ScrollSnapAxis::Both || scrollSnapType.axis == ScrollSnapAxis::YAxis;
     if (scrollSnapType.axis == ScrollSnapAxis::Block) {
@@ -263,6 +267,16 @@
         auto alignment = child->style().scrollSnapAlign();
         auto stop = child->style().scrollSnapStop();
 
+        // From https://drafts.csswg.org/css-scroll-snap-1/#scroll-snap-align:
+        // "Start and end alignments are resolved with respect to the writing mode of the snap container unless the
+        // scroll snap area is larger than the snapport, in which case they are resolved with respect to the writing
+        // mode of the box itself."
+        bool areaXAxisFlipped = scrollerXAxisFlipped;
+        bool areaYAxisFlipped = scrollerYAxisFlipped;
+        bool areaHasVerticalWritingMode = isVerticalWritingMode(child->style().writingMode());
+        if ((areaHasVerticalWritingMode && scrollSnapArea.height() > scrollSnapPort.height()) || (!areaHasVerticalWritingMode && scrollSnapArea.width() > scrollSnapPort.width()))
+            std::tie(areaXAxisFlipped, areaYAxisFlipped) = axesFlippedForWritingModeAndDirection(child->style().writingMode(), child->style().direction());
+
         ScrollSnapAxisAlignType xAlign = scrollerHasVerticalWritingMode ? alignment.blockAlign : alignment.inlineAlign;
         ScrollSnapAxisAlignType yAlign = scrollerHasVerticalWritingMode ? alignment.inlineAlign : alignment.blockAlign;
         bool snapsHorizontally = hasHorizontalSnapOffsets && xAlign != ScrollSnapAxisAlignType::None;
@@ -270,7 +284,6 @@
 
         if (!snapsHorizontally && !snapsVertically)
             continue;
-
         // The scroll snap area is defined via its scroll position, so convert the snap area rectangle to be relative to scroll offsets.
         auto snapAreaOriginRelativeToBorderEdge = scrollSnapArea.location() - scrollSnapPort.location();
         LayoutRect scrollSnapAreaAsOffsets(scrollableArea.scrollOffsetFromPosition(roundedIntPoint(snapAreaOriginRelativeToBorderEdge)), scrollSnapArea.size());
@@ -277,12 +290,12 @@
         snapAreas.append(scrollSnapAreaAsOffsets);
 
         if (snapsHorizontally) {
-            auto absoluteScrollXPosition = computeScrollSnapAlignOffset(scrollSnapArea.x(), scrollSnapArea.maxX(), xAlign, xAxisFlipped) - computeScrollSnapAlignOffset(scrollSnapPort.x(), scrollSnapPort.maxX(), xAlign, xAxisFlipped);
+            auto absoluteScrollXPosition = computeScrollSnapAlignOffset(scrollSnapArea.x(), scrollSnapArea.maxX(), xAlign, areaXAxisFlipped) - computeScrollSnapAlignOffset(scrollSnapPort.x(), scrollSnapPort.maxX(), xAlign, areaXAxisFlipped);
             auto absoluteScrollOffset = clampTo<int>(scrollableArea.scrollOffsetFromPosition({ roundToInt(absoluteScrollXPosition), 0 }).x(), 0, maxScrollOffset.x());
             addOrUpdateStopForSnapOffset(horizontalSnapOffsetsMap, { absoluteScrollOffset, stop, snapAreas.size() - 1 });
         }
         if (snapsVertically) {
-            auto absoluteScrollYPosition = computeScrollSnapAlignOffset(scrollSnapArea.y(), scrollSnapArea.maxY(), yAlign, yAxisFlipped) - computeScrollSnapAlignOffset(scrollSnapPort.y(), scrollSnapPort.maxY(), yAlign, yAxisFlipped);
+            auto absoluteScrollYPosition = computeScrollSnapAlignOffset(scrollSnapArea.y(), scrollSnapArea.maxY(), yAlign, areaYAxisFlipped) - computeScrollSnapAlignOffset(scrollSnapPort.y(), scrollSnapPort.maxY(), yAlign, areaYAxisFlipped);
             auto absoluteScrollOffset = clampTo<int>(scrollableArea.scrollOffsetFromPosition({ 0, roundToInt(absoluteScrollYPosition) }).y(), 0, maxScrollOffset.y());
             addOrUpdateStopForSnapOffset(verticalSnapOffsetsMap, { absoluteScrollOffset, stop, snapAreas.size() - 1 });
         }
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to