cranpose_ui_graphics/accessibility.rs
1/// What the person set in the system's accessibility settings.
2#[derive(Clone, Copy, Debug, PartialEq)]
3pub struct AccessibilityOptions {
4 /// The text size setting as a multiplier of the default, 1.0 when the
5 /// person left it alone. Dynamic Type on iOS, the font size on Android
6 /// and the web, the text scale of the desktop.
7 pub font_scale: f32,
8 /// Whether the person asked for less motion. Every animation then ends on
9 /// its first frame.
10 pub reduce_motion: bool,
11 /// Whether the person asked for less transparency. Glass then draws as a
12 /// flat surface with no blur.
13 pub reduce_transparency: bool,
14 /// Whether the person asked for more contrast. Secondary text, separators
15 /// and fills then draw darker on light and lighter on dark.
16 pub increase_contrast: bool,
17 /// Whether the person asked for bold text. Every text style then gains a
18 /// weight step.
19 pub bold_text: bool,
20 /// Whether the system inverts colors and leaves this app's window to
21 /// invert its own, the way iOS Smart Invert does. The theme then swaps to
22 /// its other palette and pictures stay as they are. A system that inverts
23 /// the whole screen itself reports false.
24 pub invert_colors: bool,
25}
26
27impl Default for AccessibilityOptions {
28 fn default() -> Self {
29 Self::DEFAULT
30 }
31}
32
33impl AccessibilityOptions {
34 pub(crate) const DEFAULT: Self = Self {
35 font_scale: 1.0,
36 reduce_motion: false,
37 reduce_transparency: false,
38 increase_contrast: false,
39 bold_text: false,
40 invert_colors: false,
41 };
42
43 /// The options with the font scale made a plain number: finite and above
44 /// zero, else 1.0.
45 pub fn normalized(mut self) -> Self {
46 if !(self.font_scale.is_finite() && self.font_scale > 0.0) {
47 self.font_scale = 1.0;
48 }
49 self
50 }
51}
52
53/// Installs what the platform reports. A backend calls this at start and on
54/// every change, and forces a root render when the answer is true, so the
55/// theme, the glass and the animations read the new options.
56pub fn set_platform_accessibility_options(options: AccessibilityOptions) -> bool {
57 let options = options.normalized();
58 crate::thread_state::with(|state| state.accessibility_options.replace(options) != options)
59}
60
61/// What the platform last reported.
62pub fn platform_accessibility_options() -> AccessibilityOptions {
63 crate::thread_state::with(|state| state.accessibility_options.get())
64}