api: Change logical/physical position and size on window (#1620)

* Add `RequestedSize` and `RequestedPosition` enum to enable asking for
  logical or physical size/position.
* Rename `Window::size()` to `Window::physical_size()`
* Make `Window::set_size(...)` take an `Into<RequestedSize>`
* Rename `Window::position()` to `Window::physical_position()`
* Make `Window::set_position(...)` take an `Into<RequestedPosition>`
* Change `WindowAdapter` and related classes to be able to handle
  requests being made in the either physical or logical units.

Implement this for C++, Rust and node.
This commit is contained in:
Tobias Hunger 2022-09-13 08:55:31 +02:00 committed by GitHub
parent 9bef6f519a
commit 53a3c72b57
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
11 changed files with 298 additions and 85 deletions

View file

@ -313,9 +313,11 @@ fn gen_corelib(
"slint_windowrc_request_redraw",
"slint_windowrc_on_close_requested",
"slint_windowrc_position",
"slint_windowrc_set_position",
"slint_windowrc_set_logical_position",
"slint_windowrc_set_physical_position",
"slint_windowrc_size",
"slint_windowrc_set_size",
"slint_windowrc_set_logical_size",
"slint_windowrc_set_physical_size",
"slint_new_path_elements",
"slint_new_path_events",
"slint_color_brighter",

View file

@ -25,6 +25,8 @@ struct ComponentVTable;
struct ItemVTable;
}
#include "slint_internal.h"
#include "slint_size.h"
#include "slint_point.h"
#include "slint_backend_internal.h"
#include "slint_qt_internal.h"
#include "slint_selector_internal.h"
@ -178,23 +180,33 @@ public:
void request_redraw() const { cbindgen_private::slint_windowrc_request_redraw(&inner); }
slint::Point<int> position() const
slint::PhysicalPosition position() const
{
slint::Point<int> pos { 0, 0 };
slint::PhysicalPosition pos { 0, 0 };
cbindgen_private::slint_windowrc_position(&inner, &pos);
return pos;
}
void set_position(const slint::Point<int> &pos)
void set_logical_position(const slint::LogicalPosition &pos)
{
cbindgen_private::slint_windowrc_set_position(&inner, &pos);
cbindgen_private::slint_windowrc_set_logical_position(&inner, &pos);
}
slint::Size<unsigned int> size() const { return cbindgen_private::slint_windowrc_size(&inner); }
void set_size(const slint::Size<unsigned int> &size)
void set_physical_position(const slint::PhysicalPosition &pos)
{
cbindgen_private::slint_windowrc_set_size(&inner, &size);
cbindgen_private::slint_windowrc_set_physical_position(&inner, &pos);
}
slint::PhysicalSize size() const { return cbindgen_private::slint_windowrc_size(&inner); }
void set_logical_size(const slint::LogicalSize &size)
{
cbindgen_private::slint_windowrc_set_logical_size(&inner, &size);
}
void set_physical_size(const slint::PhysicalSize &size)
{
cbindgen_private::slint_windowrc_set_physical_size(&inner, &size);
}
/// Registers a font by the specified path. The path must refer to an existing
@ -416,20 +428,27 @@ public:
/// Returns the position of the window on the screen, in physical screen coordinates and
/// including a window frame (if present).
slint::Point<int> position() const { return inner.position(); }
slint::PhysicalPosition position() const { return inner.position(); }
/// Sets the position of the window on the screen, in physical screen coordinates and including
/// a window frame (if present).
/// Note that on some windowing systems, such as Wayland, this functionality is not available.
void set_position(const slint::Point<int> &pos) { inner.set_position(pos); }
void set_position(const slint::LogicalPosition &pos) { inner.set_logical_position(pos); }
/// Sets the position of the window on the screen, in physical screen coordinates and including
/// a window frame (if present).
/// Note that on some windowing systems, such as Wayland, this functionality is not available.
void set_position(const slint::PhysicalPosition &pos) { inner.set_physical_position(pos); }
/// Returns the size of the window on the screen, in physical screen coordinates and excluding
/// a window frame (if present).
slint::Size<unsigned int> size() const { return inner.size(); }
slint::PhysicalSize size() const { return inner.size(); }
/// Resizes the window to the specified size on the screen, in logical pixels and excluding
/// a window frame (if present).
void set_size(const slint::LogicalSize &size) { inner.set_logical_size(size); }
/// Resizes the window to the specified size on the screen, in physical pixels and excluding
/// a window frame (if present).
void set_size(const slint::Size<unsigned int> &size) { inner.set_size(size); }
void set_size(const slint::PhysicalSize &size) { inner.set_physical_size(size); }
/// \private
private_api::WindowAdapterRc &window_handle() { return inner; }

View file

@ -3,6 +3,8 @@
#pragma once
#include <cstdint>
namespace slint {
/// The Point structure is used to represent a two-dimensional point
@ -26,4 +28,9 @@ template<typename T>
using Point2D = Point<T>;
}
/// A position in logical pixel coordinates
using LogicalPosition = Point<float>;
/// A position in physical pixel coordinates
using PhysicalPosition = Point<int32_t>;
}

