From 2056170f34985d7e0943eabd0a8065cfee99572a Mon Sep 17 00:00:00 2001 From: griffi-gh Date: Sun, 15 Jan 2023 19:31:02 +0100 Subject: [PATCH] camera works --- src/game.rs | 50 ++++++++++++++++++++++++++++++++++++---------- src/game/camera.rs | 24 ++++++++++++++++------ 2 files changed, 57 insertions(+), 17 deletions(-) diff --git a/src/game.rs b/src/game.rs index 93e6991..8059892 100644 --- a/src/game.rs +++ b/src/game.rs @@ -1,6 +1,6 @@ use glium::{Surface, uniform}; use glium::glutin::{ - event::{Event, WindowEvent}, + event::{Event, WindowEvent, VirtualKeyCode}, event_loop::{EventLoop, ControlFlow}, }; @@ -24,22 +24,17 @@ pub fn run() { log::info!("loading assets"); let assets = Assets::load_all_sync(&display); log::info!("init camera"); - let camera = Camera { - position: [0., 0., -1.], - direction: [0., 0., 1.], - ..Default::default() - }; + let mut camera = Camera::default(); log::info!("game loaded"); //======================= - let vertex1 = ChunkVertex { position: [-0.5, -0.5, 1.], uv: [0., 0.], normal: [0., 1., 0.] }; - let vertex2 = ChunkVertex { position: [ 0.0, 0.5, 1.], uv: [0., 1.], normal: [0., 1., 0.] }; - let vertex3 = ChunkVertex { position: [ 0.5, -0.25, 1.], uv: [1., 1.], normal: [0., 1., 0.] }; + let vertex1 = ChunkVertex { position: [-0.5, -0.5, 0.], uv: [0., 0.], normal: [0., 1., 0.] }; + let vertex2 = ChunkVertex { position: [ 0.0, 0.5, 0.], uv: [0., 1.], normal: [0., 1., 0.] }; + let vertex3 = ChunkVertex { position: [ 0.5, -0.25, 0.], uv: [1., 1.], normal: [0., 1., 0.] }; let shape = vec![vertex1, vertex2, vertex3]; let vertex_buffer = glium::VertexBuffer::new(&display, &shape).unwrap(); //======================= - event_loop.run(move |ev, _, control_flow| { #[allow(clippy::single_match, clippy::collapsible_match)] match ev { @@ -49,12 +44,45 @@ pub fn run() { *control_flow = ControlFlow::Exit; return }, + WindowEvent::KeyboardInput { input, .. } => { + match input.virtual_keycode { + Some(VirtualKeyCode::Up) => { + camera.pitch += 0.01; + } + Some(VirtualKeyCode::Down) => { + camera.pitch -= 0.01; + } + Some(VirtualKeyCode::Right) => { + camera.yaw -= 0.01; + } + Some(VirtualKeyCode::Left) => { + camera.yaw += 0.01; + } + + Some(VirtualKeyCode::W) => { + camera.position[2] += 0.01; + } + Some(VirtualKeyCode::S) => { + camera.position[2] -= 0.01; + } + Some(VirtualKeyCode::A) => { + camera.position[0] -= 0.01; + } + Some(VirtualKeyCode::D) => { + camera.position[0] += 0.01; + } + + _ => () + } + } _ => () }, _ => () } + let mut target = display.draw(); let target_dimensions = target.get_dimensions(); + camera.update_direction(); let perspective = camera.perspective_matrix(target_dimensions); let view = camera.view_matrix(); target.clear_color_and_depth((0.5, 0.5, 1., 1.), 1.); @@ -67,7 +95,7 @@ pub fn run() { [1., 0., 0., 0.], [0., 1., 0., 0.], [0., 0., 1., 0.], - [0., 0., 0., 1.0f32] + [0., 0., 0., 1.0_f32] ], view: view, perspective: perspective, diff --git a/src/game/camera.rs b/src/game/camera.rs index df9e9ef..bf36fc9 100644 --- a/src/game/camera.rs +++ b/src/game/camera.rs @@ -6,6 +6,8 @@ use std::f32::consts::PI; pub struct Camera { + pub yaw: f32, + pub pitch: f32, pub position: [f32; 3], pub direction: [f32; 3], pub up: [f32; 3], @@ -14,6 +16,15 @@ pub struct Camera { pub zfar: f32, } impl Camera { + /// Update camera direction based on yaw/pitch + pub fn update_direction(&mut self) { + self.direction = [ + self.yaw.cos() * self.pitch.cos(), + self.pitch.sin(), + self.yaw.sin() * self.pitch.cos(), + ]; + } + pub fn view_matrix(&self) -> [[f32; 4]; 4] { let position = self.position; let direction = self.direction; @@ -55,14 +66,13 @@ impl Camera { let aspect_ratio = height as f32 / width as f32; let f = 1.0 / (fov / 2.0).tan(); [ - [f * aspect_ratio , 0.0, 0.0 , 0.0], - [ 0.0 , f , 0.0 , 0.0], - [ 0.0 , 0.0, (zfar+znear)/(zfar-znear) , 1.0], - [ 0.0 , 0.0, -(2.0*zfar*znear)/(zfar-znear), 0.0], + [f*aspect_ratio, 0.0, 0.0, 0.0], + [0.0, f, 0.0, 0.0], + [0.0, 0.0, (zfar+znear)/(zfar-znear), 1.0], + [0.0, 0.0, -(2.0*zfar*znear)/(zfar-znear), 0.0], ] - } + } } - impl Default for Camera { fn default() -> Self { Self { @@ -72,6 +82,8 @@ impl Default for Camera { fov: PI / 3., zfar: 1024., znear: 0.1, + yaw: 0., + pitch: 0., } } }