iced-rs/iced · error

Stroke rectangle

Error message

Stroke rectangle

What it means

Raised when lyon's stroke tessellator fails on a rectangle stroke in the wgpu backend. The code tessellates a Box2D from top_left and size and asserts success; a panic means the rectangle or stroke options were degenerate (zero/negative size or non-finite values), which lyon treats as an invalid tessellation request.

Solutions

  1. Ensure the rectangle's width and height are > 0 and finite before stroking it.
  2. Skip stroking widgets whose computed size is zero in your view code.
  3. Clamp animated sizes to a small positive minimum when animating to zero.
  4. Update iced/lyon for newer tessellator handling of degenerate rectangles.

Example fix

// before
frame.stroke(rect, Stroke::default().width(2.0));
// after
if rect.width > 0.0 && rect.height > 0.0 {
    frame.stroke(rect, Stroke::default().width(2.0));
}
Defensive patterns

Strategy: validation

Validate before calling

if !(rect.width > 0.0 && rect.height > 0.0
    && rect.width.is_finite() && rect.height.is_finite()) {
    return; // skip stroking degenerate rectangle
}

Type guard

fn is_strokable(r: &iced::Rectangle) -> bool {
    r.width > 0.0 && r.height > 0.0 && r.width.is_finite() && r.height.is_finite()
}

Prevention

When it happens

Trigger: Calling Stroke::stroke_rectangle (e.g. frame.stroke(Rectangle{..}, ..)) with a size of 0 or negative width/height, or non-finite top_left/size values.

Common situations: Layout computing a zero-sized widget (collapsed container, display:none-like sizing) that still gets stroked; animation interpolating a size through zero; fractional scaling producing NaN sizes.

Understand the failure class

Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.

Related errors


AI-assisted analysis of iced-rs/iced@d146509d89 (2026-09-11). Data as JSON: /api/errors/37b404c1f989dcaa. Report an issue: GitHub.

Appendix: source

Thrown at wgpu/src/geometry.rs:262

        let size = self
            .transforms
            .current
            .0
            .transform_vector(lyon::math::Vector::new(size.width, size.height));

        let mut options = tessellation::StrokeOptions::default();
        options.line_width = stroke.width;
        options.start_cap = into_line_cap(stroke.line_cap);
        options.end_cap = into_line_cap(stroke.line_cap);
        options.line_join = into_line_join(stroke.line_join);

        self.stroke_tessellator
            .tessellate_rectangle(
                &lyon::math::Box2D::new(top_left, top_left + size),
                &options,
                buffer.as_mut(),
            )
            .expect("Stroke rectangle");
    }

    fn stroke_text<'a>(&mut self, text: impl Into<geometry::Text>, stroke: impl Into<Stroke<'a>>) {
        let text = text.into();
        let stroke = stroke.into();

        text.draw_with(|glyph, _color| self.stroke(&glyph, stroke));
    }

    fn fill_text(&mut self, text: impl Into<geometry::Text>) {
        let text = text.into();

        let (scale_x, scale_y) = self.transforms.current.scale();

        if self.transforms.current.is_scale_translation()
            && scale_x == scale_y
            && scale_x > 0.0
            && scale_y > 0.0

View on GitHub (pinned to d146509d89)