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

Changeset 268825 in webkit


Ignore:
Timestamp:
Oct 21, 2020, 2:24:06 PM (6 years ago)
Author:
Alan Bujtas
Message:

[LFC][Integration] Add content dependent vertical line snapping
https://bugs.webkit.org/show_bug.cgi?id=218034

Reviewed by Antti Koivisto.

This patch ensures that IFC integration line snapping matches the legacy line layout snapping behavior (e.g. images prevent line snapping).

  • layout/inlineformatting/InlineLineBox.h:

(WebCore::Layout::LineBox::InlineLevelBox::isAtomicInlineLevelBox const):

  • layout/integration/LayoutIntegrationLineLayout.cpp:

(WebCore::LayoutIntegration::LineLayout::constructContent):

Location:
trunk/Source/WebCore
Files:
3 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebCore/ChangeLog

    r268823 r268825  
     12020-10-21  Zalan Bujtas  <zalan@apple.com>
     2
     3        [LFC][Integration] Add content dependent vertical line snapping
     4        https://bugs.webkit.org/show_bug.cgi?id=218034
     5
     6        Reviewed by Antti Koivisto.
     7
     8        This patch ensures that IFC integration line snapping matches the legacy line layout snapping behavior (e.g. images prevent line snapping).
     9
     10        * layout/inlineformatting/InlineLineBox.h:
     11        (WebCore::Layout::LineBox::InlineLevelBox::isAtomicInlineLevelBox const):
     12        * layout/integration/LayoutIntegrationLineLayout.cpp:
     13        (WebCore::LayoutIntegration::LineLayout::constructContent):
     14
    1152020-10-21  Zalan Bujtas  <zalan@apple.com>
    216
  • trunk/Source/WebCore/layout/inlineformatting/InlineLineBox.h

    r268815 r268825  
    8484
    8585        bool isInlineBox() const { return m_type == Type::InlineBox || m_type == Type::RootInlineBox; }
     86        bool isAtomicInlineLevelBox() const { return m_type == Type::AtomicInlineLevelBox; }
    8687        bool isLineBreakBox() const { return m_type == Type::LineBreakBox; }
    8788        bool hasLineBoxRelativeAlignment() const;
  • trunk/Source/WebCore/layout/integration/LayoutIntegrationLineLayout.cpp

    r268818 r268825  
    139139    auto& displayInlineContent = ensureInlineContent();
    140140
     141    auto lineNeedsLegacyIntegralVerticalPosition = [&](size_t lineIndex) {
     142        RELEASE_ASSERT(m_inlineFormattingState.lineBoxes().size() > lineIndex);
     143        // InlineTree rounds y position to integral value for certain content (see InlineFlowBox::placeBoxesInBlockDirection).
     144        auto inlineLevelBoxList = m_inlineFormattingState.lineBoxes()[lineIndex].inlineLevelBoxList();
     145        if (inlineLevelBoxList.size() == 1) {
     146            // This is text content only with root inline box.
     147            return true;
     148        }
     149        // Text + <br> (or just <br> or text<span></span><br>) behaves like text.
     150        for (auto& inlineLevelBox : inlineLevelBoxList) {
     151            if (inlineLevelBox->isAtomicInlineLevelBox()) {
     152                // Content like text<img> prevents legacy snapping.
     153                return false;
     154            }
     155        }
     156        return true;
     157    };
     158
    141159    auto constructDisplayLineRuns = [&] {
    142160        auto initialContaingBlockSize = m_layoutState.viewportSize();
     161        struct LineLegacyVerticalPositionPolicy {
     162            size_t lineIndex { 0 };
     163            bool needsIntegralPosition { true };
     164        };
     165        auto lineLegacyVerticalPositionPolicy = LineLegacyVerticalPositionPolicy { 0, lineNeedsLegacyIntegralVerticalPosition(0) };
    143166        for (auto& lineRun : m_inlineFormattingState.lineRuns()) {
    144167            auto& layoutBox = lineRun.layoutBox();
     
    165188            auto lineBoxLogicalRect = m_inlineFormattingState.lines()[lineIndex].lineBoxLogicalRect();
    166189            runRect.moveBy({ lineBoxLogicalRect.left(), lineBoxLogicalRect.top() });
    167             // InlineTree rounds y position to integral value, see InlineFlowBox::placeBoxesInBlockDirection.
    168             auto needsLegacyIntegralPosition = !layoutBox.isReplacedBox();
    169             if (needsLegacyIntegralPosition)
     190            if (lineIndex != lineLegacyVerticalPositionPolicy.lineIndex)
     191                lineLegacyVerticalPositionPolicy = LineLegacyVerticalPositionPolicy { lineIndex, lineNeedsLegacyIntegralVerticalPosition(lineIndex) };
     192            if (lineLegacyVerticalPositionPolicy.needsIntegralPosition)
    170193                runRect.setY(roundToInt(runRect.y()));
    171194
     
    216239            // Painting code (specifically TextRun's xPos) needs the line box offset to be able to compute tab positions.
    217240            lineRect.setX(lineBoxLogicalRect.left());
    218             // InlineTree rounds y position to integral value, see InlineFlowBox::placeBoxesInBlockDirection.
    219             lineRect.setY(roundToInt(lineRect.y()));
     241            if (lineNeedsLegacyIntegralVerticalPosition(lineIndex))
     242                lineRect.setY(roundToInt(lineRect.y()));
    220243            displayInlineContent.lines.append({ firstRunIndex, runCount, lineRect, scrollableOverflowRect, lineInkOverflowRect, line.baseline(), line.horizontalAlignmentOffset() });
    221244        }
Note: See TracChangeset for help on using the changeset viewer.