From ae15869d07cf6e9c59e726b733405970a9c0212c Mon Sep 17 00:00:00 2001 From: Dorota Czaplejewicz Date: Wed, 7 Dec 2022 14:31:55 +0000 Subject: [PATCH] popover: Able to receive screensaver events --- src/actors/mod.rs | 11 ++++++++++- src/actors/popover.rs | 44 ++++++++++++++++++++++++++++++++----------- src/main.rs | 8 +++++--- 3 files changed, 48 insertions(+), 15 deletions(-) diff --git a/src/actors/mod.rs b/src/actors/mod.rs index b4fdc990..8e45d673 100644 --- a/src/actors/mod.rs +++ b/src/actors/mod.rs @@ -21,4 +21,13 @@ and by receiving updates from it. // with low-level wayland and gtk sizing events. pub mod external; -pub mod popover; \ No newline at end of file +pub mod popover; + +/// The implementing actor is able to receive and handle messages. +/// Typically, it's the sending end of the channel, +/// whose other end is inside an event loop. +// TODO: implement for remaning actors and make the event loop refer to this. +pub trait Destination { + type Event; + fn send(&self, event: Self::Event); +} diff --git a/src/actors/popover.rs b/src/actors/popover.rs index e3020c2a..b2f06129 100644 --- a/src/actors/popover.rs +++ b/src/actors/popover.rs @@ -11,30 +11,52 @@ but it cannot get the user-selected overlay, because it's stored in state. To solve this, overlay will be cached in the popover actor, and updated by main state every time it changes. */ +use super::Destination; pub mod c { use super::*; use crate::util::c::Wrapped; /// The mutable instance of state pub type Actor = Wrapped; + /// It's the same because the state is a simple mutex-protected type. + /// There are no channels involved. + pub type Destination = Wrapped; +} + +pub enum Event { + Overlay(Option), + ScreensaverActive(bool), +} + +impl Destination for c::Destination { + type Event = Event; + fn send(&self, event: Self::Event) { + let actor = self.clone_ref(); + let mut actor = actor.borrow_mut(); + *actor = actor.clone().handle_event(event); + } } #[derive(Clone)] pub struct State { pub overlay: Option, + /// Settings button active + pub settings_active: bool, } impl State { - pub fn new() -> Self { - Self { overlay: None } + pub fn new(settings_active: bool) -> Self { + Self { + overlay: None, + settings_active, + } + } + + fn handle_event(mut self, event: Event) -> Self { + match event { + Event::Overlay(overlay) => { self.overlay = overlay; }, + Event::ScreensaverActive(lock_active) => { self.settings_active = !lock_active; }, + }; + self } } - -pub fn set_overlay( - actor: &c::Actor, - overlay: Option, -) { - let actor = actor.clone_ref(); - let mut actor = actor.borrow_mut(); - actor.overlay = overlay; -} \ No newline at end of file diff --git a/src/main.rs b/src/main.rs index 92a3e3cf..6c97c7cf 100644 --- a/src/main.rs +++ b/src/main.rs @@ -21,6 +21,8 @@ mod c { use std::rc::Rc; use std::time::Instant; + use crate::actors::Destination; + use crate::actors::popover; use crate::event_loop::driver; use crate::imservice::IMService; use crate::imservice::c::InputMethod; @@ -130,7 +132,7 @@ mod c { state_manager: Wrapped::new(state_manager), receiver: Wrapped::new(receiver), wayland: Box::into_raw(wayland), - popover: Wrapped::new(actors::popover::State::new()), + popover: Wrapped::new(actors::popover::State::new(true)), } } @@ -174,7 +176,7 @@ mod c { fn main_loop_handle_message( msg: Commands, panel_manager: Wrapped, - popover: &actors::popover::c::Actor, + popover: &actors::popover::c::Destination, hint_manager: HintManager, dbus_handler: *const DBusHandler, ) { @@ -195,7 +197,7 @@ mod c { overlay_name, purpose, } = description; - actors::popover::set_overlay(popover, overlay_name.clone()); + popover.send(popover::Event::Overlay(overlay_name.clone())); let layout = loading::load_layout(&name, kind, purpose, &overlay_name); let layout = Box::into_raw(Box::new(layout)); // CSS can't express "+" in the class