Skip to main content

blitz_traits/
shell.rs

1//! Abstraction over windowing / operating system ("shell") functionality
2
3use cursor_icon::CursorIcon;
4
5/// Type representing an error performing a clipboard operation
6// TODO: fill out with meaningful errors
7pub struct ClipboardError;
8
9/// Abstraction over windowing / operating system ("shell") functionality that allows a Blitz document
10/// to access that functionality without depending on a specific shell environment.
11pub trait ShellProvider: Send + Sync + 'static {
12    fn request_redraw(&self) {}
13    fn set_cursor(&self, icon: CursorIcon) {
14        let _ = icon;
15    }
16    fn set_window_title(&self, title: String) {
17        let _ = title;
18    }
19    fn set_ime_enabled(&self, is_enabled: bool) {
20        let _ = is_enabled;
21    }
22    fn set_ime_cursor_area(&self, x: f32, y: f32, width: f32, height: f32) {
23        let _ = x;
24        let _ = y;
25        let _ = width;
26        let _ = height;
27    }
28    fn get_clipboard_text(&self) -> Result<String, ClipboardError> {
29        Err(ClipboardError)
30    }
31    fn set_clipboard_text(&self, text: String) -> Result<(), ClipboardError> {
32        let _ = text;
33        Err(ClipboardError)
34    }
35    fn open_file_dialog(
36        &self,
37        multiple: bool,
38        filter: Option<FileDialogFilter>,
39    ) -> Vec<std::path::PathBuf> {
40        let _ = multiple;
41        let _ = filter;
42        vec![]
43    }
44}
45
46pub struct DummyShellProvider;
47impl ShellProvider for DummyShellProvider {}
48
49/// The system color scheme (light and dark mode)
50#[derive(Default, Debug, Clone, Copy, PartialEq)]
51pub enum ColorScheme {
52    #[default]
53    Light,
54    Dark,
55}
56
57#[derive(Debug, Clone, PartialEq)]
58pub struct Viewport {
59    pub color_scheme: ColorScheme,
60    pub window_size: (u32, u32),
61    pub hidpi_scale: f32,
62    pub zoom: f32,
63}
64
65impl Default for Viewport {
66    fn default() -> Self {
67        Self {
68            window_size: (0, 0),
69            hidpi_scale: 1.0,
70            zoom: 1.0,
71            color_scheme: ColorScheme::Light,
72        }
73    }
74}
75
76impl Viewport {
77    pub fn new(
78        physical_width: u32,
79        physical_height: u32,
80        scale_factor: f32,
81        color_scheme: ColorScheme,
82    ) -> Self {
83        Self {
84            window_size: (physical_width, physical_height),
85            hidpi_scale: scale_factor,
86            zoom: 1.0,
87            color_scheme,
88        }
89    }
90
91    /// Total scaling, computed as `hidpi_scale_factor * zoom`
92    pub fn scale(&self) -> f32 {
93        self.hidpi_scale * self.zoom
94    }
95    /// Same as [`scale`](Self::scale) but `f64` instead of `f32`
96    pub fn scale_f64(&self) -> f64 {
97        self.scale() as f64
98    }
99
100    /// Set hidpi scale factor
101    pub fn set_hidpi_scale(&mut self, scale: f32) {
102        self.hidpi_scale = scale;
103    }
104
105    /// Get document zoom level
106    pub fn zoom(&self) -> f32 {
107        self.zoom
108    }
109
110    /// Set document zoom level (`1.0` is unzoomed)
111    pub fn set_zoom(&mut self, zoom: f32) {
112        self.zoom = zoom;
113    }
114
115    pub fn zoom_by(&mut self, zoom: f32) {
116        self.zoom += zoom;
117    }
118
119    pub fn zoom_mut(&mut self) -> &mut f32 {
120        &mut self.zoom
121    }
122}
123
124/// Filter provided by the dom for an file picker
125pub struct FileDialogFilter {
126    pub name: String,
127    pub extensions: Vec<String>,
128}