| 44 |
44 |
|
ThemeDefaults::new(DEFAULT_LIGHT, DEFAULT_DARK)
|
| 45 |
45 |
|
}
|
| 46 |
46 |
|
|
| 47 |
|
- |
/// What the terminal looks like, as makeover's vocabulary.
|
|
47 |
+ |
/// What the console is being drawn on, as makeover's vocabulary.
|
| 48 |
48 |
|
///
|
| 49 |
|
- |
/// The console's equivalent of a `prefers-color-scheme` media query. `COLORFGBG`
|
| 50 |
|
- |
/// is the only signal available without writing an OSC query to the terminal and
|
| 51 |
|
- |
/// waiting for a reply, which is not worth doing before the first frame. Its
|
| 52 |
|
- |
/// background field is a color index: 0-6 and 8 are the dark ones. Absent or
|
| 53 |
|
- |
/// unparseable reads as light, which is the documented default.
|
|
49 |
+ |
/// The console's equivalent of a `prefers-color-scheme` media query, and it asks
|
|
50 |
+ |
/// two sources in order of how specific they are:
|
|
51 |
+ |
///
|
|
52 |
+ |
/// 1. **`COLORFGBG`**, what this terminal says its own background is. The most
|
|
53 |
+ |
/// specific answer there is, and the only one available without writing an
|
|
54 |
+ |
/// OSC query and waiting for a reply, which is not worth doing before the
|
|
55 |
+ |
/// first frame.
|
|
56 |
+ |
/// 2. **The session's mode file**, the polarity the desktop was switched to.
|
|
57 |
+ |
/// Less specific — it is right about sway and mako and says nothing about the
|
|
58 |
+ |
/// terminal the console happens to be running in — but it is the answer
|
|
59 |
+ |
/// whenever the terminal declines to speak.
|
|
60 |
+ |
///
|
|
61 |
+ |
/// Neither, and it is light, which is the documented default.
|
|
62 |
+ |
///
|
|
63 |
+ |
/// The second tier is not decoration. rio sets no `COLORFGBG` at all, so a night
|
|
64 |
+ |
/// session left on [`ThemeSelection::Follow`] used to render a light console on a
|
|
65 |
+ |
/// dark terminal: the desktop knew, and this function was not asking it. That is
|
|
66 |
+ |
/// also why absent and unparseable fall through here rather than both reading
|
|
67 |
+ |
/// light — no signal has to be distinguishable from a light one to have anything
|
|
68 |
+ |
/// left to fall back to.
|
| 54 |
69 |
|
pub(crate) fn ambient() -> Variant {
|
| 55 |
|
- |
let dark = std::env::var("COLORFGBG")
|
| 56 |
|
- |
.ok()
|
| 57 |
|
- |
.and_then(|value| {
|
| 58 |
|
- |
value
|
| 59 |
|
- |
.rsplit(';')
|
| 60 |
|
- |
.next()
|
| 61 |
|
- |
.and_then(|bg| bg.trim().parse::<u8>().ok())
|
| 62 |
|
- |
})
|
| 63 |
|
- |
.is_some_and(|bg| bg <= 6 || bg == 8);
|
|
70 |
+ |
terminal_background()
|
|
71 |
+ |
.or_else(session_mode)
|
|
72 |
+ |
.unwrap_or(Variant::Light)
|
|
73 |
+ |
}
|
| 64 |
74 |
|
|
| 65 |
|
- |
if dark { Variant::Dark } else { Variant::Light }
|
|
75 |
+ |
/// The variant `COLORFGBG` names, when the terminal sets it to something legible.
|
|
76 |
+ |
///
|
|
77 |
+ |
/// The background field is a color index: 0-6 and 8 are the dark ones.
|
|
78 |
+ |
fn terminal_background() -> Option<Variant> {
|
|
79 |
+ |
let value = std::env::var("COLORFGBG").ok()?;
|
|
80 |
+ |
let bg = value.rsplit(';').next()?.trim().parse::<u8>().ok()?;
|
|
81 |
+ |
Some(if bg <= 6 || bg == 8 {
|
|
82 |
+ |
Variant::Dark
|
|
83 |
+ |
} else {
|
|
84 |
+ |
Variant::Light
|
|
85 |
+ |
})
|
|
86 |
+ |
}
|
|
87 |
+ |
|
|
88 |
+ |
/// The variant the desktop was switched to, read off the mode file.
|
|
89 |
+ |
fn session_mode() -> Option<Variant> {
|
|
90 |
+ |
match crate::theme_apply::saved_mode()? {
|
|
91 |
+ |
crate::theme_apply::NIGHT => Some(Variant::Dark),
|
|
92 |
+ |
_ => Some(Variant::Light),
|
|
93 |
+ |
}
|
| 66 |
94 |
|
}
|
| 67 |
95 |
|
|
| 68 |
96 |
|
/// Every theme the console can render, from the same search path it loads from.
|
| 125 |
153 |
|
/// skeleton cannot follow a terminal background that sway, mako and Firefox
|
| 126 |
154 |
|
/// will never see.
|
| 127 |
155 |
|
///
|
|
156 |
+ |
/// Since [`ambient`] falls back to the mode file, choosing Follow inside a
|
|
157 |
+ |
/// terminal that sets no `COLORFGBG` now writes back the mode already in place
|
|
158 |
+ |
/// rather than reverting the desktop to day. That is the wanted answer: "follow
|
|
159 |
+ |
/// the terminal" is not a request to re-skin sway.
|
|
160 |
+ |
///
|
| 128 |
161 |
|
/// An id that is not in [`available`], a theme deleted between the list being
|
| 129 |
162 |
|
/// drawn and the choice being made, reads as day, because `/etc/skel` is the
|
| 130 |
163 |
|
/// day render and day is therefore the answer that changes the least.
|