config: accept FnMut instead of Fn for callbacks
This commit is contained in:
parent
37fc28c749
commit
86e582472d
5 changed files with 64 additions and 44 deletions
|
|
@ -41,23 +41,36 @@ use {
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
type Callback<T = ()> = Rc<RefCell<dyn FnMut(T)>>;
|
||||||
|
|
||||||
|
fn cb<T, F: FnMut(T) + 'static>(f: F) -> Callback<T> {
|
||||||
|
Rc::new(RefCell::new(f))
|
||||||
|
}
|
||||||
|
|
||||||
|
fn run_cb<T>(name: &str, cb: &Callback<T>, t: T) {
|
||||||
|
match cb.try_borrow_mut() {
|
||||||
|
Ok(mut cb) => cb(t),
|
||||||
|
Err(_) => log::error!("Cannot invoke {name} callback because it is already running"),
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub(crate) struct Client {
|
pub(crate) struct Client {
|
||||||
configure: extern "C" fn(),
|
configure: extern "C" fn(),
|
||||||
srv_data: *const u8,
|
srv_data: *const u8,
|
||||||
srv_unref: unsafe extern "C" fn(data: *const u8),
|
srv_unref: unsafe extern "C" fn(data: *const u8),
|
||||||
srv_handler: unsafe extern "C" fn(data: *const u8, msg: *const u8, size: usize),
|
srv_handler: unsafe extern "C" fn(data: *const u8, msg: *const u8, size: usize),
|
||||||
key_handlers: RefCell<HashMap<(Seat, ModifiedKeySym), Rc<dyn Fn()>>>,
|
key_handlers: RefCell<HashMap<(Seat, ModifiedKeySym), Callback>>,
|
||||||
timer_handlers: RefCell<HashMap<Timer, Rc<dyn Fn()>>>,
|
timer_handlers: RefCell<HashMap<Timer, Callback>>,
|
||||||
response: RefCell<Vec<Response>>,
|
response: RefCell<Vec<Response>>,
|
||||||
on_new_seat: RefCell<Option<Rc<dyn Fn(Seat)>>>,
|
on_new_seat: RefCell<Option<Callback<Seat>>>,
|
||||||
on_new_input_device: RefCell<Option<Rc<dyn Fn(InputDevice)>>>,
|
on_new_input_device: RefCell<Option<Callback<InputDevice>>>,
|
||||||
on_connector_connected: RefCell<Option<Rc<dyn Fn(Connector)>>>,
|
on_connector_connected: RefCell<Option<Callback<Connector>>>,
|
||||||
on_graphics_initialized: Cell<Option<Box<dyn FnOnce()>>>,
|
on_graphics_initialized: Cell<Option<Box<dyn FnOnce()>>>,
|
||||||
on_devices_enumerated: Cell<Option<Box<dyn FnOnce()>>>,
|
on_devices_enumerated: Cell<Option<Box<dyn FnOnce()>>>,
|
||||||
on_new_connector: RefCell<Option<Rc<dyn Fn(Connector)>>>,
|
on_new_connector: RefCell<Option<Callback<Connector>>>,
|
||||||
on_new_drm_device: RefCell<Option<Rc<dyn Fn(DrmDevice)>>>,
|
on_new_drm_device: RefCell<Option<Callback<DrmDevice>>>,
|
||||||
on_del_drm_device: RefCell<Option<Rc<dyn Fn(DrmDevice)>>>,
|
on_del_drm_device: RefCell<Option<Callback<DrmDevice>>>,
|
||||||
on_idle: RefCell<Option<Rc<dyn Fn()>>>,
|
on_idle: RefCell<Option<Callback>>,
|
||||||
bufs: RefCell<Vec<Vec<u8>>>,
|
bufs: RefCell<Vec<Vec<u8>>>,
|
||||||
reload: Cell<bool>,
|
reload: Cell<bool>,
|
||||||
read_interests: RefCell<HashMap<PollableId, Interest>>,
|
read_interests: RefCell<HashMap<PollableId, Interest>>,
|
||||||
|
|
@ -319,8 +332,10 @@ impl Client {
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_timer_tick<F: Fn() + 'static>(&self, timer: Timer, f: F) {
|
pub fn on_timer_tick<F: FnMut() + 'static>(&self, timer: Timer, mut f: F) {
|
||||||
self.timer_handlers.borrow_mut().insert(timer, Rc::new(f));
|
self.timer_handlers
|
||||||
|
.borrow_mut()
|
||||||
|
.insert(timer, cb(move |_| f()));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn get_workspace(&self, name: &str) -> Workspace {
|
pub fn get_workspace(&self, name: &str) -> Workspace {
|
||||||
|
|
@ -496,8 +511,8 @@ impl Client {
|
||||||
devices
|
devices
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_new_seat<F: Fn(Seat) + 'static>(&self, f: F) {
|
pub fn on_new_seat<F: FnMut(Seat) + 'static>(&self, f: F) {
|
||||||
*self.on_new_seat.borrow_mut() = Some(Rc::new(f));
|
*self.on_new_seat.borrow_mut() = Some(cb(f));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn quit(&self) {
|
pub fn quit(&self) {
|
||||||
|
|
@ -508,8 +523,8 @@ impl Client {
|
||||||
self.send(&ClientMessage::SwitchTo { vtnr })
|
self.send(&ClientMessage::SwitchTo { vtnr })
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_new_input_device<F: Fn(InputDevice) + 'static>(&self, f: F) {
|
pub fn on_new_input_device<F: FnMut(InputDevice) + 'static>(&self, f: F) {
|
||||||
*self.on_new_input_device.borrow_mut() = Some(Rc::new(f));
|
*self.on_new_input_device.borrow_mut() = Some(cb(f));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_double_click_interval(&self, usec: u64) {
|
pub fn set_double_click_interval(&self, usec: u64) {
|
||||||
|
|
@ -639,24 +654,24 @@ impl Client {
|
||||||
devices
|
devices
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_new_drm_device<F: Fn(DrmDevice) + 'static>(&self, f: F) {
|
pub fn on_new_drm_device<F: FnMut(DrmDevice) + 'static>(&self, f: F) {
|
||||||
*self.on_new_drm_device.borrow_mut() = Some(Rc::new(f));
|
*self.on_new_drm_device.borrow_mut() = Some(cb(f));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_del_drm_device<F: Fn(DrmDevice) + 'static>(&self, f: F) {
|
pub fn on_del_drm_device<F: FnMut(DrmDevice) + 'static>(&self, f: F) {
|
||||||
*self.on_del_drm_device.borrow_mut() = Some(Rc::new(f));
|
*self.on_del_drm_device.borrow_mut() = Some(cb(f));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_new_connector<F: Fn(Connector) + 'static>(&self, f: F) {
|
pub fn on_new_connector<F: FnMut(Connector) + 'static>(&self, f: F) {
|
||||||
*self.on_new_connector.borrow_mut() = Some(Rc::new(f));
|
*self.on_new_connector.borrow_mut() = Some(cb(f));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_idle<F: Fn() + 'static>(&self, f: F) {
|
pub fn on_idle<F: FnMut() + 'static>(&self, mut f: F) {
|
||||||
*self.on_idle.borrow_mut() = Some(Rc::new(f));
|
*self.on_idle.borrow_mut() = Some(cb(move |_| f()));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_connector_connected<F: Fn(Connector) + 'static>(&self, f: F) {
|
pub fn on_connector_connected<F: FnMut(Connector) + 'static>(&self, f: F) {
|
||||||
*self.on_connector_connected.borrow_mut() = Some(Rc::new(f));
|
*self.on_connector_connected.borrow_mut() = Some(cb(f));
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn on_graphics_initialized<F: FnOnce() + 'static>(&self, f: F) {
|
pub fn on_graphics_initialized<F: FnOnce() + 'static>(&self, f: F) {
|
||||||
|
|
@ -742,11 +757,16 @@ impl Client {
|
||||||
keymap
|
keymap
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn bind<T: Into<ModifiedKeySym>, F: Fn() + 'static>(&self, seat: Seat, mod_sym: T, f: F) {
|
pub fn bind<T: Into<ModifiedKeySym>, F: FnMut() + 'static>(
|
||||||
|
&self,
|
||||||
|
seat: Seat,
|
||||||
|
mod_sym: T,
|
||||||
|
mut f: F,
|
||||||
|
) {
|
||||||
let mod_sym = mod_sym.into();
|
let mod_sym = mod_sym.into();
|
||||||
let register = {
|
let register = {
|
||||||
let mut kh = self.key_handlers.borrow_mut();
|
let mut kh = self.key_handlers.borrow_mut();
|
||||||
let f = Rc::new(f);
|
let f = cb(move |_| f());
|
||||||
match kh.entry((seat, mod_sym)) {
|
match kh.entry((seat, mod_sym)) {
|
||||||
Entry::Occupied(mut o) => {
|
Entry::Occupied(mut o) => {
|
||||||
*o.get_mut() = f;
|
*o.get_mut() = f;
|
||||||
|
|
@ -914,34 +934,34 @@ impl Client {
|
||||||
let ms = ModifiedKeySym { mods, sym };
|
let ms = ModifiedKeySym { mods, sym };
|
||||||
let handler = self.key_handlers.borrow_mut().get(&(seat, ms)).cloned();
|
let handler = self.key_handlers.borrow_mut().get(&(seat, ms)).cloned();
|
||||||
if let Some(handler) = handler {
|
if let Some(handler) = handler {
|
||||||
handler();
|
run_cb("shortcut", &handler, ());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::NewInputDevice { device } => {
|
ServerMessage::NewInputDevice { device } => {
|
||||||
let handler = self.on_new_input_device.borrow_mut().clone();
|
let handler = self.on_new_input_device.borrow_mut().clone();
|
||||||
if let Some(handler) = handler {
|
if let Some(handler) = handler {
|
||||||
handler(device);
|
run_cb("new input device", &handler, device);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::DelInputDevice { .. } => {}
|
ServerMessage::DelInputDevice { .. } => {}
|
||||||
ServerMessage::ConnectorConnect { device } => {
|
ServerMessage::ConnectorConnect { device } => {
|
||||||
let handler = self.on_connector_connected.borrow_mut().clone();
|
let handler = self.on_connector_connected.borrow_mut().clone();
|
||||||
if let Some(handler) = handler {
|
if let Some(handler) = handler {
|
||||||
handler(device);
|
run_cb("connector connected", &handler, device);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::ConnectorDisconnect { .. } => {}
|
ServerMessage::ConnectorDisconnect { .. } => {}
|
||||||
ServerMessage::NewConnector { device } => {
|
ServerMessage::NewConnector { device } => {
|
||||||
let handler = self.on_new_connector.borrow_mut().clone();
|
let handler = self.on_new_connector.borrow_mut().clone();
|
||||||
if let Some(handler) = handler {
|
if let Some(handler) = handler {
|
||||||
handler(device);
|
run_cb("new connector", &handler, device);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::DelConnector { .. } => {}
|
ServerMessage::DelConnector { .. } => {}
|
||||||
ServerMessage::TimerExpired { timer } => {
|
ServerMessage::TimerExpired { timer } => {
|
||||||
let handler = self.timer_handlers.borrow_mut().get(&timer).cloned();
|
let handler = self.timer_handlers.borrow_mut().get(&timer).cloned();
|
||||||
if let Some(handler) = handler {
|
if let Some(handler) = handler {
|
||||||
handler();
|
run_cb("timer", &handler, ());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::GraphicsInitialized => {
|
ServerMessage::GraphicsInitialized => {
|
||||||
|
|
@ -955,19 +975,19 @@ impl Client {
|
||||||
ServerMessage::NewDrmDev { device } => {
|
ServerMessage::NewDrmDev { device } => {
|
||||||
let handler = self.on_new_drm_device.borrow_mut();
|
let handler = self.on_new_drm_device.borrow_mut();
|
||||||
if let Some(handler) = handler.deref() {
|
if let Some(handler) = handler.deref() {
|
||||||
handler(device);
|
run_cb("new drm device", handler, device);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::DelDrmDev { device } => {
|
ServerMessage::DelDrmDev { device } => {
|
||||||
let handler = self.on_del_drm_device.borrow_mut();
|
let handler = self.on_del_drm_device.borrow_mut();
|
||||||
if let Some(handler) = handler.deref() {
|
if let Some(handler) = handler.deref() {
|
||||||
handler(device);
|
run_cb("del drm device", handler, device);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::Idle => {
|
ServerMessage::Idle => {
|
||||||
let handler = self.on_idle.borrow_mut();
|
let handler = self.on_idle.borrow_mut();
|
||||||
if let Some(handler) = handler.deref() {
|
if let Some(handler) = handler.deref() {
|
||||||
handler();
|
run_cb("idle", handler, ());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ServerMessage::DevicesEnumerated => {
|
ServerMessage::DevicesEnumerated => {
|
||||||
|
|
|
||||||
|
|
@ -161,7 +161,7 @@ impl Seat {
|
||||||
///
|
///
|
||||||
/// CapsLock and NumLock are ignored during modifier evaluation. Therefore, bindings
|
/// CapsLock and NumLock are ignored during modifier evaluation. Therefore, bindings
|
||||||
/// containing these modifiers will never be invoked.
|
/// containing these modifiers will never be invoked.
|
||||||
pub fn bind<T: Into<ModifiedKeySym>, F: Fn() + 'static>(self, mod_sym: T, f: F) {
|
pub fn bind<T: Into<ModifiedKeySym>, F: FnMut() + 'static>(self, mod_sym: T, f: F) {
|
||||||
get!().bind(self, mod_sym, f)
|
get!().bind(self, mod_sym, f)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -324,12 +324,12 @@ pub fn get_seat(name: &str) -> Seat {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets a closure to run when a new seat has been created.
|
/// Sets a closure to run when a new seat has been created.
|
||||||
pub fn on_new_seat<F: Fn(Seat) + 'static>(f: F) {
|
pub fn on_new_seat<F: FnMut(Seat) + 'static>(f: F) {
|
||||||
get!().on_new_seat(f)
|
get!().on_new_seat(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets a closure to run when a new input device has been added.
|
/// Sets a closure to run when a new input device has been added.
|
||||||
pub fn on_new_input_device<F: Fn(InputDevice) + 'static>(f: F) {
|
pub fn on_new_input_device<F: FnMut(InputDevice) + 'static>(f: F) {
|
||||||
get!().on_new_input_device(f)
|
get!().on_new_input_device(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -185,7 +185,7 @@ impl Display for PciId {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the callback to be called when the display goes idle.
|
/// Sets the callback to be called when the display goes idle.
|
||||||
pub fn on_idle<F: Fn() + 'static>(f: F) {
|
pub fn on_idle<F: FnMut() + 'static>(f: F) {
|
||||||
get!().on_idle(f)
|
get!().on_idle(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -53,7 +53,7 @@ impl Timer {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the function to be executed when the timer expires.
|
/// Sets the function to be executed when the timer expires.
|
||||||
pub fn on_tick<F: Fn() + 'static>(self, f: F) {
|
pub fn on_tick<F: FnMut() + 'static>(self, f: F) {
|
||||||
get!().on_timer_tick(self, f);
|
get!().on_timer_tick(self, f);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -220,22 +220,22 @@ pub fn drm_devices() -> Vec<DrmDevice> {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the callback to be called when a new DRM device appears.
|
/// Sets the callback to be called when a new DRM device appears.
|
||||||
pub fn on_new_drm_device<F: Fn(DrmDevice) + 'static>(f: F) {
|
pub fn on_new_drm_device<F: FnMut(DrmDevice) + 'static>(f: F) {
|
||||||
get!().on_new_drm_device(f)
|
get!().on_new_drm_device(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the callback to be called when a DRM device is removed.
|
/// Sets the callback to be called when a DRM device is removed.
|
||||||
pub fn on_drm_device_removed<F: Fn(DrmDevice) + 'static>(f: F) {
|
pub fn on_drm_device_removed<F: FnMut(DrmDevice) + 'static>(f: F) {
|
||||||
get!().on_del_drm_device(f)
|
get!().on_del_drm_device(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the callback to be called when a new connector appears.
|
/// Sets the callback to be called when a new connector appears.
|
||||||
pub fn on_new_connector<F: Fn(Connector) + 'static>(f: F) {
|
pub fn on_new_connector<F: FnMut(Connector) + 'static>(f: F) {
|
||||||
get!().on_new_connector(f)
|
get!().on_new_connector(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Sets the callback to be called when a connector becomes connected to an output device.
|
/// Sets the callback to be called when a connector becomes connected to an output device.
|
||||||
pub fn on_connector_connected<F: Fn(Connector) + 'static>(f: F) {
|
pub fn on_connector_connected<F: FnMut(Connector) + 'static>(f: F) {
|
||||||
get!().on_connector_connected(f)
|
get!().on_connector_connected(f)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue