diff --git a/eframe/src/epi.rs b/eframe/src/epi.rs index a7c3ece4b726..5e8c1d11c8e7 100644 --- a/eframe/src/epi.rs +++ b/eframe/src/epi.rs @@ -341,6 +341,17 @@ pub struct WebInfo { pub location: Location, } +/// Information about the application's main window, if available. +#[derive(Clone, Debug)] +pub struct WindowInfo { + /// Coordinates of the window's outer top left corner, relative to the top left corner of the first display. + /// Unit: egui points (logical pixels). + pub position: egui::Pos2, + + /// Window inner size in egui points (logical pixels). + pub size: egui::Vec2, +} + /// Information about the URL. /// /// Everything has been percent decoded (`%20` -> ` ` etc). @@ -411,6 +422,9 @@ pub struct IntegrationInfo { /// The OS native pixels-per-point pub native_pixels_per_point: Option<f32>, + + /// Window-specific geometry information, if provided by the platform. + pub window_info: Option<WindowInfo>, } // ---------------------------------------------------------------------------- diff --git a/eframe/src/native/epi_integration.rs b/eframe/src/native/epi_integration.rs index 3f9cd45481fb..3d082fbdedb4 100644 --- a/eframe/src/native/epi_integration.rs +++ b/eframe/src/native/epi_integration.rs @@ -1,4 +1,4 @@ -use crate::epi; +use crate::{epi, WindowInfo}; use egui_winit::{native_pixels_per_point, WindowSettings}; pub fn points_to_size(points: egui::Vec2) -> winit::dpi::LogicalSize<f64> { @@ -8,6 +8,28 @@ pub fn points_to_size(points: egui::Vec2) -> winit::dpi::LogicalSize<f64> { } } +pub fn read_window_info( + window: &winit::window::Window, + pixels_per_point: f32, +) -> Option<WindowInfo> { + match window.outer_position() { + Ok(pos) => { + let pos = pos.to_logical::<f32>(pixels_per_point.into()); + let size = window + .inner_size() + .to_logical::<f32>(pixels_per_point.into()); + Some(WindowInfo { + position: egui::Pos2 { x: pos.x, y: pos.y }, + size: egui::Vec2 { + x: size.width, + y: size.height, + }, + }) + } + Err(_) => None, + } +} + pub fn window_builder( native_options: &epi::NativeOptions, window_settings: &Option<WindowSettings>, @@ -176,6 +198,7 @@ impl EpiIntegration { prefer_dark_mode, cpu_usage: None, native_pixels_per_point: Some(native_pixels_per_point(window)), + window_info: read_window_info(window, egui_ctx.pixels_per_point()), }, output: Default::default(), storage, @@ -238,6 +261,7 @@ impl EpiIntegration { ) -> egui::FullOutput { let frame_start = std::time::Instant::now(); + self.frame.info.window_info = read_window_info(window, self.egui_ctx.pixels_per_point()); let raw_input = self.egui_winit.take_egui_input(window); let full_output = self.egui_ctx.run(raw_input, |egui_ctx| { crate::profile_scope!("App::update"); diff --git a/eframe/src/web/backend.rs b/eframe/src/web/backend.rs index 41608e8a7211..c871cd893c41 100644 --- a/eframe/src/web/backend.rs +++ b/eframe/src/web/backend.rs @@ -152,6 +152,7 @@ impl AppRunner { prefer_dark_mode, cpu_usage: None, native_pixels_per_point: Some(native_pixels_per_point()), + window_info: None, }; let storage = LocalStorage::default();