summaryrefslogtreecommitdiffstats
path: root/src/display/luma.rs
blob: 479e4c947772c824be87fedd2372e0305cb6967b (plain)
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
57
58
59
60
61
62
63
64
65
pub use {
    crate::cli::{Args, TriBool},
    crossterm::tty::IsTty,
    once_cell::sync::Lazy,
    serde::Deserialize,
};

#[derive(Debug, Clone, Copy, Deserialize, PartialEq)]
#[serde(rename_all = "lowercase")]
pub enum Luma {
    Light,
    Unknown,
    Dark,
}

/// Return the light of the terminal background, which is a value
/// between 0 (black) and 1 (white).
#[cfg(target_os = "linux")]
pub fn luma() -> &'static Result<f32, terminal_light::TlError> {
    static LUMA: Lazy<Result<f32, terminal_light::TlError>> = Lazy::new(|| {
        let luma = time!(Debug, terminal_light::luma());
        info!("terminal's luma: {:?}", &luma);
        luma
    });
    &*LUMA
}

#[cfg(not(target_os = "linux"))]
pub fn luma() -> Result<&'static f32, &'static str> {
    Err("not implemented on this OS")
}

impl Luma {
    pub fn read() -> Self {
        match luma() {
            Ok(luma) if *luma > 0.6 => Self::Light,
            Ok(_) => Self::Dark,
            _ => Self::Unknown,
        }
    }
}

#[derive(Clone, Debug, Deserialize)]
#[serde(untagged)]
pub enum LumaCondition {
    Simple(Luma),
    Array(Vec<Luma>),
}

impl LumaCondition {
    pub fn is_verified(&self) -> bool {
        let luma = if std::io::stdout().is_tty() {
            Luma::read()
        } else {
            Luma::Unknown
        };
        self.includes(luma)
    }
    pub fn includes(&self, other: Luma) -> bool {
        match self {
            Self::Simple(luma) => other == *luma,
            Self::Array(arr) => arr.contains(&other),
        }
    }
}