⚠ Archived content — this site is no longer maintained.   Current WebKit documentation is at docs.webkit.org.

Changeset 267700 in webkit


Ignore:
Timestamp:
Sep 28, 2020, 8:00:14 AM (6 years ago)
Author:
Alan Bujtas
Message:

[LFC][Floats] Add support for clear on float box
https://bugs.webkit.org/show_bug.cgi?id=217045

Reviewed by Antti Koivisto.

Source/WebCore:

When the float box also has to clear other floats, we need to adjust the initial
vertical position from where we start searching for available space.
(This patch also fixes a previous find&replace renaming and addresses a post-landing comment.)

Test: fast/layoutformattingcontext/float-with-clear-simple.html

  • layout/floats/FloatingContext.cpp:

(WebCore::Layout::FloatingContext::positionForFloat const):
(WebCore::Layout::FloatingContext::positionForNonFloatingFloatAvoider const):
(WebCore::Layout::FloatingContext::absoluteCoordinates const):
(WebCore::Layout::FloatingContext::absoluteBoxGeometryCoordinates const): Deleted.

  • layout/floats/FloatingContext.h:

LayoutTests:

  • fast/layoutformattingcontext/float-with-clear-simple-expected.html: Added.
  • fast/layoutformattingcontext/float-with-clear-simple.html: Added.
