aboutsummaryrefslogtreecommitdiffstats
path: root/components/script
diff options
context:
space:
mode:
Diffstat (limited to 'components/script')
-rw-r--r--components/script/devtools.rs11
-rw-r--r--components/script/dom/element.rs62
-rw-r--r--components/script/dom/node.rs5
-rw-r--r--components/script/dom/window.rs28
4 files changed, 49 insertions, 57 deletions
diff --git a/components/script/devtools.rs b/components/script/devtools.rs
index 585ecd47a15..0d2b4a9e4eb 100644
--- a/components/script/devtools.rs
+++ b/components/script/devtools.rs
@@ -154,12 +154,13 @@ pub fn handle_get_layout(documents: &Documents,
}
fn determine_auto_margins(window: &Window, node: &Node) -> AutoMargins {
- let margin = window.margin_style_query(node.to_trusted_node_address());
+ let style = window.style_query(node.to_trusted_node_address()).unwrap();
+ let margin = style.get_margin();
AutoMargins {
- top: margin.top == margin_top::computed_value::T::Auto,
- right: margin.right == margin_right::computed_value::T::Auto,
- bottom: margin.bottom == margin_bottom::computed_value::T::Auto,
- left: margin.left == margin_left::computed_value::T::Auto,
+ top: margin.margin_top == margin_top::computed_value::T::Auto,
+ right: margin.margin_right == margin_right::computed_value::T::Auto,
+ bottom: margin.margin_bottom == margin_bottom::computed_value::T::Auto,
+ left: margin.margin_left == margin_left::computed_value::T::Auto,
}
}
diff --git a/components/script/dom/element.rs b/components/script/dom/element.rs
index c6224e7dc87..a1bcaa0437e 100644
--- a/components/script/dom/element.rs
+++ b/components/script/dom/element.rs
@@ -348,27 +348,24 @@ impl Element {
}
// https://drafts.csswg.org/cssom-view/#css-layout-box
- //
- // We'll have no content box if there's no fragment for the node, and we use
- // bounding_content_box, for simplicity, to detect this (rather than making a more specific
- // query to the layout thread).
fn has_css_layout_box(&self) -> bool {
- self.upcast::<Node>().bounding_content_box().is_some()
+ let style = self.upcast::<Node>().style();
+
+ // style will be None for elements in a display: none subtree. otherwise, the element has a
+ // layout box iff it doesn't have display: none.
+ style.map_or(false, |s| !s.get_box().clone_display().is_none())
}
// https://drafts.csswg.org/cssom-view/#potentially-scrollable
fn potentially_scrollable(&self) -> bool {
- self.has_css_layout_box() &&
- !self.overflow_x_is_visible() &&
- !self.overflow_y_is_visible()
+ self.has_css_layout_box() && !self.has_any_visible_overflow()
}
// https://drafts.csswg.org/cssom-view/#scrolling-box
fn has_scrolling_box(&self) -> bool {
// TODO: scrolling mechanism, such as scrollbar (We don't have scrollbar yet)
// self.has_scrolling_mechanism()
- self.overflow_x_is_hidden() ||
- self.overflow_y_is_hidden()
+ self.has_any_hidden_overflow()
}
fn has_overflow(&self) -> bool {
@@ -376,32 +373,33 @@ impl Element {
self.ScrollWidth() > self.ClientWidth()
}
- // used value of overflow-x is "visible"
- fn overflow_x_is_visible(&self) -> bool {
- let window = window_from_node(self);
- let overflow_pair = window.overflow_query(self.upcast::<Node>().to_trusted_node_address());
- overflow_pair.x == overflow_x::computed_value::T::Visible
- }
+ // TODO: Once #19183 is closed (overflow-x/y types moved out of mako), then we could implement
+ // a more generic `fn has_some_overflow(&self, overflow: Overflow)` rather than have
+ // these two `has_any_{visible,hidden}_overflow` methods which are very structurally
+ // similar.
- // used value of overflow-y is "visible"
- fn overflow_y_is_visible(&self) -> bool {
- let window = window_from_node(self);
- let overflow_pair = window.overflow_query(self.upcast::<Node>().to_trusted_node_address());
- overflow_pair.y == overflow_y::computed_value::T::Visible
- }
+ /// Computed value of overflow-x or overflow-y is "visible"
+ fn has_any_visible_overflow(&self) -> bool {
+ let style = self.upcast::<Node>().style();
- // used value of overflow-x is "hidden"
- fn overflow_x_is_hidden(&self) -> bool {
- let window = window_from_node(self);
- let overflow_pair = window.overflow_query(self.upcast::<Node>().to_trusted_node_address());
- overflow_pair.x == overflow_x::computed_value::T::Hidden
+ style.map_or(false, |s| {
+ let box_ = s.get_box();
+
+ box_.clone_overflow_x() == overflow_x::computed_value::T::Visible ||
+ box_.clone_overflow_y() == overflow_y::computed_value::T::Visible
+ })
}
- // used value of overflow-y is "hidden"
- fn overflow_y_is_hidden(&self) -> bool {
- let window = window_from_node(self);
- let overflow_pair = window.overflow_query(self.upcast::<Node>().to_trusted_node_address());
- overflow_pair.y == overflow_y::computed_value::T::Hidden
+ /// Computed value of overflow-x or overflow-y is "hidden"
+ fn has_any_hidden_overflow(&self) -> bool {
+ let style = self.upcast::<Node>().style();
+
+ style.map_or(false, |s| {
+ let box_ = s.get_box();
+
+ box_.clone_overflow_x() == overflow_x::computed_value::T::Hidden ||
+ box_.clone_overflow_y() == overflow_y::computed_value::T::Hidden
+ })
}
}
diff --git a/components/script/dom/node.rs b/components/script/dom/node.rs
index 68e6f63e168..28e10cf798c 100644
--- a/components/script/dom/node.rs
+++ b/components/script/dom/node.rs
@@ -82,6 +82,7 @@ use std::mem;
use std::ops::Range;
use style::context::QuirksMode;
use style::dom::OpaqueNode;
+use style::properties::ComputedValues;
use style::selector_parser::{SelectorImpl, SelectorParser};
use style::stylesheets::Stylesheet;
use style::thread_state;
@@ -619,6 +620,10 @@ impl Node {
window_from_node(self).client_rect_query(self.to_trusted_node_address())
}
+ pub fn style(&self) -> Option<Arc<ComputedValues>> {
+ window_from_node(self).style_query(self.to_trusted_node_address())
+ }
+
// https://drafts.csswg.org/cssom-view/#dom-element-scrollwidth
// https://drafts.csswg.org/cssom-view/#dom-element-scrollheight
// https://drafts.csswg.org/cssom-view/#dom-element-scrolltop
diff --git a/components/script/dom/window.rs b/components/script/dom/window.rs
index 21713696f82..e9055f54ea0 100644
--- a/components/script/dom/window.rs
+++ b/components/script/dom/window.rs
@@ -72,8 +72,7 @@ use script_layout_interface::{TrustedNodeAddress, PendingImageState};
use script_layout_interface::message::{Msg, Reflow, ReflowGoal, ScriptReflow};
use script_layout_interface::reporter::CSSErrorReporter;
use script_layout_interface::rpc::{ContentBoxResponse, ContentBoxesResponse, LayoutRPC};
-use script_layout_interface::rpc::{MarginStyleResponse, NodeScrollRootIdResponse};
-use script_layout_interface::rpc::{ResolvedStyleResponse, TextIndexResponse};
+use script_layout_interface::rpc::{NodeScrollRootIdResponse, ResolvedStyleResponse, TextIndexResponse};
use script_runtime::{CommonScriptMsg, ScriptChan, ScriptPort, ScriptThreadEventCategory, Runtime};
use script_thread::{ImageCacheMsg, MainThreadScriptChan, MainThreadScriptMsg};
use script_thread::{ScriptThread, SendableMainThreadScriptChan};
@@ -82,6 +81,7 @@ use script_traits::{ScriptToConstellationChan, ScriptMsg, ScrollState, TimerEven
use script_traits::{TimerSchedulerMsg, UntrustedNodeAddress, WindowSizeData, WindowSizeType};
use script_traits::webdriver_msg::{WebDriverJSError, WebDriverJSResult};
use selectors::attr::CaseSensitivity;
+use servo_arc;
use servo_config::opts;
use servo_config::prefs::PREFS;
use servo_geometry::{f32_rect_to_au_rect, MaxRect};
@@ -102,8 +102,7 @@ use std::sync::mpsc::{Sender, channel};
use std::sync::mpsc::TryRecvError::{Disconnected, Empty};
use style::media_queries;
use style::parser::ParserContext as CssParserContext;
-use style::properties::PropertyId;
-use style::properties::longhands::overflow_x;
+use style::properties::{ComputedValues, PropertyId};
use style::selector_parser::PseudoElement;
use style::str::HTML_SPACE_CHARACTERS;
use style::stylesheets::CssRuleType;
@@ -1403,16 +1402,6 @@ impl Window {
self.layout_rpc.node_scroll_area().client_rect
}
- pub fn overflow_query(&self,
- node: TrustedNodeAddress) -> Point2D<overflow_x::computed_value::T> {
- // NB: This is only called if the document is fully active, and the only
- // reason to bail out from a query is if there's no viewport, so this
- // *must* issue a reflow.
- assert!(self.reflow(ReflowGoal::NodeOverflowQuery(node), ReflowReason::Query));
-
- self.layout_rpc.node_overflow().0.unwrap()
- }
-
pub fn scroll_offset_query(&self, node: &Node) -> Vector2D<f32> {
if let Some(scroll_offset) = self.scroll_offsets
.borrow()
@@ -1477,11 +1466,11 @@ impl Window {
(element, response.rect)
}
- pub fn margin_style_query(&self, node: TrustedNodeAddress) -> MarginStyleResponse {
- if !self.reflow(ReflowGoal::MarginStyleQuery(node), ReflowReason::Query) {
- return MarginStyleResponse::empty();
+ pub fn style_query(&self, node: TrustedNodeAddress) -> Option<servo_arc::Arc<ComputedValues>> {
+ if !self.reflow(ReflowGoal::StyleQuery(node), ReflowReason::Query) {
+ return None
}
- self.layout_rpc.margin_style()
+ self.layout_rpc.style().0
}
pub fn text_index_query(
@@ -1898,12 +1887,11 @@ fn debug_reflow_events(id: PipelineId, reflow_goal: &ReflowGoal, reason: &Reflow
ReflowGoal::ContentBoxesQuery(_n) => "\tContentBoxesQuery",
ReflowGoal::NodesFromPointQuery(..) => "\tNodesFromPointQuery",
ReflowGoal::NodeGeometryQuery(_n) => "\tNodeGeometryQuery",
- ReflowGoal::NodeOverflowQuery(_n) => "\tNodeOverFlowQuery",
ReflowGoal::NodeScrollGeometryQuery(_n) => "\tNodeScrollGeometryQuery",
ReflowGoal::NodeScrollRootIdQuery(_n) => "\tNodeScrollRootIdQuery",
ReflowGoal::ResolvedStyleQuery(_, _, _) => "\tResolvedStyleQuery",
ReflowGoal::OffsetParentQuery(_n) => "\tOffsetParentQuery",
- ReflowGoal::MarginStyleQuery(_n) => "\tMarginStyleQuery",
+ ReflowGoal::StyleQuery(_n) => "\tStyleQuery",
ReflowGoal::TextIndexQuery(..) => "\tTextIndexQuery",
ReflowGoal::TickAnimations => "\tTickAnimations",
});