Skip to main content

i_slint_core/
lib.rs

1// Copyright © SixtyFPS GmbH <info@slint.dev>
2// SPDX-License-Identifier: GPL-3.0-only OR LicenseRef-Slint-Royalty-free-2.0 OR LicenseRef-Slint-Software-3.0
3
4// cSpell: ignore sharedvector textlayout
5
6#![doc = include_str!("README.md")]
7#![doc(html_logo_url = "https://slint.dev/logo/slint-logo-square-light.svg")]
8#![cfg_attr(docsrs, feature(doc_cfg))]
9#![deny(unsafe_code)]
10#![allow(clippy::missing_safety_doc)] // FFI surface has many exported unsafe entry points
11#![cfg_attr(slint_nightly_test, feature(non_exhaustive_omitted_patterns_lint))]
12#![cfg_attr(slint_nightly_test, warn(non_exhaustive_omitted_patterns))]
13#![no_std]
14#![debugger_visualizer(gdb_script_file = "gdb_pretty_printers.py")]
15
16extern crate alloc;
17#[cfg(feature = "std")]
18extern crate std;
19
20#[cfg(all(not(feature = "std"), feature = "unsafe-single-threaded"))]
21pub mod unsafe_single_threaded;
22#[cfg(all(not(feature = "std"), not(feature = "unsafe-single-threaded")))]
23compile_error!(
24    "At least one of the following feature need to be enabled: `std` or `unsafe-single-threaded`"
25);
26pub use crate::items::OperatingSystemType;
27#[cfg(all(not(feature = "std"), feature = "unsafe-single-threaded"))]
28pub use crate::unsafe_single_threaded::thread_local;
29#[cfg(feature = "std")]
30pub use std::thread_local;
31
32pub mod accessibility;
33pub mod animations;
34pub mod api;
35pub mod callbacks;
36pub mod component_factory;
37pub mod context;
38pub mod data_transfer;
39pub mod date_time;
40pub mod debug_log;
41pub mod future;
42pub mod graphics;
43pub mod input;
44pub mod item_focus;
45pub mod item_rendering;
46pub mod item_tree;
47pub mod items;
48pub mod layout;
49pub mod lengths;
50pub mod menus;
51pub mod model;
52pub mod partial_renderer;
53pub mod platform;
54pub mod properties;
55pub mod renderer;
56#[cfg(feature = "rtti")]
57pub mod rtti;
58pub mod sharedvector;
59pub mod slice;
60pub mod string;
61pub mod styled_text;
62pub mod textlayout;
63pub mod timers;
64pub mod translations;
65pub mod window;
66
67#[doc(inline)]
68pub use string::SharedString;
69
70#[doc(inline)]
71pub use sharedvector::SharedVector;
72
73#[doc(inline)]
74pub use graphics::{ImageInner, StaticTextures};
75
76#[doc(inline)]
77pub use properties::Property;
78
79#[doc(inline)]
80pub use callbacks::Callback;
81
82#[doc(inline)]
83pub use graphics::Color;
84
85#[doc(inline)]
86pub use graphics::Brush;
87
88#[doc(inline)]
89pub use graphics::RgbaColor;
90
91#[cfg(feature = "std")]
92#[doc(inline)]
93pub use graphics::PathData;
94
95#[doc(inline)]
96pub use graphics::BorderRadius;
97
98#[doc(inline)]
99pub use data_transfer::DataTransfer;
100
101pub use context::{SlintContext, SlintContextWeak, with_global_context};
102
103#[cfg(not(slint_int_coord))]
104pub type Coord = f32;
105#[cfg(slint_int_coord)]
106pub type Coord = i32;
107
108/// This type is not exported from the public API crate, so function having this
109/// parameter cannot be called from the public API without naming it
110#[derive(Debug, Clone, Copy, PartialEq, Eq)]
111pub struct InternalToken;
112
113#[cfg(feature = "std")]
114thread_local!(
115    /// Permit testing code to force an OS type
116    pub static OPERATING_SYSTEM_OVERRIDE: core::cell::Cell<Option<OperatingSystemType>> =
117        Default::default();
118);
119
120#[cfg(not(target_family = "wasm"))]
121pub fn detect_operating_system() -> OperatingSystemType {
122    #[cfg(feature = "std")]
123    if let Some(os_override) = OPERATING_SYSTEM_OVERRIDE.with(|os_override| os_override.get()) {
124        return os_override;
125    }
126
127    if cfg!(target_os = "android") {
128        OperatingSystemType::Android
129    } else if cfg!(target_os = "ios") {
130        OperatingSystemType::Ios
131    } else if cfg!(target_os = "macos") {
132        OperatingSystemType::Macos
133    } else if cfg!(target_os = "windows") {
134        OperatingSystemType::Windows
135    } else if cfg!(target_os = "linux") {
136        OperatingSystemType::Linux
137    } else {
138        OperatingSystemType::Other
139    }
140}
141
142#[cfg(target_family = "wasm")]
143pub fn detect_operating_system() -> OperatingSystemType {
144    if let Some(os_override) = OPERATING_SYSTEM_OVERRIDE.with(|os_override| os_override.get()) {
145        return os_override;
146    }
147
148    let mut user_agent =
149        web_sys::window().and_then(|w| w.navigator().user_agent().ok()).unwrap_or_default();
150    user_agent.make_ascii_lowercase();
151    let mut platform =
152        web_sys::window().and_then(|w| w.navigator().platform().ok()).unwrap_or_default();
153    platform.make_ascii_lowercase();
154
155    if user_agent.contains("ipad") || user_agent.contains("iphone") {
156        OperatingSystemType::Ios
157    } else if user_agent.contains("android") {
158        OperatingSystemType::Android
159    } else if platform.starts_with("mac") {
160        OperatingSystemType::Macos
161    } else if platform.starts_with("win") {
162        OperatingSystemType::Windows
163    } else if platform.starts_with("linux") {
164        OperatingSystemType::Linux
165    } else {
166        OperatingSystemType::Other
167    }
168}
169
170/// Returns true if the current platform is an Apple platform (macOS, iOS, iPadOS)
171pub fn is_apple_platform() -> bool {
172    matches!(detect_operating_system(), OperatingSystemType::Macos | OperatingSystemType::Ios)
173}
174
175pub fn open_url(url: &str, window: &crate::api::Window) -> Result<(), crate::api::PlatformError> {
176    crate::window::WindowInner::from_pub(window).context().platform().open_url(url)
177}
178
179#[cfg(target_os = "macos")]
180pub fn macos_bring_all_windows_to_front() {
181    use objc2::MainThreadMarker;
182    use objc2_app_kit::NSApplication;
183    let Some(mtm) = MainThreadMarker::new() else { return };
184    NSApplication::sharedApplication(mtm).arrangeInFront(None);
185}
186
187#[cfg(not(target_os = "macos"))]
188pub fn macos_bring_all_windows_to_front() {}