aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorbors-servo <lbergstrom+bors@mozilla.com>2018-03-27 18:51:48 -0400
committerGitHub <noreply@github.com>2018-03-27 18:51:48 -0400
commit97c12bd3927c057d5610b0295f0e8320b64af5e5 (patch)
tree25f3fcc5be8ed6d55885d7f076e4ae3d31577a79
parent84513d43bae2de596686e01d3584cb560a3e6e9e (diff)
parent688fb23d25e72fe434ebb5b927bee619f56d4f61 (diff)
downloadservo-97c12bd3927c057d5610b0295f0e8320b64af5e5.tar.gz
servo-97c12bd3927c057d5610b0295f0e8320b64af5e5.zip
Auto merge of #20456 - upsuper:remove-nscsspseudoclasses, r=emilio
Remove nsCSSPseudoClasses and friends This is the Servo side change of [bug 1449097](https://bugzilla.mozilla.org/show_bug.cgi?id=1449097) and [bug 1449089](https://bugzilla.mozilla.org/show_bug.cgi?id=1449089).
-rw-r--r--components/style/gecko/generated/bindings.rs13
-rw-r--r--components/style/gecko/generated/structs.rs91
-rw-r--r--components/style/gecko/non_ts_pseudo_class_list.rs3
-rw-r--r--components/style/gecko/selector_parser.rs59
-rw-r--r--components/style/gecko/wrapper.rs52
-rw-r--r--ports/geckolib/glue.rs13
6 files changed, 70 insertions, 161 deletions
diff --git a/components/style/gecko/generated/bindings.rs b/components/style/gecko/generated/bindings.rs
index 4e76b4679e0..02401664525 100644
--- a/components/style/gecko/generated/bindings.rs
+++ b/components/style/gecko/generated/bindings.rs
@@ -54,7 +54,6 @@ use gecko_bindings::structs::RawServoSelectorList;
use gecko_bindings::structs::RawServoSourceSizeList;
use gecko_bindings::structs::RefPtr;
use gecko_bindings::structs::RustString;
-use gecko_bindings::structs::CSSPseudoClassType;
use gecko_bindings::structs::CSSPseudoElementType;
use gecko_bindings::structs::ServoTraversalFlags;
use gecko_bindings::structs::ComputedTimingFunction_BeforeFlag;
@@ -628,12 +627,6 @@ extern "C" {
pub fn Gecko_IsRootElement(element: RawGeckoElementBorrowed) -> bool;
}
extern "C" {
- pub fn Gecko_MatchesElement(
- type_: CSSPseudoClassType,
- element: RawGeckoElementBorrowed,
- ) -> bool;
-}
-extern "C" {
pub fn Gecko_MatchLang(
element: RawGeckoElementBorrowed,
override_lang: *mut nsAtom,
@@ -648,6 +641,12 @@ extern "C" {
pub fn Gecko_GetDocumentLWTheme(aDocument: *const nsIDocument) -> nsIDocument_DocumentTheme;
}
extern "C" {
+ pub fn Gecko_IsTableBorderNonzero(element: RawGeckoElementBorrowed) -> bool;
+}
+extern "C" {
+ pub fn Gecko_IsBrowserFrame(element: RawGeckoElementBorrowed) -> bool;
+}
+extern "C" {
pub fn Gecko_AtomAttrValue(
element: RawGeckoElementBorrowed,
attribute: *mut nsAtom,
diff --git a/components/style/gecko/generated/structs.rs b/components/style/gecko/generated/structs.rs
index 923b16f41d4..874568e7d19 100644
--- a/components/style/gecko/generated/structs.rs
+++ b/components/style/gecko/generated/structs.rs
@@ -12267,97 +12267,6 @@ pub mod root {
)
);
}
- pub type CSSPseudoClassTypeBase = u8;
- #[repr(u8)]
- #[derive(Debug, Copy, Clone, PartialEq, Eq, Hash)]
- pub enum CSSPseudoClassType {
- empty = 0,
- mozOnlyWhitespace = 1,
- lang = 2,
- root = 3,
- any = 4,
- firstChild = 5,
- firstNode = 6,
- lastChild = 7,
- lastNode = 8,
- onlyChild = 9,
- firstOfType = 10,
- lastOfType = 11,
- onlyOfType = 12,
- nthChild = 13,
- nthLastChild = 14,
- nthOfType = 15,
- nthLastOfType = 16,
- mozIsHTML = 17,
- mozNativeAnonymous = 18,
- mozUseShadowTreeRoot = 19,
- mozLocaleDir = 20,
- mozLWTheme = 21,
- mozLWThemeBrightText = 22,
- mozLWThemeDarkText = 23,
- mozWindowInactive = 24,
- mozTableBorderNonzero = 25,
- mozBrowserFrame = 26,
- scope = 27,
- negation = 28,
- dir = 29,
- link = 30,
- mozAnyLink = 31,
- anyLink = 32,
- visited = 33,
- active = 34,
- checked = 35,
- disabled = 36,
- enabled = 37,
- focus = 38,
- focusWithin = 39,
- hover = 40,
- mozDragOver = 41,
- target = 42,
- indeterminate = 43,
- mozDevtoolsHighlighted = 44,
- mozStyleeditorTransitioning = 45,
- fullscreen = 46,
- mozFullScreen = 47,
- mozFocusRing = 48,
- mozBroken = 49,
- mozLoading = 50,
- mozUserDisabled = 51,
- mozSuppressed = 52,
- mozHandlerClickToPlay = 53,
- mozHandlerVulnerableUpdatable = 54,
- mozHandlerVulnerableNoUpdate = 55,
- mozHandlerDisabled = 56,
- mozHandlerBlocked = 57,
- mozHandlerCrashed = 58,
- mozMathIncrementScriptLevel = 59,
- mozHasDirAttr = 60,
- mozDirAttrLTR = 61,
- mozDirAttrRTL = 62,
- mozDirAttrLikeAuto = 63,
- mozAutofill = 64,
- mozAutofillPreview = 65,
- required = 66,
- optional = 67,
- valid = 68,
- invalid = 69,
- inRange = 70,
- outOfRange = 71,
- defaultPseudo = 72,
- placeholderShown = 73,
- mozReadOnly = 74,
- mozReadWrite = 75,
- mozSubmitInvalid = 76,
- mozUIInvalid = 77,
- mozUIValid = 78,
- mozMeterOptimum = 79,
- mozMeterSubOptimum = 80,
- mozMeterSubSubOptimum = 81,
- mozPlaceholder = 82,
- Count = 83,
- NotPseudo = 84,
- MAX = 85,
- }
#[repr(C)]
pub struct GeckoFont {
pub gecko: root::nsStyleFont,
diff --git a/components/style/gecko/non_ts_pseudo_class_list.rs b/components/style/gecko/non_ts_pseudo_class_list.rs
index 0a5fe00be02..b02e21fbf8a 100644
--- a/components/style/gecko/non_ts_pseudo_class_list.rs
+++ b/components/style/gecko/non_ts_pseudo_class_list.rs
@@ -28,9 +28,6 @@
*
* :scope -> <style scoped>, pending discussion.
*
- * This follows the order defined in layout/style/nsCSSPseudoClassList.h when
- * possible.
- *
* $gecko_type can be either "_" or an ident in Gecko's CSSPseudoClassType.
* $state can be either "_" or an expression of type ElementState. If present,
* the semantics are that the pseudo-class matches if any of the bits in
diff --git a/components/style/gecko/selector_parser.rs b/components/style/gecko/selector_parser.rs
index b6e99b2083f..1a57e5e2ba0 100644
--- a/components/style/gecko/selector_parser.rs
+++ b/components/style/gecko/selector_parser.rs
@@ -6,7 +6,7 @@
use cssparser::{BasicParseError, BasicParseErrorKind, Parser, ToCss, Token, CowRcStr, SourceLocation};
use element_state::{DocumentState, ElementState};
-use gecko_bindings::structs::{self, CSSPseudoClassType};
+use gecko_bindings::structs;
use gecko_bindings::structs::RawServoSelectorList;
use gecko_bindings::sugar::ownership::{HasBoxFFI, HasFFI, HasSimpleFFI};
use invalidation::element::document_state::InvalidationMatchingData;
@@ -133,6 +133,22 @@ impl Visit for NonTSPseudoClass {
impl NonTSPseudoClass {
+ /// Parses the name and returns a non-ts-pseudo-class if succeeds.
+ /// None otherwise. It doesn't check whether the pseudo-class is enabled
+ /// in a particular state.
+ pub fn parse_non_functional(name: &str) -> Option<Self> {
+ macro_rules! pseudo_class_parse {
+ (bare: [$(($css:expr, $name:ident, $gecko_type:tt, $state:tt, $flags:tt),)*],
+ string: [$(($s_css:expr, $s_name:ident, $s_gecko_type:tt, $s_state:tt, $s_flags:tt),)*]) => {
+ match_ignore_ascii_case! { &name,
+ $($css => Some(NonTSPseudoClass::$name),)*
+ _ => None,
+ }
+ }
+ }
+ apply_non_ts_list!(pseudo_class_parse)
+ }
+
/// Returns true if this pseudo-class has any of the given flags set.
fn has_any_flag(&self, flags: NonTSPseudoClassFlag) -> bool {
macro_rules! check_flag {
@@ -242,28 +258,6 @@ impl NonTSPseudoClass {
)
}
- /// Convert NonTSPseudoClass to Gecko's CSSPseudoClassType.
- pub fn to_gecko_pseudoclasstype(&self) -> Option<CSSPseudoClassType> {
- macro_rules! gecko_type {
- (_) => (None);
- ($gecko_type:ident) =>
- (Some(::gecko_bindings::structs::CSSPseudoClassType::$gecko_type));
- }
- macro_rules! pseudo_class_geckotype {
- (bare: [$(($css:expr, $name:ident, $gecko_type:tt, $state:tt, $flags:tt),)*],
- string: [$(($s_css:expr, $s_name:ident, $s_gecko_type:tt, $s_state:tt, $s_flags:tt),)*]) => {
- match *self {
- $(NonTSPseudoClass::$name => gecko_type!($gecko_type),)*
- $(NonTSPseudoClass::$s_name(..) => gecko_type!($s_gecko_type),)*
- NonTSPseudoClass::MozLocaleDir(_) => gecko_type!(mozLocaleDir),
- NonTSPseudoClass::Dir(_) => gecko_type!(dir),
- NonTSPseudoClass::MozAny(_) => gecko_type!(any),
- }
- }
- }
- apply_non_ts_list!(pseudo_class_geckotype)
- }
-
/// Returns true if the evaluation of the pseudo-class depends on the
/// element's attributes.
pub fn is_attr_based(&self) -> bool {
@@ -373,23 +367,12 @@ impl<'a, 'i> ::selectors::Parser<'i> for SelectorParser<'a> {
location: SourceLocation,
name: CowRcStr<'i>,
) -> Result<NonTSPseudoClass, ParseError<'i>> {
- macro_rules! pseudo_class_parse {
- (bare: [$(($css:expr, $name:ident, $gecko_type:tt, $state:tt, $flags:tt),)*],
- string: [$(($s_css:expr, $s_name:ident, $s_gecko_type:tt, $s_state:tt, $s_flags:tt),)*]) => {
- match_ignore_ascii_case! { &name,
- $($css => NonTSPseudoClass::$name,)*
- _ => return Err(location.new_custom_error(
- SelectorParseErrorKind::UnsupportedPseudoClassOrElement(name.clone())
- ))
- }
+ if let Some(pseudo_class) = NonTSPseudoClass::parse_non_functional(&name) {
+ if self.is_pseudo_class_enabled(&pseudo_class) {
+ return Ok(pseudo_class);
}
}
- let pseudo_class = apply_non_ts_list!(pseudo_class_parse);
- if self.is_pseudo_class_enabled(&pseudo_class) {
- Ok(pseudo_class)
- } else {
- Err(location.new_custom_error(SelectorParseErrorKind::UnsupportedPseudoClassOrElement(name)))
- }
+ Err(location.new_custom_error(SelectorParseErrorKind::UnsupportedPseudoClassOrElement(name)))
}
fn parse_non_ts_functional_pseudo_class<'t>(
diff --git a/components/style/gecko/wrapper.rs b/components/style/gecko/wrapper.rs
index ace76867217..9c32d301c13 100644
--- a/components/style/gecko/wrapper.rs
+++ b/components/style/gecko/wrapper.rs
@@ -32,7 +32,6 @@ use gecko_bindings::bindings;
use gecko_bindings::bindings::{Gecko_ConstructStyleChildrenIterator, Gecko_DestroyStyleChildrenIterator};
use gecko_bindings::bindings::{Gecko_ElementState, Gecko_GetDocumentLWTheme};
use gecko_bindings::bindings::{Gecko_GetLastChild, Gecko_GetNextStyleChild};
-use gecko_bindings::bindings::{Gecko_IsRootElement, Gecko_MatchesElement};
use gecko_bindings::bindings::{Gecko_SetNodeFlags, Gecko_UnsetNodeFlags};
use gecko_bindings::bindings::Gecko_ClassOrClassList;
use gecko_bindings::bindings::Gecko_ElementHasAnimations;
@@ -814,6 +813,21 @@ impl<'le> GeckoElement<'le> {
(!self.as_node().is_in_shadow_tree() && self.has_xbl_binding_parent())
}
+ /// Returns true if this node is the shadow root of an use-element shadow tree.
+ #[inline]
+ fn is_root_of_use_element_shadow_tree(&self) -> bool {
+ if !self.is_root_of_anonymous_subtree() {
+ return false
+ }
+ match self.parent_element() {
+ Some(e) => {
+ e.local_name() == &*local_name!("use") &&
+ e.namespace() == &*ns!("http://www.w3.org/2000/svg")
+ },
+ None => false,
+ }
+ }
+
fn css_transitions_info(&self) -> FnvHashMap<LonghandId, Arc<AnimationValue>> {
use gecko_bindings::bindings::Gecko_ElementTransitions_EndValueAt;
use gecko_bindings::bindings::Gecko_ElementTransitions_Length;
@@ -1981,7 +1995,7 @@ impl<'le> ::selectors::Element for GeckoElement<'le> {
}
unsafe {
- Gecko_IsRootElement(self.0)
+ bindings::Gecko_IsRootElement(self.0)
}
}
@@ -2103,11 +2117,17 @@ impl<'le> ::selectors::Element for GeckoElement<'le> {
}
true
}
- NonTSPseudoClass::MozTableBorderNonzero |
- NonTSPseudoClass::MozBrowserFrame |
- NonTSPseudoClass::MozNativeAnonymous |
- NonTSPseudoClass::MozUseShadowTreeRoot => unsafe {
- Gecko_MatchesElement(pseudo_class.to_gecko_pseudoclasstype().unwrap(), self.0)
+ NonTSPseudoClass::MozNativeAnonymous => {
+ self.is_in_native_anonymous_subtree()
+ }
+ NonTSPseudoClass::MozUseShadowTreeRoot => {
+ self.is_root_of_use_element_shadow_tree()
+ }
+ NonTSPseudoClass::MozTableBorderNonzero => unsafe {
+ bindings::Gecko_IsTableBorderNonzero(self.0)
+ }
+ NonTSPseudoClass::MozBrowserFrame => unsafe {
+ bindings::Gecko_IsBrowserFrame(self.0)
},
NonTSPseudoClass::MozIsHTML => {
self.is_html_element_in_html_document()
@@ -2235,20 +2255,10 @@ impl<'le> ::selectors::Element for GeckoElement<'le> {
#[inline]
fn blocks_ancestor_combinators(&self) -> bool {
- if !self.is_root_of_anonymous_subtree() {
- return false
- }
-
- match self.parent_element() {
- Some(e) => {
- // If this element is the shadow root of an use-element shadow
- // tree, according to the spec, we should not match rules
- // cross the shadow DOM boundary.
- e.local_name() == &*local_name!("use") &&
- e.namespace() == &*ns!("http://www.w3.org/2000/svg")
- },
- None => false,
- }
+ // If this element is the shadow root of an use-element shadow tree,
+ // according to the spec, we should not match rules cross the shadow
+ // DOM boundary.
+ self.is_root_of_use_element_shadow_tree()
}
}
diff --git a/ports/geckolib/glue.rs b/ports/geckolib/glue.rs
index 3381da47e0b..4d5cbc87fdd 100644
--- a/ports/geckolib/glue.rs
+++ b/ports/geckolib/glue.rs
@@ -31,7 +31,7 @@ use style::font_metrics::{FontMetricsProvider, get_metrics_provider_for_product}
use style::gecko::data::{GeckoStyleSheet, PerDocumentStyleData, PerDocumentStyleDataImpl};
use style::gecko::global_style_data::{GLOBAL_STYLE_DATA, GlobalStyleData, STYLE_THREAD_POOL};
use style::gecko::restyle_damage::GeckoRestyleDamage;
-use style::gecko::selector_parser::PseudoElement;
+use style::gecko::selector_parser::{NonTSPseudoClass, PseudoElement};
use style::gecko::traversal::RecalcStyleOnly;
use style::gecko::wrapper::{GeckoElement, GeckoNode};
use style::gecko_bindings::bindings;
@@ -5115,3 +5115,14 @@ pub extern "C" fn Servo_ParseCounterStyleDescriptor(
result,
).is_ok()
}
+
+#[no_mangle]
+pub unsafe extern "C" fn Servo_PseudoClass_GetStates(name: *const nsACString) -> u64 {
+ let name = name.as_ref().unwrap().as_str_unchecked();
+ match NonTSPseudoClass::parse_non_functional(name) {
+ None => 0,
+ // Ignore :any-link since it contains both visited and unvisited state.
+ Some(NonTSPseudoClass::AnyLink) => 0,
+ Some(pseudo_class) => pseudo_class.state_flag().bits(),
+ }
+}