From 86686727231a7d7b3650141fa3ad5c2674547148 Mon Sep 17 00:00:00 2001 From: Micha White Date: Thu, 20 Oct 2022 08:55:35 -0400 Subject: Move the event loop into the renderer --- src/renderer.rs | 34 ++++++++++++++++++++++++++-------- 1 file changed, 26 insertions(+), 8 deletions(-) (limited to 'src/renderer.rs') diff --git a/src/renderer.rs b/src/renderer.rs index 4768615..afcb92b 100644 --- a/src/renderer.rs +++ b/src/renderer.rs @@ -52,6 +52,7 @@ pub struct Renderer { instances: InstanceBuffer, camera: Camera, textures: TextureAtlas, + event_loop: Option>, window: Window, } @@ -128,16 +129,15 @@ impl Renderer { /// panic on some platforms. // TODO make it possible to use without a window (ie, use a bitmap in memory as a surface) // TODO this function needs to be smaller - pub fn new( - config: &RenderWindowConfig, - event_loop: &EventLoop<()>, - ) -> Result { + pub fn new(config: &RenderWindowConfig) -> Result { #[cfg(feature = "profile-with-tracy")] profiling::tracy_client::Client::start(); profiling::register_thread!("main"); // build the window - let window = config.to_window().build(event_loop)?; + let event_loop = EventLoop::new(); + let window = config.to_window().build(&event_loop)?; + let event_loop = Some(event_loop); // the instance's main purpose is to create an adapter and a surface let instance = wgpu::Instance::new(wgpu::Backends::VULKAN); @@ -226,6 +226,7 @@ impl Renderer { instances, camera, textures, + event_loop, window, }) } @@ -357,20 +358,37 @@ impl Renderer { Ok(()) } + /// Take the event loop out of the Renderer, without moving it + /// + /// # Panics + /// + /// This method must only be called once + // TODO This is a quick fix to get the event loop inside the renderer. + // In the future, we should make a separate struct that contains the + // renderer and the event loop, which we move the event loop out of + // while still being able to move the renderer. + fn event_loop(&mut self) -> EventLoop<()> { + self.event_loop.take().unwrap() + } + /// Run the renderer indefinitely - pub fn run(mut self, event_loop: EventLoop<()>) -> ! { + pub fn run(mut self, f: &'static dyn Fn(&mut Self)) -> ! { self.window.set_visible(true); + let event_loop = self.event_loop(); event_loop.run(move |event, _, control_flow| match event { Event::WindowEvent { window_id, event } => { if window_id == self.window.id() { match event { WindowEvent::Resized(size) => self.resize_renderer(size), - WindowEvent::CloseRequested => *control_flow = ControlFlow::ExitWithCode(0), + WindowEvent::CloseRequested => { + *control_flow = ControlFlow::ExitWithCode(0); + } _ => (), } } } Event::MainEventsCleared => { + f(&mut self); match self.render() { Ok(_) => {} // reconfigure the surface if it's been lost @@ -387,6 +405,6 @@ impl Renderer { profiling::finish_frame!(); } _ => {} - }) + }); } } -- cgit v1.2.3