Consume by layer, not by widget
Replaces the taking mechanism with `CursorSenses::consumes`, which decides only whether a layer stops the input reaching the layer below. Nothing is removed from the cursor, and senses on one layer no longer block each other: every sensor the pointer is inside runs. Where the cursor rests stops at the top layer under it. Something happening to the cursor stops only at a widget that answers to it, so a click-only child does not swallow a scroll -- which is what `main` gets wrong, where any hovered sensor blocks the layer below. A widget the cursor has left still hears its hover ending, but is handed no press or scroll: that input landed somewhere else. This is a hit test rather than a consumption rule, and without it a press beside a button fires the button it just left. `a_click_and_a_scroll_in_one_frame_go_to_different_widgets` goes with the per-kind taking it tested. Of the five that remain, two fail on `main`.
This commit is contained in:
1 parent
3ab9c922fd
commit
f3fd9417d4
2 files changed
+51
-91
No files matched your search
@@ -1,4 +1,4 @@
|
||||
//! Input across layers: what a widget takes, what passes through it, and
|
||||
//! Input across layers: what stops at a layer, what passes through it, and
|
||||
//! where hovering stops. These drive `run_sensors` directly, which needs no
|
||||
//! GPU and no window.
|
||||
|
||||
@@ -167,27 +167,6 @@ fn a_scroll_passes_through_every_widget_that_does_not_want_it() {
|
||||
assert_eq!(overlay_clicked.take(), []);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn a_click_and_a_scroll_in_one_frame_go_to_different_widgets() {
|
||||
let mut ui = Ui::new();
|
||||
let (list, button) = (full(&mut ui), full(&mut ui));
|
||||
let scrolled = ui.listen(&list, CursorSense::Scroll);
|
||||
let clicked = ui.listen(&button, CursorSense::click());
|
||||
ui.stack(vec![list.any(), button.any()]);
|
||||
|
||||
let mut cursor = ui.cursor((50.0, 50.0));
|
||||
cursor.scroll_delta = (0.0, 10.0).into();
|
||||
cursor.buttons.left = ActivationState::Start;
|
||||
ui.run(cursor);
|
||||
|
||||
assert_eq!(clicked.take(), [CursorSense::click()]);
|
||||
assert_eq!(
|
||||
scrolled.take(),
|
||||
[CursorSense::Scroll],
|
||||
"taking the click must not take the scroll with it"
|
||||
);
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn only_the_topmost_listener_takes_a_press() {
|
||||
let mut ui = Ui::new();
|
||||
|
||||
Reference in new issue
Block a user