Skip to content

Commit

Permalink
style: Implement parsing / selector-matching for :is() and :where().
Browse files Browse the repository at this point in the history
This implements the easy / straight-forward parts of the :where / :is
selectors.

The biggest missing piece is to handle properly invalidation when there
are combinators present inside the :where. That's the hard part of this,
actually.

But this is probably worth landing in the interim. This fixes some of
the visitors that were easy to fix.

Differential Revision: https://phabricator.services.mozilla.com/D70788
  • Loading branch information
emilio committed Apr 18, 2020
1 parent 66f1477 commit 83ea321
Show file tree
Hide file tree
Showing 10 changed files with 338 additions and 223 deletions.
3 changes: 3 additions & 0 deletions components/malloc_size_of/lib.rs
Expand Up @@ -748,6 +748,9 @@ where
Component::Slotted(ref selector) | Component::Host(Some(ref selector)) => {
selector.size_of(ops)
},
Component::Is(ref list) | Component::Where(ref list) => {
list.size_of(ops)
},
Component::PseudoElement(ref pseudo) => (*pseudo).size_of(ops),
Component::Combinator(..) |
Component::ExplicitAnyNamespace |
Expand Down
13 changes: 13 additions & 0 deletions components/selectors/builder.rs
Expand Up @@ -330,6 +330,19 @@ where
specificity.class_like_selectors += 1;
}
},
Component::Is(ref list) => {
// https://drafts.csswg.org/selectors/#specificity-rules:
//
// The specificity of an :is() pseudo-class is replaced by the
// specificity of the most specific complex selector in its
// selector list argument.
let mut max = 0;
for selector in &**list {
max = std::cmp::max(selector.specificity(), max);
}
*specificity += Specificity::from(max);
},
Component::Where(..) |
Component::ExplicitUniversalType |
Component::ExplicitAnyNamespace |
Component::ExplicitNoNamespace |
Expand Down
8 changes: 8 additions & 0 deletions components/selectors/matching.rs
Expand Up @@ -851,6 +851,14 @@ where
matches_generic_nth_child(element, context, 0, 1, true, false, flags_setter) &&
matches_generic_nth_child(element, context, 0, 1, true, true, flags_setter)
},
Component::Is(ref list) | Component::Where(ref list) => context.shared.nest(|context| {
for selector in &**list {
if matches_complex_selector(selector.iter(), element, context, flags_setter) {
return true;
}
}
false
}),
Component::Negation(ref negated) => context.shared.nest_for_negation(|context| {
let mut local_context = LocalMatchingContext {
matches_hover_and_active_quirk: MatchesHoverAndActiveQuirk::No,
Expand Down

0 comments on commit 83ea321

Please sign in to comment.