From 6937f39b929d7dc9129104a8f86aa9a56b71a1c0 Mon Sep 17 00:00:00 2001 From: Avery Radmacher Date: Thu, 2 May 2024 09:26:40 -0400 Subject: [PATCH 1/2] Factor out active monitor detection --- crates/egui-winit/src/window_settings.rs | 25 ++++++++++++++++++++---- 1 file changed, 21 insertions(+), 4 deletions(-) diff --git a/crates/egui-winit/src/window_settings.rs b/crates/egui-winit/src/window_settings.rs index c59a0f451ce..8b55b8ae3f5 100644 --- a/crates/egui-winit/src/window_settings.rs +++ b/crates/egui-winit/src/window_settings.rs @@ -127,12 +127,12 @@ impl WindowSettings { } } -fn clamp_pos_to_monitors( +fn find_active_monitor( egui_zoom_factor: f32, event_loop: &winit::event_loop::EventLoopWindowTarget, window_size_pts: egui::Vec2, - position_px: &mut egui::Pos2, -) { + position_px: &egui::Pos2, +) -> Option { crate::profile_function!(); let monitors = event_loop.available_monitors(); @@ -142,7 +142,7 @@ fn clamp_pos_to_monitors( .primary_monitor() .or_else(|| event_loop.available_monitors().next()) else { - return; // no monitors 🤷 + return None; // no monitors 🤷 }; for monitor in monitors { @@ -159,6 +159,23 @@ fn clamp_pos_to_monitors( } } + Some(active_monitor) +} + +fn clamp_pos_to_monitors( + egui_zoom_factor: f32, + event_loop: &winit::event_loop::EventLoopWindowTarget, + window_size_pts: egui::Vec2, + position_px: &mut egui::Pos2, +) { + crate::profile_function!(); + + let Some(active_monitor) = + find_active_monitor(egui_zoom_factor, event_loop, window_size_pts, position_px) + else { + return; // no monitors 🤷 + }; + let mut window_size_px = window_size_pts * (egui_zoom_factor * active_monitor.scale_factor() as f32); // Add size of title bar. This is 32 px by default in Win 10/11. From 9aeb724716eae70c9fb470c2135e89acf0b28f21 Mon Sep 17 00:00:00 2001 From: Avery Radmacher Date: Thu, 2 May 2024 09:28:46 -0400 Subject: [PATCH 2/2] Convert window position to logical coordinates `ViewportBuilder` expects position to be in logical coordinates, but it was being passed in pixels. To fix, scale by the active monitor size and `egui_zoom_factor`. --- crates/eframe/src/native/epi_integration.rs | 6 +++++- crates/egui-winit/src/window_settings.rs | 14 ++++++++++++-- 2 files changed, 17 insertions(+), 3 deletions(-) diff --git a/crates/eframe/src/native/epi_integration.rs b/crates/eframe/src/native/epi_integration.rs index b09f0f0e0c7..bd8346b3e86 100644 --- a/crates/eframe/src/native/epi_integration.rs +++ b/crates/eframe/src/native/epi_integration.rs @@ -39,7 +39,11 @@ pub fn viewport_builder( } window_settings.clamp_position_to_monitors(egui_zoom_factor, event_loop); - viewport_builder = window_settings.initialize_viewport_builder(viewport_builder); + viewport_builder = window_settings.initialize_viewport_builder( + egui_zoom_factor, + event_loop, + viewport_builder, + ); window_settings.inner_size_points() } else { if let Some(pos) = viewport_builder.position { diff --git a/crates/egui-winit/src/window_settings.rs b/crates/egui-winit/src/window_settings.rs index 8b55b8ae3f5..ec633d3df0a 100644 --- a/crates/egui-winit/src/window_settings.rs +++ b/crates/egui-winit/src/window_settings.rs @@ -50,8 +50,10 @@ impl WindowSettings { self.inner_size_points } - pub fn initialize_viewport_builder( + pub fn initialize_viewport_builder( &self, + egui_zoom_factor: f32, + event_loop: &winit::event_loop::EventLoopWindowTarget, mut viewport_builder: ViewportBuilder, ) -> ViewportBuilder { crate::profile_function!(); @@ -64,7 +66,15 @@ impl WindowSettings { self.outer_position_pixels }; if let Some(pos) = pos_px { - viewport_builder = viewport_builder.with_position(pos); + let monitor_scale_factor = if let Some(inner_size_points) = self.inner_size_points { + find_active_monitor(egui_zoom_factor, event_loop, inner_size_points, &pos) + .map_or(1.0, |monitor| monitor.scale_factor() as f32) + } else { + 1.0 + }; + + let scaled_pos = pos / (egui_zoom_factor * monitor_scale_factor); + viewport_builder = viewport_builder.with_position(scaled_pos); } if let Some(inner_size_points) = self.inner_size_points {