ferroui_controls/platform/i_top_level_impl.rs
1use super::{
2 IPlatformHandle, IPopupImpl, IWin32OptionsTopLevelImpl, IWindowBaseImpl, IWindowImpl, PlatformThemeVariant,
3};
4use crate::{AcrylicPlatformCompensationLevels, WindowResizeReason, WindowTransparencyLevel};
5use ferroui_base::input::raw::IRawInputEventArgs;
6use ferroui_base::input::IInputRoot;
7use ferroui_base::platform::surfaces::IPlatformRenderSurface;
8use ferroui_base::platform::{ICursorImpl, IOptionalFeatureProvider};
9use ferroui_base::reactive::IDisposable;
10use ferroui_base::rendering::composition::Compositor;
11use ferroui_base::{PixelPoint, Point, Rect, Size};
12use std::any::Any;
13use std::rc::Rc;
14
15/// Defines a platform-specific top-level window implementation.
16///
17/// This is the common contract of [`IWindowImpl`] and [`IPopupImpl`].
18///
19/// The callback members (`input`, `paint`, `resized`, ...) are set by the
20/// top-level that owns the implementation and called by the platform; each
21/// one is a getter/setter pair holding an optional callback.
22///
23/// Optional features are queried through the
24/// [`IOptionalFeatureProvider`] supertrait:
25/// `(top_level as &dyn IOptionalFeatureProvider).try_get::<dyn IInputPane>()`.
26pub trait ITopLevelImpl: IOptionalFeatureProvider + IDisposable {
27 /// Gets the scaling factor for window positioning and sizing.
28 fn desktop_scaling(&self) -> f64;
29
30 /// Get the platform handle.
31 fn handle(&self) -> Option<Rc<dyn IPlatformHandle>>;
32
33 /// Gets the client size of the toplevel.
34 fn client_size(&self) -> Size;
35
36 /// Gets the scaling factor for the toplevel. This is used for rendering.
37 fn render_scaling(&self) -> f64;
38
39 /// The list of native platform's surfaces that can be consumed by
40 /// rendering subsystems.
41 ///
42 /// The rendering platform checks that list and sees if it can utilize
43 /// one of them to output. It should be enough to expose a native window
44 /// handle surface and add support for a framebuffer (even if it's an
45 /// emulated one) via the framebuffer platform surface.
46 fn surfaces(&self) -> Vec<std::sync::Arc<dyn IPlatformRenderSurface>>;
47
48 /// The surfaces as the thread that renders asks for them: the function
49 /// is called by that thread whenever the renderer (re)creates its
50 /// render target (the reference reads `Surfaces` of the top-level
51 /// there).
52 ///
53 /// A top-level is an object of the UI thread, so the function cannot
54 /// reach it. This default hands out the surfaces the top-level has now.
55 /// An implementation whose surfaces change, or that has to stop handing
56 /// them out when it is closed, keeps them in a shared cell and returns
57 /// a function that reads it.
58 fn render_surfaces(
59 &self,
60 ) -> std::sync::Arc<dyn Fn() -> Vec<std::sync::Arc<dyn IPlatformRenderSurface>> + Send + Sync> {
61 let surfaces = self.surfaces();
62 std::sync::Arc::new(move || surfaces.clone())
63 }
64
65 /// Gets the compositor that is used for the toplevel, if the platform
66 /// renders through one.
67 fn compositor(&self) -> Option<Rc<Compositor>> {
68 None
69 }
70
71 /// Gets the method called when the toplevel receives input.
72 fn input(&self) -> Option<Rc<dyn Fn(Rc<dyn IRawInputEventArgs>)>>;
73
74 /// Sets a method called when the toplevel receives input.
75 fn set_input(&self, value: Option<Rc<dyn Fn(Rc<dyn IRawInputEventArgs>)>>);
76
77 /// Gets the method called when the toplevel requires painting.
78 fn paint(&self) -> Option<Rc<dyn Fn(Rect)>>;
79
80 /// Sets a method called when the toplevel requires painting.
81 fn set_paint(&self, value: Option<Rc<dyn Fn(Rect)>>);
82
83 /// Gets the method called when the toplevel is resized.
84 fn resized(&self) -> Option<Rc<dyn Fn(Size, WindowResizeReason)>>;
85
86 /// Sets a method called when the toplevel is resized.
87 fn set_resized(&self, value: Option<Rc<dyn Fn(Size, WindowResizeReason)>>);
88
89 /// Gets the method called when the toplevel's scaling changes.
90 fn scaling_changed(&self) -> Option<Rc<dyn Fn(f64)>>;
91
92 /// Sets a method called when the toplevel's scaling changes.
93 fn set_scaling_changed(&self, value: Option<Rc<dyn Fn(f64)>>);
94
95 /// Gets the method called when the toplevel's transparency level
96 /// changes.
97 fn transparency_level_changed(&self) -> Option<Rc<dyn Fn(WindowTransparencyLevel)>>;
98
99 /// Sets a method called when the toplevel's transparency level changes.
100 fn set_transparency_level_changed(&self, value: Option<Rc<dyn Fn(WindowTransparencyLevel)>>);
101
102 /// Gets the platform-specific scene info, which is passed to the render
103 /// target of the toplevel.
104 fn platform_specific_scene_info(&self) -> Option<std::sync::Arc<dyn Any + Send + Sync>> {
105 None
106 }
107
108 /// Gets the method called when the platform-specific scene info
109 /// changes.
110 fn platform_specific_scene_info_changed(&self) -> Option<Rc<dyn Fn(Option<std::sync::Arc<dyn Any + Send + Sync>>)>> {
111 None
112 }
113
114 /// Sets a method called when the platform-specific scene info changes.
115 fn set_platform_specific_scene_info_changed(&self, _value: Option<Rc<dyn Fn(Option<std::sync::Arc<dyn Any + Send + Sync>>)>>) {}
116
117 /// Sets the input root for the toplevel.
118 fn set_input_root(&self, input_root: Rc<dyn IInputRoot>);
119
120 /// Converts a point from screen to client coordinates.
121 fn point_to_client(&self, point: PixelPoint) -> Point;
122
123 /// Converts a point from client to screen coordinates.
124 fn point_to_screen(&self, point: Point) -> PixelPoint;
125
126 /// Sets the cursor associated with the toplevel; `None` stands for the
127 /// default cursor.
128 fn set_cursor(&self, cursor: Option<Rc<dyn ICursorImpl>>);
129
130 /// Gets the method called when the underlying implementation is
131 /// destroyed.
132 fn closed(&self) -> Option<Rc<dyn Fn()>>;
133
134 /// Sets a method called when the underlying implementation is
135 /// destroyed.
136 fn set_closed(&self, value: Option<Rc<dyn Fn()>>);
137
138 /// Gets the method called when the input focus is lost.
139 fn lost_focus(&self) -> Option<Rc<dyn Fn()>>;
140
141 /// Sets a method called when the input focus is lost.
142 fn set_lost_focus(&self, value: Option<Rc<dyn Fn()>>);
143
144 /// Creates a popup that belongs to the toplevel, if the platform
145 /// supports native popups.
146 fn create_popup(&self) -> Option<Rc<dyn IPopupImpl>>;
147
148 /// Sets the transparency level hint of the toplevel, in order of
149 /// preference.
150 fn set_transparency_level_hint(&self, transparency_levels: &[WindowTransparencyLevel]);
151
152 /// Gets the current transparency level of the toplevel.
153 fn transparency_level(&self) -> WindowTransparencyLevel;
154
155 /// Gets the acrylic compensation levels for the platform.
156 fn acrylic_compensation_levels(&self) -> AcrylicPlatformCompensationLevels;
157
158 /// Sets the theme variant on the frame if it should be dark or light.
159 /// Also applies for the mica and acrylic backdrops, if they are
160 /// applied; `None` follows the system.
161 fn set_frame_theme_variant(&self, theme_variant: Option<PlatformThemeVariant>);
162
163 /// Lets callers recover the concrete implementation type.
164 fn as_any(&self) -> &dyn Any;
165
166 /// The toplevel as a window base implementation, if it is one.
167 fn as_window_base_impl(&self) -> Option<&dyn IWindowBaseImpl> {
168 None
169 }
170
171 /// The toplevel as a window implementation, if it is one.
172 fn as_window_impl(&self) -> Option<&dyn IWindowImpl> {
173 None
174 }
175
176 /// The toplevel as a popup implementation, if it is one.
177 fn as_popup_impl(&self) -> Option<&dyn IPopupImpl> {
178 None
179 }
180
181 /// The toplevel as the Win32-specific options of a toplevel, if it has them.
182 fn as_win32_options_top_level_impl(&self) -> Option<&dyn IWin32OptionsTopLevelImpl> {
183 None
184 }
185}