aboutsummaryrefslogtreecommitdiffstats
path: root/components/script
diff options
context:
space:
mode:
Diffstat (limited to 'components/script')
-rw-r--r--components/script/Cargo.toml2
-rw-r--r--components/script/dom/element.rs53
-rw-r--r--components/script/layout_wrapper.rs90
3 files changed, 79 insertions, 66 deletions
diff --git a/components/script/Cargo.toml b/components/script/Cargo.toml
index d9bdeac843b..fa2d75c633d 100644
--- a/components/script/Cargo.toml
+++ b/components/script/Cargo.toml
@@ -57,7 +57,7 @@ regex = "0.1.43"
rustc-serialize = "0.3"
script_layout_interface = {path = "../script_layout_interface"}
script_traits = {path = "../script_traits"}
-selectors = {version = "0.6", features = ["heap_size"]}
+selectors = {version = "0.7", features = ["heap_size"]}
serde = "0.7.11"
smallvec = "0.1"
string_cache = {version = "0.2.20", features = ["heap_size", "unstable"]}
diff --git a/components/script/dom/element.rs b/components/script/dom/element.rs
index d9535663d46..e53f7dbb77b 100644
--- a/components/script/dom/element.rs
+++ b/components/script/dom/element.rs
@@ -2217,6 +2217,34 @@ impl VirtualMethods for Element {
}
}
+impl<'a> ::selectors::MatchAttrGeneric for Root<Element> {
+ fn match_attr<F>(&self, attr: &AttrSelector, test: F) -> bool
+ where F: Fn(&str) -> bool
+ {
+ use ::selectors::Element;
+ let local_name = {
+ if self.is_html_element_in_html_document() {
+ &attr.lower_name
+ } else {
+ &attr.name
+ }
+ };
+ match attr.namespace {
+ NamespaceConstraint::Specific(ref ns) => {
+ self.get_attribute(ns, local_name)
+ .map_or(false, |attr| {
+ test(&attr.value())
+ })
+ },
+ NamespaceConstraint::Any => {
+ self.attrs.borrow().iter().any(|attr| {
+ attr.local_name() == local_name && test(&attr.value())
+ })
+ }
+ }
+ }
+}
+
impl<'a> ::selectors::Element for Root<Element> {
type Impl = ServoSelectorImpl;
@@ -2317,31 +2345,6 @@ impl<'a> ::selectors::Element for Root<Element> {
}
}
- fn match_attr<F>(&self, attr: &AttrSelector, test: F) -> bool
- where F: Fn(&str) -> bool
- {
- let local_name = {
- if self.is_html_element_in_html_document() {
- &attr.lower_name
- } else {
- &attr.name
- }
- };
- match attr.namespace {
- NamespaceConstraint::Specific(ref ns) => {
- self.get_attribute(ns, local_name)
- .map_or(false, |attr| {
- test(&attr.value())
- })
- },
- NamespaceConstraint::Any => {
- self.attrs.borrow().iter().any(|attr| {
- attr.local_name() == local_name && test(&attr.value())
- })
- }
- }
- }
-
fn is_html_element_in_html_document(&self) -> bool {
self.html_element_in_html_document()
}
diff --git a/components/script/layout_wrapper.rs b/components/script/layout_wrapper.rs
index 7085fcae002..ebc2da9c529 100644
--- a/components/script/layout_wrapper.rs
+++ b/components/script/layout_wrapper.rs
@@ -387,17 +387,13 @@ impl<'le> TElement for ServoLayoutElement<'le> {
}
#[inline]
- fn get_attr(&self, namespace: &Namespace, name: &Atom) -> Option<&str> {
- unsafe {
- (*self.element.unsafe_get()).get_attr_val_for_layout(namespace, name)
- }
+ fn has_attr(&self, namespace: &Namespace, attr: &Atom) -> bool {
+ self.get_attr(namespace, attr).is_some()
}
#[inline]
- fn get_attrs(&self, name: &Atom) -> Vec<&str> {
- unsafe {
- (*self.element.unsafe_get()).get_attr_vals_for_layout(name)
- }
+ fn attr_equals(&self, namespace: &Namespace, attr: &Atom, val: &Atom) -> bool {
+ self.get_attr(namespace, attr).map_or(false, |x| x == val)
}
}
@@ -409,12 +405,41 @@ impl<'le> ServoLayoutElement<'le> {
chain: PhantomData,
}
}
+
+ #[inline]
+ fn get_attr(&self, namespace: &Namespace, name: &Atom) -> Option<&str> {
+ unsafe {
+ (*self.element.unsafe_get()).get_attr_val_for_layout(namespace, name)
+ }
+ }
}
fn as_element<'le>(node: LayoutJS<Node>) -> Option<ServoLayoutElement<'le>> {
node.downcast().map(ServoLayoutElement::from_layout_js)
}
+impl<'le> ::selectors::MatchAttrGeneric for ServoLayoutElement<'le> {
+ fn match_attr<F>(&self, attr: &AttrSelector, test: F) -> bool where F: Fn(&str) -> bool {
+ use ::selectors::Element;
+ let name = if self.is_html_element_in_html_document() {
+ &attr.lower_name
+ } else {
+ &attr.name
+ };
+ match attr.namespace {
+ NamespaceConstraint::Specific(ref ns) => {
+ self.get_attr(ns, name).map_or(false, |attr| test(attr))
+ },
+ NamespaceConstraint::Any => {
+ let attrs = unsafe {
+ (*self.element.unsafe_get()).get_attr_vals_for_layout(name)
+ };
+ attrs.iter().any(|attr| test(*attr))
+ }
+ }
+ }
+}
+
impl<'le> ::selectors::Element for ServoLayoutElement<'le> {
type Impl = ServoSelectorImpl;
@@ -550,22 +575,6 @@ impl<'le> ::selectors::Element for ServoLayoutElement<'le> {
}
}
- fn match_attr<F>(&self, attr: &AttrSelector, test: F) -> bool where F: Fn(&str) -> bool {
- let name = if self.is_html_element_in_html_document() {
- &attr.lower_name
- } else {
- &attr.name
- };
- match attr.namespace {
- NamespaceConstraint::Specific(ref ns) => {
- self.get_attr(ns, name).map_or(false, |attr| test(attr))
- },
- NamespaceConstraint::Any => {
- self.get_attrs(name).iter().any(|attr| test(*attr))
- }
- }
- }
-
fn is_html_element_in_html_document(&self) -> bool {
unsafe {
self.element.html_element_in_html_document_for_layout()
@@ -900,7 +909,23 @@ impl<'le> ThreadSafeLayoutElement for ServoThreadSafeLayoutElement<'le> {
///
/// Note that the element implementation is needed only for selector matching,
/// not for inheritance (styles are inherited appropiately).
-impl <'le> ::selectors::Element for ServoThreadSafeLayoutElement<'le> {
+impl<'le> ::selectors::MatchAttrGeneric for ServoThreadSafeLayoutElement<'le> {
+ fn match_attr<F>(&self, attr: &AttrSelector, test: F) -> bool
+ where F: Fn(&str) -> bool {
+ match attr.namespace {
+ NamespaceConstraint::Specific(ref ns) => {
+ self.get_attr(ns, &attr.name).map_or(false, |attr| test(attr))
+ },
+ NamespaceConstraint::Any => {
+ unsafe {
+ self.element.get_attr_vals_for_layout(&attr.name).iter()
+ .any(|attr| test(*attr))
+ }
+ }
+ }
+ }
+}
+impl<'le> ::selectors::Element for ServoThreadSafeLayoutElement<'le> {
type Impl = ServoSelectorImpl;
fn parent_element(&self) -> Option<Self> {
@@ -962,21 +987,6 @@ impl <'le> ::selectors::Element for ServoThreadSafeLayoutElement<'le> {
false
}
- fn match_attr<F>(&self, attr: &AttrSelector, test: F) -> bool
- where F: Fn(&str) -> bool {
- match attr.namespace {
- NamespaceConstraint::Specific(ref ns) => {
- self.get_attr(ns, &attr.name).map_or(false, |attr| test(attr))
- },
- NamespaceConstraint::Any => {
- unsafe {
- self.element.get_attr_vals_for_layout(&attr.name).iter()
- .any(|attr| test(*attr))
- }
- }
- }
- }
-
fn is_empty(&self) -> bool {
warn!("ServoThreadSafeLayoutElement::is_empty called");
false