LibWeb: Support more length types in SVG width/height attributes

Previously we were using the HTML parse_dimension_value method for the
height and width attributes of an SVG element. These attributes should
however be treated as css properties instead and thus also support
calc() and absolute units so we use the css parser for this instead.
This commit is contained in:
Michiel 2023-03-19 15:44:12 +01:00 committed by Andreas Kling
parent e312d6530b
commit 2480b94ae7
3 changed files with 16 additions and 16 deletions

View file

@ -5,7 +5,7 @@
* SPDX-License-Identifier: BSD-2-Clause
*/
#include <LibWeb/HTML/Parser/HTMLParser.h>
#include <LibWeb/CSS/Parser/Parser.h>
#include <LibWeb/Layout/ReplacedBox.h>
#include <LibWeb/Layout/SVGGeometryBox.h>
#include <LibWeb/Painting/SVGSVGPaintable.h>
@ -27,14 +27,14 @@ void SVGSVGBox::prepare_for_replaced_layout()
if (dom_node().has_attribute(HTML::AttributeNames::width) && dom_node().has_attribute(HTML::AttributeNames::height)) {
Optional<CSSPixels> w;
Optional<CSSPixels> h;
if (auto width = HTML::parse_dimension_value(dom_node().attribute(HTML::AttributeNames::width))) {
if (width->has_length())
w = width->to_length().to_px(*this);
}
if (auto height = HTML::parse_dimension_value(dom_node().attribute(HTML::AttributeNames::height))) {
if (height->has_length())
h = height->to_length().to_px(*this);
}
auto parsing_context = CSS::Parser::ParsingContext { document() };
auto width = parse_css_value(parsing_context, dom_node().attribute(Web::HTML::AttributeNames::width), CSS::PropertyID::Width);
if (!width.is_null() && width->has_length())
w = width->to_length().to_px(*this);
auto height = parse_css_value(parsing_context, dom_node().attribute((HTML::AttributeNames::height)), CSS::PropertyID::Height);
if (!height.is_null() && height->has_length())
h = height->to_length().to_px(*this);
if (w.has_value() && h.has_value()) {
set_intrinsic_width(*w);
set_intrinsic_height(*h);

View file

@ -6,7 +6,7 @@
#include <LibWeb/Bindings/ExceptionOrUtils.h>
#include <LibWeb/Bindings/Intrinsics.h>
#include <LibWeb/HTML/Parser/HTMLParser.h>
#include <LibWeb/CSS/Parser/Parser.h>
#include <LibWeb/Layout/BlockContainer.h>
#include <LibWeb/SVG/AttributeNames.h>
#include <LibWeb/SVG/SVGAnimatedLength.h>
@ -63,11 +63,11 @@ JS::GCPtr<Layout::Node> SVGForeignObjectElement::create_layout_node(NonnullRefPt
void SVGForeignObjectElement::apply_presentational_hints(CSS::StyleProperties& style) const
{
Base::apply_presentational_hints(style);
if (auto width_value = HTML::parse_dimension_value(attribute(SVG::AttributeNames::width)))
auto parsing_context = CSS::Parser::ParsingContext { document() };
if (auto width_value = parse_css_value(parsing_context, attribute(Web::HTML::AttributeNames::width), CSS::PropertyID::Width))
style.set_property(CSS::PropertyID::Width, width_value.release_nonnull());
if (auto height_value = HTML::parse_dimension_value(attribute(SVG::AttributeNames::height)))
if (auto height_value = parse_css_value(parsing_context, attribute(Web::HTML::AttributeNames::height), CSS::PropertyID::Height))
style.set_property(CSS::PropertyID::Height, height_value.release_nonnull());
}

View file

@ -5,7 +5,6 @@
* SPDX-License-Identifier: BSD-2-Clause
*/
#include <LibGfx/Painter.h>
#include <LibWeb/CSS/Parser/Parser.h>
#include <LibWeb/CSS/StyleComputer.h>
#include <LibWeb/DOM/Document.h>
@ -38,7 +37,8 @@ JS::GCPtr<Layout::Node> SVGSVGElement::create_layout_node(NonnullRefPtr<CSS::Sty
void SVGSVGElement::apply_presentational_hints(CSS::StyleProperties& style) const
{
auto width_attribute = attribute(SVG::AttributeNames::width);
if (auto width_value = HTML::parse_dimension_value(width_attribute)) {
auto parsing_context = CSS::Parser::ParsingContext { document() };
if (auto width_value = parse_css_value(parsing_context, attribute(Web::HTML::AttributeNames::width), CSS::PropertyID::Width)) {
style.set_property(CSS::PropertyID::Width, width_value.release_nonnull());
} else if (width_attribute == "") {
// If the `width` attribute is an empty string, it defaults to 100%.
@ -49,7 +49,7 @@ void SVGSVGElement::apply_presentational_hints(CSS::StyleProperties& style) cons
// Height defaults to 100%
auto height_attribute = attribute(SVG::AttributeNames::height);
if (auto height_value = HTML::parse_dimension_value(height_attribute)) {
if (auto height_value = parse_css_value(parsing_context, attribute(Web::HTML::AttributeNames::height), CSS::PropertyID::Height)) {
style.set_property(CSS::PropertyID::Height, height_value.release_nonnull());
} else if (height_attribute == "") {
// If the `height` attribute is an empty string, it defaults to 100%.