WebKit Bugzilla
Attachment 371557 Details for
Bug 198642
: [LFC][IFC] Line should skip all vertical adjustment when running preferred width computation
Home
|
New
|
Browse
|
Search
|
[?]
|
Reports
|
Requests
|
Help
|
New Account
|
Log In
Remember
[x]
|
Forgot Password
Login:
[x]
[patch]
Patch
bug-198642-20190606214147.patch (text/plain), 30.06 KB, created by
zalan
on 2019-06-06 21:41:50 PDT
(
hide
)
Description:
Patch
Filename:
MIME Type:
Creator:
zalan
Created:
2019-06-06 21:41:50 PDT
Size:
30.06 KB
patch
obsolete
>Subversion Revision: 246158 >diff --git a/Source/WebCore/ChangeLog b/Source/WebCore/ChangeLog >index fa420d57d11524c54507229bb1f0c97461df1ab2..06a56157693cf698c41f012f704e57b3bc7472dd 100644 >--- a/Source/WebCore/ChangeLog >+++ b/Source/WebCore/ChangeLog >@@ -1,3 +1,37 @@ >+2019-06-06 Zalan Bujtas <zalan@apple.com> >+ >+ [LFC][IFC] Line should skip all vertical adjustment when running preferred width computation >+ https://bugs.webkit.org/show_bug.cgi?id=198642 >+ <rdar://problem/51511043> >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ While layout triggers both horizontal and vertical aligment, preferred width computation should only do (logical)horizontal. >+ Make all vertical alignment computation optional in Line. >+ >+ * layout/inlineformatting/InlineFormattingContextLineLayout.cpp: >+ (WebCore::Layout::UncommittedContent::add): >+ (WebCore::Layout::InlineFormattingContext::LineLayout::placeInlineItems const): >+ (WebCore::Layout::InlineFormattingContext::LineLayout::computedIntrinsicWidth const): >+ (WebCore::Layout::InlineFormattingContext::LineLayout::createDisplayRuns const): >+ (WebCore::Layout::inlineItemHeight): Deleted. >+ * layout/inlineformatting/InlineLine.cpp: >+ (WebCore::Layout::Line::Content::Run::Run): >+ (WebCore::Layout::Line::Line): >+ (WebCore::Layout::Line::close): >+ (WebCore::Layout::Line::removeTrailingTrimmableContent): >+ (WebCore::Layout::Line::moveLogicalLeft): >+ (WebCore::Layout::Line::trailingTrimmableWidth const): >+ (WebCore::Layout::Line::appendNonBreakableSpace): >+ (WebCore::Layout::Line::appendInlineContainerStart): >+ (WebCore::Layout::Line::appendInlineContainerEnd): >+ (WebCore::Layout::Line::appendTextContent): >+ (WebCore::Layout::Line::appendNonReplacedInlineBox): >+ (WebCore::Layout::Line::appendReplacedInlineBox): >+ (WebCore::Layout::Line::appendHardLineBreak): >+ (WebCore::Layout::Line::inlineItemHeight const): >+ * layout/inlineformatting/InlineLine.h: >+ > 2019-06-06 Zalan Bujtas <zalan@apple.com> > > [LFC][IFC] Move baseline and line height computation to a dedicated function >diff --git a/Source/WebCore/layout/inlineformatting/InlineFormattingContextLineLayout.cpp b/Source/WebCore/layout/inlineformatting/InlineFormattingContextLineLayout.cpp >index 0b53764256be22a68fa4c65a28666db7f735f481..ee34338318a41bd4b4f74ada089e5c69d624d7e0 100644 >--- a/Source/WebCore/layout/inlineformatting/InlineFormattingContextLineLayout.cpp >+++ b/Source/WebCore/layout/inlineformatting/InlineFormattingContextLineLayout.cpp >@@ -44,10 +44,10 @@ namespace Layout { > struct UncommittedContent { > struct Run { > const InlineItem& inlineItem; >- Line::InlineItemSize size; >+ LayoutUnit logicalWidth; > // FIXME: add optional breaking context (start and end position) for split text content. > }; >- void add(const InlineItem&, const Line::InlineItemSize&); >+ void add(const InlineItem&, LayoutUnit logicalWidth); > void reset(); > > Vector<Run> runs() { return m_uncommittedRuns; } >@@ -60,10 +60,10 @@ private: > LayoutUnit m_width; > }; > >-void UncommittedContent::add(const InlineItem& inlineItem, const Line::InlineItemSize& size) >+void UncommittedContent::add(const InlineItem& inlineItem, LayoutUnit logicalWidth) > { >- m_uncommittedRuns.append({ inlineItem, size }); >- m_width += size.logicalWidth; >+ m_uncommittedRuns.append({ inlineItem, logicalWidth }); >+ m_width += logicalWidth; > } > > void UncommittedContent::reset() >@@ -125,34 +125,15 @@ static LayoutUnit inlineItemWidth(const LayoutState& layoutState, const InlineIt > return displayBox.width(); > } > >-static LayoutUnit inlineItemHeight(const LayoutState& layoutState, const InlineItem& inlineItem) >-{ >- auto& fontMetrics = inlineItem.style().fontMetrics(); >- if (inlineItem.isLineBreak() || is<InlineTextItem>(inlineItem)) >- return fontMetrics.height(); >- >- auto& layoutBox = inlineItem.layoutBox(); >- ASSERT(layoutState.hasDisplayBox(layoutBox)); >- auto& displayBox = layoutState.displayBoxForLayoutBox(layoutBox); >- >- if (layoutBox.isFloatingPositioned()) >- return displayBox.marginBox().height(); >- >- if (layoutBox.isReplaced()) >- return displayBox.height(); >- >- if (inlineItem.isContainerStart() || inlineItem.isContainerEnd()) >- return fontMetrics.height() + displayBox.verticalBorder() + displayBox.verticalPadding().valueOr(0); >- >- // Non-replaced inline box (e.g. inline-block) >- return displayBox.height(); >-} >- > InlineFormattingContext::LineLayout::LineContent InlineFormattingContext::LineLayout::placeInlineItems(const LineInput& lineInput) const > { >- auto mimimumLineHeight = m_formattingRoot.style().computedLineHeight(); >- auto baselineOffset = Line::halfLeadingMetrics(m_formattingRoot.style().fontMetrics(), mimimumLineHeight).height; >- auto line = Line { layoutState(), lineInput.horizontalConstraint.logicalTopLeft, lineInput.horizontalConstraint.availableLogicalWidth, mimimumLineHeight, baselineOffset }; >+ std::unique_ptr<Line> line; >+ if (lineInput.skipVerticalAligment == LineInput::SkipVerticalAligment::No) { >+ auto mimimumLineHeight = m_formattingRoot.style().computedLineHeight(); >+ auto baselineOffset = Line::halfLeadingMetrics(m_formattingRoot.style().fontMetrics(), mimimumLineHeight).height; >+ line = std::make_unique<Line>(layoutState(), lineInput.horizontalConstraint.logicalTopLeft, lineInput.horizontalConstraint.availableLogicalWidth, mimimumLineHeight, baselineOffset); >+ } else >+ line = std::make_unique<Line>(layoutState(), lineInput.horizontalConstraint.logicalTopLeft.x(), lineInput.horizontalConstraint.availableLogicalWidth); > > Vector<WeakPtr<InlineItem>> floats; > unsigned committedInlineItemCount = 0; >@@ -165,17 +146,17 @@ InlineFormattingContext::LineLayout::LineContent InlineFormattingContext::LineLa > for (auto& uncommittedRun : uncommittedContent.runs()) { > auto& inlineItem = uncommittedRun.inlineItem; > if (inlineItem.isHardLineBreak()) >- line.appendHardLineBreak(inlineItem); >+ line->appendHardLineBreak(inlineItem); > else if (is<InlineTextItem>(inlineItem)) >- line.appendTextContent(downcast<InlineTextItem>(inlineItem), uncommittedRun.size); >+ line->appendTextContent(downcast<InlineTextItem>(inlineItem), uncommittedRun.logicalWidth); > else if (inlineItem.isContainerStart()) >- line.appendInlineContainerStart(inlineItem, uncommittedRun.size); >+ line->appendInlineContainerStart(inlineItem, uncommittedRun.logicalWidth); > else if (inlineItem.isContainerEnd()) >- line.appendInlineContainerEnd(inlineItem, uncommittedRun.size); >+ line->appendInlineContainerEnd(inlineItem, uncommittedRun.logicalWidth); > else if (inlineItem.layoutBox().isReplaced()) >- line.appendReplacedInlineBox(inlineItem, uncommittedRun.size); >+ line->appendReplacedInlineBox(inlineItem, uncommittedRun.logicalWidth); > else >- line.appendNonReplacedInlineBox(inlineItem, uncommittedRun.size); >+ line->appendNonReplacedInlineBox(inlineItem, uncommittedRun.logicalWidth); > } > uncommittedContent.reset(); > }; >@@ -183,18 +164,18 @@ InlineFormattingContext::LineLayout::LineContent InlineFormattingContext::LineLa > auto closeLine = [&] { > // This might change at some point. > ASSERT(committedInlineItemCount); >- return LineContent { lineInput.firstInlineItemIndex + (committedInlineItemCount - 1), WTFMove(floats), line.close() }; >+ return LineContent { lineInput.firstInlineItemIndex + (committedInlineItemCount - 1), WTFMove(floats), line->close() }; > }; > LineBreaker lineBreaker; > // Iterate through the inline content and place the inline boxes on the current line. > for (auto inlineItemIndex = lineInput.firstInlineItemIndex; inlineItemIndex < lineInput.inlineItems.size(); ++inlineItemIndex) { >- auto availableWidth = line.availableWidth() - uncommittedContent.width(); >- auto currentLogicalRight = line.contentLogicalRight() + uncommittedContent.width(); >+ auto availableWidth = line->availableWidth() - uncommittedContent.width(); >+ auto currentLogicalRight = line->contentLogicalRight() + uncommittedContent.width(); > auto& inlineItem = lineInput.inlineItems[inlineItemIndex]; > auto itemLogicalWidth = inlineItemWidth(layoutState(), *inlineItem, currentLogicalRight); > > // FIXME: Ensure LineContext::trimmableWidth includes uncommitted content if needed. >- auto breakingContext = lineBreaker.breakingContext(*inlineItem, itemLogicalWidth, { availableWidth, currentLogicalRight, line.trailingTrimmableWidth(), !line.hasContent() }); >+ auto breakingContext = lineBreaker.breakingContext(*inlineItem, itemLogicalWidth, { availableWidth, currentLogicalRight, line->trailingTrimmableWidth(), !line->hasContent() }); > if (breakingContext.isAtBreakingOpportunity) > commitPendingContent(); > >@@ -216,17 +197,13 @@ InlineFormattingContext::LineLayout::LineContent InlineFormattingContext::LineLa > ASSERT(layoutState().hasDisplayBox(floatBox)); > // Shrink availble space for current line and move existing inline runs. > auto floatBoxWidth = layoutState().displayBoxForLayoutBox(floatBox).marginBoxWidth(); >- floatBox.isLeftFloatingPositioned() ? line.moveLogicalLeft(floatBoxWidth) : line.moveLogicalRight(floatBoxWidth); >+ floatBox.isLeftFloatingPositioned() ? line->moveLogicalLeft(floatBoxWidth) : line->moveLogicalRight(floatBoxWidth); > floats.append(makeWeakPtr(*inlineItem)); > ++committedInlineItemCount; > continue; > } > >- Optional<LayoutUnit> itemLogicalHeight; >- if (lineInput.skipVerticalAligment == LineInput::SkipVerticalAligment::No) >- itemLogicalHeight = inlineItemHeight(layoutState(), *inlineItem); >- uncommittedContent.add(*inlineItem, { itemLogicalWidth, itemLogicalHeight }); >- >+ uncommittedContent.add(*inlineItem, itemLogicalWidth); > if (breakingContext.isAtBreakingOpportunity) > commitPendingContent(); > >@@ -341,33 +318,33 @@ void InlineFormattingContext::LineLayout::createDisplayRuns(const Line::Content& > auto& lineRun = lineRuns.at(index); > > auto& inlineItem = lineRun->inlineItem; >- auto& inlineRun = lineRun->inlineRun; >+ auto& logicalRect = lineRun->logicalRect; > auto& layoutBox = inlineItem.layoutBox(); > auto& displayBox = layoutState().displayBoxForLayoutBox(layoutBox); > > if (inlineItem.isHardLineBreak()) { >- displayBox.setTopLeft(inlineRun.logicalTopLeft()); >- displayBox.setContentBoxWidth(inlineRun.logicalWidth()); >- displayBox.setContentBoxHeight(inlineRun.logicalHeight()); >- m_formattingState.addInlineRun(std::make_unique<Display::Run>(inlineRun)); >+ displayBox.setTopLeft(logicalRect.topLeft()); >+ displayBox.setContentBoxWidth(logicalRect.width()); >+ displayBox.setContentBoxHeight(logicalRect.height()); >+ m_formattingState.addInlineRun(std::make_unique<Display::Run>(logicalRect)); > continue; > } > > // Inline level box (replaced or inline-block) > if (inlineItem.isBox()) { >- auto topLeft = inlineRun.logicalTopLeft(); >+ auto topLeft = logicalRect.topLeft(); > if (layoutBox.isInFlowPositioned()) > topLeft += Geometry::inFlowPositionedPositionOffset(layoutState(), layoutBox); > displayBox.setTopLeft(topLeft); >- lineBox.expandHorizontally(inlineRun.logicalWidth()); >- m_formattingState.addInlineRun(std::make_unique<Display::Run>(inlineRun)); >+ lineBox.expandHorizontally(logicalRect.width()); >+ m_formattingState.addInlineRun(std::make_unique<Display::Run>(logicalRect)); > continue; > } > > // Inline level container start (<span>) > if (inlineItem.isContainerStart()) { >- displayBox.setTopLeft(inlineRun.logicalTopLeft()); >- lineBox.expandHorizontally(inlineRun.logicalWidth()); >+ displayBox.setTopLeft(logicalRect.topLeft()); >+ lineBox.expandHorizontally(logicalRect.width()); > continue; > } > >@@ -378,40 +355,40 @@ void InlineFormattingContext::LineLayout::createDisplayRuns(const Line::Content& > displayBox.moveHorizontally(inflowOffset.width()); > displayBox.moveVertically(inflowOffset.height()); > } >- auto marginBoxWidth = inlineRun.logicalLeft() - displayBox.left(); >+ auto marginBoxWidth = logicalRect.left() - displayBox.left(); > auto contentBoxWidth = marginBoxWidth - (displayBox.marginStart() + displayBox.borderLeft() + displayBox.paddingLeft().valueOr(0)); > // FIXME fix it for multiline. > displayBox.setContentBoxWidth(contentBoxWidth); >- displayBox.setContentBoxHeight(inlineRun.logicalHeight()); >- lineBox.expandHorizontally(inlineRun.logicalWidth()); >+ displayBox.setContentBoxHeight(logicalRect.height()); >+ lineBox.expandHorizontally(logicalRect.width()); > continue; > } > > // Text content. Try to join multiple text runs when possible. >- ASSERT(inlineRun.textContext()); >+ ASSERT(lineRun->textContext); > const Line::Content::Run* previousLineRun = !index ? nullptr : lineRuns[index - 1].get(); > if (!lineRun->isCollapsed) { > auto previousRunCanBeExtended = previousLineRun ? previousLineRun->canBeExtended : false; > auto requiresNewRun = !index || !previousRunCanBeExtended || &layoutBox != &previousLineRun->inlineItem.layoutBox(); > if (requiresNewRun) >- m_formattingState.addInlineRun(std::make_unique<Display::Run>(inlineRun)); >+ m_formattingState.addInlineRun(std::make_unique<Display::Run>(logicalRect, Display::Run::TextContext { lineRun->textContext->start, lineRun->textContext->length })); > else { > auto& lastDisplayRun = m_formattingState.inlineRuns().last(); >- lastDisplayRun->expandHorizontally(inlineRun.logicalWidth()); >- lastDisplayRun->textContext()->expand(inlineRun.textContext()->length()); >+ lastDisplayRun->expandHorizontally(logicalRect.width()); >+ lastDisplayRun->textContext()->expand(lineRun->textContext->length); > } >- lineBox.expandHorizontally(inlineRun.logicalWidth()); >+ lineBox.expandHorizontally(logicalRect.width()); > } > // FIXME take content breaking into account when part of the layout box is on the previous line. > auto firstInlineRunForLayoutBox = !previousLineRun || &previousLineRun->inlineItem.layoutBox() != &layoutBox; > if (firstInlineRunForLayoutBox) { > // Setup display box for the associated layout box. >- displayBox.setTopLeft(inlineRun.logicalTopLeft()); >- displayBox.setContentBoxWidth(lineRun->isCollapsed ? LayoutUnit() : inlineRun.logicalWidth()); >- displayBox.setContentBoxHeight(inlineRun.logicalHeight()); >+ displayBox.setTopLeft(logicalRect.topLeft()); >+ displayBox.setContentBoxWidth(lineRun->isCollapsed ? LayoutUnit() : logicalRect.width()); >+ displayBox.setContentBoxHeight(logicalRect.height()); > } else if (!lineRun->isCollapsed) { > // FIXME fix it for multirun/multiline. >- displayBox.setContentBoxWidth(displayBox.contentBoxWidth() + inlineRun.logicalWidth()); >+ displayBox.setContentBoxWidth(displayBox.contentBoxWidth() + logicalRect.width()); > } > } > // FIXME linebox needs to be ajusted after content alignment. >diff --git a/Source/WebCore/layout/inlineformatting/InlineLine.cpp b/Source/WebCore/layout/inlineformatting/InlineLine.cpp >index 1a4ec258da542a2c19df289c8224d16e1bffdddf..544ec177138fad7e2a112f361b1c6fdf4cc2c487 100644 >--- a/Source/WebCore/layout/inlineformatting/InlineLine.cpp >+++ b/Source/WebCore/layout/inlineformatting/InlineLine.cpp >@@ -47,14 +47,24 @@ bool Line::Content::isVisuallyEmpty() const > return true; > } > >-Line::Content::Run::Run(Display::Run inlineRun, const InlineItem& inlineItem, bool isCollapsed, bool canBeExtended) >- : inlineRun(inlineRun) >- , inlineItem(inlineItem) >+Line::Content::Run::Run(const InlineItem& inlineItem, const Display::Rect& logicalRect, TextContext textContext, bool isCollapsed, bool canBeExtended) >+ : inlineItem(inlineItem) >+ , logicalRect(logicalRect) >+ , textContext(textContext) > , isCollapsed(isCollapsed) > , canBeExtended(canBeExtended) > { > } > >+Line::Line(const LayoutState& layoutState, LayoutUnit logicalLeft, LayoutUnit availableWidth) >+ : m_layoutState(layoutState) >+ , m_content(std::make_unique<Line::Content>()) >+ , m_logicalTopLeft(logicalLeft, 0) >+ , m_lineLogicalWidth(availableWidth) >+ , m_skipVerticalAligment(true) >+{ >+} >+ > Line::Line(const LayoutState& layoutState, const LayoutPoint& topLeft, LayoutUnit availableWidth, LayoutUnit minimumHeight, LayoutUnit baselineOffset) > : m_layoutState(layoutState) > , m_content(std::make_unique<Line::Content>()) >@@ -67,10 +77,12 @@ Line::Line(const LayoutState& layoutState, const LayoutPoint& topLeft, LayoutUni > std::unique_ptr<Line::Content> Line::close() > { > removeTrailingTrimmableContent(); >- // Convert inline run geometry from relative to the baseline to relative to logical top. >- for (auto& run : m_content->runs()) { >- auto adjustedLogicalTop = run->inlineRun.logicalTop() + m_logicalHeight.height + m_logicalTopLeft.y(); >- run->inlineRun.setLogicalTop(adjustedLogicalTop); >+ if (!m_skipVerticalAligment) { >+ // Convert inline run geometry from relative to the baseline to relative to logical top. >+ for (auto& run : m_content->runs()) { >+ auto adjustedLogicalTop = run->logicalRect.top() + m_logicalHeight.height + m_logicalTopLeft.y(); >+ run->logicalRect.setTop(adjustedLogicalTop); >+ } > } > m_content->setLogicalRect({ logicalTop(), logicalLeft(), contentLogicalWidth(), logicalHeight() }); > return WTFMove(m_content); >@@ -82,7 +94,7 @@ void Line::removeTrailingTrimmableContent() > LayoutUnit trimmableWidth; > for (auto* trimmableRun : m_trimmableContent) { > trimmableRun->isCollapsed = true; >- trimmableWidth += trimmableRun->inlineRun.logicalWidth(); >+ trimmableWidth += trimmableRun->logicalRect.width(); > } > m_contentLogicalWidth -= trimmableWidth; > } >@@ -96,7 +108,7 @@ void Line::moveLogicalLeft(LayoutUnit delta) > m_logicalTopLeft.move(delta, 0); > m_lineLogicalWidth -= delta; > for (auto& run : m_content->runs()) >- run->inlineRun.moveHorizontally(delta); >+ run->logicalRect.moveHorizontally(delta); > } > > void Line::moveLogicalRight(LayoutUnit delta) >@@ -109,38 +121,42 @@ LayoutUnit Line::trailingTrimmableWidth() const > { > LayoutUnit trimmableWidth; > for (auto* trimmableRun : m_trimmableContent) >- trimmableWidth += trimmableRun->inlineRun.logicalWidth(); >+ trimmableWidth += trimmableRun->logicalRect.width(); > return trimmableWidth; > } > > void Line::appendNonBreakableSpace(const InlineItem& inlineItem, const Display::Rect& logicalRect) > { >- m_content->runs().append(std::make_unique<Content::Run>(Display::Run { logicalRect }, inlineItem, false, false)); >+ m_content->runs().append(std::make_unique<Content::Run>(inlineItem, logicalRect, Content::Run::TextContext { }, false, false)); > m_contentLogicalWidth += logicalRect.width(); > } > >-void Line::appendInlineContainerStart(const InlineItem& inlineItem, InlineItemSize runSize) >+void Line::appendInlineContainerStart(const InlineItem& inlineItem, LayoutUnit logicalWidth) > { >- if (runSize.logicalHeight) >- adjustBaselineAndLineHeight(inlineItem, *runSize.logicalHeight); >- >- auto& layoutBox = inlineItem.layoutBox(); >- auto& fontMetrics = layoutBox.style().fontMetrics(); >- auto& displayBox = m_layoutState.displayBoxForLayoutBox(layoutBox); >- >- auto logicalTop = -fontMetrics.ascent() - displayBox.borderTop() - displayBox.paddingTop().valueOr(0); >- auto logicalRect = Display::Rect { logicalTop, contentLogicalRight(), runSize.logicalWidth, runSize.logicalHeight.valueOr(0) }; >+ auto logicalRect = Display::Rect { }; >+ logicalRect.setLeft(contentLogicalRight()); >+ logicalRect.setWidth(logicalWidth); >+ >+ if (!m_skipVerticalAligment) { >+ auto logicalHeight = inlineItemHeight(inlineItem); >+ adjustBaselineAndLineHeight(inlineItem, logicalHeight); >+ >+ auto& displayBox = m_layoutState.displayBoxForLayoutBox(inlineItem.layoutBox()); >+ auto logicalTop = -inlineItem.style().fontMetrics().ascent() - displayBox.borderTop() - displayBox.paddingTop().valueOr(0); >+ logicalRect.setTop(logicalTop); >+ logicalRect.setHeight(logicalHeight); >+ } > appendNonBreakableSpace(inlineItem, logicalRect); > } > >-void Line::appendInlineContainerEnd(const InlineItem& inlineItem, InlineItemSize runSize) >+void Line::appendInlineContainerEnd(const InlineItem& inlineItem, LayoutUnit logicalWidth) > { > // This is really just a placeholder to mark the end of the inline level container. >- auto logicalRect = Display::Rect { 0, contentLogicalRight(), runSize.logicalWidth, runSize.logicalHeight.valueOr(0) }; >+ auto logicalRect = Display::Rect { 0, contentLogicalRight(), logicalWidth, 0 }; > appendNonBreakableSpace(inlineItem, logicalRect); > } > >-void Line::appendTextContent(const InlineTextItem& inlineItem, InlineItemSize runSize) >+void Line::appendTextContent(const InlineTextItem& inlineItem, LayoutUnit logicalWidth) > { > auto isTrimmable = TextUtil::isTrimmableContent(inlineItem); > if (!isTrimmable) >@@ -168,45 +184,56 @@ void Line::appendTextContent(const InlineTextItem& inlineItem, InlineItemSize ru > // Collapsed line items don't contribute to the line width. > auto isCompletelyCollapsed = shouldCollapseCompletely(); > auto canBeExtended = !isCompletelyCollapsed && !inlineItem.isCollapsed(); >- auto logicalRect = Display::Rect { -inlineItem.style().fontMetrics().ascent(), contentLogicalRight(), runSize.logicalWidth, runSize.logicalHeight.valueOr(0) }; >- auto textContext = Display::Run::TextContext { inlineItem.start(), inlineItem.isCollapsed() ? 1 : inlineItem.length() }; >- auto displayRun = Display::Run(logicalRect, textContext); >+ >+ auto logicalRect = Display::Rect { }; >+ logicalRect.setLeft(contentLogicalRight()); >+ logicalRect.setWidth(logicalWidth); >+ if (!m_skipVerticalAligment) { >+ logicalRect.setTop(-inlineItem.style().fontMetrics().ascent()); >+ logicalRect.setHeight(inlineItemHeight(inlineItem)); >+ } > >- auto lineItem = std::make_unique<Content::Run>(displayRun, inlineItem, isCompletelyCollapsed, canBeExtended); >+ auto textContext = Content::Run::TextContext { inlineItem.start(), inlineItem.isCollapsed() ? 1 : inlineItem.length() }; >+ auto lineItem = std::make_unique<Content::Run>(inlineItem, logicalRect, textContext, isCompletelyCollapsed, canBeExtended); > if (isTrimmable) > m_trimmableContent.add(lineItem.get()); > > m_content->runs().append(WTFMove(lineItem)); >- m_contentLogicalWidth += isCompletelyCollapsed ? LayoutUnit() : runSize.logicalWidth; >+ m_contentLogicalWidth += isCompletelyCollapsed ? LayoutUnit() : logicalWidth; > } > >-void Line::appendNonReplacedInlineBox(const InlineItem& inlineItem, InlineItemSize runSize) >+void Line::appendNonReplacedInlineBox(const InlineItem& inlineItem, LayoutUnit logicalWidth) > { >- if (runSize.logicalHeight) >- adjustBaselineAndLineHeight(inlineItem, *runSize.logicalHeight); >- >- auto inlineBoxHeight = runSize.logicalHeight.valueOr(0); > auto& displayBox = m_layoutState.displayBoxForLayoutBox(inlineItem.layoutBox()); >- auto logicalTop = -inlineBoxHeight; >- auto horizontalMargin = displayBox.horizontalMargin(); >- auto logicalRect = Display::Rect { logicalTop, contentLogicalRight() + horizontalMargin.start, runSize.logicalWidth, inlineBoxHeight }; >+ auto horizontalMargin = displayBox.horizontalMargin(); >+ auto logicalRect = Display::Rect { }; > >- m_content->runs().append(std::make_unique<Content::Run>(Display::Run { logicalRect }, inlineItem, false, false)); >- m_contentLogicalWidth += (runSize.logicalWidth + horizontalMargin.start + horizontalMargin.end); >+ logicalRect.setLeft(contentLogicalRight() + horizontalMargin.start); >+ logicalRect.setWidth(logicalWidth); >+ if (!m_skipVerticalAligment) { >+ auto logicalHeight = inlineItemHeight(inlineItem); >+ adjustBaselineAndLineHeight(inlineItem, logicalHeight); >+ >+ logicalRect.setTop(-logicalHeight); >+ logicalRect.setHeight(logicalHeight); >+ } >+ >+ m_content->runs().append(std::make_unique<Content::Run>(inlineItem, logicalRect, Content::Run::TextContext { }, false, false)); >+ m_contentLogicalWidth += (logicalWidth + horizontalMargin.start + horizontalMargin.end); > m_trimmableContent.clear(); > } > >-void Line::appendReplacedInlineBox(const InlineItem& inlineItem, InlineItemSize runSize) >+void Line::appendReplacedInlineBox(const InlineItem& inlineItem, LayoutUnit logicalWidth) > { > // FIXME Surely replaced boxes behave differently. >- appendNonReplacedInlineBox(inlineItem, runSize); >+ appendNonReplacedInlineBox(inlineItem, logicalWidth); > } > > void Line::appendHardLineBreak(const InlineItem& inlineItem) > { > auto ascent = inlineItem.layoutBox().style().fontMetrics().ascent(); > auto logicalRect = Display::Rect { -ascent, contentLogicalRight(), { }, logicalHeight() }; >- m_content->runs().append(std::make_unique<Content::Run>(Display::Run { logicalRect }, inlineItem, false, false)); >+ m_content->runs().append(std::make_unique<Content::Run>(inlineItem, logicalRect, Content::Run::TextContext { }, false, false)); > } > > void Line::adjustBaselineAndLineHeight(const InlineItem& inlineItem, LayoutUnit runHeight) >@@ -239,6 +266,30 @@ void Line::adjustBaselineAndLineHeight(const InlineItem& inlineItem, LayoutUnit > m_logicalHeight.height = std::max(runHeight, m_logicalHeight.height); > } > >+LayoutUnit Line::inlineItemHeight(const InlineItem& inlineItem) const >+{ >+ ASSERT(!m_skipVerticalAligment); >+ auto& fontMetrics = inlineItem.style().fontMetrics(); >+ if (inlineItem.isLineBreak() || is<InlineTextItem>(inlineItem)) >+ return fontMetrics.height(); >+ >+ auto& layoutBox = inlineItem.layoutBox(); >+ ASSERT(m_layoutState.hasDisplayBox(layoutBox)); >+ auto& displayBox = m_layoutState.displayBoxForLayoutBox(layoutBox); >+ >+ if (layoutBox.isFloatingPositioned()) >+ return displayBox.marginBox().height(); >+ >+ if (layoutBox.isReplaced()) >+ return displayBox.height(); >+ >+ if (inlineItem.isContainerStart() || inlineItem.isContainerEnd()) >+ return fontMetrics.height() + displayBox.verticalBorder() + displayBox.verticalPadding().valueOr(0); >+ >+ // Non-replaced inline box (e.g. inline-block) >+ return displayBox.height(); >+} >+ > Line::UsedHeightAndDepth Line::halfLeadingMetrics(const FontMetrics& fontMetrics, LayoutUnit lineLogicalHeight) > { > auto ascent = fontMetrics.ascent(); >diff --git a/Source/WebCore/layout/inlineformatting/InlineLine.h b/Source/WebCore/layout/inlineformatting/InlineLine.h >index 82db84f9ba9a9d7a1319385f6e9d7d0014150fe8..b4a28c1d09e77d2a5e240b56b19bf0c440b92335 100644 >--- a/Source/WebCore/layout/inlineformatting/InlineLine.h >+++ b/Source/WebCore/layout/inlineformatting/InlineLine.h >@@ -39,15 +39,21 @@ class Line { > WTF_MAKE_ISO_ALLOCATED(Line); > public: > Line(const LayoutState&, const LayoutPoint& topLeft, LayoutUnit availableWidth, LayoutUnit minimumLineHeight, LayoutUnit baselineOffset); >+ Line(const LayoutState&, LayoutUnit logicalLeft, LayoutUnit availableWidth); > > class Content { > public: > struct Run { >- Run(Display::Run, const InlineItem&, bool isCollapsed, bool canBeExtended); >+ struct TextContext { >+ unsigned start { 0 }; >+ unsigned length { 0 }; >+ }; >+ Run(const InlineItem&, const Display::Rect&, TextContext, bool isCollapsed, bool canBeExtended); > >- // Relative to the baseline. >- Display::Run inlineRun; > const InlineItem& inlineItem; >+ // Relative to the baseline. >+ Display::Rect logicalRect; >+ Optional<TextContext> textContext; > bool isCollapsed { false }; > bool canBeExtended { false }; > }; >@@ -75,15 +81,11 @@ public: > }; > std::unique_ptr<Content> close(); > >- struct InlineItemSize { >- LayoutUnit logicalWidth; >- Optional<LayoutUnit> logicalHeight; >- }; >- void appendTextContent(const InlineTextItem&, InlineItemSize); >- void appendNonReplacedInlineBox(const InlineItem&, InlineItemSize); >- void appendReplacedInlineBox(const InlineItem&, InlineItemSize); >- void appendInlineContainerStart(const InlineItem&, InlineItemSize); >- void appendInlineContainerEnd(const InlineItem&, InlineItemSize); >+ void appendTextContent(const InlineTextItem&, LayoutUnit logicalWidth); >+ void appendNonReplacedInlineBox(const InlineItem&, LayoutUnit logicalWidth); >+ void appendReplacedInlineBox(const InlineItem&, LayoutUnit logicalWidth); >+ void appendInlineContainerStart(const InlineItem&, LayoutUnit logicalWidth); >+ void appendInlineContainerEnd(const InlineItem&, LayoutUnit logicalWidth); > void appendHardLineBreak(const InlineItem&); > > bool hasContent() const { return !m_content->isVisuallyEmpty(); } >@@ -117,6 +119,7 @@ private: > void removeTrailingTrimmableContent(); > > void adjustBaselineAndLineHeight(const InlineItem&, LayoutUnit runHeight); >+ LayoutUnit inlineItemHeight(const InlineItem&) const; > > const LayoutState& m_layoutState; > std::unique_ptr<Content> m_content; >@@ -127,6 +130,7 @@ private: > > UsedHeightAndDepth m_logicalHeight; > LayoutUnit m_lineLogicalWidth; >+ bool m_skipVerticalAligment { false }; > }; > > }
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Formatted Diff
|
Diff
Attachments on
bug 198642
: 371557