use std::any::Any; use anyhow::Result; use super::ControllerButton; macro_rules! callbacks { ($name:ident, $($cb:tt)*) => { #[derive(Default)] pub struct $name<'a> { callbacks: Vec<(&'a str, Box)>, } impl<'a> $name<'a> { pub fn add(mut self, name: &'a str, callback: impl $($cb)* + 'static)->Self { self.callbacks.push((name, Box::new(callback))); self } } impl<'a> Into)>> for $name<'a> { fn into(self) -> Vec<(&'a str, Box)> { self.callbacks } } }; } callbacks!(ClickCallbacks, Fn() -> Result<()> + Send + Sync); callbacks!(SelectCallbacks, Fn(bool) -> anyhow::Result<()> + Send + Sync); callbacks!(CustomCallbacks, Fn(ControllerButton) -> anyhow::Result + Send + Sync); callbacks!(VecCallbacks, Fn(&dyn Any) -> Result<()> + Send + Sync); #[test] fn test_click_callback_builder() { struct Test; impl Test { fn set_click_callbacks( &self, _callbacks: Vec<(&str, Box Result<()> + Send + Sync>)>, ) -> Result<()> { Ok(()) } } let t = Test; let cbs = ClickCallbacks::default().add("test", || { println!("hello world!"); Ok(()) }); t.set_click_callbacks(cbs.into()).unwrap(); }