use crate::display::window::Window; use crate::renderer::{vulkan::VkRenderContext, Renderable}; use winit::application::ApplicationHandler; use winit::event::WindowEvent; use winit::event_loop::ActiveEventLoop; use winit::window::WindowId; use crate::scene::TriangleScene; pub struct App { window: Window, render_context: Option, scene: Option>, } impl App { pub fn new(window: Window) -> Self { Self { window, render_context: None, scene: None, } } pub fn set_scene(&mut self, mut scene: Box) { let result = self.render_context.as_mut() .ok_or_else(|| anyhow::anyhow!("No render context")) .and_then(|render_context| render_context.init_scene(&mut scene)); match result { Ok(_) => self.scene = Some(scene), Err(err) => log::warn!("{err}"), } } } impl ApplicationHandler for App { fn resumed(&mut self, event_loop: &ActiveEventLoop) { self.window .create_window(event_loop) .map_err(|err| format!("Failed to create window: {}", err)) .unwrap(); self.render_context = VkRenderContext::init(&self.window).ok(); let scene = TriangleScene::new(); self.set_scene(Box::new(scene)); } fn window_event(&mut self, event_loop: &ActiveEventLoop, _id: WindowId, event: WindowEvent) { match event { WindowEvent::CloseRequested => { match self.render_context.as_ref() { Some(render_context) => render_context.exit(), None => log::warn!("Window closed but no render context found"), }; log::debug!("The close button was pressed; stopping"); event_loop.exit(); } WindowEvent::Resized(size) => { match self.render_context.as_mut() { Some(render_context) => { if let Err(error) = render_context.update_resolution(size.width, size.height) { log::error!( "Failed to update resolution of render context : {}", error ); } } None => log::warn!("Window resized but no render context found"), }; } WindowEvent::RedrawRequested => { if !event_loop.exiting() { match self.render_context.as_mut() { Some(render_context) => { if let Err(error) = render_context.render(self.scene.as_ref()) { log::error!("Failed to render with render context : {}", error); event_loop.exit(); } } None => log::warn!("Window resized but no render context found"), }; } self.window.request_redraw(); } _ => {} } } }