selene_daemon/
event_handler.rs1use std::{
2 sync::{
3 atomic::Ordering,
4 mpsc::{Receiver, Sender, channel},
5 },
6 thread,
7};
8
9use lunar_lib::trace;
10
11use crate::{
12 SHUTDOWN,
13 listener::{IpcListener, Listener},
14 player::{PlayerError, PlayerEvent, PlayerRequest},
15};
16
17pub struct EventHandler {
18 rx: Receiver<PlayerEvent>,
19
20 listener_tx: Sender<PlayerEvent>,
21
22 #[cfg(feature = "mpris")]
23 mpris_tx: tokio::sync::mpsc::Sender<crate::mpris::MprisEvent>,
24}
25
26impl EventHandler {
27 pub fn open(player_tx: Sender<PlayerRequest>) -> Result<Sender<PlayerEvent>, PlayerError> {
28 let (tx, rx) = channel();
29
30 let listener_tx = Listener::open(player_tx.clone())?;
31
32 #[cfg(feature = "mpris")]
33 let mpris_tx = crate::mpris::MprisConnector::open(player_tx);
34
35 let event_handler = Self {
36 rx,
37
38 listener_tx,
39
40 #[cfg(feature = "mpris")]
41 mpris_tx,
42 };
43
44 thread::spawn(move || {
45 event_handler.run();
46 SHUTDOWN.store(true, Ordering::Relaxed);
47 });
48
49 Ok(tx)
50 }
51
52 fn run(self) {
53 while let Ok(event) = self.rx.recv() {
54 trace!("Sending event: {event}");
55
56 let _ = self.listener_tx.send(event.clone());
57
58 #[cfg(feature = "mpris")]
59 {
60 use crate::mpris::MprisEvent;
61
62 let mpris_event = match event {
63 PlayerEvent::CurrentlyPlayingChanged {
64 ref currently_playing,
65 } => Some(MprisEvent::CurrentlyPlayingChanged {
66 currently_playing: currently_playing.clone(),
67 }),
68 PlayerEvent::PlaybackStopped => Some(MprisEvent::PlaybackStopped),
69 PlayerEvent::PlaybackIsPlayingChanged {
70 is_playing,
71 changed_at,
72 } => Some(MprisEvent::IsPlayingChanged {
73 is_playing,
74 changed_at,
75 }),
76 PlayerEvent::ShuffleModeChanged { shuffle_mode } => {
77 Some(MprisEvent::ShuffleStatusChanged { shuffle_mode })
78 }
79 PlayerEvent::LoopModeChanged { loop_mode } => {
80 Some(MprisEvent::LoopStatusChanged { loop_mode })
81 }
82 PlayerEvent::VolumeChanged { volume } => {
83 Some(MprisEvent::VolumeChanged { volume })
84 }
85 PlayerEvent::SeekOccured { time } => Some(MprisEvent::Seeked { time }),
86 _ => None,
87 };
88
89 if let Some(mpris_event) = mpris_event {
90 let _ = self.mpris_tx.blocking_send(mpris_event);
91 }
92 }
93 }
94 }
95}
96
97pub trait EventTx {
98 fn event(&self, event: PlayerEvent);
99}
100
101impl EventTx for Sender<PlayerEvent> {
102 fn event(&self, event: PlayerEvent) {
103 let _ = self.send(event);
104 }
105}