aboutsummaryrefslogtreecommitdiffstats
path: root/components/layout/flow.rs
diff options
context:
space:
mode:
Diffstat (limited to 'components/layout/flow.rs')
-rw-r--r--components/layout/flow.rs66
1 files changed, 30 insertions, 36 deletions
diff --git a/components/layout/flow.rs b/components/layout/flow.rs
index a36fca0df0a..f20d5a0c128 100644
--- a/components/layout/flow.rs
+++ b/components/layout/flow.rs
@@ -32,7 +32,7 @@ use display_list_builder::DisplayListBuildingResult;
use floats::Floats;
use flow_list::{FlowList, FlowListIterator, MutFlowListIterator};
use flow_ref::FlowRef;
-use fragment::{Fragment, FragmentBoundsIterator, SpecificFragmentInfo};
+use fragment::{Fragment, FragmentOverflowIterator, SpecificFragmentInfo};
use incremental::{RECONSTRUCT_FLOW, REFLOW, REFLOW_OUT_OF_FLOW, RestyleDamage};
use inline::InlineFlow;
use model::{CollapsibleMargins, IntrinsicISizes, MarginCollapseInfo};
@@ -50,7 +50,7 @@ use geom::{Point2D, Rect, Size2D};
use gfx::display_list::ClippingRegion;
use serialize::{Encoder, Encodable};
use servo_msg::compositor_msg::LayerId;
-use servo_util::geometry::Au;
+use servo_util::geometry::{Au, ZERO_RECT};
use servo_util::logical_geometry::{LogicalRect, LogicalSize, WritingMode};
use std::mem;
use std::fmt;
@@ -220,8 +220,11 @@ pub trait Flow: fmt::Show + ToString + Sync {
/// Phase 5 of reflow: builds display lists.
fn build_display_list(&mut self, layout_context: &LayoutContext);
- /// Perform an iteration of fragment bounds on this flow.
- fn iterate_through_fragment_bounds(&self, iterator: &mut FragmentBoundsIterator);
+ /// Returns the union of all overflow rects of all of this flow's fragments.
+ fn compute_overflow(&self) -> Rect<Au>;
+
+ /// Iterates through overflow rects of all of this flow's fragments.
+ fn iterate_through_fragment_overflow(&self, iterator: &mut FragmentOverflowIterator);
fn compute_collapsible_block_start_margin(&mut self,
_layout_context: &mut LayoutContext,
@@ -718,7 +721,7 @@ pub struct BaseFlow {
/// The amount of overflow of this flow, relative to the containing block. Must include all the
/// pixels of all the display list items for correct invalidation.
- pub overflow: LogicalRect<Au>,
+ pub overflow: Rect<Au>,
/// Data used during parallel traversals.
///
@@ -894,7 +897,7 @@ impl BaseFlow {
children: FlowList::new(),
intrinsic_inline_sizes: IntrinsicISizes::new(),
position: LogicalRect::zero(writing_mode),
- overflow: LogicalRect::zero(writing_mode),
+ overflow: ZERO_RECT,
parallel: FlowParallelInfo::new(),
floats: Floats::new(writing_mode),
collapsible_margins: CollapsibleMargins::new(),
@@ -929,10 +932,12 @@ impl BaseFlow {
/// Ensures that all display list items generated by this flow are within the flow's overflow
/// rect. This should only be used for debugging.
pub fn validate_display_list_geometry(&self) {
- let position_with_overflow = self.position.union(&self.overflow);
- let bounds = Rect(self.stacking_relative_position,
- Size2D(position_with_overflow.size.inline,
- position_with_overflow.size.block));
+ // FIXME(pcwalton, #2795): Get the real container size.
+ let container_size = Size2D::zero();
+ let position_with_overflow = self.position
+ .to_physical(self.writing_mode, container_size)
+ .union(&self.overflow);
+ let bounds = Rect(self.stacking_relative_position, position_with_overflow.size);
let all_items = match self.display_list_building_result {
DisplayListBuildingResult::None => Vec::new(),
@@ -1175,40 +1180,29 @@ impl<'a> MutableFlowUtils for &'a mut Flow + 'a {
/// already been set.
/// Assumption: Absolute descendants have had their overflow calculated.
fn store_overflow(self, _: &LayoutContext) {
- let my_position = mut_base(self).position;
-
- // FIXME(pcwalton): We should calculate overflow on a per-fragment basis, because their
- // styles can affect overflow regions. Consider `box-shadow`, `outline`, etc.--anything
- // that can draw outside the border box. For now we assume overflow is the border box, but
- // that is wrong.
- let mut overflow = my_position;
-
+ // Calculate overflow on a per-fragment basis.
+ let mut overflow = self.compute_overflow();
if self.is_block_container() {
- let writing_mode = base(self).writing_mode;
- // FIXME(#2795): Get the real container size
+ // FIXME(#2795): Get the real container size.
let container_size = Size2D::zero();
for kid in child_iter(self) {
- if kid.is_store_overflow_delayed() {
- // Absolute flows will be handled by their CB. If we are
- // their CB, they will show up in `abs_descendants`.
- continue;
+ if base(kid).flags.contains(IS_ABSOLUTELY_POSITIONED) {
+ continue
}
- let kid_base = base(kid);
- let mut kid_overflow = kid_base.overflow.convert(
- kid_base.writing_mode, writing_mode, container_size);
- kid_overflow = kid_overflow.translate(&my_position.start);
- overflow = overflow.union(&kid_overflow)
+ let kid_overflow = base(kid).overflow;
+ let kid_position = base(kid).position.to_physical(base(kid).writing_mode,
+ container_size);
+ overflow = overflow.union(&kid_overflow.translate(&kid_position.origin))
}
- // FIXME(#2004, pcwalton): This is wrong for `position: fixed`.
- for descendant_link in mut_base(self).abs_descendants.iter() {
- let kid_base = base(descendant_link);
- let mut kid_overflow = kid_base.overflow.convert(
- kid_base.writing_mode, writing_mode, container_size);
- kid_overflow = kid_overflow.translate(&my_position.start);
- overflow = overflow.union(&kid_overflow)
+ for kid in mut_base(self).abs_descendants.iter() {
+ let kid_overflow = base(kid).overflow;
+ let kid_position = base(kid).position.to_physical(base(kid).writing_mode,
+ container_size);
+ overflow = overflow.union(&kid_overflow.translate(&kid_position.origin))
}
}
+
mut_base(self).overflow = overflow;
}