aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbors-servo <lbergstrom+bors@mozilla.com>2018-04-17 14:06:08 -0400
committerGitHub <noreply@github.com>2018-04-17 14:06:08 -0400
commit087bd20b6d4e61fd54b71ed42a0ce757f993bb66 (patch)
treed9832afccb299c9f17f28dd381863072d5ad2a97
parent50817554180199f67268b355e53124f55f68207a (diff)
parenta82ed50257ebafe33dac5595606a4c4e548102b2 (diff)
downloadservo-087bd20b6d4e61fd54b71ed42a0ce757f993bb66.tar.gz
servo-087bd20b6d4e61fd54b71ed42a0ce757f993bb66.zip
Auto merge of #20657 - emilio:gecko-sync, r=emilio
style: Sync changes from mozilla-central. See each individual commit from details.
-rw-r--r--components/layout_thread/dom_wrapper.rs8
-rw-r--r--components/script/dom/document.rs18
-rw-r--r--components/style/dom.rs9
-rw-r--r--components/style/gecko/data.rs31
-rw-r--r--components/style/gecko/generated/structs.rs2
-rw-r--r--components/style/gecko/wrapper.rs24
-rw-r--r--components/style/properties/data.py5
-rw-r--r--components/style/style_adjuster.rs113
-rw-r--r--components/style/stylesheet_set.rs2
-rw-r--r--components/style/stylesheets/import_rule.rs113
-rw-r--r--components/style/stylesheets/rules_iterator.rs11
-rw-r--r--components/style/stylesheets/stylesheet.rs80
-rw-r--r--ports/geckolib/glue.rs2
-rw-r--r--ports/geckolib/stylesheet_loader.rs5
14 files changed, 327 insertions, 96 deletions
diff --git a/components/layout_thread/dom_wrapper.rs b/components/layout_thread/dom_wrapper.rs
index 55bacd037cb..309ddaf7e93 100644
--- a/components/layout_thread/dom_wrapper.rs
+++ b/components/layout_thread/dom_wrapper.rs
@@ -397,6 +397,14 @@ impl<'le> TElement for ServoLayoutElement<'le> {
unsafe { self.element.is_html_element() }
}
+ fn is_mathml_element(&self) -> bool {
+ *self.element.namespace() == ns!(mathml)
+ }
+
+ fn is_svg_element(&self) -> bool {
+ *self.element.namespace() == ns!(svg)
+ }
+
fn style_attribute(&self) -> Option<ArcBorrow<StyleLocked<PropertyDeclarationBlock>>> {
unsafe {
(*self.element.style_attribute()).as_ref().map(|x| x.borrow_arc())
diff --git a/components/script/dom/document.rs b/components/script/dom/document.rs
index 01b9a13ba40..71df0e70356 100644
--- a/components/script/dom/document.rs
+++ b/components/script/dom/document.rs
@@ -135,7 +135,7 @@ use style::selector_parser::{RestyleDamage, Snapshot};
use style::shared_lock::{SharedRwLock as StyleSharedRwLock, SharedRwLockReadGuard};
use style::str::{split_html_space_chars, str_join};
use style::stylesheet_set::DocumentStylesheetSet;
-use style::stylesheets::{Stylesheet, StylesheetContents, Origin, OriginSet};
+use style::stylesheets::{CssRule, Stylesheet, Origin, OriginSet};
use task_source::TaskSource;
use time;
use timers::OneshotTimerCallback;
@@ -216,17 +216,25 @@ impl PartialEq for StyleSheetInDocument {
}
impl ::style::stylesheets::StylesheetInDocument for StyleSheetInDocument {
- fn contents(&self, guard: &SharedRwLockReadGuard) -> &StylesheetContents {
- self.sheet.contents(guard)
+ fn origin(&self, guard: &SharedRwLockReadGuard) -> Origin {
+ self.sheet.origin(guard)
}
- fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
- self.sheet.media(guard)
+ fn quirks_mode(&self, guard: &SharedRwLockReadGuard) -> QuirksMode {
+ self.sheet.quirks_mode(guard)
}
fn enabled(&self) -> bool {
self.sheet.enabled()
}
+
+ fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
+ self.sheet.media(guard)
+ }
+
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ self.sheet.rules(guard)
+ }
}
/// <https://dom.spec.whatwg.org/#document>
diff --git a/components/style/dom.rs b/components/style/dom.rs
index acc1c364ca8..bee4d88329e 100644
--- a/components/style/dom.rs
+++ b/components/style/dom.rs
@@ -434,6 +434,15 @@ pub trait TElement:
/// Return whether this element is an element in the HTML namespace.
fn is_html_element(&self) -> bool;
+ /// Return whether this element is an element in the MathML namespace.
+ fn is_mathml_element(&self) -> bool;
+
+ /// Return whether this element is an element in the SVG namespace.
+ fn is_svg_element(&self) -> bool;
+
+ /// Return whether this element is an element in the XUL namespace.
+ fn is_xul_element(&self) -> bool { false }
+
/// Return the list of slotted nodes of this node.
fn slotted_nodes(&self) -> &[Self::ConcreteNode] {
&[]
diff --git a/components/style/gecko/data.rs b/components/style/gecko/data.rs
index 9c58a292dfc..331b07ea551 100644
--- a/components/style/gecko/data.rs
+++ b/components/style/gecko/data.rs
@@ -5,6 +5,7 @@
//! Data needed to style a Gecko document.
use atomic_refcell::{AtomicRef, AtomicRefCell, AtomicRefMut};
+use context::QuirksMode;
use dom::TElement;
use gecko_bindings::bindings::{self, RawServoStyleSet};
use gecko_bindings::structs::{self, RawGeckoPresContextOwned, ServoStyleSetSizes, ServoStyleSheet};
@@ -17,7 +18,7 @@ use properties::ComputedValues;
use selector_parser::SnapshotMap;
use servo_arc::Arc;
use shared_lock::{Locked, SharedRwLockReadGuard, StylesheetGuards};
-use stylesheets::{StylesheetContents, StylesheetInDocument};
+use stylesheets::{CssRule, Origin, StylesheetContents, StylesheetInDocument};
use stylist::Stylist;
/// Little wrapper to a Gecko style sheet.
@@ -58,6 +59,16 @@ impl GeckoStyleSheet {
&*(self.raw()._base.mInner as *const StyleSheetInfo as *const ServoStyleSheetInner)
}
}
+
+ /// Gets the StylesheetContents for this stylesheet.
+ pub fn contents(&self) -> &StylesheetContents {
+ debug_assert!(!self.inner().mContents.mRawPtr.is_null());
+ unsafe {
+ let contents =
+ (&**StylesheetContents::as_arc(&&*self.inner().mContents.mRawPtr)) as *const _;
+ &*contents
+ }
+ }
}
impl Drop for GeckoStyleSheet {
@@ -74,13 +85,12 @@ impl Clone for GeckoStyleSheet {
}
impl StylesheetInDocument for GeckoStyleSheet {
- fn contents(&self, _: &SharedRwLockReadGuard) -> &StylesheetContents {
- debug_assert!(!self.inner().mContents.mRawPtr.is_null());
- unsafe {
- let contents =
- (&**StylesheetContents::as_arc(&&*self.inner().mContents.mRawPtr)) as *const _;
- &*contents
- }
+ fn origin(&self, _guard: &SharedRwLockReadGuard) -> Origin {
+ self.contents().origin
+ }
+
+ fn quirks_mode(&self, _guard: &SharedRwLockReadGuard) -> QuirksMode {
+ self.contents().quirks_mode
}
fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
@@ -103,6 +113,11 @@ impl StylesheetInDocument for GeckoStyleSheet {
fn enabled(&self) -> bool {
true
}
+
+ #[inline]
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ self.contents().rules(guard)
+ }
}
/// The container for data that a Servo-backed Gecko document needs to style
diff --git a/components/style/gecko/generated/structs.rs b/components/style/gecko/generated/structs.rs
index 0cf29c89cd6..ebe6b79afbc 100644
--- a/components/style/gecko/generated/structs.rs
+++ b/components/style/gecko/generated/structs.rs
@@ -18478,7 +18478,7 @@ pub mod root {
eCSSProperty_flex_grow = 105,
eCSSProperty_flex_shrink = 106,
eCSSProperty_flex_wrap = 107,
- eCSSProperty_float_ = 108,
+ eCSSProperty_float = 108,
eCSSProperty__moz_float_edge = 109,
eCSSProperty_flood_color = 110,
eCSSProperty_flood_opacity = 111,
diff --git a/components/style/gecko/wrapper.rs b/components/style/gecko/wrapper.rs
index 2764c7e73b3..c00a41049c2 100644
--- a/components/style/gecko/wrapper.rs
+++ b/components/style/gecko/wrapper.rs
@@ -674,11 +674,6 @@ impl<'le> GeckoElement<'le> {
}
#[inline]
- fn is_xul_element(&self) -> bool {
- self.namespace_id() == (structs::root::kNameSpaceID_XUL as i32)
- }
-
- #[inline]
fn has_id(&self) -> bool {
self.as_node()
.get_bool_flag(nsINode_BooleanFlag::ElementHasID)
@@ -826,7 +821,7 @@ impl<'le> GeckoElement<'le> {
match self.parent_element() {
Some(e) => {
e.local_name() == &*local_name!("use") &&
- e.namespace() == &*ns!("http://www.w3.org/2000/svg")
+ e.is_svg_element()
},
None => false,
}
@@ -1058,7 +1053,22 @@ impl<'le> TElement for GeckoElement<'le> {
#[inline]
fn is_html_element(&self) -> bool {
- self.namespace_id() == (structs::root::kNameSpaceID_XHTML as i32)
+ self.namespace_id() == structs::kNameSpaceID_XHTML as i32
+ }
+
+ #[inline]
+ fn is_mathml_element(&self) -> bool {
+ self.namespace_id() == structs::kNameSpaceID_MathML as i32
+ }
+
+ #[inline]
+ fn is_svg_element(&self) -> bool {
+ self.namespace_id() == structs::kNameSpaceID_SVG as i32
+ }
+
+ #[inline]
+ fn is_xul_element(&self) -> bool {
+ self.namespace_id() == structs::root::kNameSpaceID_XUL as i32
}
/// Return the list of slotted nodes of this node.
diff --git a/components/style/properties/data.py b/components/style/properties/data.py
index b7da420dd9e..938b2c2c2bf 100644
--- a/components/style/properties/data.py
+++ b/components/style/properties/data.py
@@ -311,10 +311,7 @@ class Longhand(object):
return "<{} as ToAnimatedValue>::AnimatedValue".format(computed)
def nscsspropertyid(self):
- ident = self.ident
- if ident == "float":
- ident = "float_"
- return "nsCSSPropertyID::eCSSProperty_%s" % ident
+ return "nsCSSPropertyID::eCSSProperty_%s" % self.ident
class Shorthand(object):
diff --git a/components/style/style_adjuster.rs b/components/style/style_adjuster.rs
index 10e62b87cc2..b7270976ead 100644
--- a/components/style/style_adjuster.rs
+++ b/components/style/style_adjuster.rs
@@ -23,6 +23,86 @@ pub struct StyleAdjuster<'a, 'b: 'a> {
style: &'a mut StyleBuilder<'b>,
}
+#[cfg(feature = "gecko")]
+fn is_topmost_svg_svg_element<E>(e: E) -> bool
+where
+ E: TElement,
+{
+ debug_assert!(e.is_svg_element());
+ if e.local_name() != &*atom!("svg") {
+ return false;
+ }
+
+ let parent = match e.traversal_parent() {
+ Some(n) => n,
+ None => return true,
+ };
+
+ if !parent.is_svg_element() {
+ return true;
+ }
+
+ parent.local_name() == &*atom!("foreignObject")
+}
+
+// https://drafts.csswg.org/css-display/#unbox
+#[cfg(feature = "gecko")]
+fn is_effective_display_none_for_display_contents<E>(element: E) -> bool
+where
+ E: TElement,
+{
+ use Atom;
+
+ // FIXME(emilio): This should be an actual static.
+ lazy_static! {
+ static ref SPECIAL_HTML_ELEMENTS: [Atom; 16] = [
+ atom!("br"), atom!("wbr"), atom!("meter"), atom!("progress"),
+ atom!("canvas"), atom!("embed"), atom!("object"), atom!("audio"),
+ atom!("iframe"), atom!("img"), atom!("video"), atom!("frame"),
+ atom!("frameset"), atom!("input"), atom!("textarea"),
+ atom!("select"),
+ ];
+ }
+
+ // https://drafts.csswg.org/css-display/#unbox-svg
+ //
+ // There's a note about "Unknown elements", but there's not a good way to
+ // know what that means, or to get that information from here, and no other
+ // UA implements this either.
+ lazy_static! {
+ static ref SPECIAL_SVG_ELEMENTS: [Atom; 6] = [
+ atom!("svg"), atom!("a"), atom!("g"), atom!("use"),
+ atom!("tspan"), atom!("textPath"),
+ ];
+ }
+
+ // https://drafts.csswg.org/css-display/#unbox-html
+ if element.is_html_element() {
+ let local_name = element.local_name();
+ return SPECIAL_HTML_ELEMENTS.iter().any(|name| &**name == local_name);
+ }
+
+ // https://drafts.csswg.org/css-display/#unbox-svg
+ if element.is_svg_element() {
+ if is_topmost_svg_svg_element(element) {
+ return true;
+ }
+ let local_name = element.local_name();
+ return !SPECIAL_SVG_ELEMENTS.iter().any(|name| &**name == local_name);
+ }
+
+ // https://drafts.csswg.org/css-display/#unbox-mathml
+ //
+ // We always treat XUL as display: none. We don't use display:
+ // contents in XUL anyway, so should be fine to be consistent with
+ // MathML unless there's a use case for it.
+ if element.is_mathml_element() || element.is_xul_element() {
+ return true;
+ }
+
+ false
+}
+
impl<'a, 'b: 'a> StyleAdjuster<'a, 'b> {
/// Trivially constructs a new StyleAdjuster.
#[inline]
@@ -377,20 +457,35 @@ impl<'a, 'b: 'a> StyleAdjuster<'a, 'b> {
}
}
- /// Native anonymous content converts display:contents into display:inline.
+ /// Handles the relevant sections in:
+ ///
+ /// https://drafts.csswg.org/css-display/#unbox-html
+ ///
+ /// And forbidding display: contents in pseudo-elements, at least for now.
#[cfg(feature = "gecko")]
- fn adjust_for_prohibited_display_contents(&mut self) {
- // TODO: We should probably convert display:contents into display:none
- // in some cases too: https://drafts.csswg.org/css-display/#unbox
- //
+ fn adjust_for_prohibited_display_contents<E>(&mut self, element: Option<E>)
+ where
+ E: TElement,
+ {
+ if self.style.get_box().clone_display() != Display::Contents {
+ return;
+ }
+
// FIXME(emilio): ::before and ::after should support display: contents,
// see bug 1418138.
- if self.style.pseudo.is_none() || self.style.get_box().clone_display() != Display::Contents
- {
+ if self.style.pseudo.is_some() {
+ self.style.mutate_box().set_display(Display::Inline);
return;
}
- self.style.mutate_box().set_display(Display::Inline);
+ let element = match element {
+ Some(e) => e,
+ None => return,
+ };
+
+ if is_effective_display_none_for_display_contents(element) {
+ self.style.mutate_box().set_display(Display::None);
+ }
}
/// If a <fieldset> has grid/flex display type, we need to inherit
@@ -657,7 +752,7 @@ impl<'a, 'b: 'a> StyleAdjuster<'a, 'b> {
self.adjust_for_visited(element);
#[cfg(feature = "gecko")]
{
- self.adjust_for_prohibited_display_contents();
+ self.adjust_for_prohibited_display_contents(element);
self.adjust_for_fieldset_content(layout_parent_style);
}
self.adjust_for_top_layer();
diff --git a/components/style/stylesheet_set.rs b/components/style/stylesheet_set.rs
index 1091b6674a1..a3b6e5cdc17 100644
--- a/components/style/stylesheet_set.rs
+++ b/components/style/stylesheet_set.rs
@@ -478,7 +478,7 @@ where
sheet: &S,
guard: &SharedRwLockReadGuard,
) -> &mut SheetCollection<S> {
- let origin = sheet.contents(guard).origin;
+ let origin = sheet.origin(guard);
self.collections.borrow_mut_for_origin(&origin)
}
diff --git a/components/style/stylesheets/import_rule.rs b/components/style/stylesheets/import_rule.rs
index 75557ed50ee..fb50ec69732 100644
--- a/components/style/stylesheets/import_rule.rs
+++ b/components/style/stylesheets/import_rule.rs
@@ -6,6 +6,7 @@
//!
//! [import]: https://drafts.csswg.org/css-cascade-3/#at-import
+use context::QuirksMode;
use cssparser::SourceLocation;
use media_queries::MediaList;
use shared_lock::{DeepCloneParams, DeepCloneWithLock};
@@ -13,13 +14,52 @@ use shared_lock::{SharedRwLock, SharedRwLockReadGuard, ToCssWithGuard};
use std::fmt::{self, Write};
use str::CssStringWriter;
use style_traits::{CssWriter, ToCss};
-use stylesheets::{StylesheetContents, StylesheetInDocument};
+use stylesheets::{CssRule, Origin, StylesheetInDocument};
use values::CssUrl;
+/// With asynchronous stylesheet parsing, we can't synchronously create a
+/// GeckoStyleSheet. So we use this placeholder instead.
+#[derive(Clone, Debug)]
+pub struct PendingSheet {
+ origin: Origin,
+ quirks_mode: QuirksMode,
+}
+
/// A sheet that is held from an import rule.
#[cfg(feature = "gecko")]
#[derive(Debug)]
-pub struct ImportSheet(pub ::gecko::data::GeckoStyleSheet);
+pub enum ImportSheet {
+ /// A bonafide stylesheet.
+ Sheet(::gecko::data::GeckoStyleSheet),
+ /// An @import created while parsing off-main-thread, whose Gecko sheet has
+ /// yet to be created and attached.
+ Pending(PendingSheet),
+}
+
+#[cfg(feature = "gecko")]
+impl ImportSheet {
+ /// Creates a new ImportSheet from a GeckoStyleSheet.
+ pub fn new(sheet: ::gecko::data::GeckoStyleSheet) -> Self {
+ ImportSheet::Sheet(sheet)
+ }
+
+ /// Creates a pending ImportSheet for a load that has not started yet.
+ pub fn new_pending(origin: Origin, quirks_mode: QuirksMode) -> Self {
+ ImportSheet::Pending(PendingSheet {
+ origin,
+ quirks_mode,
+ })
+ }
+
+ /// Returns a reference to the GeckoStyleSheet in this ImportSheet, if it
+ /// exists.
+ pub fn as_sheet(&self) -> Option<&::gecko::data::GeckoStyleSheet> {
+ match *self {
+ ImportSheet::Sheet(ref s) => Some(s),
+ ImportSheet::Pending(_) => None,
+ }
+ }
+}
#[cfg(feature = "gecko")]
impl DeepCloneWithLock for ImportSheet {
@@ -31,10 +71,53 @@ impl DeepCloneWithLock for ImportSheet {
) -> Self {
use gecko::data::GeckoStyleSheet;
use gecko_bindings::bindings;
- let clone = unsafe {
- bindings::Gecko_StyleSheet_Clone(self.0.raw() as *const _, params.reference_sheet)
- };
- ImportSheet(unsafe { GeckoStyleSheet::from_addrefed(clone) })
+ match *self {
+ ImportSheet::Sheet(ref s) => {
+ let clone = unsafe {
+ bindings::Gecko_StyleSheet_Clone(s.raw() as *const _, params.reference_sheet)
+ };
+ ImportSheet::Sheet(unsafe { GeckoStyleSheet::from_addrefed(clone) })
+ },
+ ImportSheet::Pending(ref p) => ImportSheet::Pending(p.clone()),
+ }
+ }
+}
+
+#[cfg(feature = "gecko")]
+impl StylesheetInDocument for ImportSheet {
+ fn origin(&self, _guard: &SharedRwLockReadGuard) -> Origin {
+ match *self {
+ ImportSheet::Sheet(ref s) => s.contents().origin,
+ ImportSheet::Pending(ref p) => p.origin,
+ }
+ }
+
+ fn quirks_mode(&self, _guard: &SharedRwLockReadGuard) -> QuirksMode {
+ match *self {
+ ImportSheet::Sheet(ref s) => s.contents().quirks_mode,
+ ImportSheet::Pending(ref p) => p.quirks_mode,
+ }
+ }
+
+ fn enabled(&self) -> bool {
+ match *self {
+ ImportSheet::Sheet(ref s) => s.enabled(),
+ ImportSheet::Pending(_) => true,
+ }
+ }
+
+ fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
+ match *self {
+ ImportSheet::Sheet(ref s) => s.media(guard),
+ ImportSheet::Pending(_) => None,
+ }
+ }
+
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ match *self {
+ ImportSheet::Sheet(ref s) => s.contents().rules(guard),
+ ImportSheet::Pending(_) => &[],
+ }
}
}
@@ -43,19 +126,27 @@ impl DeepCloneWithLock for ImportSheet {
#[derive(Debug)]
pub struct ImportSheet(pub ::servo_arc::Arc<::stylesheets::Stylesheet>);
+#[cfg(feature = "servo")]
impl StylesheetInDocument for ImportSheet {
- /// Get the media associated with this stylesheet.
- fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
- self.0.media(guard)
+ fn origin(&self, guard: &SharedRwLockReadGuard) -> Origin {
+ self.0.origin(guard)
}
- fn contents(&self, guard: &SharedRwLockReadGuard) -> &StylesheetContents {
- self.0.contents(guard)
+ fn quirks_mode(&self, guard: &SharedRwLockReadGuard) -> QuirksMode {
+ self.0.quirks_mode(guard)
}
fn enabled(&self) -> bool {
self.0.enabled()
}
+
+ fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
+ self.0.media(guard)
+ }
+
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ self.0.rules(guard)
+ }
}
#[cfg(feature = "servo")]
diff --git a/components/style/stylesheets/rules_iterator.rs b/components/style/stylesheets/rules_iterator.rs
index 3d63a218ff4..b46e24c22c7 100644
--- a/components/style/stylesheets/rules_iterator.rs
+++ b/components/style/stylesheets/rules_iterator.rs
@@ -9,7 +9,7 @@ use media_queries::Device;
use shared_lock::SharedRwLockReadGuard;
use smallvec::SmallVec;
use std::slice;
-use stylesheets::{CssRule, CssRules, DocumentRule, ImportRule, MediaRule, SupportsRule};
+use stylesheets::{CssRule, DocumentRule, ImportRule, MediaRule, SupportsRule};
use stylesheets::StylesheetInDocument;
/// An iterator over a list of rules.
@@ -35,10 +35,10 @@ where
device: &'a Device,
quirks_mode: QuirksMode,
guard: &'a SharedRwLockReadGuard<'b>,
- rules: &'a CssRules,
+ rules: &'a [CssRule],
) -> Self {
let mut stack = SmallVec::new();
- stack.push(rules.0.iter());
+ stack.push(rules.iter());
Self {
device: device,
quirks_mode: quirks_mode,
@@ -102,10 +102,7 @@ where
}
import_rule
.stylesheet
- .contents(self.guard)
- .rules
- .read_with(self.guard)
- .0
+ .rules(self.guard)
.iter()
},
CssRule::Document(ref doc_rule) => {
diff --git a/components/style/stylesheets/stylesheet.rs b/components/style/stylesheets/stylesheet.rs
index 4bccbb504c9..08c2cb05f7a 100644
--- a/components/style/stylesheets/stylesheet.rs
+++ b/components/style/stylesheets/stylesheet.rs
@@ -103,22 +103,10 @@ impl StylesheetContents {
}
}
- /// Return an iterator using the condition `C`.
+ /// Returns a reference to the list of rules.
#[inline]
- pub fn iter_rules<'a, 'b, C>(
- &'a self,
- device: &'a Device,
- guard: &'a SharedRwLockReadGuard<'b>,
- ) -> RulesIterator<'a, 'b, C>
- where
- C: NestedRuleIterationCondition,
- {
- RulesIterator::new(
- device,
- self.quirks_mode,
- guard,
- &self.rules.read_with(guard),
- )
+ pub fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ &self.rules.read_with(guard).0
}
/// Measure heap usage.
@@ -189,32 +177,20 @@ macro_rules! rule_filter {
/// A trait to represent a given stylesheet in a document.
pub trait StylesheetInDocument {
- /// Get the contents of this stylesheet.
- fn contents(&self, guard: &SharedRwLockReadGuard) -> &StylesheetContents;
-
/// Get the stylesheet origin.
- fn origin(&self, guard: &SharedRwLockReadGuard) -> Origin {
- self.contents(guard).origin
- }
+ fn origin(&self, guard: &SharedRwLockReadGuard) -> Origin;
/// Get the stylesheet quirks mode.
- fn quirks_mode(&self, guard: &SharedRwLockReadGuard) -> QuirksMode {
- self.contents(guard).quirks_mode
- }
+ fn quirks_mode(&self, guard: &SharedRwLockReadGuard) -> QuirksMode;
+
+ /// Get whether this stylesheet is enabled.
+ fn enabled(&self) -> bool;
/// Get the media associated with this stylesheet.
fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList>;
- /// Returns whether the style-sheet applies for the current device.
- fn is_effective_for_device(&self, device: &Device, guard: &SharedRwLockReadGuard) -> bool {
- match self.media(guard) {
- Some(medialist) => medialist.evaluate(device, self.quirks_mode(guard)),
- None => true,
- }
- }
-
- /// Get whether this stylesheet is enabled.
- fn enabled(&self) -> bool;
+ /// Returns a reference to the list of rules in this stylesheet.
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule];
/// Return an iterator using the condition `C`.
#[inline]
@@ -226,7 +202,15 @@ pub trait StylesheetInDocument {
where
C: NestedRuleIterationCondition,
{
- self.contents(guard).iter_rules(device, guard)
+ RulesIterator::new(device, self.quirks_mode(guard), guard, self.rules(guard))
+ }
+
+ /// Returns whether the style-sheet applies for the current device.
+ fn is_effective_for_device(&self, device: &Device, guard: &SharedRwLockReadGuard) -> bool {
+ match self.media(guard) {
+ Some(medialist) => medialist.evaluate(device, self.quirks_mode(guard)),
+ None => true,
+ }
}
/// Return an iterator over the effective rules within the style-sheet, as
@@ -255,8 +239,12 @@ pub trait StylesheetInDocument {
}
impl StylesheetInDocument for Stylesheet {
- fn contents(&self, _: &SharedRwLockReadGuard) -> &StylesheetContents {
- &self.contents
+ fn origin(&self, _guard: &SharedRwLockReadGuard) -> Origin {
+ self.contents.origin
+ }
+
+ fn quirks_mode(&self, _guard: &SharedRwLockReadGuard) -> QuirksMode {
+ self.contents.quirks_mode
}
fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
@@ -266,6 +254,11 @@ impl StylesheetInDocument for Stylesheet {
fn enabled(&self) -> bool {
!self.disabled()
}
+
+ #[inline]
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ self.contents.rules(guard)
+ }
}
/// A simple wrapper over an `Arc<Stylesheet>`, with pointer comparison, and
@@ -289,8 +282,12 @@ impl ToMediaListKey for DocumentStyleSheet {
}
impl StylesheetInDocument for DocumentStyleSheet {
- fn contents(&self, guard: &SharedRwLockReadGuard) -> &StylesheetContents {
- self.0.contents(guard)
+ fn origin(&self, guard: &SharedRwLockReadGuard) -> Origin {
+ self.0.origin(guard)
+ }
+
+ fn quirks_mode(&self, guard: &SharedRwLockReadGuard) -> QuirksMode {
+ self.0.quirks_mode(guard)
}
fn media<'a>(&'a self, guard: &'a SharedRwLockReadGuard) -> Option<&'a MediaList> {
@@ -300,6 +297,11 @@ impl StylesheetInDocument for DocumentStyleSheet {
fn enabled(&self) -> bool {
self.0.enabled()
}
+
+ #[inline]
+ fn rules<'a, 'b: 'a>(&'a self, guard: &'b SharedRwLockReadGuard) -> &'a [CssRule] {
+ self.0.rules(guard)
+ }
}
impl Stylesheet {
diff --git a/ports/geckolib/glue.rs b/ports/geckolib/glue.rs
index ce957398391..3a476640de1 100644
--- a/ports/geckolib/glue.rs
+++ b/ports/geckolib/glue.rs
@@ -2048,7 +2048,7 @@ pub extern "C" fn Servo_ImportRule_GetSheet(
rule: RawServoImportRuleBorrowed,
) -> *const ServoStyleSheet {
read_locked_arc(rule, |rule: &ImportRule| {
- rule.stylesheet.0.raw() as *const ServoStyleSheet
+ rule.stylesheet.as_sheet().unwrap().raw() as *const ServoStyleSheet
})
}
diff --git a/ports/geckolib/stylesheet_loader.rs b/ports/geckolib/stylesheet_loader.rs
index 0addb4f9ef8..1dfe30e8bdb 100644
--- a/ports/geckolib/stylesheet_loader.rs
+++ b/ports/geckolib/stylesheet_loader.rs
@@ -55,9 +55,8 @@ impl StyleStylesheetLoader for StylesheetLoader {
debug_assert!(!child_sheet.is_null(),
"Import rules should always have a strong sheet");
- let stylesheet = unsafe {
- ImportSheet(GeckoStyleSheet::from_addrefed(child_sheet))
- };
+ let sheet = unsafe { GeckoStyleSheet::from_addrefed(child_sheet) };
+ let stylesheet = ImportSheet::new(sheet);
Arc::new(lock.wrap(ImportRule { url, source_location, stylesheet }))
}
}