Skip to content
Permalink
Browse files
[LFC][IFC] Add right to left direction support for text-overflow: ell…
…ipsis

https://bugs.webkit.org/show_bug.cgi?id=244251

Reviewed by Antti Koivisto.

Compute the ellipsis start position using the display boxes in the reversed direction when the inline content has right to left flow.

* Source/WebCore/layout/formattingContexts/inline/display/InlineDisplayContentBuilder.cpp:
(WebCore::Layout::InlineDisplayContentBuilder::build):
(WebCore::Layout::InlineDisplayContentBuilder::processOverflownRunsForEllipsis):
* Source/WebCore/layout/formattingContexts/inline/display/InlineDisplayContentBuilder.h:

Canonical link: https://commits.webkit.org/253689@main
  • Loading branch information
alanbaradlay committed Aug 23, 2022
1 parent 9269904 commit d20113bd2d4e87c09d6616b1fc3b431c3b2ec2a0
Show file tree
Hide file tree
Showing 2 changed files with 15 additions and 12 deletions.
@@ -104,7 +104,7 @@ DisplayBoxes InlineDisplayContentBuilder::build(const LineBuilder::LineContent&
processBidiContent(lineContent, lineBox, displayLine, boxes);
else
processNonBidiContent(lineContent, lineBox, displayLine, boxes);
processOverflownRunsForEllipsis(lineContent, boxes, displayLine.right());
processOverflownRunsForEllipsis(lineContent, boxes, displayLine);
collectInkOverflowForTextDecorations(boxes, displayLine);
collectInkOverflowForInlineBoxes(boxes);
return boxes;
@@ -756,15 +756,15 @@ void InlineDisplayContentBuilder::processBidiContent(const LineBuilder::LineCont
handleTrailingOpenInlineBoxes();
}

void InlineDisplayContentBuilder::processOverflownRunsForEllipsis(const LineBuilder::LineContent& lineContent, DisplayBoxes& boxes, InlineLayoutUnit lineBoxRight)
void InlineDisplayContentBuilder::processOverflownRunsForEllipsis(const LineBuilder::LineContent& lineContent, DisplayBoxes& boxes, const InlineDisplay::Line& displayLine)
{
if (root().style().textOverflow() != TextOverflow::Ellipsis)
return;
auto& rootInlineBox = boxes[0];
auto isLeftToRightDirection = rootInlineBox.style().isLeftToRightDirection();
ASSERT(rootInlineBox.isRootInlineBox());

if (rootInlineBox.right() <= lineBoxRight) {
ASSERT(boxes.last().right() <= lineBoxRight);
if (displayLine.contentLogicalWidth() <= displayLine.lineBoxRect().width()) {
ASSERT(lineContent.runs.isEmpty() || !lineContent.runs[lineContent.runs.size() - 1].isTruncated());
return;
}
@@ -774,31 +774,34 @@ void InlineDisplayContentBuilder::processOverflownRunsForEllipsis(const LineBuil
auto ellipsisWidth = !m_lineIndex ? root().firstLineStyle().fontCascade().width(ellipsisRun) : root().style().fontCascade().width(ellipsisRun);

auto ellipsisVisualLeft = [&] {
auto truncatedWidth = [&] () -> float {
auto ellipsedContentWidth = [&] () -> float {
for (auto& lineRun : lineContent.runs) {
if (lineRun.isTruncated())
return lineRun.isText() ? lineRun.textContent()->partiallyVisibleContent->width : 0.f;
}
return { };
};
auto left = 0.f;
for (auto& box : boxes) {
auto ellipsisStart = isLeftToRightDirection ? 0.f : displayLine.right();
for (size_t i = 0; i < boxes.size(); ++i) {
auto& box = isLeftToRightDirection ? boxes[i] : boxes[boxes.size() - 1 - i];
if (box.isInlineBox())
continue;
switch (box.isVisuallyHidden()) {
case InlineDisplay::Box::IsVisuallyHidden::No:
left = std::max(left, box.right());
ellipsisStart = isLeftToRightDirection ? std::max(ellipsisStart, box.right()) : std::min(ellipsisStart, box.left());
break;
case InlineDisplay::Box::IsVisuallyHidden::Partially:
return std::max(left, box.left() + truncatedWidth());
ellipsisStart = isLeftToRightDirection ? std::max(ellipsisStart, box.left() + ellipsedContentWidth()) : std::min(ellipsisStart, box.right() - ellipsedContentWidth());
FALLTHROUGH;
case InlineDisplay::Box::IsVisuallyHidden::Yes:
return left;
return isLeftToRightDirection ? ellipsisStart : ellipsisStart - ellipsisWidth;
default:
ASSERT_NOT_REACHED();
break;
}
}
return left;
ASSERT_NOT_REACHED();
return ellipsisStart;
}();
auto ellispisBoxRect = InlineRect { rootInlineBox.top(), ellipsisVisualLeft, ellipsisWidth, rootInlineBox.height() };

@@ -54,7 +54,7 @@ class InlineDisplayContentBuilder {
private:
void processNonBidiContent(const LineBuilder::LineContent&, const LineBox&, const InlineDisplay::Line&, DisplayBoxes&);
void processBidiContent(const LineBuilder::LineContent&, const LineBox&, const InlineDisplay::Line&, DisplayBoxes&);
void processOverflownRunsForEllipsis(const LineBuilder::LineContent&, DisplayBoxes&, InlineLayoutUnit lineBoxRight);
void processOverflownRunsForEllipsis(const LineBuilder::LineContent&, DisplayBoxes&, const InlineDisplay::Line&);
void collectInkOverflowForInlineBoxes(DisplayBoxes&);
void collectInkOverflowForTextDecorations(DisplayBoxes&, const InlineDisplay::Line&);

0 comments on commit d20113b

Please sign in to comment.