Location:
trunk
Files:
2 added
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/LayoutTests/ChangeLog

    r267696 r267700  
     12020-09-28  Zalan Bujtas  <zalan@apple.com>
     2
     3        [LFC][Floats] Add support for clear on float box
     4        https://bugs.webkit.org/show_bug.cgi?id=217045
     5
     6        Reviewed by Antti Koivisto.
     7
     8        * fast/layoutformattingcontext/float-with-clear-simple-expected.html: Added.
     9        * fast/layoutformattingcontext/float-with-clear-simple.html: Added.
     10
    1112020-09-28  Angelos Oikonomopoulos  <angelos@igalia.com>
    212
  • trunk/Source/WebCore/ChangeLog

    r267699 r267700  
     12020-09-28  Zalan Bujtas  <zalan@apple.com>
     2
     3        [LFC][Floats] Add support for clear on float box
     4        https://bugs.webkit.org/show_bug.cgi?id=217045
     5
     6        Reviewed by Antti Koivisto.
     7
     8        When the float box also has to clear other floats, we need to adjust the initial
     9        vertical position from where we start searching for available space.
     10        (This patch also fixes a previous find&replace renaming and addresses a post-landing comment.)
     11
     12        Test: fast/layoutformattingcontext/float-with-clear-simple.html
     13
     14        * layout/floats/FloatingContext.cpp:
     15        (WebCore::Layout::FloatingContext::positionForFloat const):
     16        (WebCore::Layout::FloatingContext::positionForNonFloatingFloatAvoider const):
     17        (WebCore::Layout::FloatingContext::absoluteCoordinates const):
     18        (WebCore::Layout::FloatingContext::absoluteBoxGeometryCoordinates const): Deleted.
     19        * layout/floats/FloatingContext.h:
     20
    1212020-09-28  Aditya Keerthi  <akeerthi@apple.com>
    222
  • trunk/Source/WebCore/layout/FormattingState.cpp

    r267657 r267700  
    5353    // Should never need to mutate a display box outside of the formatting context.
    5454    ASSERT(&layoutState().establishedFormattingState(layoutBox.formattingContextRoot()) == this);
    55     // Anonymous text wrappers do not need display boxes.
     55    // Anonymous text wrappers do not need to compute box geometry. They initiate inline runs.
    5656    ASSERT(!layoutBox.isInlineTextBox());
    5757    return layoutState().ensureGeometryForBox(layoutBox);
  • trunk/Source/WebCore/layout/floats/FloatingContext.cpp

    r267158 r267700  
    228228    if (isEmpty()) {
    229229        auto& boxGeometry = formattingContext().geometryForBox(layoutBox);
    230 
    231230        auto alignWithContainingBlock = [&]() -> Position {
    232231            // If there is no floating to align with, push the box to the left/right edge of its containing block's content box.
    233232            if (layoutBox.isLeftFloatingPositioned())
    234233                return { horizontalConstraints.logicalLeft + boxGeometry.marginStart() };
    235 
    236234            return { horizontalConstraints.logicalRight() - boxGeometry.marginEnd() - boxGeometry.logicalWidth() };
    237235        };
    238 
    239236        // No float box on the context yet -> align it with the containing block's left/right edge.
    240237        return { alignWithContainingBlock(), boxGeometry.logicalTop() };
     
    243240    // Find the top most position where the float box fits.
    244241    ASSERT(!isEmpty());
    245     auto previousFloatAbsoluteTop = floatingState().floats().last().rectWithMargin().top();
    246     auto absoluteBoxGeometryCoordinates = this->absoluteBoxGeometryCoordinates(layoutBox);
    247     auto absoluteTopLeft = absoluteBoxGeometryCoordinates.topLeft;
    248     // Incoming float cannot be placed higher than existing floats (margin box of the last float).
    249     // Take the static position (where the box would go if it wasn't floating) and adjust it with the last float.
     242    auto absoluteCoordinates = this->absoluteCoordinates(layoutBox);
     243    auto absoluteTopLeft = absoluteCoordinates.topLeft;
     244    auto verticalPositionCandidate = absoluteTopLeft.y();
     245
    250246    auto& boxGeometry = formattingContext().geometryForBox(layoutBox);
    251     if (absoluteTopLeft.y() - boxGeometry.marginBefore() < previousFloatAbsoluteTop)
    252         absoluteTopLeft.setY(previousFloatAbsoluteTop + boxGeometry.marginBefore());
     247    if (layoutBox.hasFloatClear()) {
     248        // The vertical position candidate needs to clear the existing floats in this context.
     249        auto floatBottom = [&]() -> Optional<PositionInContextRoot> {
     250            switch (layoutBox.style().clear()) {
     251            case Clear::Left:
     252                return floatingState().leftBottom(root());
     253            case Clear::Right:
     254                return floatingState().rightBottom(root());
     255            case Clear::Both:
     256                return floatingState().bottom(root());
     257            default:
     258                ASSERT_NOT_REACHED();
     259            }
     260            return { };
     261        };
     262        if (auto bottomWithClear = floatBottom())
     263            verticalPositionCandidate = *bottomWithClear + boxGeometry.marginBefore();
     264    } else {
     265        // Incoming float cannot be placed higher than existing floats (margin box of the last float).
     266        // Take the static position (where the box would go if it wasn't floating) and adjust it with the last float.
     267        auto previousFloatAbsoluteTop = floatingState().floats().last().rectWithMargin().top();
     268        if (verticalPositionCandidate - boxGeometry.marginBefore() < previousFloatAbsoluteTop)
     269            verticalPositionCandidate = previousFloatAbsoluteTop + boxGeometry.marginBefore();
     270    }
     271    absoluteTopLeft.setY(verticalPositionCandidate);
    253272    auto horizontalMargin = computedHorizontalMargin(layoutBox, horizontalConstraints.logicalWidth);
    254273    auto margins = Edges { { *horizontalMargin.start, *horizontalMargin.end }, { boxGeometry.marginBefore(), boxGeometry.marginAfter() } };
    255     auto floatBox = FloatAvoider { layoutBox, absoluteTopLeft, boxGeometry.logicalWidth(), margins, absoluteBoxGeometryCoordinates.containingBlockContentBox };
     274    auto floatBox = FloatAvoider { layoutBox, absoluteTopLeft, boxGeometry.logicalWidth(), margins, absoluteCoordinates.containingBlockContentBox };
    256275    findAvailablePosition(floatBox, m_floatingState.floats());
    257     // From formatting root coordinate system back to containing block's.
    258     auto containingBlockTopLeft = absoluteBoxGeometryCoordinates.containingBlockTopLeft;
     276    // Convert box coordinates from formatting root back to containing block.
     277    auto containingBlockTopLeft = absoluteCoordinates.containingBlockTopLeft;
    259278    return { floatBox.left() + margins.horizontal.left - containingBlockTopLeft.x(), floatBox.top() + margins.vertical.top - containingBlockTopLeft.y() };
    260279}
     
    270289        return formattingContext().geometryForBox(layoutBox).logicalTopLeft();
    271290
    272     auto absoluteBoxGeometryCoordinates = this->absoluteBoxGeometryCoordinates(layoutBox);
     291    auto absoluteCoordinates = this->absoluteCoordinates(layoutBox);
    273292    auto& boxGeometry = formattingContext().geometryForBox(layoutBox);
    274293    auto horizontalMargin = computedHorizontalMargin(layoutBox, horizontalConstraints.logicalWidth);
    275294    auto margins = Edges { { *horizontalMargin.start, *horizontalMargin.end }, { boxGeometry.marginBefore(), boxGeometry.marginAfter() } };
    276     auto floatAvoider = FloatAvoider { layoutBox, absoluteBoxGeometryCoordinates.topLeft, boxGeometry.logicalWidth(), margins, absoluteBoxGeometryCoordinates.containingBlockContentBox };
     295    auto floatAvoider = FloatAvoider { layoutBox, absoluteCoordinates.topLeft, boxGeometry.logicalWidth(), margins, absoluteCoordinates.containingBlockContentBox };
    277296    findPositionForFormattingContextRoot(floatAvoider);
    278     auto containingBlockTopLeft = absoluteBoxGeometryCoordinates.containingBlockTopLeft;
     297    auto containingBlockTopLeft = absoluteCoordinates.containingBlockTopLeft;
    279298    return { floatAvoider.left() - containingBlockTopLeft.x(), floatAvoider.top() - containingBlockTopLeft.y() };
    280299}
     
    456475}
    457476
    458 FloatingContext::AbsoluteCoordinateValuesForFloatAvoider FloatingContext::absoluteBoxGeometryCoordinates(const Box& floatAvoider) const
     477FloatingContext::AbsoluteCoordinateValuesForFloatAvoider FloatingContext::absoluteCoordinates(const Box& floatAvoider) const
    459478{
    460479    auto& containingBlock = floatAvoider.containingBlock();
  • trunk/Source/WebCore/layout/floats/FloatingContext.h

    r267076 r267700  
    7575
    7676    struct AbsoluteCoordinateValuesForFloatAvoider;
    77     AbsoluteCoordinateValuesForFloatAvoider absoluteBoxGeometryCoordinates(const Box&) const;
     77    AbsoluteCoordinateValuesForFloatAvoider absoluteCoordinates(const Box&) const;
    7878    LayoutPoint mapTopLeftToFloatingStateRoot(const Box&) const;
    7979    Point mapPointFromFormattingContextRootToFloatingStateRoot(Point) const;
Note: See TracChangeset for help on using the changeset viewer.