diff --git a/gui/src/rt/context.rs b/gui/src/rt/context.rs index 95074c8cd..4a8be562b 100644 --- a/gui/src/rt/context.rs +++ b/gui/src/rt/context.rs @@ -59,12 +59,14 @@ impl<'a> RuntimeContext<'a> { /// # Panics /// If this call has been nested. - pub(super) fn run(&mut self, f: impl FnOnce()) { + pub(super) fn run(&mut self, f: impl FnOnce() -> R) -> R { assert!(CONTEXT.get().is_null()); CONTEXT.set(unsafe { transmute(self) }); - f(); + let r = f(); CONTEXT.set(null_mut()); + + r } } diff --git a/gui/src/rt/mod.rs b/gui/src/rt/mod.rs index 88c2b40df..ff1831a08 100644 --- a/gui/src/rt/mod.rs +++ b/gui/src/rt/mod.rs @@ -101,6 +101,29 @@ impl Runtime { true } + + fn redraw(&mut self, el: &ActiveEventLoop, win: WindowId) { + // Get target window. + let win = match self.windows.get(&win).unwrap().upgrade() { + Some(v) => v, + None => return, + }; + + // Setup context. + let mut cx = RuntimeContext { + el, + windows: &mut self.windows, + on_close: &mut self.on_close, + }; + + // Redraw. + let e = match cx.run(move || win.redraw()) { + Ok(_) => return, + Err(e) => e, + }; + + todo!() + } } impl ApplicationHandler for Runtime { @@ -127,7 +150,7 @@ impl ApplicationHandler for Runtime { match event { WindowEvent::CloseRequested => self.on_close.raise(window_id, ()), WindowEvent::Destroyed => drop(self.windows.remove(&window_id)), - WindowEvent::RedrawRequested => todo!(), + WindowEvent::RedrawRequested => self.redraw(event_loop, window_id), _ => {} } } diff --git a/gui/src/rt/window.rs b/gui/src/rt/window.rs index addc9d902..3520f8d7d 100644 --- a/gui/src/rt/window.rs +++ b/gui/src/rt/window.rs @@ -1,2 +1,6 @@ +use std::error::Error; + /// Encapsulates winit window with application-specific logic. -pub trait RuntimeWindow {} +pub trait RuntimeWindow { + fn redraw(&self) -> Result<(), Box>; +} diff --git a/gui/src/ui/backend/window.rs b/gui/src/ui/backend/window.rs index d6c7b7841..e98e794cf 100644 --- a/gui/src/ui/backend/window.rs +++ b/gui/src/ui/backend/window.rs @@ -6,6 +6,7 @@ use slint::platform::{Renderer, WindowAdapter}; use slint::{PhysicalSize, PlatformError}; use std::any::Any; use std::cell::Cell; +use std::error::Error; use std::rc::Rc; use winit::window::WindowId; @@ -36,7 +37,17 @@ impl Window { } } -impl RuntimeWindow for Window {} +impl RuntimeWindow for Window { + fn redraw(&self) -> Result<(), Box> { + // Wayland will show the window on the first render so we need to check visibility flag + // here. + if self.visible.get().is_some_and(|v| v) { + self.renderer.render()?; + } + + Ok(()) + } +} impl WindowAdapter for Window { fn window(&self) -> &slint::Window {