LibWeb: Avoid text-aligning content that is too long for its line box

Previously, we would always respect the `text-align` property, even if
the text being aligned was too long for its line box and would be
clipped. This led to seeing the clipped middle/end of strings when we
should instead always see the beginning of the text.
This commit is contained in:
FalseHonesty 2023-06-01 20:42:41 -04:00 committed by Andreas Kling
parent 54fb9477a4
commit de9604212f
Notes: sideshowbarker 2024-07-16 23:34:44 +09:00
3 changed files with 38 additions and 12 deletions

View file

@ -0,0 +1,9 @@
Viewport <#document> at (0,0) content-size 800x600 children: not-inline
BlockContainer <html> at (0,0) content-size 800x33.46875 [BFC] children: not-inline
BlockContainer <body> at (8,8) content-size 784x17.46875 children: not-inline
BlockContainer <div.outer> at (18,8) content-size 80x17.46875 children: not-inline
BlockContainer <span.text> at (18,8) content-size 80x17.46875 [BFC] children: inline
line 0 width: 189.875, height: 17.46875, bottom: 17.46875, baseline: 13.53125
frag 0 from TextNode start: 0, length: 22, rect: [18,8 189.875x17.46875]
"My super long message!"
TextNode <#text>

View file

@ -0,0 +1,13 @@
<!DOCTYPE html><style>
.outer {
margin-left: 10px;
width: 80px;
}
.text {
display: block;
text-align: center;
overflow: hidden;
white-space: nowrap;
}
</style><div class="outer"><span class="text">My super long message!

View file

@ -170,18 +170,22 @@ void LineBuilder::update_last_line()
CSSPixels excess_horizontal_space = m_available_width_for_current_line - line_box.width();
switch (text_align) {
case CSS::TextAlign::Center:
case CSS::TextAlign::LibwebCenter:
x_offset += excess_horizontal_space / 2;
break;
case CSS::TextAlign::Right:
x_offset += excess_horizontal_space;
break;
case CSS::TextAlign::Left:
case CSS::TextAlign::Justify:
default:
break;
// If (after justification, if any) the inline contents of a line box are too long to fit within it,
// then the contents are start-aligned: any content that doesn't fit overflows the line boxs end edge.
if (excess_horizontal_space > 0) {
switch (text_align) {
case CSS::TextAlign::Center:
case CSS::TextAlign::LibwebCenter:
x_offset += excess_horizontal_space / 2;
break;
case CSS::TextAlign::Right:
x_offset += excess_horizontal_space;
break;
case CSS::TextAlign::Left:
case CSS::TextAlign::Justify:
default:
break;
}
}
auto strut_baseline = [&] {