mirror of
https://github.com/servo/servo.git
synced 2025-08-06 14:10:11 +01:00
Use a more compact representation to store eager pseudo-elements.
This means that ElementStyles only need a single word to store eager pseudos. MozReview-Commit-ID: 5bDXlDweN46
This commit is contained in:
parent
1ff008caa3
commit
3f0d022ba2
6 changed files with 207 additions and 97 deletions
|
@ -19,6 +19,7 @@ use selectors::parser::{AttrSelector, SelectorMethods};
|
|||
use std::borrow::Cow;
|
||||
use std::fmt;
|
||||
use std::fmt::Debug;
|
||||
use std::mem;
|
||||
|
||||
/// A pseudo-element, both public and private.
|
||||
///
|
||||
|
@ -26,10 +27,13 @@ use std::fmt::Debug;
|
|||
#[derive(Clone, Debug, PartialEq, Eq, Hash)]
|
||||
#[cfg_attr(feature = "servo", derive(HeapSizeOf))]
|
||||
#[allow(missing_docs)]
|
||||
#[repr(usize)]
|
||||
pub enum PseudoElement {
|
||||
// Eager pseudos. Keep these first so that eager_index() works.
|
||||
After = 0,
|
||||
Before,
|
||||
After,
|
||||
Selection,
|
||||
// Non-eager pseudos.
|
||||
DetailsSummary,
|
||||
DetailsContent,
|
||||
ServoText,
|
||||
|
@ -48,8 +52,8 @@ impl ToCss for PseudoElement {
|
|||
fn to_css<W>(&self, dest: &mut W) -> fmt::Result where W: fmt::Write {
|
||||
use self::PseudoElement::*;
|
||||
dest.write_str(match *self {
|
||||
Before => "::before",
|
||||
After => "::after",
|
||||
Before => "::before",
|
||||
Selection => "::selection",
|
||||
DetailsSummary => "::-servo-details-summary",
|
||||
DetailsContent => "::-servo-details-content",
|
||||
|
@ -67,15 +71,30 @@ impl ToCss for PseudoElement {
|
|||
}
|
||||
}
|
||||
|
||||
/// The number of eager pseudo-elements. Keep this in sync with cascade_type.
|
||||
pub const EAGER_PSEUDO_COUNT: usize = 3;
|
||||
|
||||
impl PseudoElement {
|
||||
/// Gets the canonical index of this eagerly-cascaded pseudo-element.
|
||||
#[inline]
|
||||
pub fn eager_index(&self) -> usize {
|
||||
debug_assert!(self.is_eager());
|
||||
self.clone() as usize
|
||||
}
|
||||
|
||||
/// Creates a pseudo-element from an eager index.
|
||||
#[inline]
|
||||
pub fn from_eager_index(i: usize) -> Self {
|
||||
assert!(i < EAGER_PSEUDO_COUNT);
|
||||
let result: PseudoElement = unsafe { mem::transmute(i) };
|
||||
debug_assert!(result.is_eager());
|
||||
result
|
||||
}
|
||||
|
||||
/// Whether the current pseudo element is :before or :after.
|
||||
#[inline]
|
||||
pub fn is_before_or_after(&self) -> bool {
|
||||
match *self {
|
||||
PseudoElement::Before |
|
||||
PseudoElement::After => true,
|
||||
_ => false,
|
||||
}
|
||||
matches!(*self, PseudoElement::After | PseudoElement::Before)
|
||||
}
|
||||
|
||||
/// Whether this pseudo-element is eagerly-cascaded.
|
||||
|
@ -99,11 +118,13 @@ impl PseudoElement {
|
|||
/// Returns which kind of cascade type has this pseudo.
|
||||
///
|
||||
/// For more info on cascade types, see docs/components/style.md
|
||||
///
|
||||
/// Note: Keep this in sync with EAGER_PSEUDO_COUNT.
|
||||
#[inline]
|
||||
pub fn cascade_type(&self) -> PseudoElementCascadeType {
|
||||
match *self {
|
||||
PseudoElement::Before |
|
||||
PseudoElement::After |
|
||||
PseudoElement::Before |
|
||||
PseudoElement::Selection => PseudoElementCascadeType::Eager,
|
||||
PseudoElement::DetailsSummary => PseudoElementCascadeType::Lazy,
|
||||
PseudoElement::DetailsContent |
|
||||
|
@ -387,6 +408,17 @@ impl SelectorImpl {
|
|||
pseudo.cascade_type()
|
||||
}
|
||||
|
||||
/// A helper to traverse each eagerly cascaded pseudo-element, executing
|
||||
/// `fun` on it.
|
||||
#[inline]
|
||||
pub fn each_eagerly_cascaded_pseudo_element<F>(mut fun: F)
|
||||
where F: FnMut(PseudoElement),
|
||||
{
|
||||
for i in 0..EAGER_PSEUDO_COUNT {
|
||||
fun(PseudoElement::from_eager_index(i));
|
||||
}
|
||||
}
|
||||
|
||||
/// Executes `fun` for each pseudo-element.
|
||||
#[inline]
|
||||
pub fn each_pseudo_element<F>(mut fun: F)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue