🐛 Ensure line height is properly handled on line breaks

This commit is contained in:
Elena Torro 2025-07-21 11:37:56 +02:00
parent b40b1fa2e4
commit eeee52a738
4 changed files with 1306 additions and 113 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 233 KiB

After

Width:  |  Height:  |  Size: 153 KiB

Before After
Before After

View file

@ -12,6 +12,7 @@ pub fn render(
.surfaces
.canvas(surface_id.unwrap_or(SurfaceId::Fills));
let mut offset_y = 0.0;
let container_height = shape.selrect().height();
for builder in paragraphs {
@ -19,15 +20,19 @@ pub fn render(
skia_paragraph.layout(shape.bounds().width());
let paragraph_height: f32 = skia_paragraph.height();
let offset_y = match shape.vertical_align() {
let paragraph_offset_y = match shape.vertical_align() {
VerticalAlign::Center => (container_height - paragraph_height) / 2.0,
VerticalAlign::Bottom => container_height - paragraph_height,
_ => 0.0,
};
offset_y += paragraph_offset_y;
let xy = (shape.selrect().x(), shape.selrect().y() + offset_y);
skia_paragraph.paint(canvas, xy);
offset_y += paragraph_height;
for line_metrics in skia_paragraph.get_line_metrics().iter() {
let style_metrics: Vec<_> = line_metrics
.get_style_metrics(line_metrics.start_index..line_metrics.end_index)
@ -38,6 +43,11 @@ pub fn render(
let total_line_width = line_metrics.width as f32;
let total_chars = line_metrics.end_index - line_metrics.start_index;
// No text decoration for empty lines
if total_chars == 0 || style_metrics.is_empty() {
continue;
}
for (i, (index, style_metric)) in style_metrics.iter().enumerate() {
let text_style = style_metric.text_style;
let font_metrics = style_metric.font_metrics;

View file

@ -275,6 +275,26 @@ impl Paragraph {
1 => skia::textlayout::TextDirection::RTL,
_ => skia::textlayout::TextDirection::LTR,
});
// Force minimum line height for empty lines using strut style
if !self.children.is_empty() {
let reference_child = self
.children
.iter()
.find(|child| !child.text.trim().is_empty())
.unwrap_or(&self.children[0]);
let mut strut_style = skia::textlayout::StrutStyle::default();
strut_style.set_font_size(reference_child.font_size);
strut_style.set_height(self.line_height);
strut_style.set_height_override(true);
strut_style.set_half_leading(false);
strut_style.set_leading(0.0);
strut_style.set_strut_enabled(true);
strut_style.set_force_strut_height(true);
style.set_strut_style(strut_style);
}
style
}
@ -339,6 +359,7 @@ impl TextLeaf {
style.set_letter_spacing(paragraph.letter_spacing);
style.set_height(paragraph.line_height);
style.set_height_override(true);
style.set_half_leading(false);
style.set_decoration_type(match self.text_decoration {
0 => skia::textlayout::TextDecoration::NO_DECORATION,