Skip to content
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 53 additions & 5 deletions webrender/src/frame.rs
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,7 @@ pub struct Frame {
AuxiliaryLists,
BuildHasherDefault<FnvHasher>>,
pub root_scroll_layer_id: Option<ScrollLayerId>,
current_scroll_layer_id: Option<ScrollLayerId>,
id: FrameId,
debug: bool,
frame_builder_config: FrameBuilderConfig,
Expand Down Expand Up @@ -200,6 +201,7 @@ impl Frame {
pipeline_auxiliary_lists: HashMap::with_hasher(Default::default()),
layers: HashMap::with_hasher(Default::default()),
root_scroll_layer_id: None,
current_scroll_layer_id: None,
id: FrameId(0),
debug: debug,
frame_builder: None,
Expand Down Expand Up @@ -296,16 +298,62 @@ impl Frame {
None => return false,
};

let scroll_layer_id = match self.get_scroll_layer(&cursor, root_scroll_layer_id) {
Some(scroll_layer_id) => scroll_layer_id,
None => return false,
let scroll_layer_id = match (phase, self.get_scroll_layer(&cursor, root_scroll_layer_id),
self.current_scroll_layer_id) {
(ScrollEventPhase::Start, Some(scroll_layer_id), _) => {
self.current_scroll_layer_id = Some(scroll_layer_id);
scroll_layer_id
},
(ScrollEventPhase::Start, None, _) => return false,
(_, _, Some(scroll_layer_id)) => scroll_layer_id,
(_, _, None) => return false,
};

let non_root_overscroll = if scroll_layer_id != root_scroll_layer_id {
let child_layer = self.layers.get(&scroll_layer_id).unwrap();
let overscroll_amount = child_layer.overscroll_amount();
overscroll_amount.width != 0.0 || overscroll_amount.height != 0.0
} else {
false
};

if non_root_overscroll && phase == ScrollEventPhase::Start {
let mut current_layer = self.layers.get_mut(&scroll_layer_id).unwrap();
current_layer.scrolling.non_root_overscroll = true;
};

let switch_layer = if phase == ScrollEventPhase::Move(true) {
let current_layer = self.layers.get_mut(&scroll_layer_id).unwrap();
current_layer.scrolling.non_root_overscroll && non_root_overscroll
} else {
false
};

if phase == ScrollEventPhase::End {
let mut current_layer = self.layers.get_mut(&scroll_layer_id).unwrap();
current_layer.scrolling.non_root_overscroll = false;
};

let layer = if switch_layer {
let mut nearest_parent_layer_id = root_scroll_layer_id;
{
let root_layer = self.layers.get(&root_scroll_layer_id).unwrap();
for &child_layer_id in root_layer.children.iter() {
if child_layer_id != scroll_layer_id {
nearest_parent_layer_id = child_layer_id;
} else {
break;
}
};
}
self.layers.get_mut(&nearest_parent_layer_id).unwrap()
} else {
self.layers.get_mut(&scroll_layer_id).unwrap()
};

let layer = self.layers.get_mut(&scroll_layer_id).unwrap();
if layer.scrolling.started_bouncing_back && phase == ScrollEventPhase::Move(false) {
return false
}

let overscroll_amount = layer.overscroll_amount();
let overscrolling = CAN_OVERSCROLL && (overscroll_amount.width != 0.0 ||
overscroll_amount.height != 0.0);
Expand Down
3 changes: 2 additions & 1 deletion webrender/src/layer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -106,16 +106,17 @@ pub struct ScrollingState {
pub spring: Spring,
pub started_bouncing_back: bool,
pub bouncing_back: bool,
pub non_root_overscroll: bool,
}

impl ScrollingState {
pub fn new() -> ScrollingState {
ScrollingState {
non_root_overscroll: false,
offset: Point2D::new(0.0, 0.0),
spring: Spring::at(Point2D::new(0.0, 0.0), STIFFNESS, DAMPING),
started_bouncing_back: false,
bouncing_back: false,
}
}
}