Skip to content

Commit

Permalink
LibWeb: Don't crash when calling getBBox() on the outermost SVG element
Browse files Browse the repository at this point in the history
(cherry picked from commit b140206a91e809426248f85a5471f734d8e86997)
  • Loading branch information
tcl3 authored and nico committed Nov 2, 2024
1 parent 01a305b commit b76de7e
Show file tree
Hide file tree
Showing 3 changed files with 17 additions and 1 deletion.
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Bounding box of empty SVG element - x: 0, y: 0, width: 0, height: 0
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<!DOCTYPE html>
<script src="../include.js"></script>
<svg></svg>
<script>
test(() => {
const svgElement = document.querySelector("svg");
const boundingBox = svgElement.getBBox();
println(`Bounding box of empty SVG element - x: ${boundingBox.x}, y: ${boundingBox.y}, width: ${boundingBox.width}, height: ${boundingBox.height}`);
svgElement.remove();
});
</script>
6 changes: 5 additions & 1 deletion Userland/Libraries/LibWeb/SVG/SVGGraphicsElement.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -285,6 +285,7 @@ Optional<float> SVGGraphicsElement::stroke_width() const
return width.to_px(*layout_node(), scaled_viewport_size).to_double();
}

// https://svgwg.org/svg2-draft/types.html#__svg__SVGGraphicsElement__getBBox
JS::NonnullGCPtr<Geometry::DOMRect> SVGGraphicsElement::get_b_box(Optional<SVGBoundingBoxOptions>)
{
// FIXME: It should be possible to compute this without layout updates. The bounding box is within the
Expand All @@ -295,7 +296,10 @@ JS::NonnullGCPtr<Geometry::DOMRect> SVGGraphicsElement::get_b_box(Optional<SVGBo
if (!layout_node())
return Geometry::DOMRect::create(realm());
// Invert the SVG -> screen space transform.
auto svg_element_rect = shadow_including_first_ancestor_of_type<SVG::SVGSVGElement>()->paintable_box()->absolute_rect();
auto owner_svg_element = this->owner_svg_element();
if (!owner_svg_element)
return Geometry::DOMRect::create(realm());
auto svg_element_rect = owner_svg_element->paintable_box()->absolute_rect();
auto inverse_transform = static_cast<Painting::SVGGraphicsPaintable&>(*paintable_box()).computed_transforms().svg_to_css_pixels_transform().inverse();
auto translated_rect = paintable_box()->absolute_rect().to_type<float>().translated(-svg_element_rect.location().to_type<float>());
if (inverse_transform.has_value())
Expand Down

0 comments on commit b76de7e

Please sign in to comment.