mirror of
https://github.com/servo/servo.git
synced 2025-08-16 10:55:34 +01:00
Auto merge of #14020 - mrobinson:scroll_root_prep, r=pcwalton
Fold some DisplayList methods into DisplayListBuildState <!-- Please describe your changes on the following line: --> --- <!-- Thank you for contributing to Servo! Please replace each `[ ]` by `[X]` when the step is complete, and replace `__` with appropriate data: --> - [x] `./mach build -d` does not report any errors - [x] `./mach test-tidy` does not report any errors - [ ] These changes fix #__ (github issue number if applicable). <!-- Either: --> - [ ] There are tests for these changes OR - [x] These changes do not require tests because they should not change behavior. <!-- Pull requests that do not address these steps are welcome, but they will require additional verification as part of the review process. --> This makes the API used to build display lists quite a bit simpler and reduces the amount of auxiliary data structures that need to be passed around. It is also important preparation work for separating scrolling areas from stacking contexts. <!-- Reviewable:start --> --- This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/servo/servo/14020) <!-- Reviewable:end -->
This commit is contained in:
commit
021cabd3e6
4 changed files with 150 additions and 137 deletions
|
@ -29,7 +29,6 @@ use range::Range;
|
|||
use std::cmp::{self, Ordering};
|
||||
use std::collections::HashMap;
|
||||
use std::fmt;
|
||||
use std::mem;
|
||||
use std::sync::Arc;
|
||||
use style::computed_values::{border_style, filter, image_rendering, mix_blend_mode};
|
||||
use style_traits::cursor::Cursor;
|
||||
|
@ -54,96 +53,6 @@ pub struct DisplayList {
|
|||
}
|
||||
|
||||
impl DisplayList {
|
||||
pub fn new(root_stacking_context: StackingContext,
|
||||
all_items: Vec<DisplayItem>)
|
||||
-> DisplayList {
|
||||
let mut mapped_items = HashMap::new();
|
||||
for item in all_items.into_iter() {
|
||||
let items = mapped_items.entry(item.stacking_context_id()).or_insert(Vec::new());
|
||||
items.push(item);
|
||||
}
|
||||
|
||||
let mut list = Vec::new();
|
||||
DisplayList::generate_display_list(&mut list, &mut mapped_items, root_stacking_context);
|
||||
|
||||
DisplayList {
|
||||
list: list,
|
||||
}
|
||||
}
|
||||
|
||||
fn generate_display_list(list: &mut Vec<DisplayItem>,
|
||||
mapped_items: &mut HashMap<StackingContextId, Vec<DisplayItem>>,
|
||||
mut stacking_context: StackingContext) {
|
||||
let mut child_stacking_contexts =
|
||||
mem::replace(&mut stacking_context.children, Vec::new());
|
||||
child_stacking_contexts.sort();
|
||||
let mut child_stacking_contexts = child_stacking_contexts.into_iter().peekable();
|
||||
|
||||
let mut child_items = mapped_items.remove(&stacking_context.id)
|
||||
.unwrap_or(Vec::new());
|
||||
child_items.sort_by(|a, b| a.base().section.cmp(&b.base().section));
|
||||
child_items.reverse();
|
||||
|
||||
let stacking_context_id = stacking_context.id;
|
||||
let real_stacking_context = stacking_context.context_type == StackingContextType::Real;
|
||||
if real_stacking_context {
|
||||
list.push(DisplayItem::PushStackingContext(Box::new(PushStackingContextItem {
|
||||
base: BaseDisplayItem::empty(),
|
||||
stacking_context: stacking_context,
|
||||
})));
|
||||
}
|
||||
|
||||
// Properly order display items that make up a stacking context. "Steps" here
|
||||
// refer to the steps in CSS 2.1 Appendix E.
|
||||
// Steps 1 and 2: Borders and background for the root.
|
||||
while child_items.last().map_or(false,
|
||||
|child| child.section() == DisplayListSection::BackgroundAndBorders) {
|
||||
list.push(child_items.pop().unwrap());
|
||||
}
|
||||
|
||||
// Step 3: Positioned descendants with negative z-indices.
|
||||
while child_stacking_contexts.peek().map_or(false, |child| child.z_index < 0) {
|
||||
let context = child_stacking_contexts.next().unwrap();
|
||||
DisplayList::generate_display_list(list, mapped_items, context);
|
||||
}
|
||||
|
||||
// Step 4: Block backgrounds and borders.
|
||||
while child_items.last().map_or(false,
|
||||
|child| child.section() == DisplayListSection::BlockBackgroundsAndBorders) {
|
||||
list.push(child_items.pop().unwrap());
|
||||
}
|
||||
|
||||
// Step 5: Floats.
|
||||
while child_stacking_contexts.peek().map_or(false,
|
||||
|child| child.context_type == StackingContextType::PseudoFloat) {
|
||||
let context = child_stacking_contexts.next().unwrap();
|
||||
DisplayList::generate_display_list(list, mapped_items, context);
|
||||
}
|
||||
|
||||
// Step 6 & 7: Content and inlines that generate stacking contexts.
|
||||
while child_items.last().map_or(false,
|
||||
|child| child.section() == DisplayListSection::Content) {
|
||||
list.push(child_items.pop().unwrap());
|
||||
}
|
||||
|
||||
// Step 8 & 9: Positioned descendants with nonnegative, numeric z-indices.
|
||||
for child in child_stacking_contexts {
|
||||
DisplayList::generate_display_list(list, mapped_items, child);
|
||||
}
|
||||
|
||||
// Step 10: Outlines.
|
||||
list.extend(child_items);
|
||||
|
||||
if real_stacking_context {
|
||||
list.push(DisplayItem::PopStackingContext(Box::new(
|
||||
PopStackingContextItem {
|
||||
base: BaseDisplayItem::empty(),
|
||||
stacking_context_id: stacking_context_id,
|
||||
}
|
||||
)));
|
||||
}
|
||||
}
|
||||
|
||||
// Return all nodes containing the point of interest, bottommost first, and
|
||||
// respecting the `pointer-events` CSS property.
|
||||
pub fn hit_test(&self,
|
||||
|
@ -424,6 +333,22 @@ impl StackingContext {
|
|||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
pub fn root() -> StackingContext {
|
||||
StackingContext::new(StackingContextId::new(0),
|
||||
StackingContextType::Real,
|
||||
&Rect::zero(),
|
||||
&Rect::zero(),
|
||||
0,
|
||||
filter::T::new(Vec::new()),
|
||||
mix_blend_mode::T::normal,
|
||||
Matrix4D::identity(),
|
||||
Matrix4D::identity(),
|
||||
true,
|
||||
ScrollPolicy::Scrollable,
|
||||
None)
|
||||
}
|
||||
|
||||
pub fn add_child(&mut self, mut child: StackingContext) {
|
||||
child.update_overflow_for_all_children();
|
||||
self.children.push(child);
|
||||
|
@ -474,6 +399,27 @@ impl StackingContext {
|
|||
}
|
||||
print_tree.end_level();
|
||||
}
|
||||
|
||||
pub fn to_display_list_items(self) -> (DisplayItem, DisplayItem) {
|
||||
let mut base_item = BaseDisplayItem::empty();
|
||||
base_item.stacking_context_id = self.id;
|
||||
|
||||
let pop_item = DisplayItem::PopStackingContext(Box::new(
|
||||
PopStackingContextItem {
|
||||
base: base_item.clone(),
|
||||
stacking_context_id: self.id,
|
||||
}
|
||||
));
|
||||
|
||||
let push_item = DisplayItem::PushStackingContext(Box::new(
|
||||
PushStackingContextItem {
|
||||
base: base_item,
|
||||
stacking_context: self,
|
||||
}
|
||||
));
|
||||
|
||||
(push_item, pop_item)
|
||||
}
|
||||
}
|
||||
|
||||
impl Ord for StackingContext {
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue