1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
use crate::blocks::{Block, Configure, Message, Sender};
use crate::utils;
use serde::Deserialize;
use std::thread;
#[derive(Configure, Deserialize)]
pub struct Volume {
#[serde(default = "default_name")]
name: String,
#[serde(default = "default_period")]
period: f32,
#[serde(default = "default_update_signal")]
update_signal: i32,
}
fn default_name() -> String {
"volume".to_string()
}
fn default_period() -> f32 {
10.0
}
fn default_update_signal() -> i32 {
signal_hook::SIGUSR2
}
impl Sender for Volume {
fn add_sender(&self, s: crossbeam_channel::Sender<Message>) {
let name = self.get_name();
let re = regex::Regex::new(r"(?P<mute>\d)\n(?P<volume>\d+)").unwrap();
let mut block = Block::new(self.name.clone(), true);
let mut monitor = utils::monitor_command("pulsemixer", &["--get-mute", "--get-volume"], self.period);
let recv = utils::wait_for_signal(self.update_signal, self.period);
thread::spawn(move || loop {
let output = monitor.read();
block.full_text = Some(if let Some(captures) = re.captures(&output) {
if captures.name("mute").unwrap().as_str() == "0" {
format!(" {}%", captures.name("volume").unwrap().as_str())
} else {
"".to_string()
}
} else {
output
});
s.send((name.clone(), block.to_string())).unwrap();
recv.recv().unwrap();
});
}
}