diff options
author | Sam Atkins <atkinssj@gmail.com> | 2021-07-20 16:11:19 +0100 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2021-07-22 23:09:01 +0200 |
commit | a44d7670ab937783e233f7d9a3ef73a39fcd8720 (patch) | |
tree | 639c6e8553199aefee9c0e099e814ef3356861be /Userland/Libraries/LibWeb/CSS | |
parent | b693a22c2dab20b4c3c74bbf1a1b8e69f44e6ddf (diff) | |
download | serenity-a44d7670ab937783e233f7d9a3ef73a39fcd8720.zip |
LibWeb: Resolve CSS list-style from value list
This resolves the three sub-properties, appearing in any order:
- list-style-image
- list-style-position
- list-style-type
Added `list-style-position` values to support this, though they are not
yet used in rendering.
Diffstat (limited to 'Userland/Libraries/LibWeb/CSS')
-rw-r--r-- | Userland/Libraries/LibWeb/CSS/Identifiers.json | 2 | ||||
-rw-r--r-- | Userland/Libraries/LibWeb/CSS/Parser/Parser.cpp | 1 | ||||
-rw-r--r-- | Userland/Libraries/LibWeb/CSS/StyleResolver.cpp | 102 |
3 files changed, 99 insertions, 6 deletions
diff --git a/Userland/Libraries/LibWeb/CSS/Identifiers.json b/Userland/Libraries/LibWeb/CSS/Identifiers.json index d09767a16f..29490eead7 100644 --- a/Userland/Libraries/LibWeb/CSS/Identifiers.json +++ b/Userland/Libraries/LibWeb/CSS/Identifiers.json @@ -99,6 +99,7 @@ "inline", "inline-block", "inset", + "inside", "justify", "large", "larger", @@ -125,6 +126,7 @@ "nw-resize", "nwse-resize", "outset", + "outside", "overline", "pointer", "pre", diff --git a/Userland/Libraries/LibWeb/CSS/Parser/Parser.cpp b/Userland/Libraries/LibWeb/CSS/Parser/Parser.cpp index e99e6f3d9a..108f59b698 100644 --- a/Userland/Libraries/LibWeb/CSS/Parser/Parser.cpp +++ b/Userland/Libraries/LibWeb/CSS/Parser/Parser.cpp @@ -1621,7 +1621,6 @@ RefPtr<StyleValue> Parser::parse_css_value(PropertyID property_id, TokenStream<S RefPtr<StyleValue> Parser::parse_css_value(ParsingContext const& context, PropertyID property_id, StyleComponentValueRule const& component_value) { dbgln_if(CSS_PARSER_TRACE, "Parser::parse_css_value '{}'", component_value.to_debug_string()); - // FIXME: Figure out if we still need takes_integer_value, and if so, move this information // into Properties.json. auto takes_integer_value = [](PropertyID property_id) -> bool { diff --git a/Userland/Libraries/LibWeb/CSS/StyleResolver.cpp b/Userland/Libraries/LibWeb/CSS/StyleResolver.cpp index 13f7238164..fd641b4cdc 100644 --- a/Userland/Libraries/LibWeb/CSS/StyleResolver.cpp +++ b/Userland/Libraries/LibWeb/CSS/StyleResolver.cpp @@ -335,6 +335,56 @@ static inline bool is_line_width(StyleValue const& value) } } +static inline bool is_list_style_image(StyleValue const& value) +{ + if (value.is_builtin_or_dynamic()) + return true; + if (value.is_image()) + return true; + if (value.is_identifier() && value.to_identifier() == ValueID::None) + return true; + + return false; +} + +static inline bool is_list_style_position(StyleValue const& value) +{ + if (value.is_builtin_or_dynamic()) + return true; + + switch (value.to_identifier()) { + case ValueID::Inside: + case ValueID::Outside: + return true; + default: + return false; + } +} + +static inline bool is_list_style_type(StyleValue const& value) +{ + if (value.is_builtin_or_dynamic()) + return true; + // FIXME: Handle strings and symbols("...") syntax + switch (value.to_identifier()) { + case CSS::ValueID::None: + case CSS::ValueID::Disc: + case CSS::ValueID::Circle: + case CSS::ValueID::Square: + case CSS::ValueID::Decimal: + case CSS::ValueID::DecimalLeadingZero: + case CSS::ValueID::LowerAlpha: + case CSS::ValueID::LowerLatin: + case CSS::ValueID::UpperAlpha: + case CSS::ValueID::UpperLatin: + case CSS::ValueID::UpperRoman: + case CSS::ValueID::LowerRoman: + return true; + default: + return true; + } +} + static void set_property_expanding_shorthands(StyleProperties& style, CSS::PropertyID property_id, StyleValue const& value, DOM::Document& document, bool is_internally_generated_pseudo_property = false) { CSS::DeprecatedParsingContext deprecated_context(document); @@ -1202,17 +1252,59 @@ static void set_property_expanding_shorthands(StyleProperties& style, CSS::Prope return; } - // FIXME: Handle all three parts of ListStyle. (list-style-positon, list-style-image, list-style-type) if (value.is_value_list()) { auto parts = static_cast<CSS::ValueListStyleValue const&>(value).values(); - if (!parts.is_empty()) { - auto list_style = Parser::parse_css_value(context, property_id, parts[0]); - if (list_style) - style.set_property(CSS::PropertyID::ListStyleType, *list_style); + + if (!parts.is_empty() && parts.size() <= 3) { + RefPtr<StyleValue> position_value; + RefPtr<StyleValue> image_value; + RefPtr<StyleValue> type_value; + + // FIXME: `none` is ambiguous as it is a valid value for ListStyleImage and ListStyleType, + // so requires special handling. https://www.w3.org/TR/css-lists-3/#propdef-list-style + + for (auto& part : parts) { + auto value = Parser::parse_css_value(context, property_id, part); + if (!value) + return; + + if (is_list_style_position(*value)) { + if (position_value) + return; + position_value = move(value); + continue; + } + if (is_list_style_image(*value)) { + if (image_value) + return; + image_value = move(value); + continue; + } + if (is_list_style_type(*value)) { + if (type_value) + return; + type_value = move(value); + continue; + } + } + + if (position_value) + style.set_property(CSS::PropertyID::ListStylePosition, *position_value); + if (image_value) + style.set_property(CSS::PropertyID::ListStyleImage, *image_value); + if (type_value) + style.set_property(CSS::PropertyID::ListStyleType, *type_value); } return; } + if (is_list_style_position(value)) + style.set_property(CSS::PropertyID::ListStylePosition, value); + else if (is_list_style_image(value)) + style.set_property(CSS::PropertyID::ListStyleImage, value); + else if (is_list_style_type(value)) + style.set_property(CSS::PropertyID::ListStyleType, value); + return; } |