diff options
-rw-r--r-- | components/gfx/display_list/mod.rs | 52 | ||||
-rw-r--r-- | components/util/dlist.rs | 47 |
2 files changed, 50 insertions, 49 deletions
diff --git a/components/gfx/display_list/mod.rs b/components/gfx/display_list/mod.rs index 7caa3835486..75861005dce 100644 --- a/components/gfx/display_list/mod.rs +++ b/components/gfx/display_list/mod.rs @@ -95,31 +95,34 @@ struct StackingContext { } impl StackingContext { - /// Creates a stacking context from a display list, consuming that display list in the process. - fn new(list: &mut DisplayList) -> StackingContext { - let mut stacking_context = StackingContext { + /// Creates a new empty stacking context. + #[inline] + fn new() -> StackingContext { + StackingContext { background_and_borders: DisplayList::new(), block_backgrounds_and_borders: DisplayList::new(), floats: DisplayList::new(), content: DisplayList::new(), positioned_descendants: Vec::new(), - }; + } + } + /// Initializes a stacking context from a display list, consuming that display list in the + /// process. + fn init_from_list(&mut self, list: &mut DisplayList) { while !list.list.is_empty() { let mut head = DisplayList::from_list(servo_dlist::split(&mut list.list)); match head.front().unwrap().base().level { BackgroundAndBordersStackingLevel => { - stacking_context.background_and_borders.append_from(&mut head) + self.background_and_borders.append_from(&mut head) } BlockBackgroundsAndBordersStackingLevel => { - stacking_context.block_backgrounds_and_borders.append_from(&mut head) + self.block_backgrounds_and_borders.append_from(&mut head) } - FloatStackingLevel => stacking_context.floats.append_from(&mut head), - ContentStackingLevel => stacking_context.content.append_from(&mut head), + FloatStackingLevel => self.floats.append_from(&mut head), + ContentStackingLevel => self.content.append_from(&mut head), PositionedDescendantStackingLevel(z_index) => { - match stacking_context.positioned_descendants - .iter_mut() - .find(|& &(z, _)| z_index == z) { + match self.positioned_descendants.iter_mut().find(|& &(z, _)| z_index == z) { Some(&(_, ref mut my_list)) => { my_list.append_from(&mut head); continue @@ -127,12 +130,10 @@ impl StackingContext { None => {} } - stacking_context.positioned_descendants.push((z_index, head)) + self.positioned_descendants.push((z_index, head)) } } } - - stacking_context } } @@ -237,43 +238,38 @@ impl DisplayList { return } - let StackingContext { - mut background_and_borders, - mut block_backgrounds_and_borders, - mut floats, - mut content, - mut positioned_descendants - } = StackingContext::new(self); + let mut stacking_context = StackingContext::new(); + stacking_context.init_from_list(self); debug_assert!(self.list.is_empty()); // Steps 1 and 2: Borders and background for the root. - self.append_from(&mut background_and_borders); + self.append_from(&mut stacking_context.background_and_borders); // Sort positioned children according to z-index. - positioned_descendants.sort_by(|&(z_index_a, _), &(z_index_b, _)| { + stacking_context.positioned_descendants.sort_by(|&(z_index_a, _), &(z_index_b, _)| { z_index_a.cmp(&z_index_b) }); // Step 3: Positioned descendants with negative z-indices. - for &(ref mut z_index, ref mut list) in positioned_descendants.iter_mut() { + for &(ref mut z_index, ref mut list) in stacking_context.positioned_descendants.iter_mut() { if *z_index < 0 { self.append_from(list) } } // Step 4: Block backgrounds and borders. - self.append_from(&mut block_backgrounds_and_borders); + self.append_from(&mut stacking_context.block_backgrounds_and_borders); // Step 5: Floats. - self.append_from(&mut floats); + self.append_from(&mut stacking_context.floats); // TODO(pcwalton): Step 6: Inlines that generate stacking contexts. // Step 7: Content. - self.append_from(&mut content); + self.append_from(&mut stacking_context.content); // Steps 8 and 9: Positioned descendants with nonnegative z-indices. - for &(ref mut z_index, ref mut list) in positioned_descendants.iter_mut() { + for &(ref mut z_index, ref mut list) in stacking_context.positioned_descendants.iter_mut() { if *z_index >= 0 { self.append_from(list) } diff --git a/components/util/dlist.rs b/components/util/dlist.rs index 420a77a2698..2abae04b047 100644 --- a/components/util/dlist.rs +++ b/components/util/dlist.rs @@ -10,13 +10,13 @@ use std::ptr; struct RawDList<T> { length: uint, - head: Option<Box<RawNode<T>>>, + head: *mut RawNode<T>, tail: *mut RawNode<T>, } #[allow(dead_code)] struct RawNode<T> { - next: Option<Box<RawNode<T>>>, + next: *mut RawNode<T>, prev: *mut RawNode<T>, value: T, } @@ -38,27 +38,32 @@ pub fn split<T>(list: &mut DList<T>) -> DList<T> { if list.length == 0 { fail!("split_dlist(): empty list") } - let mut head_node = mem::replace(&mut list.head, None); - let head_node_ptr: *mut RawNode<T> = &mut **head_node.as_mut().unwrap(); - let mut head_list = RawDList { + let head_node = mem::replace(&mut list.head, ptr::null_mut()); + let head_list = RawDList { length: 1, head: head_node, - tail: head_node_ptr, + tail: head_node, }; - debug_assert!(list.head.is_none()); - mem::swap(&mut head_list.head.as_mut().unwrap().next, &mut list.head); - debug_assert!(head_list.head.as_mut().unwrap().next.is_none()); - debug_assert!(head_list.head.as_mut().unwrap().prev.is_null()); - head_list.head.as_mut().unwrap().prev = ptr::null_mut(); + debug_assert!(list.head.is_null()); + + unsafe { + mem::swap(&mut (*head_list.head).next, &mut list.head); + debug_assert!((*head_list.head).next.is_null()); + debug_assert!((*head_list.head).prev.is_null()); + (*head_list.head).prev = ptr::null_mut(); + } list.length -= 1; if list.length == 0 { list.tail = ptr::null_mut() } else { if list.length == 1 { - list.tail = &mut **list.head.as_mut().unwrap() as *mut RawNode<T> + list.tail = list.head + } + + unsafe { + (*list.head).prev = ptr::null_mut() } - list.head.as_mut().unwrap().prev = ptr::null_mut() } unsafe { @@ -73,19 +78,19 @@ pub fn append_from<T>(this: &mut DList<T>, other: &mut DList<T>) { let this = mem::transmute::<&mut DList<T>,&mut RawDList<T>>(this); let other = mem::transmute::<&mut DList<T>,&mut RawDList<T>>(other); if this.length == 0 { - this.head = mem::replace(&mut other.head, None); + this.head = mem::replace(&mut other.head, ptr::null_mut()); this.tail = mem::replace(&mut other.tail, ptr::null_mut()); this.length = mem::replace(&mut other.length, 0); return } - (*this.tail).next = match mem::replace(&mut other.head, None) { - None => return, - Some(mut head) => { - head.prev = this.tail; - Some(head) - } - }; + let old_other_head = mem::replace(&mut other.head, ptr::null_mut()); + if old_other_head.is_null() { + return + } + (*old_other_head).prev = this.tail; + (*this.tail).next = old_other_head; + this.tail = mem::replace(&mut other.tail, ptr::null_mut()); this.length += other.length; other.length = 0; |