Add `Area::sense` and improve hit-testing of buttons in menus (#4234)
Previously, putting the cursor in the gap between two menu buttons would not hover any of the buttons, but the click-sensitive menu itself. Now the menu is no longer click-sensitive.
This commit is contained in:
parent
9cfaf8b961
commit
8a880d6d0f
|
|
@ -61,6 +61,7 @@ impl State {
|
|||
#[derive(Clone, Copy, Debug)]
|
||||
pub struct Area {
|
||||
pub(crate) id: Id,
|
||||
sense: Option<Sense>,
|
||||
movable: bool,
|
||||
interactable: bool,
|
||||
enabled: bool,
|
||||
|
|
@ -78,6 +79,7 @@ impl Area {
|
|||
pub fn new(id: Id) -> Self {
|
||||
Self {
|
||||
id,
|
||||
sense: None,
|
||||
movable: true,
|
||||
interactable: true,
|
||||
constrain: false,
|
||||
|
|
@ -114,7 +116,7 @@ impl Area {
|
|||
self
|
||||
}
|
||||
|
||||
/// moveable by dragging the area?
|
||||
/// Moveable by dragging the area?
|
||||
#[inline]
|
||||
pub fn movable(mut self, movable: bool) -> Self {
|
||||
self.movable = movable;
|
||||
|
|
@ -139,6 +141,15 @@ impl Area {
|
|||
self
|
||||
}
|
||||
|
||||
/// Explicitly set a sense.
|
||||
///
|
||||
/// If not set, this will default to `Sense::drag()` if movable, `Sense::click()` if interactable, and `Sense::hover()` otherwise.
|
||||
#[inline]
|
||||
pub fn sense(mut self, sense: Sense) -> Self {
|
||||
self.sense = Some(sense);
|
||||
self
|
||||
}
|
||||
|
||||
/// `order(Order::Foreground)` for an Area that should always be on top
|
||||
#[inline]
|
||||
pub fn order(mut self, order: Order) -> Self {
|
||||
|
|
@ -255,6 +266,7 @@ impl Area {
|
|||
pub(crate) fn begin(self, ctx: &Context) -> Prepared {
|
||||
let Self {
|
||||
id,
|
||||
sense,
|
||||
movable,
|
||||
order,
|
||||
interactable,
|
||||
|
|
@ -299,13 +311,15 @@ impl Area {
|
|||
// interact right away to prevent frame-delay
|
||||
let mut move_response = {
|
||||
let interact_id = layer_id.id.with("move");
|
||||
let sense = if movable {
|
||||
Sense::drag()
|
||||
} else if interactable {
|
||||
Sense::click() // allow clicks to bring to front
|
||||
} else {
|
||||
Sense::hover()
|
||||
};
|
||||
let sense = sense.unwrap_or_else(|| {
|
||||
if movable {
|
||||
Sense::drag()
|
||||
} else if interactable {
|
||||
Sense::click() // allow clicks to bring to front
|
||||
} else {
|
||||
Sense::hover()
|
||||
}
|
||||
});
|
||||
|
||||
let move_response = ctx.create_widget(WidgetRect {
|
||||
id: interact_id,
|
||||
|
|
|
|||
|
|
@ -149,7 +149,8 @@ pub(crate) fn menu_ui<'c, R>(
|
|||
.order(Order::Foreground)
|
||||
.fixed_pos(pos)
|
||||
.constrain_to(ctx.screen_rect())
|
||||
.interactable(true);
|
||||
.interactable(true)
|
||||
.sense(Sense::hover());
|
||||
|
||||
let area_response = area.show(ctx, |ui| {
|
||||
set_menu_style(ui.style_mut());
|
||||
|
|
|
|||
Loading…
Reference in New Issue