2024-02-17 21:04:02 -06:00
|
|
|
use crate::element::{UiElement, MeasureContext, ProcessContext};
|
2024-02-17 14:43:46 -06:00
|
|
|
|
|
|
|
pub struct Interactable<T: UiElement> {
|
|
|
|
pub element: T,
|
|
|
|
pub hovered: Option<Box<dyn FnOnce()>>,
|
|
|
|
pub clicked: Option<Box<dyn FnOnce()>>,
|
|
|
|
}
|
|
|
|
|
|
|
|
impl<T: UiElement> Interactable<T> {
|
|
|
|
pub fn new(element: T) -> Self {
|
|
|
|
Self {
|
|
|
|
element,
|
|
|
|
hovered: None,
|
|
|
|
clicked: None,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
pub fn on_click(self, clicked: impl FnOnce() + 'static) -> Self {
|
|
|
|
Self {
|
|
|
|
clicked: Some(Box::new(clicked)),
|
|
|
|
..self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
pub fn on_hover(self, clicked: impl FnOnce() + 'static) -> Self {
|
|
|
|
Self {
|
|
|
|
clicked: Some(Box::new(clicked)),
|
|
|
|
..self
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
impl<T: UiElement> UiElement for Interactable<T> {
|
2024-02-17 21:04:02 -06:00
|
|
|
fn measure(&self, ctx: MeasureContext) -> crate::measure::Response {
|
|
|
|
self.element.measure(ctx)
|
2024-02-17 14:43:46 -06:00
|
|
|
}
|
|
|
|
|
2024-02-17 21:04:02 -06:00
|
|
|
fn process(&self, ctx: ProcessContext) {
|
|
|
|
self.element.process(ctx)
|
2024-02-17 14:43:46 -06:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
pub trait IntoInteractable<T: UiElement>: UiElement {
|
|
|
|
fn into_interactable(self) -> Interactable<T>;
|
|
|
|
}
|
|
|
|
|
|
|
|
impl<T: UiElement> IntoInteractable<T> for T {
|
|
|
|
fn into_interactable(self) -> Interactable<Self> {
|
|
|
|
Interactable::new(self)
|
|
|
|
}
|
|
|
|
}
|