View file

@ -3,6 +3,8 @@
#pragma once
#include <cstdint>
namespace slint {
/// The Size structure is used to represent a two-dimensional size
@ -26,4 +28,9 @@ template<typename T>
using Size2D = Size<T>;
}
/// A size given in logical pixels
using LogicalSize = Size<float>;
/// A size given in physical pixels.
using PhysicalSize = Size<uint32_t>;
}

View file

@ -55,20 +55,22 @@ class Component {
}
interface Point {
x: Number;
y: Number;
x: number;
y: number;
}
interface Size {
width: Number;
height: Number;
width: number;
height: number;
}
interface SlintWindow {
show(): void;
hide(): void;
position: Point;
size: Size;
logical_position: Point;
physical_position: Point;
logical_size: Size;
physical_size: Size;
}
/**
@ -87,17 +89,29 @@ class WindowAPI implements SlintWindow {
hide(): void {
this.impl.hide();
}
get position(): Point {
return this.impl.get_position();
get logical_position(): Point {
return this.impl.get_logical_position();
}
set position(pos: Point) {
this.impl.set_position(pos);
set logical_position(pos: Point) {
this.impl.set_logical_position(pos);
}
get size(): Size {
return this.impl.get_size();
get physical_position(): Point {
return this.impl.get_physical_position();
}
set size(size: Size) {
this.impl.set_size(size);
set physical_position(pos: Point) {
this.impl.set_physical_position(pos);
}
get logical_size(): Size {
return this.impl.get_logical_size();
}
set logical_size(size: Size) {
this.impl.set_logical_size(size);
}
get physical_size(): Size {
return this.impl.get_physical_size();
}
set physical_size(size: Size) {
this.impl.set_physical_size(size);
}
}

View file

@ -491,24 +491,24 @@ declare_types! {
method show(mut cx) {
let this = cx.this();
let window = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
window.show();
let window_adapter = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
window_adapter.show();
Ok(JsUndefined::new().as_value(&mut cx))
}
method hide(mut cx) {
let this = cx.this();
let window = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
window.hide();
let window_adapter = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
window_adapter.hide();
Ok(JsUndefined::new().as_value(&mut cx))
}
method get_position(mut cx) {
method get_logical_position(mut cx) {
let this = cx.this();
let window = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let pos = window.position();
let window_adapter = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let pos = window_adapter.position().to_logical(window_adapter.window().scale_factor());
let point_object = JsObject::new(&mut cx);
let x_value = JsNumber::new(&mut cx, pos.x).as_value(&mut cx);
@ -518,21 +518,63 @@ declare_types! {
Ok(point_object.as_value(&mut cx))
}
method set_position(mut cx) {
method get_physical_position(mut cx) {
let this = cx.this();
let window = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let window_adapter = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let pos = window_adapter.position();
let point_object = JsObject::new(&mut cx);
let x_value = JsNumber::new(&mut cx, pos.x).as_value(&mut cx);
point_object.set(&mut cx, "x", x_value)?;
let y_value = JsNumber::new(&mut cx, pos.y).as_value(&mut cx);
point_object.set(&mut cx, "y", y_value)?;
Ok(point_object.as_value(&mut cx))
}
method set_logical_position(mut cx) {
let this = cx.this();
let window = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window_adapter = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let point_object = cx.argument::<JsObject>(0)?;
let x = point_object.get(&mut cx, "x")?.downcast_or_throw::<JsNumber, _>(&mut cx)?.value();
let y = point_object.get(&mut cx, "y")?.downcast_or_throw::<JsNumber, _>(&mut cx)?.value();
window.set_position(i_slint_core::api::PhysicalPosition::new(x as i32, y as i32));
window_adapter.set_position(i_slint_core::api::LogicalPosition::new(x as f32, y as f32).into());
Ok(JsUndefined::new().as_value(&mut cx))
}
method get_size(mut cx) {
method set_physical_position(mut cx) {
let this = cx.this();
let window = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window_adapter = window.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let point_object = cx.argument::<JsObject>(0)?;
let x = point_object.get(&mut cx, "x")?.downcast_or_throw::<JsNumber, _>(&mut cx)?.value();
let y = point_object.get(&mut cx, "y")?.downcast_or_throw::<JsNumber, _>(&mut cx)?.value();
window_adapter.set_position(i_slint_core::api::PhysicalPosition::new(x as i32, y as i32).into());
Ok(JsUndefined::new().as_value(&mut cx))
}
method get_logical_size(mut cx) {
let this = cx.this();
let window_adapter = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window_adapter = window_adapter.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let size = window_adapter.window().size().to_logical(window_adapter.window().scale_factor());
let size_object = JsObject::new(&mut cx);
let width_value = JsNumber::new(&mut cx, size.width).as_value(&mut cx);
size_object.set(&mut cx, "width", width_value)?;
let height_value = JsNumber::new(&mut cx, size.height).as_value(&mut cx);
size_object.set(&mut cx, "height", height_value)?;
Ok(size_object.as_value(&mut cx))
}
method get_physical_size(mut cx) {
let this = cx.this();
let window_adapter = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window_adapter = window_adapter.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
@ -546,7 +588,22 @@ declare_types! {
Ok(size_object.as_value(&mut cx))
}
method set_size(mut cx) {
method set_logical_size(mut cx) {
let this = cx.this();
let window_adapter = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window_adapter = window_adapter.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;
let window = window_adapter.window();
let size_object = cx.argument::<JsObject>(0)?;
let width = size_object.get(&mut cx, "width")?.downcast_or_throw::<JsNumber, _>(&mut cx)?.value();
let height = size_object.get(&mut cx, "height")?.downcast_or_throw::<JsNumber, _>(&mut cx)?.value();
window.set_size(i_slint_core::api::LogicalSize::new(width as f32, height as f32));
Ok(JsUndefined::new().as_value(&mut cx))
}
method set_physical_size(mut cx) {
let this = cx.this();
let window_adapter = cx.borrow(&this, |x| x.0.as_ref().cloned());
let window_adapter = window_adapter.ok_or(()).or_else(|()| cx.throw_error("Invalid type"))?;

View file

@ -1576,20 +1576,28 @@ impl WindowAdapterSealed for QtWindow {
let qp = cpp! {unsafe [widget_ptr as "QWidget*"] -> qttypes::QPoint as "QPoint" {
return widget_ptr->pos();
}};
i_slint_core::api::PhysicalPosition::new(qp.x as _, qp.y as _)
// Qt returns logical coordinates, so scale those!
i_slint_core::api::LogicalPosition::new(qp.x as _, qp.y as _)
.to_physical(self.window().scale_factor())
}
fn set_position(&self, position: i_slint_core::api::PhysicalPosition) {
fn set_position(&self, position: i_slint_core::api::RequestedPosition) {
let physical_position = position.to_physical(self.window().scale_factor());
let widget_ptr = self.widget_ptr();
let pos = qttypes::QPoint { x: position.x as _, y: position.y as _ };
let pos = qttypes::QPoint { x: physical_position.x as _, y: physical_position.y as _ };
cpp! {unsafe [widget_ptr as "QWidget*", pos as "QPoint"] {
widget_ptr->move(pos);
}};
}
fn set_inner_size(&self, size: i_slint_core::api::PhysicalSize) {
fn set_size(&self, size: i_slint_core::api::RequestedSize) {
let logical_size = size.to_logical(self.window().scale_factor());
let widget_ptr = self.widget_ptr();
let sz = qttypes::QSize { width: size.width as _, height: size.height as _ };
let sz = qttypes::QSize {
width: logical_size.width.round() as _,
height: logical_size.height.round() as _,
};
// Qt uses logical units!
cpp! {unsafe [widget_ptr as "QWidget*", sz as "QSize"] {
widget_ptr->resize(sz);
}};

View file

@ -59,7 +59,7 @@ impl WindowAdapterSealed for TestingWindow {
unimplemented!()
}
fn set_position(&self, _position: i_slint_core::api::PhysicalPosition) {
fn set_position(&self, _position: i_slint_core::api::RequestedPosition) {
unimplemented!()
}
}

View file

@ -22,6 +22,28 @@ use corelib::{graphics::*, Coord};
use i_slint_core as corelib;
use winit::dpi::LogicalSize;
fn position_to_winit(pos: &corelib::api::RequestedPosition) -> winit::dpi::Position {
match pos {
corelib::api::RequestedPosition::Logical(pos) => {
winit::dpi::Position::new(winit::dpi::LogicalPosition::new(pos.x, pos.y))
}
corelib::api::RequestedPosition::Physical(pos) => {
winit::dpi::Position::new(winit::dpi::PhysicalPosition::new(pos.x, pos.y))
}
}
}
fn size_to_winit(pos: &corelib::api::RequestedSize) -> winit::dpi::Size {
match pos {
corelib::api::RequestedSize::Logical(size) => {
winit::dpi::Size::new(winit::dpi::LogicalSize::new(size.width, size.height))
}
corelib::api::RequestedSize::Physical(size) => {
winit::dpi::Size::new(winit::dpi::PhysicalSize::new(size.width, size.height))
}
}
}
/// GraphicsWindow is an implementation of the [WindowAdapter][`crate::eventloop::WindowAdapter`] trait. This is
/// typically instantiated by entry factory functions of the different graphics back ends.
pub(crate) struct GLWindow<Renderer: WinitCompatibleRenderer + 'static> {
@ -318,9 +340,7 @@ impl<Renderer: WinitCompatibleRenderer + 'static> WindowAdapterSealed for GLWind
if must_resize {
let win = self.window();
win.set_size(
i_slint_core::api::LogicalSize::new(width, height).to_physical(win.scale_factor()),
);
win.set_size(i_slint_core::api::LogicalSize::new(width, height));
}
}
@ -458,12 +478,20 @@ impl<Renderer: WinitCompatibleRenderer + 'static> WindowAdapterSealed for GLWind
))
}
if let Some(requested_size) = requested_size {
if let Some(requested_size) = &requested_size {
// It would be nice to bound this with our constraints, but those are in logical coordinates
// and we don't know the scale factor yet...
window_builder.with_inner_size(winit::dpi::Size::new(
winit::dpi::PhysicalSize::new(requested_size.width, requested_size.height),
))
if let Some(sf) = scale_factor_override {
let physical_size = requested_size.to_physical(sf as f32);
window_builder.with_inner_size(winit::dpi::Size::new(
winit::dpi::PhysicalSize::new(
physical_size.width,
physical_size.height,
),
))
} else {
window_builder.with_inner_size(size_to_winit(requested_size))
}
} else if s.width > 0 as Coord && s.height > 0 as Coord {
// Make sure that the window's inner size is in sync with the root window item's
// width/height.
@ -477,10 +505,8 @@ impl<Renderer: WinitCompatibleRenderer + 'static> WindowAdapterSealed for GLWind
let window_builder =
if no_frame { window_builder.with_decorations(false) } else { window_builder };
let window_builder = if let Some(requested_position) = requested_position {
window_builder.with_position(winit::dpi::Position::new(
winit::dpi::PhysicalPosition::new(requested_position.x, requested_position.y),
))
let window_builder = if let Some(pos) = &requested_position {
window_builder.with_position(position_to_winit(pos))
} else {
window_builder
};
@ -590,9 +616,10 @@ impl<Renderer: WinitCompatibleRenderer + 'static> WindowAdapterSealed for GLWind
fn position(&self) -> corelib::api::PhysicalPosition {
match &*self.map_state.borrow() {
GraphicsWindowBackendState::Unmapped { requested_position, .. } => {
requested_position.unwrap_or_default()
}
GraphicsWindowBackendState::Unmapped { requested_position, .. } => requested_position
.as_ref()
.map(|p| p.to_physical(self.window().scale_factor()))
.unwrap_or_default(),
GraphicsWindowBackendState::Mapped(mapped_window) => mapped_window
.canvas
.with_window_handle(|winit_window| match winit_window.outer_position() {
@ -604,22 +631,20 @@ impl<Renderer: WinitCompatibleRenderer + 'static> WindowAdapterSealed for GLWind
}
}
fn set_position(&self, position: corelib::api::PhysicalPosition) {
fn set_position(&self, position: corelib::api::RequestedPosition) {
match &mut *self.map_state.borrow_mut() {
GraphicsWindowBackendState::Unmapped { requested_position, .. } => {
*requested_position = Some(position)
}
GraphicsWindowBackendState::Mapped(mapped_window) => {
mapped_window.canvas.with_window_handle(|winit_window| {
winit_window.set_outer_position(winit::dpi::Position::new(
winit::dpi::PhysicalPosition::new(position.x, position.y),
))
winit_window.set_outer_position(position_to_winit(&position))
})
}
}
}
fn set_inner_size(&self, size: corelib::api::PhysicalSize) {
fn set_size(&self, size: corelib::api::RequestedSize) {
if let Ok(mut map_state) = self.map_state.try_borrow_mut() {
// otherwise we are called from the resize event
match &mut *map_state {
@ -628,8 +653,7 @@ impl<Renderer: WinitCompatibleRenderer + 'static> WindowAdapterSealed for GLWind
}
GraphicsWindowBackendState::Mapped(mapped_window) => {
mapped_window.canvas.with_window_handle(|winit_window| {
winit_window
.set_inner_size(winit::dpi::PhysicalSize::new(size.width, size.height));
winit_window.set_inner_size(size_to_winit(&size));
});
}
}
@ -650,8 +674,8 @@ struct MappedWindow<Renderer: WinitCompatibleRenderer> {
enum GraphicsWindowBackendState<Renderer: WinitCompatibleRenderer> {
Unmapped {
requested_position: Option<corelib::api::PhysicalPosition>,
requested_size: Option<corelib::api::PhysicalSize>,
requested_position: Option<corelib::api::RequestedPosition>,
requested_size: Option<corelib::api::RequestedSize>,
},
Mapped(MappedWindow<Renderer>),
}

View file

@ -48,7 +48,7 @@ impl LogicalPosition {
/// A position represented in the coordinate space of physical device pixels. That is the space after applying
/// a display device specific scale factor to pixels from the logical coordinate space.
#[derive(Debug, Default, Copy, Clone, PartialEq)]
#[derive(Debug, Default, Copy, Clone, Eq, PartialEq)]
pub struct PhysicalPosition {
/// The x coordinate.
pub x: i32,
@ -81,9 +81,28 @@ impl PhysicalPosition {
}
}
/// The requested position to render the window at.
#[derive(Clone, Debug, derive_more::From, PartialEq)]
pub enum RequestedPosition {
/// In physical screen coordinates
Physical(PhysicalPosition),
/// In logical screen coordinates
Logical(LogicalPosition),
}
impl RequestedPosition {
/// Turn the `RequestedPosition` into a `PhysicalPosition`.
pub fn to_physical(&self, scale_factor: f32) -> PhysicalPosition {
match self {
RequestedPosition::Physical(pos) => pos.clone(),
RequestedPosition::Logical(pos) => pos.to_physical(scale_factor),
}
}
}
/// A size represented in the coordinate space of logical pixels. That is the space before applying
/// a display device specific scale factor.
#[derive(Debug, Default, Copy, Clone)]
#[derive(Debug, Default, Copy, Clone, PartialEq)]
pub struct LogicalSize {
/// The width in logical pixels.
pub width: f32,
@ -122,7 +141,7 @@ impl LogicalSize {
/// A size represented in the coordinate space of physical device pixels. That is the space after applying
/// a display device specific scale factor to pixels from the logical coordinate space.
#[derive(Debug, Default, Copy, Clone, PartialEq)]
#[derive(Debug, Default, Copy, Clone, Eq, PartialEq)]
pub struct PhysicalSize {
/// The width in physical pixels.
pub width: u32,
@ -158,6 +177,33 @@ impl PhysicalSize {
}
}
/// The requested size to render the window.
#[derive(Clone, Debug, derive_more::From, PartialEq)]
pub enum RequestedSize {
/// In physical screen pixels.
Physical(PhysicalSize),
/// In logical screen pixels.
Logical(LogicalSize),
}
impl RequestedSize {
/// Turn the `RequestedSize` into a `PhysicalSize`.
pub fn to_physical(&self, scale_factor: f32) -> PhysicalSize {
match self {
RequestedSize::Physical(size) => size.clone(),
RequestedSize::Logical(size) => size.to_physical(scale_factor),
}
}
/// Turn the `RequestedSize` into a `LogicalSize`.
pub fn to_logical(&self, scale_factor: f32) -> LogicalSize {
match self {
RequestedSize::Physical(size) => size.to_logical(scale_factor),
RequestedSize::Logical(size) => size.clone(),
}
}
}
/// This enum describes a low-level access to specific graphics APIs used
/// by the renderer.
#[derive(Clone)]
@ -344,7 +390,8 @@ impl Window {
/// Sets the position of the window on the screen, in physical screen coordinates and including
/// a window frame (if present).
/// Note that on some windowing systems, such as Wayland, this functionality is not available.
pub fn set_position(&self, position: PhysicalPosition) {
pub fn set_position(&self, position: impl Into<RequestedPosition>) {
let position = position.into();
self.0.window_adapter().set_position(position)
}
@ -356,11 +403,14 @@ impl Window {
/// Resizes the window to the specified size on the screen, in physical pixels and excluding
/// a window frame (if present).
pub fn set_size(&self, size: PhysicalSize) {
pub fn set_size(&self, size: impl Into<RequestedSize>) {
let size = size.into();
let l = size.to_logical(self.scale_factor());
let p = size.to_physical(self.scale_factor());
self.0.set_window_item_geometry(l.width as _, l.height as _);
if self.0.inner_size.replace(size) != size {
self.0.window_adapter().set_inner_size(size);
if self.0.inner_size.replace(p) != p {
self.0.window_adapter().set_size(size);
}
}

View file

@ -6,7 +6,9 @@
#![warn(missing_docs)]
//! Exposed Window API
use crate::api::{CloseRequestResponse, PhysicalPosition, PhysicalSize, Window};
use crate::api::{
CloseRequestResponse, PhysicalPosition, PhysicalSize, RequestedPosition, RequestedSize, Window,
};
use crate::component::{ComponentRc, ComponentRef, ComponentVTable, ComponentWeak};
use crate::graphics::{Point, Rect, Size};
use crate::input::{
@ -123,13 +125,13 @@ pub trait WindowAdapterSealed {
/// a window frame (if present).
///
/// The default implementation does nothing
fn set_position(&self, _position: PhysicalPosition) {}
fn set_position(&self, _position: RequestedPosition) {}
/// Resizes the window to the specified size on the screen, in physical pixels and excluding
/// a window frame (if present).
/// Resizes the window to the specified size on the screen, in physical or logical pixels
/// and excluding a window frame (if present).
///
/// The default implementation does nothing
fn set_inner_size(&self, _size: PhysicalSize) {}
fn set_size(&self, _size: RequestedSize) {}
/// Return the renderer
fn renderer(&self) -> &dyn Renderer;
@ -928,12 +930,24 @@ pub mod ffi {
/// a window frame (if present).
/// Note that on some windowing systems, such as Wayland, this functionality is not available.
#[no_mangle]
pub unsafe extern "C" fn slint_windowrc_set_position(
pub unsafe extern "C" fn slint_windowrc_set_physical_position(
handle: *const WindowAdapterRcOpaque,
pos: &euclid::default::Point2D<i32>,
) {
let window_adapter = &*(handle as *const Rc<dyn WindowAdapter>);
window_adapter.set_position(crate::api::PhysicalPosition::new(pos.x, pos.y));
window_adapter.set_position(crate::api::PhysicalPosition::new(pos.x, pos.y).into());
}
/// Sets the position of the window on the screen, in physical screen coordinates and including
/// a window frame (if present).
/// Note that on some windowing systems, such as Wayland, this functionality is not available.
#[no_mangle]
pub unsafe extern "C" fn slint_windowrc_set_logical_position(
handle: *const WindowAdapterRcOpaque,
pos: &euclid::default::Point2D<f32>,
) {
let window_adapter = &*(handle as *const Rc<dyn WindowAdapter>);
window_adapter.set_position(crate::api::LogicalPosition::new(pos.x, pos.y).into());
}
/// Returns the size of the window on the screen, in physical screen coordinates and excluding
@ -947,11 +961,22 @@ pub mod ffi {
/// Resizes the window to the specified size on the screen, in physical pixels and excluding
/// a window frame (if present).
#[no_mangle]
pub unsafe extern "C" fn slint_windowrc_set_size(
pub unsafe extern "C" fn slint_windowrc_set_physical_size(
handle: *const WindowAdapterRcOpaque,
size: &IntSize,
) {
let window_adapter = &*(handle as *const Rc<dyn WindowAdapter>);
window_adapter.set_inner_size(crate::api::PhysicalSize::new(size.width, size.height));
window_adapter.set_size(crate::api::PhysicalSize::new(size.width, size.height).into());
}
/// Resizes the window to the specified size on the screen, in physical pixels and excluding
/// a window frame (if present).
#[no_mangle]
pub unsafe extern "C" fn slint_windowrc_set_logical_size(
handle: *const WindowAdapterRcOpaque,
size: &Size,
) {
let window_adapter = &*(handle as *const Rc<dyn WindowAdapter>);
window_adapter.set_size(crate::api::LogicalSize::new(size.width, size.height).into());
}
}