diff --git a/emigui/src/containers/scroll_area.rs b/emigui/src/containers/scroll_area.rs index 153cb264..ff08a4e4 100644 --- a/emigui/src/containers/scroll_area.rs +++ b/emigui/src/containers/scroll_area.rs @@ -181,10 +181,10 @@ impl Prepared { // intentionally use same id for inside and outside of handle let interact_id = id.with("vertical"); - let handle_interact = ui.interact(handle_rect, interact_id, Sense::click_and_drag()); + let mut interact = ui.interact(handle_rect, interact_id, Sense::click_and_drag()); if let Some(mouse_pos) = ui.input().mouse.pos { - if handle_interact.active { + if interact.active { if inner_rect.top() <= mouse_pos.y && mouse_pos.y <= inner_rect.bottom() { state.offset.y += ui.input().mouse.delta.y * content_size.y / inner_rect.height(); @@ -199,6 +199,8 @@ impl Prepared { let mpos_top = mouse_pos.y - handle_rect.height() / 2.0; state.offset.y = remap(mpos_top, top..=bottom, 0.0..=content_size.y); } + + interact = interact.union(scroll_bg_interact); } } @@ -212,8 +214,8 @@ impl Prepared { ); let style = ui.style(); - let handle_fill_color = style.interact(&handle_interact).fill_color; - let handle_outline = style.interact(&handle_interact).rect_outline; + let handle_fill_color = style.interact(&interact).fill_color; + let handle_outline = style.interact(&interact).rect_outline; ui.add_paint_cmd(paint::PaintCmd::Rect { rect: outer_scroll_rect, diff --git a/emigui/src/containers/window.rs b/emigui/src/containers/window.rs index a279ec98..4a7f8fc2 100644 --- a/emigui/src/containers/window.rs +++ b/emigui/src/containers/window.rs @@ -168,7 +168,6 @@ impl<'open> Window<'open> { let mut area = area.begin(ctx); { - // TODO: pick style for frame and title based on interaction let mut frame = frame.begin(&mut area.content_ui); { let ui = &mut frame.content_ui; @@ -211,6 +210,7 @@ impl<'open> Window<'open> { *open = false; } } + // TODO: pick style for title based on move interaction title_bar.title_ui(ui); } @@ -402,6 +402,11 @@ fn resize_hover( } } + if ctx.memory().interaction.drag_interest { + // Another widget will become active if we drag here + return None; + } + let side_interact_radius = 5.0; // TODO: from style let corner_interact_radius = 10.0; // TODO if rect.expand(side_interact_radius).contains(mouse_pos) { diff --git a/emigui/src/context.rs b/emigui/src/context.rs index 49b4343f..86a68529 100644 --- a/emigui/src/context.rs +++ b/emigui/src/context.rs @@ -147,28 +147,7 @@ impl Context { } fn begin_frame_mut(&mut self, new_raw_input: RawInput) { - if !self.input().mouse.could_be_click { - self.memory().interaction.click_id = None; - } - - if !self.input.mouse.down || self.input.mouse.pos.is_none() { - // mouse was not down last frame - self.memory().interaction.click_id = None; - self.memory().interaction.drag_id = None; - - let window_interaction = self.memory().window_interaction.take(); - if let Some(window_interaction) = window_interaction { - if !window_interaction.is_resize() { - // Throw windows because it is fun: - let area_layer = window_interaction.area_layer; - let area_state = self.memory().areas.get(area_layer.id).clone(); - if let Some(mut area_state) = area_state { - area_state.vel = self.input().mouse.velocity; - self.memory().areas.set_state(area_layer, area_state); - } - } - } - } + self.memory().begin_frame(&self.input); self.used_ids.lock().clear(); @@ -307,6 +286,10 @@ impl Context { let interaction_id = interaction_id.unwrap(); let mut memory = self.memory(); + + memory.interaction.click_interest |= hovered && sense.click; + memory.interaction.drag_interest |= hovered && sense.drag; + let active = memory.interaction.click_id == Some(interaction_id) || memory.interaction.drag_id == Some(interaction_id); diff --git a/emigui/src/memory.rs b/emigui/src/memory.rs index 1504b505..c403bf22 100644 --- a/emigui/src/memory.rs +++ b/emigui/src/memory.rs @@ -43,6 +43,14 @@ pub struct Interaction { /// A widget interested in drags that has a mouse press on it. pub drag_id: Option, + + /// Any interest in catching clicks this frame? + /// Cleared to false at start of each frame. + pub click_interest: bool, + + /// Any interest in catching clicks this frame? + /// Cleared to false at start of each frame. + pub drag_interest: bool, } #[derive(Clone, Debug, Default, serde_derive::Deserialize, serde_derive::Serialize)] @@ -63,6 +71,34 @@ pub struct Areas { } impl Memory { + pub(crate) fn begin_frame(&mut self, prev_input: &crate::input::InputState) { + self.interaction.click_interest = false; + self.interaction.drag_interest = false; + + if !prev_input.mouse.could_be_click { + self.interaction.click_id = None; + } + + if !prev_input.mouse.down || prev_input.mouse.pos.is_none() { + // mouse was not down last frame + self.interaction.click_id = None; + self.interaction.drag_id = None; + + let window_interaction = self.window_interaction.take(); + if let Some(window_interaction) = window_interaction { + if !window_interaction.is_resize() { + // Throw windows because it is fun: + let area_layer = window_interaction.area_layer; + let area_state = self.areas.get(area_layer.id).clone(); + if let Some(mut area_state) = area_state { + area_state.vel = prev_input.mouse.velocity; + self.areas.set_state(area_layer, area_state); + } + } + } + } + } + pub(crate) fn end_frame(&mut self) { self.areas.end_frame() }