mirror of
https://github.com/RGBCube/serenity
synced 2025-07-25 04:57:44 +00:00
LibHTML: Use an enum for CSS property ID's
Instead of using string everywhere, have the CSS parser produce enum values, since they are a lot nicer to work with. In the future we should generate most of this code based on a list of supported CSS properties.
This commit is contained in:
parent
19dbfc3153
commit
31ac19543a
18 changed files with 207 additions and 94 deletions
62
Libraries/LibHTML/CSS/PropertyID.h
Normal file
62
Libraries/LibHTML/CSS/PropertyID.h
Normal file
|
@ -0,0 +1,62 @@
|
|||
#pragma once
|
||||
|
||||
#include <AK/Traits.h>
|
||||
|
||||
namespace CSS {
|
||||
enum class PropertyID {
|
||||
Invalid,
|
||||
|
||||
BackgroundColor,
|
||||
BorderBottomColor,
|
||||
BorderBottomStyle,
|
||||
BorderBottomWidth,
|
||||
BorderCollapse,
|
||||
BorderLeftColor,
|
||||
BorderLeftStyle,
|
||||
BorderLeftWidth,
|
||||
BorderRightColor,
|
||||
BorderRightStyle,
|
||||
BorderRightWidth,
|
||||
BorderSpacing,
|
||||
BorderTopColor,
|
||||
BorderTopStyle,
|
||||
BorderTopWidth,
|
||||
Color,
|
||||
Display,
|
||||
FontFamily,
|
||||
FontSize,
|
||||
FontStyle,
|
||||
FontVariant,
|
||||
FontWeight,
|
||||
Height,
|
||||
LetterSpacing,
|
||||
LineHeight,
|
||||
ListStyle,
|
||||
ListStyleImage,
|
||||
ListStylePosition,
|
||||
ListStyleType,
|
||||
MarginBottom,
|
||||
MarginLeft,
|
||||
MarginRight,
|
||||
MarginTop,
|
||||
PaddingBottom,
|
||||
PaddingLeft,
|
||||
PaddingRight,
|
||||
PaddingTop,
|
||||
TextAlign,
|
||||
TextDecoration,
|
||||
TextIndent,
|
||||
TextTransform,
|
||||
Visibility,
|
||||
WhiteSpace,
|
||||
Width,
|
||||
WordSpacing,
|
||||
};
|
||||
}
|
||||
|
||||
namespace AK {
|
||||
template<>
|
||||
struct Traits<CSS::PropertyID> : public GenericTraits<CSS::PropertyID> {
|
||||
static unsigned hash(CSS::PropertyID property_id) { return int_hash((unsigned)property_id); }
|
||||
};
|
||||
}
|
|
@ -4,7 +4,7 @@
|
|||
#include <LibHTML/CSS/StyleValue.h>
|
||||
|
||||
struct StyleProperty {
|
||||
String name;
|
||||
CSS::PropertyID property_id;
|
||||
NonnullRefPtr<StyleValue> value;
|
||||
bool important { false };
|
||||
};
|
||||
|
|
|
@ -2,38 +2,38 @@
|
|||
#include <LibHTML/CSS/StyleProperties.h>
|
||||
#include <ctype.h>
|
||||
|
||||
void StyleProperties::set_property(const String& name, NonnullRefPtr<StyleValue> value)
|
||||
void StyleProperties::set_property(CSS::PropertyID id, NonnullRefPtr<StyleValue> value)
|
||||
{
|
||||
m_property_values.set(name, move(value));
|
||||
m_property_values.set((unsigned)id, move(value));
|
||||
}
|
||||
|
||||
Optional<NonnullRefPtr<StyleValue>> StyleProperties::property(const String& name) const
|
||||
Optional<NonnullRefPtr<StyleValue>> StyleProperties::property(CSS::PropertyID id) const
|
||||
{
|
||||
auto it = m_property_values.find(name);
|
||||
auto it = m_property_values.find((unsigned)id);
|
||||
if (it == m_property_values.end())
|
||||
return {};
|
||||
return it->value;
|
||||
}
|
||||
|
||||
Length StyleProperties::length_or_fallback(const StringView& property_name, const Length& fallback) const
|
||||
Length StyleProperties::length_or_fallback(CSS::PropertyID id, const Length& fallback) const
|
||||
{
|
||||
auto value = property(property_name);
|
||||
auto value = property(id);
|
||||
if (!value.has_value())
|
||||
return fallback;
|
||||
return value.value()->to_length();
|
||||
}
|
||||
|
||||
String StyleProperties::string_or_fallback(const StringView& property_name, const StringView& fallback) const
|
||||
String StyleProperties::string_or_fallback(CSS::PropertyID id, const StringView& fallback) const
|
||||
{
|
||||
auto value = property(property_name);
|
||||
auto value = property(id);
|
||||
if (!value.has_value())
|
||||
return fallback;
|
||||
return value.value()->to_string();
|
||||
}
|
||||
|
||||
Color StyleProperties::color_or_fallback(const StringView& property_name, const Document& document, Color fallback) const
|
||||
Color StyleProperties::color_or_fallback(CSS::PropertyID id, const Document& document, Color fallback) const
|
||||
{
|
||||
auto value = property(property_name);
|
||||
auto value = property(id);
|
||||
if (!value.has_value())
|
||||
return fallback;
|
||||
return value.value()->to_color(document);
|
||||
|
@ -41,8 +41,8 @@ Color StyleProperties::color_or_fallback(const StringView& property_name, const
|
|||
|
||||
void StyleProperties::load_font() const
|
||||
{
|
||||
auto font_family = string_or_fallback("font-family", "Katica");
|
||||
auto font_weight = string_or_fallback("font-weight", "normal");
|
||||
auto font_family = string_or_fallback(CSS::PropertyID::FontFamily, "Katica");
|
||||
auto font_weight = string_or_fallback(CSS::PropertyID::FontWeight, "normal");
|
||||
|
||||
String weight;
|
||||
if (font_weight == "lighter")
|
||||
|
|
|
@ -15,15 +15,15 @@ public:
|
|||
inline void for_each_property(Callback callback) const
|
||||
{
|
||||
for (auto& it : m_property_values)
|
||||
callback(it.key, *it.value);
|
||||
callback((CSS::PropertyID)it.key, *it.value);
|
||||
}
|
||||
|
||||
void set_property(const String& name, NonnullRefPtr<StyleValue> value);
|
||||
Optional<NonnullRefPtr<StyleValue>> property(const String& name) const;
|
||||
void set_property(CSS::PropertyID, NonnullRefPtr<StyleValue> value);
|
||||
Optional<NonnullRefPtr<StyleValue>> property(CSS::PropertyID) const;
|
||||
|
||||
Length length_or_fallback(const StringView& property_name, const Length& fallback) const;
|
||||
String string_or_fallback(const StringView& property_name, const StringView& fallback) const;
|
||||
Color color_or_fallback(const StringView& property_name, const Document&, Color fallback) const;
|
||||
Length length_or_fallback(CSS::PropertyID, const Length& fallback) const;
|
||||
String string_or_fallback(CSS::PropertyID, const StringView& fallback) const;
|
||||
Color color_or_fallback(CSS::PropertyID, const Document&, Color fallback) const;
|
||||
|
||||
const Font& font() const
|
||||
{
|
||||
|
@ -33,7 +33,7 @@ public:
|
|||
}
|
||||
|
||||
private:
|
||||
HashMap<String, NonnullRefPtr<StyleValue>> m_property_values;
|
||||
HashMap<unsigned, NonnullRefPtr<StyleValue>> m_property_values;
|
||||
|
||||
void load_font() const;
|
||||
|
||||
|
|
|
@ -61,37 +61,36 @@ NonnullRefPtrVector<StyleRule> StyleResolver::collect_matching_rules(const Eleme
|
|||
return matching_rules;
|
||||
}
|
||||
|
||||
bool StyleResolver::is_inherited_property(const StringView& name)
|
||||
bool StyleResolver::is_inherited_property(CSS::PropertyID property_id)
|
||||
{
|
||||
static HashTable<String> inherited_properties;
|
||||
static HashTable<CSS::PropertyID> inherited_properties;
|
||||
if (inherited_properties.is_empty()) {
|
||||
inherited_properties.set("border-collapse");
|
||||
inherited_properties.set("border-spacing");
|
||||
inherited_properties.set("color");
|
||||
inherited_properties.set("font-family");
|
||||
inherited_properties.set("font-size");
|
||||
inherited_properties.set("font-style");
|
||||
inherited_properties.set("font-variant");
|
||||
inherited_properties.set("font-weight");
|
||||
inherited_properties.set("font");
|
||||
inherited_properties.set("letter-spacing");
|
||||
inherited_properties.set("line-height");
|
||||
inherited_properties.set("list-style-image");
|
||||
inherited_properties.set("list-style-position");
|
||||
inherited_properties.set("list-style-type");
|
||||
inherited_properties.set("list-style");
|
||||
inherited_properties.set("text-align");
|
||||
inherited_properties.set("text-indent");
|
||||
inherited_properties.set("text-transform");
|
||||
inherited_properties.set("visibility");
|
||||
inherited_properties.set("white-space");
|
||||
inherited_properties.set("word-spacing");
|
||||
inherited_properties.set(CSS::PropertyID::BorderCollapse);
|
||||
inherited_properties.set(CSS::PropertyID::BorderSpacing);
|
||||
inherited_properties.set(CSS::PropertyID::Color);
|
||||
inherited_properties.set(CSS::PropertyID::FontFamily);
|
||||
inherited_properties.set(CSS::PropertyID::FontSize);
|
||||
inherited_properties.set(CSS::PropertyID::FontStyle);
|
||||
inherited_properties.set(CSS::PropertyID::FontVariant);
|
||||
inherited_properties.set(CSS::PropertyID::FontWeight);
|
||||
inherited_properties.set(CSS::PropertyID::LetterSpacing);
|
||||
inherited_properties.set(CSS::PropertyID::LineHeight);
|
||||
inherited_properties.set(CSS::PropertyID::ListStyle);
|
||||
inherited_properties.set(CSS::PropertyID::ListStyleImage);
|
||||
inherited_properties.set(CSS::PropertyID::ListStylePosition);
|
||||
inherited_properties.set(CSS::PropertyID::ListStyleType);
|
||||
inherited_properties.set(CSS::PropertyID::TextAlign);
|
||||
inherited_properties.set(CSS::PropertyID::TextIndent);
|
||||
inherited_properties.set(CSS::PropertyID::TextTransform);
|
||||
inherited_properties.set(CSS::PropertyID::Visibility);
|
||||
inherited_properties.set(CSS::PropertyID::WhiteSpace);
|
||||
inherited_properties.set(CSS::PropertyID::WordSpacing);
|
||||
|
||||
// FIXME: This property is not supposed to be inherited, but we currently
|
||||
// rely on inheritance to propagate decorations into line boxes.
|
||||
inherited_properties.set("text-decoration");
|
||||
inherited_properties.set(CSS::PropertyID::TextDecoration);
|
||||
}
|
||||
return inherited_properties.contains(name);
|
||||
return inherited_properties.contains(property_id);
|
||||
}
|
||||
|
||||
NonnullRefPtr<StyleProperties> StyleResolver::resolve_style(const Element& element, const StyleProperties* parent_style) const
|
||||
|
@ -99,9 +98,9 @@ NonnullRefPtr<StyleProperties> StyleResolver::resolve_style(const Element& eleme
|
|||
auto style = StyleProperties::create();
|
||||
|
||||
if (parent_style) {
|
||||
parent_style->for_each_property([&](const StringView& name, auto& value) {
|
||||
if (is_inherited_property(name))
|
||||
style->set_property(name, value);
|
||||
parent_style->for_each_property([&](auto property_id, auto& value) {
|
||||
if (is_inherited_property(property_id))
|
||||
style->set_property(property_id, value);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -110,7 +109,7 @@ NonnullRefPtr<StyleProperties> StyleResolver::resolve_style(const Element& eleme
|
|||
auto matching_rules = collect_matching_rules(element);
|
||||
for (auto& rule : matching_rules) {
|
||||
for (auto& property : rule.declaration().properties()) {
|
||||
style->set_property(property.name, property.value);
|
||||
style->set_property(property.property_id, property.value);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -118,7 +117,7 @@ NonnullRefPtr<StyleProperties> StyleResolver::resolve_style(const Element& eleme
|
|||
if (!style_attribute.is_null()) {
|
||||
if (auto declaration = parse_css_declaration(style_attribute)) {
|
||||
for (auto& property : declaration->properties()) {
|
||||
style->set_property(property.name, property.value);
|
||||
style->set_property(property.property_id, property.value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -22,7 +22,7 @@ public:
|
|||
|
||||
NonnullRefPtrVector<StyleRule> collect_matching_rules(const Element&) const;
|
||||
|
||||
static bool is_inherited_property(const StringView&);
|
||||
static bool is_inherited_property(CSS::PropertyID);
|
||||
|
||||
private:
|
||||
template<typename Callback>
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
#include <AK/StringView.h>
|
||||
#include <LibDraw/Color.h>
|
||||
#include <LibHTML/CSS/Length.h>
|
||||
#include <LibHTML/CSS/PropertyID.h>
|
||||
|
||||
class Document;
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue