From 516d6420790e3cf3f168bfcbce88bcf9fbd18e17 Mon Sep 17 00:00:00 2001 From: Max Ammann Date: Tue, 13 Dec 2022 17:52:02 +0100 Subject: [PATCH] Define a minimum and maximum pitch (#149) --- maplibre-winit/src/input/tilt_handler.rs | 7 +--- maplibre/src/render/camera.rs | 51 ++++++++++++++---------- 2 files changed, 32 insertions(+), 26 deletions(-) diff --git a/maplibre-winit/src/input/tilt_handler.rs b/maplibre-winit/src/input/tilt_handler.rs index 8d01bc5e..0cf8e222 100644 --- a/maplibre-winit/src/input/tilt_handler.rs +++ b/maplibre-winit/src/input/tilt_handler.rs @@ -16,10 +16,7 @@ impl UpdateState for TiltHandler { fn update_state( &mut self, MapContext { - world: World { - view_state: _view_state, - .. - }, + world: World { view_state, .. }, .. }: &mut MapContext, dt: Duration, @@ -27,7 +24,7 @@ impl UpdateState for TiltHandler { let dt = dt.as_secs_f64() * (1.0 / self.speed); let delta = self.delta_pitch * dt; - _view_state.camera_mut().pitch_self(delta); + view_state.camera_mut().tilt(delta); self.delta_pitch -= delta; } } diff --git a/maplibre/src/render/camera.rs b/maplibre/src/render/camera.rs index 1be13249..e180c163 100644 --- a/maplibre/src/render/camera.rs +++ b/maplibre/src/render/camera.rs @@ -66,6 +66,9 @@ impl ModelViewProjection { } } +const MIN_PITCH: Rad = Rad(-0.5); +const MAX_PITCH: Rad = Rad(0.5); + #[derive(Debug, Clone)] pub struct Camera { position: Point3, // The z axis never changes, the zoom is used instead @@ -87,7 +90,7 @@ impl SignificantlyDifferent for Camera { } impl Camera { - pub fn new>, Y: Into>, P: Into>>( + pub fn new>, Y: Into>, P: Into>>( position: V, yaw: Y, pitch: P, @@ -103,14 +106,6 @@ impl Camera { } } - pub fn move_to(&mut self, point: Point3) { - self.position = point; - } - - pub fn move_relative(&mut self, delta: Vector3) { - self.position += delta; - } - pub fn resize(&mut self, width: u32, height: u32) { self.width = width as f64; self.height = height as f64; @@ -364,7 +359,7 @@ impl Camera { self.yaw } - pub fn yaw_self>>(&mut self, delta: P) { + pub fn rotate>>(&mut self, delta: P) { self.yaw += delta.into(); } @@ -372,13 +367,33 @@ impl Camera { self.pitch } - pub fn pitch_self>>(&mut self, delta: P) { - self.pitch += delta.into(); + pub fn tilt>>(&mut self, delta: P) { + let new_pitch = self.pitch + delta.into(); + + if new_pitch <= MAX_PITCH && new_pitch >= MIN_PITCH { + self.pitch = new_pitch; + } + } + + pub fn move_relative(&mut self, delta: Vector3) { + self.position += delta; + } + + pub fn move_to(&mut self, new_position: Point3) { + self.position = new_position; + } + + pub fn position_vector(&self) -> Vector3 { + self.position.to_vec() + } + + pub fn homogenous_position(&self) -> Vector4 { + self.position.to_homogeneous() } } pub struct Perspective { - fovy: cgmath::Rad, + fovy: Rad, znear: f64, zfar: f64, @@ -386,13 +401,7 @@ pub struct Perspective { } impl Perspective { - pub fn new>>( - width: u32, - height: u32, - fovy: F, - znear: f64, - zfar: f64, - ) -> Self { + pub fn new>>(width: u32, height: u32, fovy: F, znear: f64, zfar: f64) -> Self { let rad = fovy.into(); Self { current_projection: Self::calc_matrix(width as f64 / height as f64, rad, znear, zfar), @@ -411,7 +420,7 @@ impl Perspective { ); } - fn calc_matrix(aspect: f64, fovy: cgmath::Rad, znear: f64, zfar: f64) -> Matrix4 { + fn calc_matrix(aspect: f64, fovy: Rad, znear: f64, zfar: f64) -> Matrix4 { OPENGL_TO_WGPU_MATRIX * cgmath::perspective(fovy, aspect, znear, zfar) } }