Don't render glyphs located outside of `BufferElement`'s bounds

Antonio Scandurra created

Change summary

gpui/src/elements/label.rs       |  7 ++++++-
gpui/src/text_layout.rs          | 12 +++++++++---
zed/src/editor/buffer_element.rs |  9 ++++-----
3 files changed, 19 insertions(+), 9 deletions(-)

Detailed changes

gpui/src/elements/label.rs 🔗

@@ -134,7 +134,12 @@ impl Element for Label {
         layout: &mut Self::LayoutState,
         ctx: &mut PaintContext,
     ) -> Self::PaintState {
-        layout.line.paint(bounds, layout.colors.as_slice(), ctx)
+        layout.line.paint(
+            bounds.origin(),
+            RectF::new(vec2f(0., 0.), bounds.size()),
+            layout.colors.as_slice(),
+            ctx,
+        )
     }
 
     fn dispatch_event(

gpui/src/text_layout.rs 🔗

@@ -181,7 +181,13 @@ impl Line {
         }
     }
 
-    pub fn paint(&self, bounds: RectF, colors: &[(Range<usize>, ColorU)], ctx: &mut PaintContext) {
+    pub fn paint(
+        &self,
+        origin: Vector2F,
+        bounds: RectF,
+        colors: &[(Range<usize>, ColorU)],
+        ctx: &mut PaintContext,
+    ) {
         let mut colors = colors.iter().peekable();
         let mut color = ColorU::black();
 
@@ -190,7 +196,7 @@ impl Line {
             let descent = ctx.font_cache.descent(run.font_id, self.font_size);
             let max_glyph_width = bounding_box.x();
             for glyph in &run.glyphs {
-                let glyph_origin = bounds.origin() + glyph.position - vec2f(0.0, descent);
+                let glyph_origin = glyph.position - vec2f(0.0, descent);
                 if glyph_origin.x() + max_glyph_width < bounds.origin().x() {
                     continue;
                 }
@@ -211,7 +217,7 @@ impl Line {
                     font_id: run.font_id,
                     font_size: self.font_size,
                     id: glyph.id,
-                    origin: glyph_origin + vec2f(0., bounding_box.y() / 2.),
+                    origin: origin + glyph_origin + vec2f(0., bounding_box.y() / 2.),
                     color,
                 });
             }

zed/src/editor/buffer_element.rs 🔗

@@ -184,7 +184,8 @@ impl BufferElement {
                     ix as f32 * line_height - (scroll_top % line_height),
                 );
             line.paint(
-                RectF::new(line_origin, vec2f(line.width, line_height)),
+                line_origin,
+                RectF::new(vec2f(0., 0.), vec2f(line.width, line_height)),
                 &[(0..line.len, ColorU::black())],
                 ctx,
             );
@@ -280,11 +281,9 @@ impl BufferElement {
         // Draw glyphs
         for (ix, line) in layout.line_layouts.iter().enumerate() {
             let row = start_row + ix as u32;
-            let line_origin =
-                content_origin + vec2f(-scroll_left, row as f32 * line_height - scroll_top);
-
             line.paint(
-                RectF::new(line_origin, vec2f(line.width, line_height)),
+                content_origin + vec2f(-scroll_left, row as f32 * line_height - scroll_top),
+                RectF::new(vec2f(scroll_left, 0.), vec2f(bounds.width(), line_height)),
                 &[(0..line.len, ColorU::black())],
                 ctx,
             );