/* This Source Code Form is subject to the terms of the Mozilla Public *License,v.2.0.IfacopyoftheMPLwasnotdistributedwiththis
* file, You can obtain one at https://mozilla.org/MPL/2.0/. */
//! Visitor traits for selectors.
#![deny(missing_docs)]
usecrate::attr::NamespaceConstraint; usecrate::parser::{Combinator, Component, RelativeSelector, Selector, SelectorImpl}; use bitflags::bitflags;
/// A trait to visit selector properties. /// /// All the `visit_foo` methods return a boolean indicating whether the /// traversal should continue or not. pubtrait SelectorVisitor: Sized { /// The selector implementation this visitor wants to visit. typeImpl: SelectorImpl;
/// Visit an attribute selector that may match (there are other selectors /// that may never match, like those containing whitespace or the empty /// string). fn visit_attribute_selector(
&mutself,
_namespace: &NamespaceConstraint<&<Self::Implas SelectorImpl>::NamespaceUrl>,
_local_name: &<Self::Implas SelectorImpl>::LocalName,
_local_name_lower: &<Self::Implas SelectorImpl>::LocalName,
) -> bool { true
}
/// Visit a nested relative selector list. The caller is responsible to call visit /// into the internal selectors if / as needed. /// /// The default implementation skips it altogether. fn visit_relative_selector_list(&mutself, _list: &[RelativeSelector<Self::Impl>]) -> bool { true
}
/// Visit a nested selector list. The caller is responsible to call visit /// into the internal selectors if / as needed. /// /// The default implementation does this. fn visit_selector_list(
&mutself,
_list_kind: SelectorListKind,
list: &[Selector<Self::Impl>],
) -> bool { for nested in list { if !nested.visit(self) { returnfalse;
}
} true
}
/// Visits a complex selector. /// /// Gets the combinator to the right of the selector, or `None` if the /// selector is the rightmost one. fn visit_complex_selector(&mutself, _combinator_to_right: Option<Combinator>) -> bool { true
}
}
bitflags! { /// The kinds of components the visitor is visiting the selector list of, if any #[derive(Clone, Copy, Default)] pubstruct SelectorListKind: u8 { /// The visitor is inside :not(..) const NEGATION = 1 << 0; /// The visitor is inside :is(..) const IS = 1 << 1; /// The visitor is inside :where(..) constWHERE = 1 << 2; /// The visitor is inside :nth-child(.. of <selector list>) or /// :nth-last-child(.. of <selector list>) const NTH_OF = 1 << 3; /// The visitor is inside :has(..) const HAS = 1 << 4;
}
}
impl SelectorListKind { /// Construct a SelectorListKind for the corresponding component. pubfn from_component<Impl: SelectorImpl>(component: &Component<Impl>) -> Self { match component {
Component::Negation(_) => SelectorListKind::NEGATION,
Component::Is(_) => SelectorListKind::IS,
Component::Where(_) => SelectorListKind::WHERE,
Component::NthOf(_) => SelectorListKind::NTH_OF,
_ => SelectorListKind::empty(),
}
}
/// Whether the visitor is inside :not(..) pubfn in_negation(&self) -> bool { self.intersects(SelectorListKind::NEGATION)
}
/// Whether the visitor is inside :is(..) pubfn in_is(&self) -> bool { self.intersects(SelectorListKind::IS)
}
/// Whether the visitor is inside :where(..) pubfn in_where(&self) -> bool { self.intersects(SelectorListKind::WHERE)
}
/// Whether the visitor is inside :nth-child(.. of <selector list>) or /// :nth-last-child(.. of <selector list>) pubfn in_nth_of(&self) -> bool { self.intersects(SelectorListKind::NTH_OF)
}
/// Whether the visitor is inside :has(..) pubfn in_has(&self) -> bool { self.intersects(SelectorListKind::HAS)
}
/// Whether this nested selector is relevant for nth-of dependencies. pubfn relevant_to_nth_of_dependencies(&self) -> bool { // Order of nesting for `:has` and `:nth-child(.. of ..)` doesn't matter, because: // * `:has(:nth-child(.. of ..))`: The location of the anchoring element is // independent from where `:nth-child(.. of ..)` is applied. // * `:nth-child(.. of :has(..))`: Invalidations inside `:has` must first use the // `:has` machinary to find the anchor, then carry out the remaining invalidation. self.in_nth_of() && !self.in_has()
}
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.