1#![warn(missing_docs)]
5extern crate alloc;
14use crate::api::PlatformError;
15use crate::lengths::LogicalLength;
16use crate::Coord;
17use crate::SharedString;
18use alloc::boxed::Box;
19
20pub use euclid;
21pub type Rect = euclid::default::Rect<Coord>;
23pub type IntRect = euclid::default::Rect<i32>;
25pub type Point = euclid::default::Point2D<Coord>;
27pub type Size = euclid::default::Size2D<Coord>;
29pub type IntSize = euclid::default::Size2D<u32>;
31pub type Transform = euclid::default::Transform2D<Coord>;
33
34pub(crate) mod color;
35pub use color::*;
36
37#[cfg(feature = "std")]
38mod path;
39#[cfg(feature = "std")]
40pub use path::*;
41
42mod brush;
43pub use brush::*;
44
45pub(crate) mod image;
46pub use self::image::*;
47
48pub(crate) mod bitmapfont;
49pub use self::bitmapfont::*;
50
51pub mod rendering_metrics_collector;
52
53#[cfg(feature = "box-shadow-cache")]
54pub mod boxshadowcache;
55
56pub mod border_radius;
57pub use border_radius::*;
58
59#[cfg(feature = "unstable-wgpu-26")]
60pub mod wgpu_26;
61
62pub struct CachedGraphicsData<T> {
67 pub data: T,
69 pub dependency_tracker: Option<core::pin::Pin<Box<crate::properties::PropertyTracker>>>,
72}
73
74impl<T> CachedGraphicsData<T> {
75 pub fn new(update_fn: impl FnOnce() -> T) -> Self {
78 let dependency_tracker = Box::pin(crate::properties::PropertyTracker::default());
79 let data = dependency_tracker.as_ref().evaluate(update_fn);
80 Self { data, dependency_tracker: Some(dependency_tracker) }
81 }
82}
83
84pub struct RenderingCache<T> {
90 slab: slab::Slab<CachedGraphicsData<T>>,
91 generation: usize,
92}
93
94impl<T> Default for RenderingCache<T> {
95 fn default() -> Self {
96 Self { slab: Default::default(), generation: 1 }
97 }
98}
99
100impl<T> RenderingCache<T> {
101 pub fn generation(&self) -> usize {
104 self.generation
105 }
106
107 pub fn get_mut(&mut self, index: usize) -> Option<&mut CachedGraphicsData<T>> {
109 self.slab.get_mut(index)
110 }
111
112 pub fn contains(&self, index: usize) -> bool {
114 self.slab.contains(index)
115 }
116
117 pub fn insert(&mut self, data: CachedGraphicsData<T>) -> usize {
119 self.slab.insert(data)
120 }
121
122 pub fn get(&self, index: usize) -> Option<&CachedGraphicsData<T>> {
124 self.slab.get(index)
125 }
126
127 pub fn remove(&mut self, index: usize) -> CachedGraphicsData<T> {
129 self.slab.remove(index)
130 }
131
132 pub fn clear(&mut self) {
135 self.slab.clear();
136 self.generation += 1;
137 }
138}
139#[derive(Debug, Clone, PartialEq, Default)]
143pub struct FontRequest {
144 pub family: Option<SharedString>,
147 pub weight: Option<i32>,
149 pub pixel_size: Option<LogicalLength>,
151 pub letter_spacing: Option<LogicalLength>,
154 pub italic: bool,
156}
157
158#[cfg(feature = "shared-fontdb")]
159impl FontRequest {
160 pub fn to_fontdb_query(&self) -> i_slint_common::sharedfontdb::fontdb::Query<'_> {
162 use i_slint_common::sharedfontdb::fontdb::{Query, Style, Weight};
163 Query {
164 style: if self.italic { Style::Italic } else { Style::Normal },
165 weight: Weight(self.weight.unwrap_or(400) as _),
166 ..Default::default()
167 }
168 }
169}
170
171#[derive(Debug, Clone, PartialEq)]
174pub enum RequestedOpenGLVersion {
175 OpenGL(Option<(u8, u8)>),
177 OpenGLES(Option<(u8, u8)>),
179}
180
181#[derive(Debug, Clone)]
184pub enum RequestedGraphicsAPI {
185 OpenGL(RequestedOpenGLVersion),
187 Metal,
189 Vulkan,
191 Direct3D,
193 #[cfg(feature = "unstable-wgpu-26")]
194 WGPU26(wgpu_26::api::WGPUConfiguration),
196}
197
198impl TryFrom<&RequestedGraphicsAPI> for RequestedOpenGLVersion {
199 type Error = PlatformError;
200
201 fn try_from(requested_graphics_api: &RequestedGraphicsAPI) -> Result<Self, Self::Error> {
202 match requested_graphics_api {
203 RequestedGraphicsAPI::OpenGL(requested_open_glversion) => {
204 Ok(requested_open_glversion.clone())
205 }
206 RequestedGraphicsAPI::Metal => {
207 Err("Metal rendering is not supported with an OpenGL renderer".into())
208 }
209 RequestedGraphicsAPI::Vulkan => {
210 Err("Vulkan rendering is not supported with an OpenGL renderer".into())
211 }
212 RequestedGraphicsAPI::Direct3D => {
213 Err("Direct3D rendering is not supported with an OpenGL renderer".into())
214 }
215 #[cfg(feature = "unstable-wgpu-26")]
216 RequestedGraphicsAPI::WGPU26(..) => {
217 Err("WGPU 26.x rendering is not supported with an OpenGL renderer".into())
218 }
219 }
220 }
221}
222
223impl From<RequestedOpenGLVersion> for RequestedGraphicsAPI {
224 fn from(version: RequestedOpenGLVersion) -> Self {
225 Self::OpenGL(version)
226 }
227}
228
229#[cfg(feature = "unstable-wgpu-26")]
232pub fn create_graphics_api_wgpu_26(
233 instance: wgpu_26::wgpu::Instance,
234 device: wgpu_26::wgpu::Device,
235 queue: wgpu_26::wgpu::Queue,
236) -> crate::api::GraphicsAPI<'static> {
237 crate::api::GraphicsAPI::WGPU26 { instance, device, queue }
238}
239
240#[cfg(feature = "ffi")]
242pub mod ffi {
243 #![allow(unsafe_code)]
244
245 #[cfg(cbindgen)]
247 #[repr(C)]
248 struct Rect {
249 x: f32,
250 y: f32,
251 width: f32,
252 height: f32,
253 }
254
255 #[cfg(cbindgen)]
257 #[repr(C)]
258 struct IntRect {
259 x: i32,
260 y: i32,
261 width: i32,
262 height: i32,
263 }
264
265 #[cfg(cbindgen)]
267 #[repr(C)]
268 struct Point {
269 x: f32,
270 y: f32,
271 }
272
273 #[cfg(cbindgen)]
275 #[repr(C)]
276 struct Box2D<T, U> {
277 min: euclid::Point2D<T>,
278 max: euclid::Point2D<T>,
279 _unit: std::marker::PhantomData<U>,
280 }
281
282 #[cfg(feature = "std")]
283 pub use super::path::ffi::*;
284
285 pub fn physical_size_from_api(
289 size: crate::api::PhysicalSize,
290 ) -> crate::graphics::euclid::default::Size2D<u32> {
291 size.to_euclid()
292 }
293
294 pub fn physical_position_from_api(
298 position: crate::api::PhysicalPosition,
299 ) -> crate::graphics::euclid::default::Point2D<i32> {
300 position.to_euclid()
301 }
302
303 pub fn physical_position_to_api(
306 position: crate::graphics::euclid::default::Point2D<i32>,
307 ) -> crate::api::PhysicalPosition {
308 crate::api::PhysicalPosition::from_euclid(position)
309 }
310}