fix event stuff

This commit is contained in:
2025-12-10 13:29:36 -05:00
parent 6156c66a20
commit 76f75192d5
2 changed files with 30 additions and 19 deletions

View File

@@ -1,4 +1,4 @@
use std::hash::Hash;
use std::{cell::RefCell, hash::Hash, rc::Rc};
use crate::{
layout::{Ui, UiModule, WidgetId, WidgetRef},
@@ -77,10 +77,14 @@ impl<E: DefaultEvent> Event for E {
pub trait EventModule<E: Event, Ctx>: UiModule + Default {
fn register(&mut self, id: WidgetId, event: E, f: impl EventFn<Ctx, E::Data>);
fn run(&mut self, id: WidgetId, event: E) -> Option<impl FnOnce(EventCtx<Ctx, E::Data>)>;
fn run<'a>(
&mut self,
id: WidgetId,
event: E,
) -> Option<impl FnOnce(EventCtx<Ctx, E::Data>) + use<'a, Self, Ctx, E>>;
}
type EventFnMap<Ctx, Data> = HashMap<WidgetId, Vec<Box<dyn EventFn<Ctx, Data>>>>;
type EventFnMap<Ctx, Data> = HashMap<WidgetId, Vec<Rc<RefCell<dyn EventFn<Ctx, Data>>>>>;
pub struct DefaultEventModule<E: Event, Ctx> {
map: HashMap<E, EventFnMap<Ctx, <E as Event>::Data>>,
}
@@ -103,16 +107,21 @@ impl<E: HashableEvent, Ctx: 'static> EventModule<E, Ctx> for DefaultEventModule<
.or_default()
.entry(id)
.or_default()
.push(Box::new(f));
.push(Rc::new(RefCell::new(f)));
}
fn run(&mut self, id: WidgetId, event: E) -> Option<impl FnOnce(EventCtx<Ctx, E::Data>)> {
if let Some(map) = self.map.get_mut(&event)
&& let Some(fs) = map.get_mut(&id)
fn run<'a>(
&mut self,
id: WidgetId,
event: E,
) -> Option<impl FnOnce(EventCtx<Ctx, E::Data>) + use<'a, Ctx, E>> {
if let Some(map) = self.map.get(&event)
&& let Some(fs) = map.get(&id)
{
let fs = fs.clone();
Some(move |ctx: EventCtx<Ctx, <E as Event>::Data>| {
for f in fs {
f(EventCtx {
f.borrow_mut()(EventCtx {
ui: ctx.ui,
state: ctx.state,
data: ctx.data.clone(),
@@ -130,10 +139,11 @@ impl<E: HashableEvent, Ctx: 'static> DefaultEventModule<E, Ctx> {
where
E::Data: Clone,
{
if let Some(map) = self.map.get_mut(&event) {
for fs in map.values_mut() {
if let Some(map) = self.map.get(&event) {
for fs in map.values() {
let fs = fs.clone();
for f in fs {
f(EventCtx {
f.borrow_mut()(EventCtx {
ui: ctx.ui,
state: ctx.state,
data: ctx.data.clone(),
@@ -168,7 +178,7 @@ impl Ui {
{
eprintln!("FIXME");
f(EventCtx {
ui: &mut Ui::new(),
ui: self,
state: ctx,
data,
});

View File

@@ -3,6 +3,7 @@ use crate::{
layout::{UiModule, UiRegion, Vec2},
util::HashMap,
};
use std::cell::RefCell;
use std::{
ops::{BitOr, Deref, DerefMut},
rc::Rc,
@@ -97,7 +98,7 @@ pub enum ActivationState {
/// but I'm not sure how or if worth it
pub struct Sensor<Ctx, Data> {
pub senses: CursorSenses,
pub f: Box<dyn EventFn<Ctx, Data>>,
pub f: Rc<RefCell<dyn EventFn<Ctx, Data>>>,
}
pub type SensorMap<Ctx, Data> = HashMap<WidgetId, SensorGroup<Ctx, Data>>;
@@ -207,7 +208,7 @@ impl<Ctx: 'static> CursorModule<Ctx> {
scroll_delta: cursor.scroll_delta,
sense,
};
(sensor.f)(EventCtx {
(sensor.f.borrow_mut())(EventCtx {
ui,
state: ctx,
data,
@@ -308,15 +309,15 @@ impl<E: Event<Data = <CursorSenses as Event>::Data> + Into<CursorSenses>, Ctx: '
// TODO: does not add to active if currently active
self.map.entry(id).or_default().sensors.push(Sensor {
senses: senses.into(),
f: Box::new(f),
f: Rc::new(RefCell::new(f)),
});
}
fn run(
fn run<'a>(
&mut self,
id: WidgetId,
event: E,
) -> Option<impl FnOnce(EventCtx<Ctx, <E as Event>::Data>)> {
) -> Option<impl FnOnce(EventCtx<Ctx, <E as Event>::Data>) + use<'a, Ctx, E>> {
let senses = event.into();
if let Some(group) = self.map.get_mut(&id) {
let fs: Vec<_> = group
@@ -324,7 +325,7 @@ impl<E: Event<Data = <CursorSenses as Event>::Data> + Into<CursorSenses>, Ctx: '
.iter_mut()
.filter_map(|sensor| {
if sensor.senses.iter().any(|s| senses.contains(s)) {
Some(&mut sensor.f)
Some(sensor.f.clone())
} else {
None
}
@@ -332,7 +333,7 @@ impl<E: Event<Data = <CursorSenses as Event>::Data> + Into<CursorSenses>, Ctx: '
.collect();
Some(move |ctx: EventCtx<Ctx, CursorData>| {
for f in fs {
f(EventCtx {
f.borrow_mut()(EventCtx {
state: ctx.state,
ui: ctx.ui,
data: ctx.data.clone(),