mirror of
https://github.com/RGBCube/serenity
synced 2025-07-27 03:37:45 +00:00
LibWeb: Rename directory LibHTML => LibWeb
Let's rename this to LibWeb since it aims to provide more parts of the web platform than just HTML. :^)
This commit is contained in:
parent
7a6c4a72d5
commit
830a57c6b2
158 changed files with 360 additions and 360 deletions
3
Libraries/LibWeb/CSS/.gitignore
vendored
Normal file
3
Libraries/LibWeb/CSS/.gitignore
vendored
Normal file
|
@ -0,0 +1,3 @@
|
|||
DefaultStyleSheetSource.cpp
|
||||
PropertyID.cpp
|
||||
PropertyID.h
|
139
Libraries/LibWeb/CSS/Default.css
Normal file
139
Libraries/LibWeb/CSS/Default.css
Normal file
|
@ -0,0 +1,139 @@
|
|||
html {
|
||||
font-family: Katica;
|
||||
}
|
||||
|
||||
head, link, meta, script, style, title {
|
||||
display: none;
|
||||
}
|
||||
|
||||
body {
|
||||
margin-left: 8;
|
||||
margin-top: 8;
|
||||
margin-right: 8;
|
||||
margin-bottom: 8;
|
||||
}
|
||||
|
||||
h1, h2 {
|
||||
font-family: Pebbleton;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
h3 {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
pre {
|
||||
font-family: Csilla;
|
||||
font-weight: lighter;
|
||||
margin-bottom: 8;
|
||||
margin-top: 8;
|
||||
white-space: pre;
|
||||
}
|
||||
|
||||
code {
|
||||
font-family: Csilla;
|
||||
font-weight: lighter;
|
||||
}
|
||||
|
||||
u, ins {
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
strong, b {
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
html, address,
|
||||
blockquote,
|
||||
body, dd, div,
|
||||
dl, dt, fieldset, form,
|
||||
frame, frameset,
|
||||
h1, h2, h3, h4,
|
||||
h5, h6, noframes,
|
||||
ol, p, ul, center,
|
||||
dir, hr, menu, pre,
|
||||
header, footer {
|
||||
display: block;
|
||||
}
|
||||
|
||||
center {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
h1, h2, h3 {
|
||||
margin-top: 8;
|
||||
margin-bottom: 8;
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
}
|
||||
|
||||
h4, p,
|
||||
blockquote, ul,
|
||||
fieldset, form,
|
||||
ol, dl, dir,
|
||||
menu {
|
||||
margin-top: 4;
|
||||
margin-bottom: 4;
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
}
|
||||
|
||||
h5, h6 {
|
||||
margin-top: 2;
|
||||
margin-bottom: 2;
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
}
|
||||
|
||||
li {
|
||||
display: list-item;
|
||||
margin-left: 8;
|
||||
margin-top: 2;
|
||||
margin-bottom: 2;
|
||||
}
|
||||
|
||||
a:link {
|
||||
color: -libhtml-link;
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
a:hover {
|
||||
color: red;
|
||||
}
|
||||
|
||||
hr {
|
||||
margin-top: 4;
|
||||
margin-bottom: 4;
|
||||
border-top-width: 1;
|
||||
border-left-width: 1;
|
||||
border-right-width: 1;
|
||||
border-bottom-width: 1;
|
||||
border-top-color: #888888;
|
||||
border-left-color: #888888;
|
||||
border-right-color: #888888;
|
||||
border-bottom-color: #888888;
|
||||
border-top-style: inset;
|
||||
border-left-style: inset;
|
||||
border-right-style: inset;
|
||||
border-bottom-style: inset;
|
||||
}
|
||||
|
||||
blink {
|
||||
display: inline;
|
||||
}
|
||||
|
||||
table {
|
||||
display: table;
|
||||
}
|
||||
|
||||
tr {
|
||||
display: table-row;
|
||||
}
|
||||
|
||||
td {
|
||||
display: table-cell;
|
||||
}
|
||||
|
||||
basefont {
|
||||
display: block;
|
||||
}
|
82
Libraries/LibWeb/CSS/Length.h
Normal file
82
Libraries/LibWeb/CSS/Length.h
Normal file
|
@ -0,0 +1,82 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/String.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class Length {
|
||||
public:
|
||||
enum class Type {
|
||||
Auto,
|
||||
Absolute,
|
||||
};
|
||||
|
||||
Length() {}
|
||||
Length(int value, Type type)
|
||||
: m_type(type)
|
||||
, m_value(value)
|
||||
{
|
||||
}
|
||||
Length(float value, Type type)
|
||||
: m_type(type)
|
||||
, m_value(value)
|
||||
{
|
||||
}
|
||||
~Length() {}
|
||||
|
||||
bool is_auto() const { return m_type == Type::Auto; }
|
||||
bool is_absolute() const { return m_type == Type::Absolute; }
|
||||
|
||||
float value() const { return m_value; }
|
||||
|
||||
String to_string() const
|
||||
{
|
||||
if (is_auto())
|
||||
return "[Length/auto]";
|
||||
return String::format("%g [Length/px]", m_value);
|
||||
}
|
||||
|
||||
float to_px() const
|
||||
{
|
||||
if (is_auto())
|
||||
return 0;
|
||||
return m_value;
|
||||
}
|
||||
|
||||
private:
|
||||
Type m_type { Type::Auto };
|
||||
float m_value { 0 };
|
||||
};
|
||||
|
||||
inline const LogStream& operator<<(const LogStream& stream, const Length& value)
|
||||
{
|
||||
return stream << value.to_string();
|
||||
}
|
||||
|
||||
}
|
40
Libraries/LibWeb/CSS/LengthBox.h
Normal file
40
Libraries/LibWeb/CSS/LengthBox.h
Normal file
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LibWeb/CSS/Length.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
struct LengthBox {
|
||||
Length top;
|
||||
Length right;
|
||||
Length bottom;
|
||||
Length left;
|
||||
};
|
||||
|
||||
}
|
316
Libraries/LibWeb/CSS/Properties.json
Normal file
316
Libraries/LibWeb/CSS/Properties.json
Normal file
|
@ -0,0 +1,316 @@
|
|||
{
|
||||
"background-attachment": {
|
||||
"inherited": false,
|
||||
"initial": "scroll"
|
||||
},
|
||||
"background-color": {
|
||||
"inherited": false,
|
||||
"initial": "transparent"
|
||||
},
|
||||
"background-image": {
|
||||
"inherited": false,
|
||||
"initial": "none"
|
||||
},
|
||||
"background-position": {
|
||||
"inherited": false,
|
||||
"initial": "0% 0%"
|
||||
},
|
||||
"background-repeat": {
|
||||
"inherited": false,
|
||||
"initial": "repeat"
|
||||
},
|
||||
"border": {
|
||||
"longhands": [
|
||||
"border-width",
|
||||
"border-style",
|
||||
"border-color"
|
||||
]
|
||||
},
|
||||
"border-bottom-color": {
|
||||
"initial": "currentColor",
|
||||
"inherited": false
|
||||
},
|
||||
"border-bottom-style": {
|
||||
"initial": "none",
|
||||
"inherited": false
|
||||
},
|
||||
"border-bottom-width": {
|
||||
"initial": "medium",
|
||||
"inherited": false
|
||||
},
|
||||
"border-color": {
|
||||
"longhands": [
|
||||
"border-top-color",
|
||||
"border-right-color",
|
||||
"border-bottom-color",
|
||||
"border-left-color"
|
||||
]
|
||||
},
|
||||
"border-collapse": {
|
||||
"inherited": true,
|
||||
"initial": "separate"
|
||||
},
|
||||
"border-left-color": {
|
||||
"initial": "currentColor",
|
||||
"inherited": false
|
||||
},
|
||||
"border-left-style": {
|
||||
"initial": "none",
|
||||
"inherited": false
|
||||
},
|
||||
"border-left-width": {
|
||||
"initial": "medium",
|
||||
"inherited": false
|
||||
},
|
||||
"border-right-color": {
|
||||
"initial": "currentColor",
|
||||
"inherited": false
|
||||
},
|
||||
"border-right-style": {
|
||||
"initial": "none",
|
||||
"inherited": false
|
||||
},
|
||||
"border-right-width": {
|
||||
"initial": "medium",
|
||||
"inherited": false
|
||||
},
|
||||
"border-spacing": {
|
||||
"inherited": true,
|
||||
"initial": "0"
|
||||
},
|
||||
"border-style": {
|
||||
"longhands": [
|
||||
"border-top-style",
|
||||
"border-right-style",
|
||||
"border-bottom-style",
|
||||
"border-left-style"
|
||||
]
|
||||
},
|
||||
"border-top-color": {
|
||||
"initial": "currentColor",
|
||||
"inherited": false
|
||||
},
|
||||
"border-top-style": {
|
||||
"initial": "none",
|
||||
"inherited": false
|
||||
},
|
||||
"border-top-width": {
|
||||
"initial": "medium",
|
||||
"inherited": false
|
||||
},
|
||||
"border-width": {
|
||||
"longhands": [
|
||||
"border-top-width",
|
||||
"border-right-width",
|
||||
"border-bottom-width",
|
||||
"border-left-width"
|
||||
]
|
||||
},
|
||||
"bottom": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
},
|
||||
"caption-side": {
|
||||
"inherited": true,
|
||||
"initial": "top"
|
||||
},
|
||||
"clear": {
|
||||
"inherited": false,
|
||||
"initial": "none"
|
||||
},
|
||||
"clip": {
|
||||
"inherited": true,
|
||||
"initial": "auto"
|
||||
},
|
||||
"color": {
|
||||
"inherited": true,
|
||||
"initial": ""
|
||||
},
|
||||
"cursor": {
|
||||
"inherited": true,
|
||||
"initial": "auto"
|
||||
},
|
||||
"direction": {
|
||||
"inherited": true,
|
||||
"initial": "ltr"
|
||||
},
|
||||
"display": {
|
||||
"inherited": false,
|
||||
"initial": "inline"
|
||||
},
|
||||
"float": {
|
||||
"inherited": false,
|
||||
"initial": "none"
|
||||
},
|
||||
"font-family": {
|
||||
"inherited": true,
|
||||
"initial": "sans-serif"
|
||||
},
|
||||
"font-size": {
|
||||
"inherited": true,
|
||||
"initial": "medium"
|
||||
},
|
||||
"font-style": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"font-variant": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"font-weight": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"height": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
},
|
||||
"left": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
},
|
||||
"letter-spacing": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"line-height": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"list-style": {
|
||||
"longhands": [
|
||||
"list-style-type",
|
||||
"list-style-position",
|
||||
"list-style-image"
|
||||
]
|
||||
},
|
||||
"list-style-image": {
|
||||
"inherited": true,
|
||||
"initial": "none"
|
||||
},
|
||||
"list-style-position": {
|
||||
"inherited": true,
|
||||
"initial": "outside"
|
||||
},
|
||||
"list-style-type": {
|
||||
"inherited": true,
|
||||
"initial": "disc"
|
||||
},
|
||||
"margin": {
|
||||
"longhands": [
|
||||
"margin-top",
|
||||
"margin-right",
|
||||
"margin-bottom",
|
||||
"margin-left"
|
||||
]
|
||||
},
|
||||
"margin-bottom": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"margin-left": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"margin-right": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"margin-top": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"max-height": {
|
||||
"inherited": false,
|
||||
"initial": "none"
|
||||
},
|
||||
"max-width": {
|
||||
"inherited": false,
|
||||
"initial": "none"
|
||||
},
|
||||
"min-height": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"min-width": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"padding": {
|
||||
"longhands": [
|
||||
"padding-top",
|
||||
"padding-right",
|
||||
"padding-bottom",
|
||||
"padding-left"
|
||||
]
|
||||
},
|
||||
"padding-bottom": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"padding-left": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"padding-right": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"padding-top": {
|
||||
"inherited": false,
|
||||
"initial": "0"
|
||||
},
|
||||
"position": {
|
||||
"inherited": false,
|
||||
"initial": "static"
|
||||
},
|
||||
"right": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
},
|
||||
"text-align": {
|
||||
"inherited": true,
|
||||
"initial": "left"
|
||||
},
|
||||
"text-decoration": {
|
||||
"inherited": false,
|
||||
"initial": "none"
|
||||
},
|
||||
"text-indent": {
|
||||
"inherited": true,
|
||||
"initial": "0"
|
||||
},
|
||||
"text-transform": {
|
||||
"inherited": true,
|
||||
"initial": "none"
|
||||
},
|
||||
"top": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
},
|
||||
"vertical-align": {
|
||||
"inherited": false,
|
||||
"initial": "baseline"
|
||||
},
|
||||
"visibility": {
|
||||
"inherited": true,
|
||||
"initial": "visible"
|
||||
},
|
||||
"width": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
},
|
||||
"white-space": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"word-spacing": {
|
||||
"inherited": true,
|
||||
"initial": "normal"
|
||||
},
|
||||
"z-index": {
|
||||
"inherited": false,
|
||||
"initial": "auto"
|
||||
}
|
||||
}
|
67
Libraries/LibWeb/CSS/Selector.cpp
Normal file
67
Libraries/LibWeb/CSS/Selector.cpp
Normal file
|
@ -0,0 +1,67 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibWeb/CSS/Selector.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
Selector::Selector(Vector<ComplexSelector>&& component_lists)
|
||||
: m_complex_selectors(move(component_lists))
|
||||
{
|
||||
}
|
||||
|
||||
Selector::~Selector()
|
||||
{
|
||||
}
|
||||
|
||||
Specificity Selector::specificity() const
|
||||
{
|
||||
unsigned ids = 0;
|
||||
unsigned tag_names = 0;
|
||||
unsigned classes = 0;
|
||||
|
||||
for (auto& list : m_complex_selectors) {
|
||||
for (auto& simple_selector : list.compound_selector) {
|
||||
switch (simple_selector.type) {
|
||||
case SimpleSelector::Type::Id:
|
||||
++ids;
|
||||
break;
|
||||
case SimpleSelector::Type::Class:
|
||||
++classes;
|
||||
break;
|
||||
case SimpleSelector::Type::TagName:
|
||||
++tag_names;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return { ids, classes, tag_names };
|
||||
}
|
||||
|
||||
}
|
96
Libraries/LibWeb/CSS/Selector.h
Normal file
96
Libraries/LibWeb/CSS/Selector.h
Normal file
|
@ -0,0 +1,96 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/String.h>
|
||||
#include <AK/Vector.h>
|
||||
#include <LibWeb/CSS/Specificity.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class Selector {
|
||||
public:
|
||||
struct SimpleSelector {
|
||||
enum class Type {
|
||||
Invalid,
|
||||
Universal,
|
||||
TagName,
|
||||
Id,
|
||||
Class,
|
||||
};
|
||||
Type type { Type::Invalid };
|
||||
|
||||
enum class PseudoClass {
|
||||
None,
|
||||
Link,
|
||||
Hover,
|
||||
FirstChild,
|
||||
LastChild,
|
||||
OnlyChild,
|
||||
Empty,
|
||||
};
|
||||
PseudoClass pseudo_class { PseudoClass::None };
|
||||
|
||||
String value;
|
||||
|
||||
enum class AttributeMatchType {
|
||||
None,
|
||||
HasAttribute,
|
||||
ExactValueMatch,
|
||||
};
|
||||
|
||||
AttributeMatchType attribute_match_type { AttributeMatchType::None };
|
||||
String attribute_name;
|
||||
String attribute_value;
|
||||
};
|
||||
|
||||
struct ComplexSelector {
|
||||
enum class Relation {
|
||||
None,
|
||||
ImmediateChild,
|
||||
Descendant,
|
||||
AdjacentSibling,
|
||||
GeneralSibling,
|
||||
};
|
||||
Relation relation { Relation::None };
|
||||
|
||||
using CompoundSelector = Vector<SimpleSelector>;
|
||||
CompoundSelector compound_selector;
|
||||
};
|
||||
|
||||
explicit Selector(Vector<ComplexSelector>&&);
|
||||
~Selector();
|
||||
|
||||
const Vector<ComplexSelector>& complex_selectors() const { return m_complex_selectors; }
|
||||
|
||||
Specificity specificity() const;
|
||||
|
||||
private:
|
||||
Vector<ComplexSelector> m_complex_selectors;
|
||||
};
|
||||
|
||||
}
|
152
Libraries/LibWeb/CSS/SelectorEngine.cpp
Normal file
152
Libraries/LibWeb/CSS/SelectorEngine.cpp
Normal file
|
@ -0,0 +1,152 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibWeb/CSS/SelectorEngine.h>
|
||||
#include <LibWeb/DOM/Document.h>
|
||||
#include <LibWeb/DOM/Element.h>
|
||||
#include <LibWeb/DOM/Text.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
namespace SelectorEngine {
|
||||
|
||||
static bool matches_hover_pseudo_class(const Element& element)
|
||||
{
|
||||
auto* hovered_node = element.document().hovered_node();
|
||||
if (!hovered_node)
|
||||
return false;
|
||||
if (&element == hovered_node)
|
||||
return true;
|
||||
return element.is_ancestor_of(*hovered_node);
|
||||
}
|
||||
|
||||
bool matches(const Selector::SimpleSelector& component, const Element& element)
|
||||
{
|
||||
switch (component.pseudo_class) {
|
||||
case Selector::SimpleSelector::PseudoClass::None:
|
||||
break;
|
||||
case Selector::SimpleSelector::PseudoClass::Link:
|
||||
if (!element.is_link())
|
||||
return false;
|
||||
break;
|
||||
case Selector::SimpleSelector::PseudoClass::Hover:
|
||||
if (!matches_hover_pseudo_class(element))
|
||||
return false;
|
||||
break;
|
||||
case Selector::SimpleSelector::PseudoClass::FirstChild:
|
||||
if (element.previous_element_sibling())
|
||||
return false;
|
||||
break;
|
||||
case Selector::SimpleSelector::PseudoClass::LastChild:
|
||||
if (element.next_element_sibling())
|
||||
return false;
|
||||
break;
|
||||
case Selector::SimpleSelector::PseudoClass::OnlyChild:
|
||||
if (element.previous_element_sibling() || element.next_element_sibling())
|
||||
return false;
|
||||
break;
|
||||
case Selector::SimpleSelector::PseudoClass::Empty:
|
||||
if (element.first_child_of_type<Element>() || element.first_child_of_type<Text>())
|
||||
return false;
|
||||
break;
|
||||
}
|
||||
|
||||
switch (component.attribute_match_type) {
|
||||
case Selector::SimpleSelector::AttributeMatchType::HasAttribute:
|
||||
if (!element.has_attribute(component.attribute_name))
|
||||
return false;
|
||||
break;
|
||||
case Selector::SimpleSelector::AttributeMatchType::ExactValueMatch:
|
||||
if (element.attribute(component.attribute_name) != component.attribute_value)
|
||||
return false;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
switch (component.type) {
|
||||
case Selector::SimpleSelector::Type::Universal:
|
||||
return true;
|
||||
case Selector::SimpleSelector::Type::Id:
|
||||
return component.value == element.attribute("id");
|
||||
case Selector::SimpleSelector::Type::Class:
|
||||
return element.has_class(component.value);
|
||||
case Selector::SimpleSelector::Type::TagName:
|
||||
return component.value == element.tag_name();
|
||||
default:
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
}
|
||||
|
||||
bool matches(const Selector& selector, int component_list_index, const Element& element)
|
||||
{
|
||||
auto& component_list = selector.complex_selectors()[component_list_index];
|
||||
for (auto& component : component_list.compound_selector) {
|
||||
if (!matches(component, element))
|
||||
return false;
|
||||
}
|
||||
switch (component_list.relation) {
|
||||
case Selector::ComplexSelector::Relation::None:
|
||||
return true;
|
||||
case Selector::ComplexSelector::Relation::Descendant:
|
||||
ASSERT(component_list_index != 0);
|
||||
for (auto* ancestor = element.parent(); ancestor; ancestor = ancestor->parent()) {
|
||||
if (!is<Element>(*ancestor))
|
||||
continue;
|
||||
if (matches(selector, component_list_index - 1, to<Element>(*ancestor)))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
case Selector::ComplexSelector::Relation::ImmediateChild:
|
||||
ASSERT(component_list_index != 0);
|
||||
if (!element.parent() || !is<Element>(*element.parent()))
|
||||
return false;
|
||||
return matches(selector, component_list_index - 1, to<Element>(*element.parent()));
|
||||
case Selector::ComplexSelector::Relation::AdjacentSibling:
|
||||
ASSERT(component_list_index != 0);
|
||||
if (auto* sibling = element.previous_element_sibling())
|
||||
return matches(selector, component_list_index - 1, *sibling);
|
||||
return false;
|
||||
case Selector::ComplexSelector::Relation::GeneralSibling:
|
||||
ASSERT(component_list_index != 0);
|
||||
for (auto* sibling = element.previous_element_sibling(); sibling; sibling = sibling->previous_element_sibling()) {
|
||||
if (matches(selector, component_list_index - 1, *sibling))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
|
||||
bool matches(const Selector& selector, const Element& element)
|
||||
{
|
||||
ASSERT(!selector.complex_selectors().is_empty());
|
||||
return matches(selector, selector.complex_selectors().size() - 1, element);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
41
Libraries/LibWeb/CSS/SelectorEngine.h
Normal file
41
Libraries/LibWeb/CSS/SelectorEngine.h
Normal file
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LibWeb/CSS/Selector.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class Element;
|
||||
|
||||
namespace SelectorEngine {
|
||||
|
||||
bool matches(const Selector&, const Element&);
|
||||
|
||||
}
|
||||
|
||||
}
|
64
Libraries/LibWeb/CSS/Specificity.h
Normal file
64
Libraries/LibWeb/CSS/Specificity.h
Normal file
|
@ -0,0 +1,64 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
namespace Web {
|
||||
|
||||
class Specificity {
|
||||
public:
|
||||
Specificity(unsigned ids, unsigned classes, unsigned tag_names)
|
||||
: m_ids(ids)
|
||||
, m_classes(classes)
|
||||
, m_tag_names(tag_names)
|
||||
{
|
||||
}
|
||||
|
||||
unsigned ids() const { return m_ids; }
|
||||
unsigned classes() const { return m_classes; }
|
||||
unsigned tag_names() const { return m_tag_names; }
|
||||
|
||||
bool operator<(const Specificity& other) const
|
||||
{
|
||||
return m_ids < other.m_ids
|
||||
|| m_classes < other.m_classes
|
||||
|| m_tag_names < other.m_tag_names;
|
||||
}
|
||||
|
||||
bool operator==(const Specificity& other) const
|
||||
{
|
||||
return m_ids == other.m_ids
|
||||
|| m_classes < other.m_classes
|
||||
|| m_tag_names < other.m_tag_names;
|
||||
}
|
||||
|
||||
private:
|
||||
unsigned m_ids { 0 };
|
||||
unsigned m_classes { 0 };
|
||||
unsigned m_tag_names { 0 };
|
||||
};
|
||||
|
||||
}
|
40
Libraries/LibWeb/CSS/StyleDeclaration.cpp
Normal file
40
Libraries/LibWeb/CSS/StyleDeclaration.cpp
Normal file
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibWeb/CSS/StyleDeclaration.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
StyleDeclaration::StyleDeclaration(Vector<StyleProperty>&& properties)
|
||||
: m_properties(move(properties))
|
||||
{
|
||||
}
|
||||
|
||||
StyleDeclaration::~StyleDeclaration()
|
||||
{
|
||||
}
|
||||
|
||||
}
|
58
Libraries/LibWeb/CSS/StyleDeclaration.h
Normal file
58
Libraries/LibWeb/CSS/StyleDeclaration.h
Normal file
|
@ -0,0 +1,58 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/String.h>
|
||||
#include <AK/Vector.h>
|
||||
#include <LibWeb/CSS/StyleValue.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
struct StyleProperty {
|
||||
CSS::PropertyID property_id;
|
||||
NonnullRefPtr<StyleValue> value;
|
||||
bool important { false };
|
||||
};
|
||||
|
||||
class StyleDeclaration : public RefCounted<StyleDeclaration> {
|
||||
public:
|
||||
static NonnullRefPtr<StyleDeclaration> create(Vector<StyleProperty>&& properties)
|
||||
{
|
||||
return adopt(*new StyleDeclaration(move(properties)));
|
||||
}
|
||||
|
||||
~StyleDeclaration();
|
||||
|
||||
const Vector<StyleProperty>& properties() const { return m_properties; }
|
||||
|
||||
public:
|
||||
explicit StyleDeclaration(Vector<StyleProperty>&&);
|
||||
|
||||
Vector<StyleProperty> m_properties;
|
||||
};
|
||||
|
||||
}
|
183
Libraries/LibWeb/CSS/StyleProperties.cpp
Normal file
183
Libraries/LibWeb/CSS/StyleProperties.cpp
Normal file
|
@ -0,0 +1,183 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibCore/DirIterator.h>
|
||||
#include <LibWeb/CSS/StyleProperties.h>
|
||||
#include <LibWeb/FontCache.h>
|
||||
#include <ctype.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
StyleProperties::StyleProperties()
|
||||
{
|
||||
}
|
||||
|
||||
StyleProperties::StyleProperties(const StyleProperties& other)
|
||||
: m_property_values(*new HashMap(other.m_property_values))
|
||||
{
|
||||
if (other.m_font) {
|
||||
m_font = other.m_font->clone();
|
||||
} else {
|
||||
m_font = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
NonnullRefPtr<StyleProperties> StyleProperties::clone() const
|
||||
{
|
||||
return adopt(*new StyleProperties(*this));
|
||||
}
|
||||
|
||||
void StyleProperties::set_property(CSS::PropertyID id, NonnullRefPtr<StyleValue> value)
|
||||
{
|
||||
m_property_values.set((unsigned)id, move(value));
|
||||
}
|
||||
|
||||
Optional<NonnullRefPtr<StyleValue>> StyleProperties::property(CSS::PropertyID id) const
|
||||
{
|
||||
auto it = m_property_values.find((unsigned)id);
|
||||
if (it == m_property_values.end())
|
||||
return {};
|
||||
return it->value;
|
||||
}
|
||||
|
||||
Length StyleProperties::length_or_fallback(CSS::PropertyID id, const Length& fallback) const
|
||||
{
|
||||
auto value = property(id);
|
||||
if (!value.has_value())
|
||||
return fallback;
|
||||
return value.value()->to_length();
|
||||
}
|
||||
|
||||
String StyleProperties::string_or_fallback(CSS::PropertyID id, const StringView& fallback) const
|
||||
{
|
||||
auto value = property(id);
|
||||
if (!value.has_value())
|
||||
return fallback;
|
||||
return value.value()->to_string();
|
||||
}
|
||||
|
||||
Color StyleProperties::color_or_fallback(CSS::PropertyID id, const Document& document, Color fallback) const
|
||||
{
|
||||
auto value = property(id);
|
||||
if (!value.has_value())
|
||||
return fallback;
|
||||
return value.value()->to_color(document);
|
||||
}
|
||||
|
||||
void StyleProperties::load_font() const
|
||||
{
|
||||
auto font_family = string_or_fallback(CSS::PropertyID::FontFamily, "Katica");
|
||||
auto font_weight = string_or_fallback(CSS::PropertyID::FontWeight, "normal");
|
||||
|
||||
if (auto cached_font = FontCache::the().get({ font_family, font_weight })) {
|
||||
m_font = cached_font;
|
||||
return;
|
||||
}
|
||||
|
||||
String weight;
|
||||
if (font_weight == "lighter")
|
||||
weight = "Thin";
|
||||
else if (font_weight == "normal")
|
||||
weight = "";
|
||||
else if (font_weight == "bold")
|
||||
weight = "Bold";
|
||||
else {
|
||||
dbg() << "Unknown font-weight: " << font_weight;
|
||||
weight = "";
|
||||
}
|
||||
|
||||
auto look_for_file = [](const StringView& expected_name) -> String {
|
||||
// TODO: handle font sizes properly?
|
||||
Core::DirIterator it { "/res/fonts/", Core::DirIterator::Flags::SkipDots };
|
||||
while (it.has_next()) {
|
||||
String name = it.next_path();
|
||||
ASSERT(name.ends_with(".font"));
|
||||
if (!name.starts_with(expected_name))
|
||||
continue;
|
||||
|
||||
// Check that a numeric size immediately
|
||||
// follows the font name. This prevents,
|
||||
// for example, matching KaticaBold when
|
||||
// the regular Katica is requested.
|
||||
if (!isdigit(name[expected_name.length()]))
|
||||
continue;
|
||||
|
||||
return name;
|
||||
}
|
||||
return {};
|
||||
};
|
||||
|
||||
String file_name = look_for_file(String::format("%s%s", font_family.characters(), weight.characters()));
|
||||
if (file_name.is_null() && weight == "")
|
||||
file_name = look_for_file(String::format("%sRegular", font_family.characters()));
|
||||
|
||||
if (file_name.is_null()) {
|
||||
dbg() << "Failed to find a font for family " << font_family << " weight " << font_weight;
|
||||
|
||||
if (font_weight == "bold")
|
||||
m_font = Gfx::Font::default_bold_font();
|
||||
else
|
||||
m_font = Gfx::Font::default_font();
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef HTML_DEBUG
|
||||
dbg() << "Found font " << file_name << " for family " << font_family << " weight " << font_weight;
|
||||
#endif
|
||||
|
||||
m_font = Gfx::Font::load_from_file(String::format("/res/fonts/%s", file_name.characters()));
|
||||
FontCache::the().set({ font_family, font_weight }, *m_font);
|
||||
}
|
||||
|
||||
float StyleProperties::line_height() const
|
||||
{
|
||||
auto line_height_length = length_or_fallback(CSS::PropertyID::LineHeight, {});
|
||||
if (line_height_length.is_absolute())
|
||||
return (float)font().glyph_height() * line_height_length.to_px();
|
||||
return (float)font().glyph_height() * 1.4f;
|
||||
}
|
||||
|
||||
bool StyleProperties::operator==(const StyleProperties& other) const
|
||||
{
|
||||
if (m_property_values.size() != other.m_property_values.size())
|
||||
return false;
|
||||
|
||||
for (auto& it : m_property_values) {
|
||||
auto jt = other.m_property_values.find(it.key);
|
||||
if (jt == other.m_property_values.end())
|
||||
return false;
|
||||
auto& my_value = *it.value;
|
||||
auto& other_value = *jt->value;
|
||||
if (my_value.type() != other_value.type())
|
||||
return false;
|
||||
if (my_value.to_string() != other_value.to_string())
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
}
|
81
Libraries/LibWeb/CSS/StyleProperties.h
Normal file
81
Libraries/LibWeb/CSS/StyleProperties.h
Normal file
|
@ -0,0 +1,81 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/HashMap.h>
|
||||
#include <AK/NonnullRefPtr.h>
|
||||
#include <LibGfx/Font.h>
|
||||
#include <LibGfx/Forward.h>
|
||||
#include <LibWeb/CSS/StyleValue.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class StyleProperties : public RefCounted<StyleProperties> {
|
||||
public:
|
||||
StyleProperties();
|
||||
|
||||
explicit StyleProperties(const StyleProperties&);
|
||||
|
||||
static NonnullRefPtr<StyleProperties> create() { return adopt(*new StyleProperties); }
|
||||
|
||||
NonnullRefPtr<StyleProperties> clone() const;
|
||||
|
||||
template<typename Callback>
|
||||
inline void for_each_property(Callback callback) const
|
||||
{
|
||||
for (auto& it : m_property_values)
|
||||
callback((CSS::PropertyID)it.key, *it.value);
|
||||
}
|
||||
|
||||
void set_property(CSS::PropertyID, NonnullRefPtr<StyleValue> value);
|
||||
Optional<NonnullRefPtr<StyleValue>> property(CSS::PropertyID) 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 Gfx::Font& font() const
|
||||
{
|
||||
if (!m_font)
|
||||
load_font();
|
||||
return *m_font;
|
||||
}
|
||||
|
||||
float line_height() const;
|
||||
|
||||
bool operator==(const StyleProperties&) const;
|
||||
bool operator!=(const StyleProperties& other) const { return !(*this == other); }
|
||||
|
||||
private:
|
||||
HashMap<unsigned, NonnullRefPtr<StyleValue>> m_property_values;
|
||||
|
||||
void load_font() const;
|
||||
|
||||
mutable RefPtr<Gfx::Font> m_font;
|
||||
};
|
||||
|
||||
}
|
300
Libraries/LibWeb/CSS/StyleResolver.cpp
Normal file
300
Libraries/LibWeb/CSS/StyleResolver.cpp
Normal file
|
@ -0,0 +1,300 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibWeb/CSS/SelectorEngine.h>
|
||||
#include <LibWeb/CSS/StyleResolver.h>
|
||||
#include <LibWeb/CSS/StyleSheet.h>
|
||||
#include <LibWeb/DOM/Document.h>
|
||||
#include <LibWeb/DOM/Element.h>
|
||||
#include <LibWeb/Dump.h>
|
||||
#include <LibWeb/Parser/CSSParser.h>
|
||||
#include <ctype.h>
|
||||
#include <stdio.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
StyleResolver::StyleResolver(Document& document)
|
||||
: m_document(document)
|
||||
{
|
||||
}
|
||||
|
||||
StyleResolver::~StyleResolver()
|
||||
{
|
||||
}
|
||||
|
||||
static StyleSheet& default_stylesheet()
|
||||
{
|
||||
static StyleSheet* sheet;
|
||||
if (!sheet) {
|
||||
extern const char default_stylesheet_source[];
|
||||
String css = default_stylesheet_source;
|
||||
sheet = parse_css(css).leak_ref();
|
||||
}
|
||||
return *sheet;
|
||||
}
|
||||
|
||||
template<typename Callback>
|
||||
void StyleResolver::for_each_stylesheet(Callback callback) const
|
||||
{
|
||||
callback(default_stylesheet());
|
||||
for (auto& sheet : document().stylesheets()) {
|
||||
callback(sheet);
|
||||
}
|
||||
}
|
||||
|
||||
NonnullRefPtrVector<StyleRule> StyleResolver::collect_matching_rules(const Element& element) const
|
||||
{
|
||||
NonnullRefPtrVector<StyleRule> matching_rules;
|
||||
|
||||
for_each_stylesheet([&](auto& sheet) {
|
||||
for (auto& rule : sheet.rules()) {
|
||||
for (auto& selector : rule.selectors()) {
|
||||
if (SelectorEngine::matches(selector, element)) {
|
||||
matching_rules.append(rule);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
#ifdef HTML_DEBUG
|
||||
dbgprintf("Rules matching Element{%p}\n", &element);
|
||||
for (auto& rule : matching_rules) {
|
||||
dump_rule(rule);
|
||||
}
|
||||
#endif
|
||||
|
||||
return matching_rules;
|
||||
}
|
||||
|
||||
bool StyleResolver::is_inherited_property(CSS::PropertyID property_id)
|
||||
{
|
||||
static HashTable<CSS::PropertyID> inherited_properties;
|
||||
if (inherited_properties.is_empty()) {
|
||||
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(CSS::PropertyID::TextDecoration);
|
||||
}
|
||||
return inherited_properties.contains(property_id);
|
||||
}
|
||||
|
||||
static Vector<String> split_on_whitespace(const StringView& string)
|
||||
{
|
||||
if (string.is_empty())
|
||||
return {};
|
||||
|
||||
Vector<String> v;
|
||||
size_t substart = 0;
|
||||
for (size_t i = 0; i < string.length(); ++i) {
|
||||
char ch = string.characters_without_null_termination()[i];
|
||||
if (isspace(ch)) {
|
||||
size_t sublen = i - substart;
|
||||
if (sublen != 0)
|
||||
v.append(string.substring_view(substart, sublen));
|
||||
substart = i + 1;
|
||||
}
|
||||
}
|
||||
size_t taillen = string.length() - substart;
|
||||
if (taillen != 0)
|
||||
v.append(string.substring_view(substart, taillen));
|
||||
return v;
|
||||
}
|
||||
|
||||
static void set_property_expanding_shorthands(StyleProperties& style, CSS::PropertyID property_id, const StyleValue& value)
|
||||
{
|
||||
if (property_id == CSS::PropertyID::BorderStyle) {
|
||||
style.set_property(CSS::PropertyID::BorderTopStyle, value);
|
||||
style.set_property(CSS::PropertyID::BorderRightStyle, value);
|
||||
style.set_property(CSS::PropertyID::BorderBottomStyle, value);
|
||||
style.set_property(CSS::PropertyID::BorderLeftStyle, value);
|
||||
return;
|
||||
}
|
||||
|
||||
if (property_id == CSS::PropertyID::BorderWidth) {
|
||||
style.set_property(CSS::PropertyID::BorderTopWidth, value);
|
||||
style.set_property(CSS::PropertyID::BorderRightWidth, value);
|
||||
style.set_property(CSS::PropertyID::BorderBottomWidth, value);
|
||||
style.set_property(CSS::PropertyID::BorderLeftWidth, value);
|
||||
return;
|
||||
}
|
||||
|
||||
if (property_id == CSS::PropertyID::BorderColor) {
|
||||
style.set_property(CSS::PropertyID::BorderTopColor, value);
|
||||
style.set_property(CSS::PropertyID::BorderRightColor, value);
|
||||
style.set_property(CSS::PropertyID::BorderBottomColor, value);
|
||||
style.set_property(CSS::PropertyID::BorderLeftColor, value);
|
||||
return;
|
||||
}
|
||||
|
||||
if (property_id == CSS::PropertyID::Margin) {
|
||||
if (value.is_length()) {
|
||||
style.set_property(CSS::PropertyID::MarginTop, value);
|
||||
style.set_property(CSS::PropertyID::MarginRight, value);
|
||||
style.set_property(CSS::PropertyID::MarginBottom, value);
|
||||
style.set_property(CSS::PropertyID::MarginLeft, value);
|
||||
return;
|
||||
}
|
||||
if (value.is_string()) {
|
||||
auto parts = split_on_whitespace(value.to_string());
|
||||
if (parts.size() == 2) {
|
||||
auto vertical = parse_css_value(parts[0]);
|
||||
auto horizontal = parse_css_value(parts[1]);
|
||||
style.set_property(CSS::PropertyID::MarginTop, vertical);
|
||||
style.set_property(CSS::PropertyID::MarginBottom, vertical);
|
||||
style.set_property(CSS::PropertyID::MarginLeft, horizontal);
|
||||
style.set_property(CSS::PropertyID::MarginRight, horizontal);
|
||||
return;
|
||||
}
|
||||
if (parts.size() == 3) {
|
||||
auto top = parse_css_value(parts[0]);
|
||||
auto horizontal = parse_css_value(parts[1]);
|
||||
auto bottom = parse_css_value(parts[2]);
|
||||
style.set_property(CSS::PropertyID::MarginTop, top);
|
||||
style.set_property(CSS::PropertyID::MarginBottom, bottom);
|
||||
style.set_property(CSS::PropertyID::MarginLeft, horizontal);
|
||||
style.set_property(CSS::PropertyID::MarginRight, horizontal);
|
||||
return;
|
||||
}
|
||||
if (parts.size() == 4) {
|
||||
auto top = parse_css_value(parts[0]);
|
||||
auto right = parse_css_value(parts[1]);
|
||||
auto bottom = parse_css_value(parts[2]);
|
||||
auto left = parse_css_value(parts[3]);
|
||||
style.set_property(CSS::PropertyID::MarginTop, top);
|
||||
style.set_property(CSS::PropertyID::MarginBottom, bottom);
|
||||
style.set_property(CSS::PropertyID::MarginLeft, left);
|
||||
style.set_property(CSS::PropertyID::MarginRight, right);
|
||||
return;
|
||||
}
|
||||
dbg() << "Unsure what to do with CSS margin value '" << value.to_string() << "'";
|
||||
return;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
if (property_id == CSS::PropertyID::Padding) {
|
||||
if (value.is_length()) {
|
||||
style.set_property(CSS::PropertyID::PaddingTop, value);
|
||||
style.set_property(CSS::PropertyID::PaddingRight, value);
|
||||
style.set_property(CSS::PropertyID::PaddingBottom, value);
|
||||
style.set_property(CSS::PropertyID::PaddingLeft, value);
|
||||
return;
|
||||
}
|
||||
if (value.is_string()) {
|
||||
auto parts = split_on_whitespace(value.to_string());
|
||||
if (parts.size() == 2) {
|
||||
auto vertical = parse_css_value(parts[0]);
|
||||
auto horizontal = parse_css_value(parts[1]);
|
||||
style.set_property(CSS::PropertyID::PaddingTop, vertical);
|
||||
style.set_property(CSS::PropertyID::PaddingBottom, vertical);
|
||||
style.set_property(CSS::PropertyID::PaddingLeft, horizontal);
|
||||
style.set_property(CSS::PropertyID::PaddingRight, horizontal);
|
||||
return;
|
||||
}
|
||||
if (parts.size() == 3) {
|
||||
auto top = parse_css_value(parts[0]);
|
||||
auto horizontal = parse_css_value(parts[1]);
|
||||
auto bottom = parse_css_value(parts[2]);
|
||||
style.set_property(CSS::PropertyID::PaddingTop, top);
|
||||
style.set_property(CSS::PropertyID::PaddingBottom, bottom);
|
||||
style.set_property(CSS::PropertyID::PaddingLeft, horizontal);
|
||||
style.set_property(CSS::PropertyID::PaddingRight, horizontal);
|
||||
return;
|
||||
}
|
||||
if (parts.size() == 4) {
|
||||
auto top = parse_css_value(parts[0]);
|
||||
auto right = parse_css_value(parts[1]);
|
||||
auto bottom = parse_css_value(parts[2]);
|
||||
auto left = parse_css_value(parts[3]);
|
||||
style.set_property(CSS::PropertyID::PaddingTop, top);
|
||||
style.set_property(CSS::PropertyID::PaddingBottom, bottom);
|
||||
style.set_property(CSS::PropertyID::PaddingLeft, left);
|
||||
style.set_property(CSS::PropertyID::PaddingRight, right);
|
||||
return;
|
||||
}
|
||||
dbg() << "Unsure what to do with CSS padding value '" << value.to_string() << "'";
|
||||
return;
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
style.set_property(property_id, value);
|
||||
}
|
||||
|
||||
NonnullRefPtr<StyleProperties> StyleResolver::resolve_style(const Element& element, const StyleProperties* parent_style) const
|
||||
{
|
||||
auto style = StyleProperties::create();
|
||||
|
||||
if (parent_style) {
|
||||
parent_style->for_each_property([&](auto property_id, auto& value) {
|
||||
if (is_inherited_property(property_id))
|
||||
set_property_expanding_shorthands(style, property_id, value);
|
||||
});
|
||||
}
|
||||
|
||||
element.apply_presentational_hints(*style);
|
||||
|
||||
auto matching_rules = collect_matching_rules(element);
|
||||
for (auto& rule : matching_rules) {
|
||||
for (auto& property : rule.declaration().properties()) {
|
||||
set_property_expanding_shorthands(style, property.property_id, property.value);
|
||||
}
|
||||
}
|
||||
|
||||
auto style_attribute = element.attribute("style");
|
||||
if (!style_attribute.is_null()) {
|
||||
if (auto declaration = parse_css_declaration(style_attribute)) {
|
||||
for (auto& property : declaration->properties()) {
|
||||
set_property_expanding_shorthands(style, property.property_id, property.value);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return style;
|
||||
}
|
||||
|
||||
}
|
62
Libraries/LibWeb/CSS/StyleResolver.h
Normal file
62
Libraries/LibWeb/CSS/StyleResolver.h
Normal file
|
@ -0,0 +1,62 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/NonnullRefPtrVector.h>
|
||||
#include <AK/OwnPtr.h>
|
||||
#include <LibWeb/CSS/StyleProperties.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class Document;
|
||||
class Element;
|
||||
class ParentNode;
|
||||
class StyleRule;
|
||||
class StyleSheet;
|
||||
|
||||
class StyleResolver {
|
||||
public:
|
||||
explicit StyleResolver(Document&);
|
||||
~StyleResolver();
|
||||
|
||||
Document& document() { return m_document; }
|
||||
const Document& document() const { return m_document; }
|
||||
|
||||
NonnullRefPtr<StyleProperties> resolve_style(const Element&, const StyleProperties* parent_style) const;
|
||||
|
||||
NonnullRefPtrVector<StyleRule> collect_matching_rules(const Element&) const;
|
||||
|
||||
static bool is_inherited_property(CSS::PropertyID);
|
||||
|
||||
private:
|
||||
template<typename Callback>
|
||||
void for_each_stylesheet(Callback) const;
|
||||
|
||||
Document& m_document;
|
||||
};
|
||||
|
||||
}
|
41
Libraries/LibWeb/CSS/StyleRule.cpp
Normal file
41
Libraries/LibWeb/CSS/StyleRule.cpp
Normal file
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibWeb/CSS/StyleRule.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
StyleRule::StyleRule(Vector<Selector>&& selectors, NonnullRefPtr<StyleDeclaration>&& declaration)
|
||||
: m_selectors(move(selectors))
|
||||
, m_declaration(move(declaration))
|
||||
{
|
||||
}
|
||||
|
||||
StyleRule::~StyleRule()
|
||||
{
|
||||
}
|
||||
|
||||
}
|
54
Libraries/LibWeb/CSS/StyleRule.h
Normal file
54
Libraries/LibWeb/CSS/StyleRule.h
Normal file
|
@ -0,0 +1,54 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/NonnullRefPtrVector.h>
|
||||
#include <LibWeb/CSS/Selector.h>
|
||||
#include <LibWeb/CSS/StyleDeclaration.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class StyleRule : public RefCounted<StyleRule> {
|
||||
public:
|
||||
static NonnullRefPtr<StyleRule> create(Vector<Selector>&& selectors, NonnullRefPtr<StyleDeclaration>&& declaration)
|
||||
{
|
||||
return adopt(*new StyleRule(move(selectors), move(declaration)));
|
||||
}
|
||||
|
||||
~StyleRule();
|
||||
|
||||
const Vector<Selector>& selectors() const { return m_selectors; }
|
||||
const StyleDeclaration& declaration() const { return m_declaration; }
|
||||
|
||||
private:
|
||||
StyleRule(Vector<Selector>&&, NonnullRefPtr<StyleDeclaration>&&);
|
||||
|
||||
Vector<Selector> m_selectors;
|
||||
NonnullRefPtr<StyleDeclaration> m_declaration;
|
||||
};
|
||||
|
||||
}
|
40
Libraries/LibWeb/CSS/StyleSheet.cpp
Normal file
40
Libraries/LibWeb/CSS/StyleSheet.cpp
Normal file
|
@ -0,0 +1,40 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <LibWeb/CSS/StyleSheet.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
StyleSheet::StyleSheet(NonnullRefPtrVector<StyleRule>&& rules)
|
||||
: m_rules(move(rules))
|
||||
{
|
||||
}
|
||||
|
||||
StyleSheet::~StyleSheet()
|
||||
{
|
||||
}
|
||||
|
||||
}
|
51
Libraries/LibWeb/CSS/StyleSheet.h
Normal file
51
Libraries/LibWeb/CSS/StyleSheet.h
Normal file
|
@ -0,0 +1,51 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/NonnullRefPtrVector.h>
|
||||
#include <LibWeb/CSS/StyleRule.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class StyleSheet : public RefCounted<StyleSheet> {
|
||||
public:
|
||||
static NonnullRefPtr<StyleSheet> create(NonnullRefPtrVector<StyleRule>&& rules)
|
||||
{
|
||||
return adopt(*new StyleSheet(move(rules)));
|
||||
}
|
||||
|
||||
~StyleSheet();
|
||||
|
||||
const NonnullRefPtrVector<StyleRule>& rules() const { return m_rules; }
|
||||
|
||||
private:
|
||||
explicit StyleSheet(NonnullRefPtrVector<StyleRule>&&);
|
||||
|
||||
NonnullRefPtrVector<StyleRule> m_rules;
|
||||
};
|
||||
|
||||
}
|
82
Libraries/LibWeb/CSS/StyleValue.cpp
Normal file
82
Libraries/LibWeb/CSS/StyleValue.cpp
Normal file
|
@ -0,0 +1,82 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <AK/ByteBuffer.h>
|
||||
#include <LibGfx/Bitmap.h>
|
||||
#include <LibGfx/PNGLoader.h>
|
||||
#include <LibWeb/CSS/StyleValue.h>
|
||||
#include <LibWeb/DOM/Document.h>
|
||||
#include <LibWeb/Frame.h>
|
||||
#include <LibWeb/ResourceLoader.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
StyleValue::StyleValue(Type type)
|
||||
: m_type(type)
|
||||
{
|
||||
}
|
||||
|
||||
StyleValue::~StyleValue()
|
||||
{
|
||||
}
|
||||
|
||||
String IdentifierStyleValue::to_string() const
|
||||
{
|
||||
switch (id()) {
|
||||
case CSS::ValueID::Invalid:
|
||||
return "(invalid)";
|
||||
case CSS::ValueID::VendorSpecificLink:
|
||||
return "-libhtml-link";
|
||||
default:
|
||||
ASSERT_NOT_REACHED();
|
||||
}
|
||||
}
|
||||
|
||||
Color IdentifierStyleValue::to_color(const Document& document) const
|
||||
{
|
||||
if (id() == CSS::ValueID::VendorSpecificLink)
|
||||
return document.link_color();
|
||||
return {};
|
||||
}
|
||||
|
||||
ImageStyleValue::ImageStyleValue(const URL& url, Document& document)
|
||||
: StyleValue(Type::Image)
|
||||
, m_url(url)
|
||||
, m_document(document.make_weak_ptr())
|
||||
{
|
||||
NonnullRefPtr<ImageStyleValue> protector(*this);
|
||||
ResourceLoader::the().load(url, [this, protector](auto& data) {
|
||||
if (!m_document)
|
||||
return;
|
||||
m_bitmap = Gfx::load_png_from_memory(data.data(), data.size());
|
||||
if (!m_bitmap)
|
||||
return;
|
||||
// FIXME: Do less than a full repaint if possible?
|
||||
m_document->frame()->set_needs_display({});
|
||||
});
|
||||
}
|
||||
|
||||
}
|
228
Libraries/LibWeb/CSS/StyleValue.h
Normal file
228
Libraries/LibWeb/CSS/StyleValue.h
Normal file
|
@ -0,0 +1,228 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020, Andreas Kling <kling@serenityos.org>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this
|
||||
* list of conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice,
|
||||
* this list of conditions and the following disclaimer in the documentation
|
||||
* and/or other materials provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
* DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
* CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
* OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/RefCounted.h>
|
||||
#include <AK/RefPtr.h>
|
||||
#include <AK/String.h>
|
||||
#include <AK/StringView.h>
|
||||
#include <AK/URL.h>
|
||||
#include <AK/WeakPtr.h>
|
||||
#include <LibGfx/Color.h>
|
||||
#include <LibGfx/Bitmap.h>
|
||||
#include <LibWeb/CSS/Length.h>
|
||||
#include <LibWeb/CSS/PropertyID.h>
|
||||
|
||||
namespace Web {
|
||||
|
||||
class Document;
|
||||
|
||||
namespace CSS {
|
||||
enum class ValueID {
|
||||
Invalid,
|
||||
VendorSpecificLink,
|
||||
Center,
|
||||
Left,
|
||||
Right,
|
||||
Justify,
|
||||
};
|
||||
}
|
||||
|
||||
class StyleValue : public RefCounted<StyleValue> {
|
||||
public:
|
||||
virtual ~StyleValue();
|
||||
|
||||
enum class Type {
|
||||
Invalid,
|
||||
Inherit,
|
||||
Initial,
|
||||
String,
|
||||
Length,
|
||||
Color,
|
||||
Identifier,
|
||||
Image,
|
||||
};
|
||||
|
||||
Type type() const { return m_type; }
|
||||
|
||||
bool is_inherit() const { return type() == Type::Inherit; }
|
||||
bool is_initial() const { return type() == Type::Initial; }
|
||||
bool is_color() const { return type() == Type::Color; }
|
||||
bool is_identifier() const { return type() == Type::Identifier; }
|
||||
bool is_image() const { return type() == Type::Image; }
|
||||
bool is_string() const { return type() == Type::String; }
|
||||
bool is_length() const { return type() == Type::Length; }
|
||||
|
||||
virtual String to_string() const = 0;
|
||||
virtual Length to_length() const { return {}; }
|
||||
virtual Color to_color(const Document&) const { return {}; }
|
||||
|
||||
virtual bool is_auto() const { return false; }
|
||||
|
||||
protected:
|
||||
explicit StyleValue(Type);
|
||||
|
||||
private:
|
||||
Type m_type { Type::Invalid };
|
||||
};
|
||||
|
||||
class StringStyleValue : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<StringStyleValue> create(const String& string)
|
||||
{
|
||||
return adopt(*new StringStyleValue(string));
|
||||
}
|
||||
virtual ~StringStyleValue() override {}
|
||||
|
||||
String to_string() const override { return m_string; }
|
||||
|
||||
private:
|
||||
explicit StringStyleValue(const String& string)
|
||||
: StyleValue(Type::String)
|
||||
, m_string(string)
|
||||
{
|
||||
}
|
||||
|
||||
String m_string;
|
||||
};
|
||||
|
||||
class LengthStyleValue : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<LengthStyleValue> create(const Length& length)
|
||||
{
|
||||
return adopt(*new LengthStyleValue(length));
|
||||
}
|
||||
virtual ~LengthStyleValue() override {}
|
||||
|
||||
virtual String to_string() const override { return m_length.to_string(); }
|
||||
virtual Length to_length() const override { return m_length; }
|
||||
|
||||
const Length& length() const { return m_length; }
|
||||
|
||||
virtual bool is_auto() const override { return m_length.is_auto(); }
|
||||
|
||||
private:
|
||||
explicit LengthStyleValue(const Length& length)
|
||||
: StyleValue(Type::Length)
|
||||
, m_length(length)
|
||||
{
|
||||
}
|
||||
|
||||
Length m_length;
|
||||
};
|
||||
|
||||
class InitialStyleValue final : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<InitialStyleValue> create() { return adopt(*new InitialStyleValue); }
|
||||
virtual ~InitialStyleValue() override {}
|
||||
|
||||
String to_string() const override { return "initial"; }
|
||||
|
||||
private:
|
||||
InitialStyleValue()
|
||||
: StyleValue(Type::Initial)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
class InheritStyleValue final : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<InheritStyleValue> create() { return adopt(*new InheritStyleValue); }
|
||||
virtual ~InheritStyleValue() override {}
|
||||
|
||||
String to_string() const override { return "inherit"; }
|
||||
|
||||
private:
|
||||
InheritStyleValue()
|
||||
: StyleValue(Type::Inherit)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
class ColorStyleValue : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<ColorStyleValue> create(Color color)
|
||||
{
|
||||
return adopt(*new ColorStyleValue(color));
|
||||
}
|
||||
virtual ~ColorStyleValue() override {}
|
||||
|
||||
Color color() const { return m_color; }
|
||||
String to_string() const override { return m_color.to_string(); }
|
||||
Color to_color(const Document&) const override { return m_color; }
|
||||
|
||||
private:
|
||||
explicit ColorStyleValue(Color color)
|
||||
: StyleValue(Type::Color)
|
||||
, m_color(color)
|
||||
{
|
||||
}
|
||||
|
||||
Color m_color;
|
||||
};
|
||||
|
||||
class IdentifierStyleValue final : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<IdentifierStyleValue> create(CSS::ValueID id)
|
||||
{
|
||||
return adopt(*new IdentifierStyleValue(id));
|
||||
}
|
||||
virtual ~IdentifierStyleValue() override {}
|
||||
|
||||
CSS::ValueID id() const { return m_id; }
|
||||
|
||||
virtual String to_string() const override;
|
||||
virtual Color to_color(const Document&) const override;
|
||||
|
||||
private:
|
||||
explicit IdentifierStyleValue(CSS::ValueID id)
|
||||
: StyleValue(Type::Identifier)
|
||||
, m_id(id)
|
||||
{
|
||||
}
|
||||
|
||||
CSS::ValueID m_id { CSS::ValueID::Invalid };
|
||||
};
|
||||
|
||||
class ImageStyleValue final : public StyleValue {
|
||||
public:
|
||||
static NonnullRefPtr<ImageStyleValue> create(const URL& url, Document& document) { return adopt(*new ImageStyleValue(url, document)); }
|
||||
virtual ~ImageStyleValue() override {}
|
||||
|
||||
String to_string() const override { return String::format("Image{%s}", m_url.to_string().characters()); }
|
||||
|
||||
const Gfx::Bitmap* bitmap() const { return m_bitmap; }
|
||||
|
||||
private:
|
||||
ImageStyleValue(const URL&, Document&);
|
||||
|
||||
URL m_url;
|
||||
WeakPtr<Document> m_document;
|
||||
RefPtr<Gfx::Bitmap> m_bitmap;
|
||||
};
|
||||
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue