mirror of
https://github.com/servo/servo.git
synced 2025-08-03 20:50:07 +01:00
Introduce SelectorInner and use it for top-level matching.
MozReview-Commit-ID: DxG6USsPIkh
This commit is contained in:
parent
11745fb983
commit
9524c5cb57
9 changed files with 138 additions and 109 deletions
|
@ -86,7 +86,7 @@ use net_traits::request::CorsSettings;
|
||||||
use ref_filter_map::ref_filter_map;
|
use ref_filter_map::ref_filter_map;
|
||||||
use script_layout_interface::message::ReflowQueryType;
|
use script_layout_interface::message::ReflowQueryType;
|
||||||
use script_thread::Runnable;
|
use script_thread::Runnable;
|
||||||
use selectors::matching::{ElementSelectorFlags, StyleRelations, matches};
|
use selectors::matching::{ElementSelectorFlags, StyleRelations, matches_selector_list};
|
||||||
use selectors::matching::{HAS_EDGE_CHILD_SELECTOR, HAS_SLOW_SELECTOR, HAS_SLOW_SELECTOR_LATER_SIBLINGS};
|
use selectors::matching::{HAS_EDGE_CHILD_SELECTOR, HAS_SLOW_SELECTOR, HAS_SLOW_SELECTOR_LATER_SIBLINGS};
|
||||||
use selectors::parser::{AttrSelector, NamespaceConstraint};
|
use selectors::parser::{AttrSelector, NamespaceConstraint};
|
||||||
use servo_atoms::Atom;
|
use servo_atoms::Atom;
|
||||||
|
@ -2050,7 +2050,7 @@ impl ElementMethods for Element {
|
||||||
match SelectorParser::parse_author_origin_no_namespace(&selectors) {
|
match SelectorParser::parse_author_origin_no_namespace(&selectors) {
|
||||||
Err(()) => Err(Error::Syntax),
|
Err(()) => Err(Error::Syntax),
|
||||||
Ok(selectors) => {
|
Ok(selectors) => {
|
||||||
Ok(matches(&selectors.0, &Root::from_ref(self), None))
|
Ok(matches_selector_list(&selectors.0, &Root::from_ref(self), None))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2068,7 +2068,7 @@ impl ElementMethods for Element {
|
||||||
let root = self.upcast::<Node>();
|
let root = self.upcast::<Node>();
|
||||||
for element in root.inclusive_ancestors() {
|
for element in root.inclusive_ancestors() {
|
||||||
if let Some(element) = Root::downcast::<Element>(element) {
|
if let Some(element) = Root::downcast::<Element>(element) {
|
||||||
if matches(&selectors.0, &element, None)
|
if matches_selector_list(&selectors.0, &element, None)
|
||||||
{
|
{
|
||||||
return Ok(Some(element));
|
return Ok(Some(element));
|
||||||
}
|
}
|
||||||
|
|
|
@ -68,7 +68,7 @@ use script_layout_interface::{LayoutElementType, LayoutNodeType, TrustedNodeAddr
|
||||||
use script_layout_interface::message::Msg;
|
use script_layout_interface::message::Msg;
|
||||||
use script_traits::DocumentActivity;
|
use script_traits::DocumentActivity;
|
||||||
use script_traits::UntrustedNodeAddress;
|
use script_traits::UntrustedNodeAddress;
|
||||||
use selectors::matching::matches;
|
use selectors::matching::matches_selector_list;
|
||||||
use selectors::parser::SelectorList;
|
use selectors::parser::SelectorList;
|
||||||
use servo_url::ServoUrl;
|
use servo_url::ServoUrl;
|
||||||
use std::borrow::ToOwned;
|
use std::borrow::ToOwned;
|
||||||
|
@ -332,7 +332,7 @@ impl<'a> Iterator for QuerySelectorIterator {
|
||||||
// (instead of passing `None`)? Probably.
|
// (instead of passing `None`)? Probably.
|
||||||
self.iterator.by_ref().filter_map(|node| {
|
self.iterator.by_ref().filter_map(|node| {
|
||||||
if let Some(element) = Root::downcast(node) {
|
if let Some(element) = Root::downcast(node) {
|
||||||
if matches(selectors, &element, None) {
|
if matches_selector_list(selectors, &element, None) {
|
||||||
return Some(Root::upcast(element));
|
return Some(Root::upcast(element));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -695,7 +695,7 @@ impl Node {
|
||||||
// Step 3.
|
// Step 3.
|
||||||
Ok(selectors) => {
|
Ok(selectors) => {
|
||||||
Ok(self.traverse_preorder().filter_map(Root::downcast).find(|element| {
|
Ok(self.traverse_preorder().filter_map(Root::downcast).find(|element| {
|
||||||
matches(&selectors.0, element, None)
|
matches_selector_list(&selectors.0, element, None)
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||||
use bloom::BloomFilter;
|
use bloom::BloomFilter;
|
||||||
use parser::{CaseSensitivity, Combinator, ComplexSelector, LocalName};
|
use parser::{CaseSensitivity, Combinator, ComplexSelector, LocalName};
|
||||||
use parser::{SimpleSelector, Selector};
|
use parser::{SimpleSelector, Selector, SelectorInner};
|
||||||
use precomputed_hash::PrecomputedHash;
|
use precomputed_hash::PrecomputedHash;
|
||||||
use std::borrow::Borrow;
|
use std::borrow::Borrow;
|
||||||
use tree::Element;
|
use tree::Element;
|
||||||
|
@ -92,27 +92,28 @@ impl ElementSelectorFlags {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn matches<E>(selector_list: &[Selector<E::Impl>],
|
pub fn matches_selector_list<E>(selector_list: &[Selector<E::Impl>],
|
||||||
element: &E,
|
element: &E,
|
||||||
parent_bf: Option<&BloomFilter>)
|
parent_bf: Option<&BloomFilter>)
|
||||||
-> bool
|
-> bool
|
||||||
where E: Element
|
where E: Element
|
||||||
{
|
{
|
||||||
selector_list.iter().any(|selector| {
|
selector_list.iter().any(|selector| {
|
||||||
selector.pseudo_element.is_none() &&
|
selector.pseudo_element.is_none() &&
|
||||||
matches_complex_selector(&*selector.complex_selector,
|
matches_selector(&selector.inner,
|
||||||
element,
|
element,
|
||||||
parent_bf,
|
parent_bf,
|
||||||
&mut StyleRelations::empty(),
|
&mut StyleRelations::empty(),
|
||||||
&mut |_, _| {})
|
&mut |_, _| {})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
fn may_match<E>(mut selector: &ComplexSelector<E::Impl>,
|
fn may_match<E>(sel: &SelectorInner<E::Impl>,
|
||||||
bf: &BloomFilter)
|
bf: &BloomFilter)
|
||||||
-> bool
|
-> bool
|
||||||
where E: Element,
|
where E: Element,
|
||||||
{
|
{
|
||||||
|
let mut selector = &*sel.complex;
|
||||||
// See if the bloom filter can exclude any of the descendant selectors, and
|
// See if the bloom filter can exclude any of the descendant selectors, and
|
||||||
// reject if we can.
|
// reject if we can.
|
||||||
loop {
|
loop {
|
||||||
|
@ -159,28 +160,24 @@ fn may_match<E>(mut selector: &ComplexSelector<E::Impl>,
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Determines whether the given element matches the given complex selector.
|
/// Determines whether the given element matches the given complex selector.
|
||||||
pub fn matches_complex_selector<E, F>(selector: &ComplexSelector<E::Impl>,
|
pub fn matches_selector<E, F>(selector: &SelectorInner<E::Impl>,
|
||||||
element: &E,
|
element: &E,
|
||||||
parent_bf: Option<&BloomFilter>,
|
parent_bf: Option<&BloomFilter>,
|
||||||
relations: &mut StyleRelations,
|
relations: &mut StyleRelations,
|
||||||
flags_setter: &mut F)
|
flags_setter: &mut F)
|
||||||
-> bool
|
-> bool
|
||||||
where E: Element,
|
where E: Element,
|
||||||
F: FnMut(&E, ElementSelectorFlags),
|
F: FnMut(&E, ElementSelectorFlags),
|
||||||
{
|
{
|
||||||
|
// Use the bloom filter to fast-reject.
|
||||||
if let Some(filter) = parent_bf {
|
if let Some(filter) = parent_bf {
|
||||||
if !may_match::<E>(selector, filter) {
|
if !may_match::<E>(selector, filter) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
match matches_complex_selector_internal(selector,
|
// Match the selector.
|
||||||
element,
|
matches_complex_selector(&selector.complex, element, relations, flags_setter)
|
||||||
relations,
|
|
||||||
flags_setter) {
|
|
||||||
SelectorMatchingResult::Matched => true,
|
|
||||||
_ => false
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A result of selector matching, includes 3 failure types,
|
/// A result of selector matching, includes 3 failure types,
|
||||||
|
@ -233,6 +230,24 @@ enum SelectorMatchingResult {
|
||||||
NotMatchedGlobally,
|
NotMatchedGlobally,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Matches a complex selector.
|
||||||
|
pub fn matches_complex_selector<E, F>(selector: &ComplexSelector<E::Impl>,
|
||||||
|
element: &E,
|
||||||
|
relations: &mut StyleRelations,
|
||||||
|
flags_setter: &mut F)
|
||||||
|
-> bool
|
||||||
|
where E: Element,
|
||||||
|
F: FnMut(&E, ElementSelectorFlags),
|
||||||
|
{
|
||||||
|
match matches_complex_selector_internal(selector,
|
||||||
|
element,
|
||||||
|
relations,
|
||||||
|
flags_setter) {
|
||||||
|
SelectorMatchingResult::Matched => true,
|
||||||
|
_ => false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn matches_complex_selector_internal<E, F>(selector: &ComplexSelector<E::Impl>,
|
fn matches_complex_selector_internal<E, F>(selector: &ComplexSelector<E::Impl>,
|
||||||
element: &E,
|
element: &E,
|
||||||
relations: &mut StyleRelations,
|
relations: &mut StyleRelations,
|
||||||
|
|
|
@ -121,9 +121,27 @@ impl<Impl: SelectorImpl> SelectorList<Impl> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// The cores parts of a selector used for matching. This exists to make that
|
||||||
|
/// information accessibly separately from the specificity and pseudo-element
|
||||||
|
/// information that lives on |Selector| proper. We may want to refactor things
|
||||||
|
/// and move that information elsewhere, at which point we could rename this
|
||||||
|
/// to |Selector|.
|
||||||
|
#[derive(PartialEq, Eq, Hash, Clone)]
|
||||||
|
pub struct SelectorInner<Impl: SelectorImpl> {
|
||||||
|
pub complex: Arc<ComplexSelector<Impl>>,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<Impl: SelectorImpl> SelectorInner<Impl> {
|
||||||
|
pub fn new(c: Arc<ComplexSelector<Impl>>) -> Self {
|
||||||
|
SelectorInner {
|
||||||
|
complex: c,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(PartialEq, Eq, Hash, Clone)]
|
#[derive(PartialEq, Eq, Hash, Clone)]
|
||||||
pub struct Selector<Impl: SelectorImpl> {
|
pub struct Selector<Impl: SelectorImpl> {
|
||||||
pub complex_selector: Arc<ComplexSelector<Impl>>,
|
pub inner: SelectorInner<Impl>,
|
||||||
pub pseudo_element: Option<Impl::PseudoElement>,
|
pub pseudo_element: Option<Impl::PseudoElement>,
|
||||||
pub specificity: u32,
|
pub specificity: u32,
|
||||||
}
|
}
|
||||||
|
@ -141,7 +159,7 @@ impl<Impl: SelectorImpl> SelectorMethods for Selector<Impl> {
|
||||||
fn visit<V>(&self, visitor: &mut V) -> bool
|
fn visit<V>(&self, visitor: &mut V) -> bool
|
||||||
where V: SelectorVisitor<Impl = Impl>,
|
where V: SelectorVisitor<Impl = Impl>,
|
||||||
{
|
{
|
||||||
self.complex_selector.visit(visitor)
|
self.inner.complex.visit(visitor)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -321,6 +339,9 @@ impl<Impl: SelectorImpl> Debug for Selector<Impl> {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<Impl: SelectorImpl> Debug for SelectorInner<Impl> {
|
||||||
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { self.complex.to_css(f) }
|
||||||
|
}
|
||||||
impl<Impl: SelectorImpl> Debug for ComplexSelector<Impl> {
|
impl<Impl: SelectorImpl> Debug for ComplexSelector<Impl> {
|
||||||
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { self.to_css(f) }
|
fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { self.to_css(f) }
|
||||||
}
|
}
|
||||||
|
@ -353,7 +374,7 @@ impl<Impl: SelectorImpl> ToCss for SelectorList<Impl> {
|
||||||
|
|
||||||
impl<Impl: SelectorImpl> ToCss for Selector<Impl> {
|
impl<Impl: SelectorImpl> ToCss for Selector<Impl> {
|
||||||
fn to_css<W>(&self, dest: &mut W) -> fmt::Result where W: fmt::Write {
|
fn to_css<W>(&self, dest: &mut W) -> fmt::Result where W: fmt::Write {
|
||||||
self.complex_selector.to_css(dest)?;
|
self.inner.complex.to_css(dest)?;
|
||||||
if let Some(ref pseudo) = self.pseudo_element {
|
if let Some(ref pseudo) = self.pseudo_element {
|
||||||
pseudo.to_css(dest)?;
|
pseudo.to_css(dest)?;
|
||||||
}
|
}
|
||||||
|
@ -672,7 +693,7 @@ fn parse_selector<P, Impl>(parser: &P, input: &mut CssParser) -> Result<Selector
|
||||||
parse_complex_selector_and_pseudo_element(parser, input)?;
|
parse_complex_selector_and_pseudo_element(parser, input)?;
|
||||||
Ok(Selector {
|
Ok(Selector {
|
||||||
specificity: specificity(&complex, pseudo_element.as_ref()),
|
specificity: specificity(&complex, pseudo_element.as_ref()),
|
||||||
complex_selector: Arc::new(complex),
|
inner: SelectorInner::new(Arc::new(complex)),
|
||||||
pseudo_element: pseudo_element,
|
pseudo_element: pseudo_element,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
@ -1305,48 +1326,48 @@ pub mod tests {
|
||||||
assert_eq!(parse(":lang(4)"), Err(())) ;
|
assert_eq!(parse(":lang(4)"), Err(())) ;
|
||||||
assert_eq!(parse(":lang(en US)"), Err(())) ;
|
assert_eq!(parse(":lang(en US)"), Err(())) ;
|
||||||
assert_eq!(parse("EeÉ"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse("EeÉ"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
||||||
name: DummyAtom::from("EeÉ"),
|
name: DummyAtom::from("EeÉ"),
|
||||||
lower_name: DummyAtom::from("eeÉ") })),
|
lower_name: DummyAtom::from("eeÉ") })),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 0, 1),
|
specificity: specificity(0, 0, 1),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse(".foo:lang(en-US)"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse(".foo:lang(en-US)"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Class(DummyAtom::from("foo")),
|
SimpleSelector::Class(DummyAtom::from("foo")),
|
||||||
SimpleSelector::NonTSPseudoClass(PseudoClass::Lang("en-US".to_owned()))
|
SimpleSelector::NonTSPseudoClass(PseudoClass::Lang("en-US".to_owned()))
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 2, 0),
|
specificity: specificity(0, 2, 0),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse("#bar"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse("#bar"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::ID(DummyAtom::from("bar"))),
|
compound_selector: vec!(SimpleSelector::ID(DummyAtom::from("bar"))),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(1, 0, 0),
|
specificity: specificity(1, 0, 0),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse("e.foo#bar"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse("e.foo#bar"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
||||||
name: DummyAtom::from("e"),
|
name: DummyAtom::from("e"),
|
||||||
lower_name: DummyAtom::from("e") }),
|
lower_name: DummyAtom::from("e") }),
|
||||||
SimpleSelector::Class(DummyAtom::from("foo")),
|
SimpleSelector::Class(DummyAtom::from("foo")),
|
||||||
SimpleSelector::ID(DummyAtom::from("bar"))),
|
SimpleSelector::ID(DummyAtom::from("bar"))),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(1, 1, 1),
|
specificity: specificity(1, 1, 1),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse("e.foo #bar"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse("e.foo #bar"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::ID(DummyAtom::from("bar"))),
|
compound_selector: vec!(SimpleSelector::ID(DummyAtom::from("bar"))),
|
||||||
next: Some((Arc::new(ComplexSelector {
|
next: Some((Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
||||||
|
@ -1355,7 +1376,7 @@ pub mod tests {
|
||||||
SimpleSelector::Class(DummyAtom::from("foo"))),
|
SimpleSelector::Class(DummyAtom::from("foo"))),
|
||||||
next: None,
|
next: None,
|
||||||
}), Combinator::Descendant)),
|
}), Combinator::Descendant)),
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(1, 1, 1),
|
specificity: specificity(1, 1, 1),
|
||||||
}))));
|
}))));
|
||||||
|
@ -1363,7 +1384,7 @@ pub mod tests {
|
||||||
// https://github.com/mozilla/servo/pull/1652
|
// https://github.com/mozilla/servo/pull/1652
|
||||||
let mut parser = DummyParser::default();
|
let mut parser = DummyParser::default();
|
||||||
assert_eq!(parse_ns("[Foo]", &parser), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse_ns("[Foo]", &parser), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::AttrExists(AttrSelector {
|
compound_selector: vec!(SimpleSelector::AttrExists(AttrSelector {
|
||||||
name: DummyAtom::from("Foo"),
|
name: DummyAtom::from("Foo"),
|
||||||
lower_name: DummyAtom::from("foo"),
|
lower_name: DummyAtom::from("foo"),
|
||||||
|
@ -1373,14 +1394,14 @@ pub mod tests {
|
||||||
}),
|
}),
|
||||||
})),
|
})),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 1, 0),
|
specificity: specificity(0, 1, 0),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse_ns("svg|circle", &parser), Err(()));
|
assert_eq!(parse_ns("svg|circle", &parser), Err(()));
|
||||||
parser.ns_prefixes.insert(DummyAtom("svg".into()), DummyAtom(SVG.into()));
|
parser.ns_prefixes.insert(DummyAtom("svg".into()), DummyAtom(SVG.into()));
|
||||||
assert_eq!(parse_ns("svg|circle", &parser), Ok(SelectorList(vec![Selector {
|
assert_eq!(parse_ns("svg|circle", &parser), Ok(SelectorList(vec![Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: Some(DummyAtom("svg".into())),
|
prefix: Some(DummyAtom("svg".into())),
|
||||||
|
@ -1392,7 +1413,7 @@ pub mod tests {
|
||||||
})
|
})
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 0, 1),
|
specificity: specificity(0, 0, 1),
|
||||||
}])));
|
}])));
|
||||||
|
@ -1402,7 +1423,7 @@ pub mod tests {
|
||||||
// https://github.com/servo/rust-selectors/pull/82
|
// https://github.com/servo/rust-selectors/pull/82
|
||||||
parser.default_ns = Some(MATHML.into());
|
parser.default_ns = Some(MATHML.into());
|
||||||
assert_eq!(parse_ns("[Foo]", &parser), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse_ns("[Foo]", &parser), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: None,
|
prefix: None,
|
||||||
|
@ -1418,13 +1439,13 @@ pub mod tests {
|
||||||
}),
|
}),
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 1, 0),
|
specificity: specificity(0, 1, 0),
|
||||||
}))));
|
}))));
|
||||||
// Default namespace does apply to type selectors
|
// Default namespace does apply to type selectors
|
||||||
assert_eq!(parse_ns("e", &parser), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse_ns("e", &parser), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(
|
compound_selector: vec!(
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: None,
|
prefix: None,
|
||||||
|
@ -1435,12 +1456,12 @@ pub mod tests {
|
||||||
lower_name: DummyAtom::from("e") }),
|
lower_name: DummyAtom::from("e") }),
|
||||||
),
|
),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 0, 1),
|
specificity: specificity(0, 0, 1),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse("[attr |= \"foo\"]"), Ok(SelectorList(vec![Selector {
|
assert_eq!(parse("[attr |= \"foo\"]"), Ok(SelectorList(vec![Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::AttrDashMatch(AttrSelector {
|
SimpleSelector::AttrDashMatch(AttrSelector {
|
||||||
name: DummyAtom::from("attr"),
|
name: DummyAtom::from("attr"),
|
||||||
|
@ -1452,23 +1473,23 @@ pub mod tests {
|
||||||
}, DummyAtom::from("foo"))
|
}, DummyAtom::from("foo"))
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(0, 1, 0),
|
specificity: specificity(0, 1, 0),
|
||||||
}])));
|
}])));
|
||||||
// https://github.com/mozilla/servo/issues/1723
|
// https://github.com/mozilla/servo/issues/1723
|
||||||
assert_eq!(parse("::before"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse("::before"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(),
|
compound_selector: vec!(),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: Some(PseudoElement::Before),
|
pseudo_element: Some(PseudoElement::Before),
|
||||||
specificity: specificity(0, 0, 1),
|
specificity: specificity(0, 0, 1),
|
||||||
}))));
|
}))));
|
||||||
// https://github.com/servo/servo/issues/15335
|
// https://github.com/servo/servo/issues/15335
|
||||||
assert_eq!(parse(":: before"), Err(()));
|
assert_eq!(parse(":: before"), Err(()));
|
||||||
assert_eq!(parse("div ::after"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse("div ::after"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(),
|
compound_selector: vec!(),
|
||||||
next: Some((Arc::new(ComplexSelector {
|
next: Some((Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
compound_selector: vec!(SimpleSelector::LocalName(LocalName {
|
||||||
|
@ -1476,12 +1497,12 @@ pub mod tests {
|
||||||
lower_name: DummyAtom::from("div") })),
|
lower_name: DummyAtom::from("div") })),
|
||||||
next: None,
|
next: None,
|
||||||
}), Combinator::Descendant)),
|
}), Combinator::Descendant)),
|
||||||
}),
|
})),
|
||||||
pseudo_element: Some(PseudoElement::After),
|
pseudo_element: Some(PseudoElement::After),
|
||||||
specificity: specificity(0, 0, 2),
|
specificity: specificity(0, 0, 2),
|
||||||
}))));
|
}))));
|
||||||
assert_eq!(parse("#d1 > .ok"), Ok(SelectorList(vec![Selector {
|
assert_eq!(parse("#d1 > .ok"), Ok(SelectorList(vec![Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Class(DummyAtom::from("ok")),
|
SimpleSelector::Class(DummyAtom::from("ok")),
|
||||||
],
|
],
|
||||||
|
@ -1491,12 +1512,12 @@ pub mod tests {
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}), Combinator::Child)),
|
}), Combinator::Child)),
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: (1 << 20) + (1 << 10) + (0 << 0),
|
specificity: (1 << 20) + (1 << 10) + (0 << 0),
|
||||||
}])));
|
}])));
|
||||||
assert_eq!(parse(":not(.babybel, #provel.old)"), Ok(SelectorList(vec!(Selector {
|
assert_eq!(parse(":not(.babybel, #provel.old)"), Ok(SelectorList(vec!(Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec!(SimpleSelector::Negation(
|
compound_selector: vec!(SimpleSelector::Negation(
|
||||||
vec!(
|
vec!(
|
||||||
Arc::new(ComplexSelector {
|
Arc::new(ComplexSelector {
|
||||||
|
@ -1513,7 +1534,7 @@ pub mod tests {
|
||||||
)
|
)
|
||||||
)),
|
)),
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: specificity(1, 1, 0),
|
specificity: specificity(1, 1, 0),
|
||||||
}))));
|
}))));
|
||||||
|
|
|
@ -1150,11 +1150,7 @@ impl<'le> ::selectors::Element for GeckoElement<'le> {
|
||||||
},
|
},
|
||||||
NonTSPseudoClass::MozAny(ref sels) => {
|
NonTSPseudoClass::MozAny(ref sels) => {
|
||||||
sels.iter().any(|s| {
|
sels.iter().any(|s| {
|
||||||
matches_complex_selector(s,
|
matches_complex_selector(s, self, relations, flags_setter)
|
||||||
self,
|
|
||||||
None,
|
|
||||||
relations,
|
|
||||||
flags_setter)
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
NonTSPseudoClass::MozSystemMetric(ref s) |
|
NonTSPseudoClass::MozSystemMetric(ref s) |
|
||||||
|
|
|
@ -16,8 +16,8 @@ use heapsize::HeapSizeOf;
|
||||||
use selector_parser::{AttrValue, NonTSPseudoClass, Snapshot, SelectorImpl};
|
use selector_parser::{AttrValue, NonTSPseudoClass, Snapshot, SelectorImpl};
|
||||||
use selectors::{Element, MatchAttr};
|
use selectors::{Element, MatchAttr};
|
||||||
use selectors::matching::{ElementSelectorFlags, StyleRelations};
|
use selectors::matching::{ElementSelectorFlags, StyleRelations};
|
||||||
use selectors::matching::matches_complex_selector;
|
use selectors::matching::matches_selector;
|
||||||
use selectors::parser::{AttrSelector, Combinator, ComplexSelector, SelectorMethods, SimpleSelector};
|
use selectors::parser::{AttrSelector, Combinator, ComplexSelector, SelectorInner, SelectorMethods, SimpleSelector};
|
||||||
use selectors::visitor::SelectorVisitor;
|
use selectors::visitor::SelectorVisitor;
|
||||||
use std::clone::Clone;
|
use std::clone::Clone;
|
||||||
use std::sync::Arc;
|
use std::sync::Arc;
|
||||||
|
@ -298,13 +298,10 @@ impl<'a, E> Element for ElementWrapper<'a, E>
|
||||||
// snapshot.
|
// snapshot.
|
||||||
#[cfg(feature = "gecko")]
|
#[cfg(feature = "gecko")]
|
||||||
{
|
{
|
||||||
|
use selectors::matching::matches_complex_selector;
|
||||||
if let NonTSPseudoClass::MozAny(ref selectors) = *pseudo_class {
|
if let NonTSPseudoClass::MozAny(ref selectors) = *pseudo_class {
|
||||||
return selectors.iter().any(|s| {
|
return selectors.iter().any(|s| {
|
||||||
matches_complex_selector(s,
|
matches_complex_selector(s, self, relations, _setter)
|
||||||
self,
|
|
||||||
None,
|
|
||||||
relations,
|
|
||||||
_setter)
|
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -493,7 +490,7 @@ impl Sensitivities {
|
||||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||||
struct Dependency {
|
struct Dependency {
|
||||||
#[cfg_attr(feature = "servo", ignore_heap_size_of = "Arc")]
|
#[cfg_attr(feature = "servo", ignore_heap_size_of = "Arc")]
|
||||||
selector: Arc<ComplexSelector<SelectorImpl>>,
|
selector: SelectorInner<SelectorImpl>,
|
||||||
hint: RestyleHint,
|
hint: RestyleHint,
|
||||||
sensitivities: Sensitivities,
|
sensitivities: Sensitivities,
|
||||||
}
|
}
|
||||||
|
@ -603,7 +600,7 @@ impl DependencySet {
|
||||||
self.add_dependency(Dependency {
|
self.add_dependency(Dependency {
|
||||||
sensitivities: sensitivities,
|
sensitivities: sensitivities,
|
||||||
hint: hint,
|
hint: hint,
|
||||||
selector: current.clone(),
|
selector: SelectorInner::new(current.clone()),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -699,13 +696,13 @@ impl DependencySet {
|
||||||
// We can ignore the selector flags, since they would have already been set during
|
// We can ignore the selector flags, since they would have already been set during
|
||||||
// original matching for any element that might change its matching behavior here.
|
// original matching for any element that might change its matching behavior here.
|
||||||
let matched_then =
|
let matched_then =
|
||||||
matches_complex_selector(&dep.selector, snapshot, None,
|
matches_selector(&dep.selector, snapshot, None,
|
||||||
&mut StyleRelations::empty(),
|
&mut StyleRelations::empty(),
|
||||||
&mut |_, _| {});
|
&mut |_, _| {});
|
||||||
let matches_now =
|
let matches_now =
|
||||||
matches_complex_selector(&dep.selector, element, None,
|
matches_selector(&dep.selector, element, None,
|
||||||
&mut StyleRelations::empty(),
|
&mut StyleRelations::empty(),
|
||||||
&mut |_, _| {});
|
&mut |_, _| {});
|
||||||
if matched_then != matches_now {
|
if matched_then != matches_now {
|
||||||
hint.insert(dep.hint);
|
hint.insert(dep.hint);
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,8 +26,8 @@ use selectors::Element;
|
||||||
use selectors::bloom::BloomFilter;
|
use selectors::bloom::BloomFilter;
|
||||||
use selectors::matching::{AFFECTED_BY_ANIMATIONS, AFFECTED_BY_TRANSITIONS};
|
use selectors::matching::{AFFECTED_BY_ANIMATIONS, AFFECTED_BY_TRANSITIONS};
|
||||||
use selectors::matching::{AFFECTED_BY_STYLE_ATTRIBUTE, AFFECTED_BY_PRESENTATIONAL_HINTS};
|
use selectors::matching::{AFFECTED_BY_STYLE_ATTRIBUTE, AFFECTED_BY_PRESENTATIONAL_HINTS};
|
||||||
use selectors::matching::{ElementSelectorFlags, StyleRelations, matches_complex_selector};
|
use selectors::matching::{ElementSelectorFlags, StyleRelations, matches_selector};
|
||||||
use selectors::parser::{Selector, SimpleSelector, LocalName as LocalNameSelector, ComplexSelector};
|
use selectors::parser::{Selector, SelectorInner, SimpleSelector, LocalName as LocalNameSelector};
|
||||||
use shared_lock::{Locked, SharedRwLockReadGuard, StylesheetGuards};
|
use shared_lock::{Locked, SharedRwLockReadGuard, StylesheetGuards};
|
||||||
use sink::Push;
|
use sink::Push;
|
||||||
use smallvec::VecLike;
|
use smallvec::VecLike;
|
||||||
|
@ -336,7 +336,7 @@ impl Stylist {
|
||||||
};
|
};
|
||||||
|
|
||||||
map.insert(Rule {
|
map.insert(Rule {
|
||||||
selector: selector.complex_selector.clone(),
|
selector: selector.inner.clone(),
|
||||||
style_rule: locked.clone(),
|
style_rule: locked.clone(),
|
||||||
specificity: selector.specificity,
|
specificity: selector.specificity,
|
||||||
source_order: self.rules_source_order,
|
source_order: self.rules_source_order,
|
||||||
|
@ -346,7 +346,7 @@ impl Stylist {
|
||||||
|
|
||||||
for selector in &style_rule.selectors.0 {
|
for selector in &style_rule.selectors.0 {
|
||||||
let needs_cache_revalidation =
|
let needs_cache_revalidation =
|
||||||
self.dependencies.note_selector(&selector.complex_selector);
|
self.dependencies.note_selector(&selector.inner.complex);
|
||||||
if needs_cache_revalidation {
|
if needs_cache_revalidation {
|
||||||
self.selectors_for_cache_revalidation.push(selector.clone());
|
self.selectors_for_cache_revalidation.push(selector.clone());
|
||||||
}
|
}
|
||||||
|
@ -826,18 +826,18 @@ impl Stylist {
|
||||||
F: FnMut(&E, ElementSelectorFlags)
|
F: FnMut(&E, ElementSelectorFlags)
|
||||||
{
|
{
|
||||||
use selectors::matching::StyleRelations;
|
use selectors::matching::StyleRelations;
|
||||||
use selectors::matching::matches_complex_selector;
|
use selectors::matching::matches_selector;
|
||||||
|
|
||||||
let len = self.selectors_for_cache_revalidation.len();
|
let len = self.selectors_for_cache_revalidation.len();
|
||||||
let mut results = BitVec::from_elem(len, false);
|
let mut results = BitVec::from_elem(len, false);
|
||||||
|
|
||||||
for (i, ref selector) in self.selectors_for_cache_revalidation
|
for (i, ref selector) in self.selectors_for_cache_revalidation
|
||||||
.iter().enumerate() {
|
.iter().enumerate() {
|
||||||
results.set(i, matches_complex_selector(&selector.complex_selector,
|
results.set(i, matches_selector(&selector.inner,
|
||||||
element,
|
element,
|
||||||
Some(bloom),
|
Some(bloom),
|
||||||
&mut StyleRelations::empty(),
|
&mut StyleRelations::empty(),
|
||||||
flags_setter));
|
flags_setter));
|
||||||
}
|
}
|
||||||
|
|
||||||
results
|
results
|
||||||
|
@ -1081,8 +1081,8 @@ impl SelectorMap {
|
||||||
// correct, and also to not trigger rule tree assertions.
|
// correct, and also to not trigger rule tree assertions.
|
||||||
let mut important = vec![];
|
let mut important = vec![];
|
||||||
for rule in self.other_rules.iter() {
|
for rule in self.other_rules.iter() {
|
||||||
if rule.selector.compound_selector.is_empty() &&
|
if rule.selector.complex.compound_selector.is_empty() &&
|
||||||
rule.selector.next.is_none() {
|
rule.selector.complex.next.is_none() {
|
||||||
let style_rule = rule.style_rule.read_with(guard);
|
let style_rule = rule.style_rule.read_with(guard);
|
||||||
let block = style_rule.block.read_with(guard);
|
let block = style_rule.block.read_with(guard);
|
||||||
if block.any_normal() {
|
if block.any_normal() {
|
||||||
|
@ -1157,8 +1157,8 @@ impl SelectorMap {
|
||||||
block.any_normal()
|
block.any_normal()
|
||||||
};
|
};
|
||||||
if any_declaration_for_importance &&
|
if any_declaration_for_importance &&
|
||||||
matches_complex_selector(&*rule.selector, element, parent_bf,
|
matches_selector(&rule.selector, element, parent_bf,
|
||||||
relations, flags_setter) {
|
relations, flags_setter) {
|
||||||
matching_rules.push(
|
matching_rules.push(
|
||||||
rule.to_applicable_declaration_block(cascade_level));
|
rule.to_applicable_declaration_block(cascade_level));
|
||||||
}
|
}
|
||||||
|
@ -1191,7 +1191,7 @@ impl SelectorMap {
|
||||||
|
|
||||||
/// Retrieve the first ID name in Rule, or None otherwise.
|
/// Retrieve the first ID name in Rule, or None otherwise.
|
||||||
pub fn get_id_name(rule: &Rule) -> Option<Atom> {
|
pub fn get_id_name(rule: &Rule) -> Option<Atom> {
|
||||||
for ss in &rule.selector.compound_selector {
|
for ss in &rule.selector.complex.compound_selector {
|
||||||
// TODO(pradeep): Implement case-sensitivity based on the
|
// TODO(pradeep): Implement case-sensitivity based on the
|
||||||
// document type and quirks mode.
|
// document type and quirks mode.
|
||||||
if let SimpleSelector::ID(ref id) = *ss {
|
if let SimpleSelector::ID(ref id) = *ss {
|
||||||
|
@ -1204,7 +1204,7 @@ impl SelectorMap {
|
||||||
|
|
||||||
/// Retrieve the FIRST class name in Rule, or None otherwise.
|
/// Retrieve the FIRST class name in Rule, or None otherwise.
|
||||||
pub fn get_class_name(rule: &Rule) -> Option<Atom> {
|
pub fn get_class_name(rule: &Rule) -> Option<Atom> {
|
||||||
for ss in &rule.selector.compound_selector {
|
for ss in &rule.selector.complex.compound_selector {
|
||||||
// TODO(pradeep): Implement case-sensitivity based on the
|
// TODO(pradeep): Implement case-sensitivity based on the
|
||||||
// document type and quirks mode.
|
// document type and quirks mode.
|
||||||
if let SimpleSelector::Class(ref class) = *ss {
|
if let SimpleSelector::Class(ref class) = *ss {
|
||||||
|
@ -1217,7 +1217,7 @@ impl SelectorMap {
|
||||||
|
|
||||||
/// Retrieve the name if it is a type selector, or None otherwise.
|
/// Retrieve the name if it is a type selector, or None otherwise.
|
||||||
pub fn get_local_name(rule: &Rule) -> Option<LocalNameSelector<SelectorImpl>> {
|
pub fn get_local_name(rule: &Rule) -> Option<LocalNameSelector<SelectorImpl>> {
|
||||||
for ss in &rule.selector.compound_selector {
|
for ss in &rule.selector.complex.compound_selector {
|
||||||
if let SimpleSelector::LocalName(ref n) = *ss {
|
if let SimpleSelector::LocalName(ref n) = *ss {
|
||||||
return Some(LocalNameSelector {
|
return Some(LocalNameSelector {
|
||||||
name: n.name.clone(),
|
name: n.name.clone(),
|
||||||
|
@ -1245,7 +1245,7 @@ pub struct Rule {
|
||||||
/// style rule was a generic parameter to it. It's not trivial though, due
|
/// style rule was a generic parameter to it. It's not trivial though, due
|
||||||
/// to the specificity.
|
/// to the specificity.
|
||||||
#[cfg_attr(feature = "servo", ignore_heap_size_of = "Arc")]
|
#[cfg_attr(feature = "servo", ignore_heap_size_of = "Arc")]
|
||||||
pub selector: Arc<ComplexSelector<SelectorImpl>>,
|
pub selector: SelectorInner<SelectorImpl>,
|
||||||
/// The actual style rule.
|
/// The actual style rule.
|
||||||
#[cfg_attr(feature = "servo", ignore_heap_size_of = "Arc")]
|
#[cfg_attr(feature = "servo", ignore_heap_size_of = "Arc")]
|
||||||
pub style_rule: Arc<Locked<StyleRule>>,
|
pub style_rule: Arc<Locked<StyleRule>>,
|
||||||
|
|
|
@ -84,7 +84,7 @@ fn test_parse_stylesheet() {
|
||||||
CssRule::Style(Arc::new(stylesheet.shared_lock.wrap(StyleRule {
|
CssRule::Style(Arc::new(stylesheet.shared_lock.wrap(StyleRule {
|
||||||
selectors: SelectorList(vec![
|
selectors: SelectorList(vec![
|
||||||
Selector {
|
Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: None,
|
prefix: None,
|
||||||
|
@ -104,7 +104,7 @@ fn test_parse_stylesheet() {
|
||||||
}, "hidden".to_owned(), CaseSensitivity::CaseInsensitive)
|
}, "hidden".to_owned(), CaseSensitivity::CaseInsensitive)
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: (0 << 20) + (1 << 10) + (1 << 0),
|
specificity: (0 << 20) + (1 << 10) + (1 << 0),
|
||||||
},
|
},
|
||||||
|
@ -120,7 +120,7 @@ fn test_parse_stylesheet() {
|
||||||
CssRule::Style(Arc::new(stylesheet.shared_lock.wrap(StyleRule {
|
CssRule::Style(Arc::new(stylesheet.shared_lock.wrap(StyleRule {
|
||||||
selectors: SelectorList(vec![
|
selectors: SelectorList(vec![
|
||||||
Selector {
|
Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: None,
|
prefix: None,
|
||||||
|
@ -132,12 +132,12 @@ fn test_parse_stylesheet() {
|
||||||
}),
|
}),
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: (0 << 20) + (0 << 10) + (1 << 0),
|
specificity: (0 << 20) + (0 << 10) + (1 << 0),
|
||||||
},
|
},
|
||||||
Selector {
|
Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: None,
|
prefix: None,
|
||||||
|
@ -149,7 +149,7 @@ fn test_parse_stylesheet() {
|
||||||
}),
|
}),
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: (0 << 20) + (0 << 10) + (1 << 0),
|
specificity: (0 << 20) + (0 << 10) + (1 << 0),
|
||||||
},
|
},
|
||||||
|
@ -162,7 +162,7 @@ fn test_parse_stylesheet() {
|
||||||
CssRule::Style(Arc::new(stylesheet.shared_lock.wrap(StyleRule {
|
CssRule::Style(Arc::new(stylesheet.shared_lock.wrap(StyleRule {
|
||||||
selectors: SelectorList(vec![
|
selectors: SelectorList(vec![
|
||||||
Selector {
|
Selector {
|
||||||
complex_selector: Arc::new(ComplexSelector {
|
inner: SelectorInner::new(Arc::new(ComplexSelector {
|
||||||
compound_selector: vec![
|
compound_selector: vec![
|
||||||
SimpleSelector::Namespace(Namespace {
|
SimpleSelector::Namespace(Namespace {
|
||||||
prefix: None,
|
prefix: None,
|
||||||
|
@ -180,7 +180,7 @@ fn test_parse_stylesheet() {
|
||||||
],
|
],
|
||||||
next: None,
|
next: None,
|
||||||
}), Combinator::Child)),
|
}), Combinator::Child)),
|
||||||
}),
|
})),
|
||||||
pseudo_element: None,
|
pseudo_element: None,
|
||||||
specificity: (1 << 20) + (1 << 10) + (0 << 0),
|
specificity: (1 << 20) + (1 << 10) + (0 << 0),
|
||||||
},
|
},
|
||||||
|
|
|
@ -35,7 +35,7 @@ fn get_mock_rules(css_selectors: &[&str]) -> (Vec<Vec<Rule>>, SharedRwLock) {
|
||||||
let rule = locked.read_with(&guard);
|
let rule = locked.read_with(&guard);
|
||||||
rule.selectors.0.iter().map(|s| {
|
rule.selectors.0.iter().map(|s| {
|
||||||
Rule {
|
Rule {
|
||||||
selector: s.complex_selector.clone(),
|
selector: s.inner.clone(),
|
||||||
style_rule: locked.clone(),
|
style_rule: locked.clone(),
|
||||||
specificity: s.specificity,
|
specificity: s.specificity,
|
||||||
source_order: i,
|
source_order: i,
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue