[librsvg: 1/3] Add a user agent stylesheet
- From: Federico Mena Quintero <federico src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [librsvg: 1/3] Add a user agent stylesheet
- Date: Tue, 24 Mar 2020 15:06:11 +0000 (UTC)
commit a904d1785b8cbafc5a3887130d5bd98b4d3dc1cc
Author: Paolo Borelli <pborelli gnome org>
Date: Fri Mar 20 14:48:51 2020 +0100
Add a user agent stylesheet
Add a stylesheet with the user agent defaults present in the
specification and remove the special cases in SpecifiedValues.
Note: this breaks a couple of reftests because we do not
currently handle correctly the priority of presentation
attributes and user agent css.
Makefile.am | 1 +
rsvg_internals/src/css.rs | 16 ++++++++++++----
rsvg_internals/src/document.rs | 12 +++++++++---
rsvg_internals/src/element.rs | 38 ++++++++++---------------------------
rsvg_internals/src/properties.rs | 11 -----------
rsvg_internals/src/ua.css | 41 ++++++++++++++++++++++++++++++++++++++++
6 files changed, 73 insertions(+), 46 deletions(-)
---
diff --git a/Makefile.am b/Makefile.am
index e1a92eab..bf2c1888 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -130,6 +130,7 @@ RUST_EXTRA = \
rsvg_internals/benches/lighting.rs \
rsvg_internals/benches/pixel_iterators.rs \
rsvg_internals/benches/srgb.rs \
+ rsvg_internals/src/ua.css \
$(NULL)
if DEBUG_RELEASE
diff --git a/rsvg_internals/src/css.rs b/rsvg_internals/src/css.rs
index 130e5806..57e74031 100644
--- a/rsvg_internals/src/css.rs
+++ b/rsvg_internals/src/css.rs
@@ -566,7 +566,6 @@ impl selectors::Element for RsvgElement {
/// Origin for a stylesheet, per https://www.w3.org/TR/CSS22/cascade.html#cascading-order
///
/// This is used when sorting selector matches according to their origin and specificity.
-#[allow(unused)]
#[derive(Copy, Clone, Eq, Ord, PartialEq, PartialOrd)]
pub enum Origin {
UserAgent,
@@ -735,7 +734,12 @@ impl Stylesheet {
}
/// Runs the CSS cascade on the specified tree from all the stylesheets
-pub fn cascade(root: &mut Node, stylesheets: &[Stylesheet], extra: &[Stylesheet]) {
+pub fn cascade(
+ root: &mut Node,
+ ua_stylesheets: &[Stylesheet],
+ author_stylesheets: &[Stylesheet],
+ user_stylesheets: &[Stylesheet],
+) {
for mut node in root.descendants().filter(|n| n.is_element()) {
let mut matches = Vec::new();
@@ -748,8 +752,12 @@ pub fn cascade(root: &mut Node, stylesheets: &[Stylesheet], extra: &[Stylesheet]
QuirksMode::NoQuirks,
);
- for stylesheet in stylesheets.iter().chain(extra.iter()) {
- stylesheet.get_matches(&node, &mut match_ctx, &mut matches);
+ for s in ua_stylesheets
+ .iter()
+ .chain(author_stylesheets)
+ .chain(user_stylesheets)
+ {
+ s.get_matches(&node, &mut match_ctx, &mut matches);
}
matches.as_mut_slice().sort();
diff --git a/rsvg_internals/src/document.rs b/rsvg_internals/src/document.rs
index a5d67d76..23a5ccf4 100644
--- a/rsvg_internals/src/document.rs
+++ b/rsvg_internals/src/document.rs
@@ -2,9 +2,11 @@
use gdk_pixbuf::{PixbufLoader, PixbufLoaderExt};
use markup5ever::QualName;
+use once_cell::sync::Lazy;
use std::cell::RefCell;
use std::collections::hash_map::Entry;
use std::collections::HashMap;
+use std::include_str;
use std::rc::Rc;
use crate::allowed_url::{AllowedUrl, AllowedUrlError, Fragment};
@@ -20,6 +22,10 @@ use crate::structure::{IntrinsicDimensions, Svg};
use crate::surface_utils::shared_surface::SharedImageSurface;
use crate::xml::xml_load_from_possibly_compressed_stream;
+static UA_STYLESHEETS: Lazy<Vec<Stylesheet>> = Lazy::new(|| {
+ vec![Stylesheet::from_data(include_str!("ua.css"), None, Origin::UserAgent).unwrap()]
+});
+
/// A loaded SVG file and its derived data.
pub struct Document {
/// Tree of nodes; the root is guaranteed to be an `<svg>` element.
@@ -103,10 +109,10 @@ impl Document {
/// Runs the CSS cascade on the document tree
///
- /// This uses the document's internal stylesheets, plus an extra set of stylesheets
- /// supplied by the caller.
+ /// This uses the deafault UserAgent stylesheet, the document's internal stylesheets,
+ /// plus an extra set of stylesheets supplied by the caller.
pub fn cascade(&mut self, extra: &[Stylesheet]) {
- css::cascade(&mut self.tree, &self.stylesheets, extra);
+ css::cascade(&mut self.tree, &UA_STYLESHEETS, &self.stylesheets, extra);
}
}
diff --git a/rsvg_internals/src/element.rs b/rsvg_internals/src/element.rs
index 6166c4f0..486d54fa 100644
--- a/rsvg_internals/src/element.rs
+++ b/rsvg_internals/src/element.rs
@@ -372,18 +372,13 @@ impl fmt::Display for Element {
macro_rules! e {
($name:ident, $element_type:ident) => {
- pub fn $name(
- element_name: &QualName,
- id: Option<&str>,
- class: Option<&str>,
- specified_values: SpecifiedValues,
- ) -> Element {
+ pub fn $name(element_name: &QualName, id: Option<&str>, class: Option<&str>) -> Element {
Element {
element_type: ElementType::$element_type,
element_name: element_name.clone(),
id: id.map(str::to_string),
class: class.map(str::to_string),
- specified_values,
+ specified_values: Default::default(),
important_styles: Default::default(),
transform: Default::default(),
result: Ok(()),
@@ -469,20 +464,13 @@ mod creators {
use creators::*;
-type ElementCreateFn = fn(
- element_name: &QualName,
- id: Option<&str>,
- class: Option<&str>,
- specified_values: SpecifiedValues,
-) -> Element;
+type ElementCreateFn =
+ fn(element_name: &QualName, id: Option<&str>, class: Option<&str>) -> Element;
-// For now it's just an enum, if some element needs more than one flag
-// we will need something fancier
#[derive(Copy, Clone, PartialEq)]
enum ElementCreateFlags {
Default,
IgnoreClass,
- OverflowHidden,
}
// Lines in comments are elements that we don't support.
@@ -543,17 +531,17 @@ static ELEMENT_CREATORS: Lazy<HashMap<&'static str, (ElementCreateFn, ElementCre
/* ("glyph", ), */
/* ("glyphRef", ), */
/* ("hkern", ), */
- ("image", create_image, OverflowHidden),
+ ("image", create_image, Default),
("line", create_line, Default),
("linearGradient", create_linear_gradient, Default),
- ("marker", create_marker, OverflowHidden),
+ ("marker", create_marker, Default),
("mask", create_mask, Default),
/* ("metadata", ), */
/* ("missing-glyph", ), */
/* ("mpath", ), */
/* ("multiImage", ), */
("path", create_path, Default),
- ("pattern", create_pattern, OverflowHidden),
+ ("pattern", create_pattern, Default),
("polygon", create_polygon, Default),
("polyline", create_polyline, Default),
("radialGradient", create_radial_gradient, Default),
@@ -564,9 +552,9 @@ static ELEMENT_CREATORS: Lazy<HashMap<&'static str, (ElementCreateFn, ElementCre
("style", create_style, IgnoreClass),
/* ("subImage", ), */
/* ("subImageRef", ), */
- ("svg", create_svg, OverflowHidden),
+ ("svg", create_svg, Default),
("switch", create_switch, Default),
- ("symbol", create_symbol, OverflowHidden),
+ ("symbol", create_symbol, Default),
("text", create_text, Default),
/* ("textPath", ), */
/* ("title", ), */
@@ -623,15 +611,9 @@ pub fn create_element(name: &QualName, pbag: &PropertyBag) -> Element {
class = None;
};
- let specified_values = if flags == ElementCreateFlags::OverflowHidden {
- SpecifiedValues::with_overflow_hidden()
- } else {
- SpecifiedValues::default()
- };
-
// sizes::print_sizes();
- create_fn(name, id, class, specified_values)
+ create_fn(name, id, class)
}
#[cfg(ignore)]
diff --git a/rsvg_internals/src/properties.rs b/rsvg_internals/src/properties.rs
index f250c263..277705ae 100644
--- a/rsvg_internals/src/properties.rs
+++ b/rsvg_internals/src/properties.rs
@@ -262,17 +262,6 @@ impl Default for SpecifiedValues {
}
}
-impl SpecifiedValues {
- pub fn with_overflow_hidden() -> SpecifiedValues {
- let mut s = SpecifiedValues::default();
- s.set_parsed_property(&ParsedProperty::Overflow(SpecifiedValue::Specified(
- Overflow::Hidden,
- )));
-
- s
- }
-}
-
#[derive(Debug, Default, Clone)]
pub struct ComputedValues {
pub baseline_shift: BaselineShift,
diff --git a/rsvg_internals/src/ua.css b/rsvg_internals/src/ua.css
new file mode 100644
index 00000000..3292f8ac
--- /dev/null
+++ b/rsvg_internals/src/ua.css
@@ -0,0 +1,41 @@
+/* See https://www.w3.org/TR/SVG/styling.html#UAStyleSheet
+ *
+ * Commented out rules cannot yet be parsed.
+ */
+
+/*
+@namespace url(http://www.w3.org/2000/svg);
+@namespace xml url(http://www.w3.org/XML/1998/namespace);
+*/
+
+svg:not(:root), image, marker, pattern, symbol { overflow: hidden; }
+
+/*
+*:not(svg),
+*:not(foreignObject) > svg {
+ transform-origin: 0 0;
+}
+
+*[xml|space=preserve] {
+ text-space-collapse: preserve-spaces;
+}
+*/
+
+defs,
+clipPath, mask, marker,
+desc, title, metadata,
+pattern, linearGradient, radialGradient,
+script, style,
+symbol {
+ display: none !important;
+}
+
+:host(use) > symbol {
+ display: inline !important;
+}
+
+/*
+:link, :visited {
+ cursor: pointer;
+}
+*
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]