From 8041c7e01d88a1997f2ca3c1ad4727b04ec12aa8 Mon Sep 17 00:00:00 2001 From: reo Date: Sat, 13 Dec 2025 18:23:52 +0300 Subject: [PATCH] Fix awkward mouse conflict issues between egui and the engine --- game/src/main.rs | 5 +++++ game/src/systems/menu.rs | 6 +++++- glium_platform/src/platform.rs | 8 +++++++- glium_platform/src/render/egui.rs | 32 +++++++++++++++++++++++++++++-- glium_platform/src/system.rs | 2 ++ platform/src/context.rs | 4 ++++ 6 files changed, 53 insertions(+), 4 deletions(-) diff --git a/game/src/main.rs b/game/src/main.rs index b49445c..0f84666 100644 --- a/game/src/main.rs +++ b/game/src/main.rs @@ -106,6 +106,11 @@ impl System for MainSystem { character_pos = tr.translation; } egui_queue.queue(move |egui_ctx| { + // disable text selection on all labels. + egui_ctx.style_mut(|style| { + style.interaction.selectable_labels = false; + }); + egui::Window::new("Debug").show(egui_ctx, |ui| { ui.label("Hello World!"); ui.label(format!("Frame Delta: {:.3}", time_ctx.frame_dt)); diff --git a/game/src/systems/menu.rs b/game/src/systems/menu.rs index 60350b7..8a4b0d5 100644 --- a/game/src/systems/menu.rs +++ b/game/src/systems/menu.rs @@ -42,6 +42,7 @@ impl System for MenuSystem { }); } + fn handle_event(&mut self, res: &mut EngineResources, scene: &mut Scene) { // The menu is toggled by pressing the escape key let input = res.get::().unwrap(); @@ -63,18 +64,21 @@ impl MenuSystem { .next() .unwrap(); - let window = res.get::().unwrap().window.lock().unwrap(); + let pctx = res.get::().unwrap(); + let window = pctx.window.lock().unwrap(); match *menu_state { MenuState::Open => { *menu_state = MenuState::Closed; window.set_cursor_grab(CursorGrabMode::Confined).or_else(|_| window.set_cursor_grab(CursorGrabMode::Locked)); window.set_cursor_visible(false); + pctx.should_egui_receive_input_events.set(false); }, MenuState::Closed => { *menu_state = MenuState::Open; window.set_cursor_grab(CursorGrabMode::None); window.set_cursor_visible(true); + pctx.should_egui_receive_input_events.set(true); }, } } diff --git a/glium_platform/src/platform.rs b/glium_platform/src/platform.rs index bb1e192..b67ef77 100644 --- a/glium_platform/src/platform.rs +++ b/glium_platform/src/platform.rs @@ -1,4 +1,4 @@ -use std::cell::RefCell; +use std::cell::{RefCell, Cell}; use std::rc::Rc; use std::sync::{Arc, Mutex, RwLock}; use raidillon_platform::{Platform, PlatformContext, TimeContext}; @@ -31,6 +31,8 @@ pub struct GliumPlatform> { time: time::Time, egui_queue: Rc>, settings: Arc>, + /// Used for [`raidillon_platform::context::PlatformContext::should_egui_receive_input_events`] + should_egui_receive_input_events: Rc>, } impl> Platform for GliumPlatform { @@ -64,6 +66,7 @@ impl> Platform for GliumPlatfor Settings::load_or_default(default_config_path()).unwrap() ) ); + let should_egui_receive_input_events = Rc::new(Cell::new(false)); Self { event_loop, @@ -75,6 +78,7 @@ impl> Platform for GliumPlatfor time, egui_queue, settings, + should_egui_receive_input_events, } } @@ -92,6 +96,7 @@ impl> Platform for GliumPlatfor window: self.window.clone(), egui_queue: self.egui_queue.clone(), settings: self.settings.clone(), + should_egui_receive_input_events: self.should_egui_receive_input_events.clone(), }; self.engine.initialize(ctx.clone()); self.settings.read().unwrap().display_settings.apply(&*self.window.lock().unwrap()); @@ -136,6 +141,7 @@ impl> Platform for GliumPlatfor window: self.window.clone(), egui_queue: self.egui_queue.clone(), env_light_dir: Vec3::new(0.0, -1.0, 0.0), + should_egui_receive_input_events: self.should_egui_receive_input_events.clone(), }; self.rendering_system_manager diff --git a/glium_platform/src/render/egui.rs b/glium_platform/src/render/egui.rs index e754ba3..3cd0583 100644 --- a/glium_platform/src/render/egui.rs +++ b/glium_platform/src/render/egui.rs @@ -8,9 +8,12 @@ use crate::system::RenderingContext; use egui_glium::EguiGlium; use winit::event::{Event, WindowEvent}; use winit::event_loop::EventLoop; +use std::cell::Cell; +use std::rc::Rc; pub struct EguiRenderer { egui_glium: EguiGlium, + should_egui_receive_input_events: Option>>, } impl RenderingSystem for EguiRenderer { @@ -21,10 +24,14 @@ impl RenderingSystem for EguiRenderer { let window = window.lock().unwrap(); let egui_glium = EguiGlium::new(ViewportId::ROOT, &display, &window, &event_loop); - Self { egui_glium } + Self { egui_glium: egui_glium, should_egui_receive_input_events: None } } fn render(&mut self, ctx: &mut RenderingContext) { + if self.should_egui_receive_input_events.is_none() { + self.should_egui_receive_input_events = Some(ctx.should_egui_receive_input_events.clone()); + } + let window = ctx.window.lock().unwrap(); self.egui_glium.run(&window, |egui_ctx| { @@ -38,7 +45,28 @@ impl RenderingSystem for EguiRenderer { let window = window.lock().unwrap(); match event { Event::WindowEvent { event, .. } => { - let _ = self.egui_glium.on_event(&window, &event); + let should_egui_receive_input_events = match self.should_egui_receive_input_events.as_ref() { + Some(v) => v.get(), + None => true, + }; + + let should_send_event = if should_egui_receive_input_events { + true + } else { + !matches!(event, + WindowEvent::KeyboardInput { .. } | + WindowEvent::ModifiersChanged(_) | + WindowEvent::CursorMoved { .. } | + WindowEvent::MouseInput { .. } | + WindowEvent::MouseWheel { .. } | + WindowEvent::Touch(_) | + WindowEvent::Ime(_) + ) + }; + + if should_send_event { + let _ = self.egui_glium.on_event(&window, &event); + } } _ => {}, } diff --git a/glium_platform/src/system.rs b/glium_platform/src/system.rs index d94e9c3..92fd553 100644 --- a/glium_platform/src/system.rs +++ b/glium_platform/src/system.rs @@ -10,6 +10,7 @@ use raidillon_core::{define_typemap, EguiQueue}; use raidillon_core::scene::Scene; use glam::Vec3; use winit::event_loop::EventLoop; +use std::cell::Cell; pub struct RenderingContext<'a> { pub scene: &'a Scene, @@ -19,6 +20,7 @@ pub struct RenderingContext<'a> { pub asset_manager: ModelManagerRef, pub egui_queue: Rc>, pub env_light_dir: Vec3, + pub should_egui_receive_input_events: Rc> } /// The internal "rendering system" trait of glium_platform. diff --git a/platform/src/context.rs b/platform/src/context.rs index fdbe087..0990527 100644 --- a/platform/src/context.rs +++ b/platform/src/context.rs @@ -1,3 +1,4 @@ +use std::cell::Cell; use std::{cell::RefCell, rc::Rc}; use std::sync::{Arc, Mutex, RwLock}; use winit::event::Event; @@ -15,6 +16,9 @@ pub struct PlatformContext { pub window: Arc>, pub egui_queue: Rc>, pub settings: Arc>, + /// Sets whether or not egui will receive input events. + /// Added to prevent the mouse state conflict between the engine and egui. + pub should_egui_receive_input_events: Rc>, } #[derive(Clone)]