slint/sixtyfps_runtime/corelib/backend.rs
Simon Hausmann 0fdb87cc69 Add Image::size()
This requires the image size query to be window independent and go
through the backend instead.

This implies minor changes for the Qt backend and bigger ones for the GL
backend:

* There exists now a thread-local IMAGE_CACHE, which is used by the
  backend's image_size() function as well as by the renderer for
  loading CPU side images.
* The image remain as decoded images in there (including SVG tree)
  and the window now has a texture_cache, which holds CachedImage
  with ImageData::Texture.
* Rendering an image item therefore fetches the CPU side image,
  calls upload_to_gpu() on it, which creates a new Rc<CachedImage>
  and that's stored in the texture_cache.
* The texture cache continues to be pruned when hiding the window.
2021-06-20 11:18:28 +02:00

77 lines
2.7 KiB
Rust

/* LICENSE BEGIN
This file is part of the SixtyFPS Project -- https://sixtyfps.io
Copyright (c) 2020 Olivier Goffart <olivier.goffart@sixtyfps.io>
Copyright (c) 2020 Simon Hausmann <simon.hausmann@sixtyfps.io>
SPDX-License-Identifier: GPL-3.0-only
This file is also available under commercial licensing terms.
Please contact info@sixtyfps.io for more information.
LICENSE END */
/*!
The backend is the abstraction for crates that need to do the actual drawing and event loop
*/
use std::path::Path;
use crate::graphics::{Image, Size};
use crate::window::ComponentWindow;
/// Behavior describing how the event loop should terminate.
pub enum EventLoopQuitBehavior {
/// Terminate the event loop when the last window was closed.
QuitOnLastWindowClosed,
/// Keep the event loop running until [`Backend::quit_event_loop()`] is called.
QuitOnlyExplicitly,
}
/// Interface implemented by backends
pub trait Backend: Send + Sync {
/// Instentiate a window for a component.
/// FIXME: should return a Box<dyn PlatformWindow>
fn create_window(&'static self) -> ComponentWindow;
/// Spins an event loop and renders the visible windows.
fn run_event_loop(&'static self, behavior: EventLoopQuitBehavior);
/// Exits the event loop.
fn quit_event_loop(&'static self);
/// This function can be used to register a custom TrueType font with SixtyFPS,
/// for use with the `font-family` property. The provided slice must be a valid TrueType
/// font.
fn register_font_from_memory(
&'static self,
data: &[u8],
) -> Result<(), Box<dyn std::error::Error>>;
/// This function can be used to register a custom TrueType font with SixtyFPS,
/// for use with the `font-family` property. The provided path must refer to a valid TrueType
/// font.
fn register_font_from_path(
&'static self,
path: &Path,
) -> Result<(), Box<dyn std::error::Error>>;
fn set_clipboard_text(&'static self, text: String);
fn clipboard_text(&'static self) -> Option<String>;
/// Send an user event to from another thread that should be run in the GUI event loop
fn post_event(&'static self, event: Box<dyn FnOnce() + Send>);
fn image_size(&'static self, image: &Image) -> Size;
}
static PRIVATE_BACKEND_INSTANCE: once_cell::sync::OnceCell<Box<dyn Backend + 'static>> =
once_cell::sync::OnceCell::new();
pub fn instance() -> Option<&'static dyn Backend> {
use std::ops::Deref;
PRIVATE_BACKEND_INSTANCE.get().map(|backend_box| backend_box.deref())
}
pub fn instance_or_init(
factory_fn: impl FnOnce() -> Box<dyn Backend + 'static>,
) -> &'static dyn Backend {
use std::ops::Deref;
PRIVATE_BACKEND_INSTANCE.get_or_init(factory_fn).deref()
}