diff options
Diffstat (limited to 'engine')
| -rw-r--r-- | engine/src/camera/fly.rs | 16 | ||||
| -rw-r--r-- | engine/src/input/mouse.rs | 2 | ||||
| -rw-r--r-- | engine/src/projection.rs | 61 | ||||
| -rw-r--r-- | engine/src/shader/default.rs | 17 | ||||
| -rw-r--r-- | engine/src/windowing.rs | 30 | ||||
| -rw-r--r-- | engine/src/windowing/mouse.rs | 21 |
6 files changed, 95 insertions, 52 deletions
diff --git a/engine/src/camera/fly.rs b/engine/src/camera/fly.rs index 7996b4d..2042c0c 100644 --- a/engine/src/camera/fly.rs +++ b/engine/src/camera/fly.rs @@ -1,15 +1,15 @@ use ecs::component::local::Local; use ecs::phase::UPDATE as UPDATE_PHASE; use ecs::sole::Single; -use ecs::system::initializable::Initializable; use ecs::system::Into; +use ecs::system::initializable::Initializable; use ecs::{Component, Query}; use crate::builder; use crate::camera::{Active as ActiveCamera, Camera}; use crate::delta_time::DeltaTime; use crate::input::keyboard::{Key, Keyboard}; -use crate::input::mouse::Motion as MouseMotion; +use crate::input::mouse::Mouse; use crate::transform::WorldPosition; use crate::vector::{Vec2, Vec3}; @@ -74,7 +74,7 @@ pub struct Options fn update( camera_query: Query<(&mut Camera, &mut WorldPosition, &mut Fly, &ActiveCamera)>, keyboard: Single<Keyboard>, - mouse_motion: Single<MouseMotion>, + mouse: Single<Mouse>, delta_time: Single<DeltaTime>, options: Local<Options>, ) @@ -82,14 +82,12 @@ fn update( for (mut camera, mut camera_world_pos, mut fly_camera, _) in &camera_query { let delta_time = delta_time.duration; - // tracing::info!("Mouse motion: {:?}", mouse_motion.position_delta); - - if mouse_motion.position_delta != (Vec2 { x: 0.0, y: 0.0 }) { + if mouse.curr_tick_position_delta != (Vec2 { x: 0.0, y: 0.0 }) { let x_offset = - mouse_motion.position_delta.x * f64::from(options.mouse_sensitivity); + mouse.curr_tick_position_delta.x * f64::from(options.mouse_sensitivity); - let y_offset = - (-mouse_motion.position_delta.y) * f64::from(options.mouse_sensitivity); + let y_offset = (-mouse.curr_tick_position_delta.y) + * f64::from(options.mouse_sensitivity); fly_camera.current_yaw += x_offset; fly_camera.current_pitch += y_offset; diff --git a/engine/src/input/mouse.rs b/engine/src/input/mouse.rs index 90091f3..c10aaf2 100644 --- a/engine/src/input/mouse.rs +++ b/engine/src/input/mouse.rs @@ -1,6 +1,6 @@ mod reexports { - pub use crate::windowing::mouse::{Button, ButtonState, Buttons, Motion}; + pub use crate::windowing::mouse::{Button, ButtonState, Buttons, Mouse}; } pub use reexports::*; diff --git a/engine/src/projection.rs b/engine/src/projection.rs index 29636e7..46df6d4 100644 --- a/engine/src/projection.rs +++ b/engine/src/projection.rs @@ -1,7 +1,7 @@ use crate::builder; -use crate::data_types::dimens::Dimens3; +use crate::data_types::dimens::Dimens; use crate::matrix::Matrix; -use crate::vector::Vec3; +use crate::vector::Vec2; #[derive(Debug, Clone)] #[non_exhaustive] @@ -25,7 +25,7 @@ impl Perspective /// Creates a perspective projection matrix using right-handed coordinates. #[inline] pub fn to_matrix_rh(&self, aspect: f32, clip_volume: ClipVolume) - -> Matrix<f32, 4, 4> + -> Matrix<f32, 4, 4> { let mut out = Matrix::new(); @@ -55,13 +55,23 @@ impl Default for Perspective } } +#[derive(Debug, Clone)] +pub enum OrthographicSize +{ + FixedSize(Dimens<f32>), + WindowSize, +} + builder! { #[builder(name = OrthographicBuilder, derives=(Debug, Clone))] -#[derive(Debug, Clone, PartialEq, PartialOrd)] +#[derive(Debug, Clone)] #[non_exhaustive] pub struct Orthographic { - pub size: Dimens3<f32>, + pub near: f32, + pub far: f32, + pub viewport_origin: Vec2<f32>, + pub size: OrthographicSize, } } @@ -75,18 +85,28 @@ impl Orthographic /// Creates a orthographic projection matrix using right-handed coordinates. pub fn to_matrix_rh( &self, - center_pos: &Vec3<f32>, + window_size: Dimens<f32>, clip_volume: ClipVolume, ) -> Matrix<f32, 4, 4> { let mut result = Matrix::<f32, 4, 4>::new(); - let left = center_pos.x - (self.size.width / 2.0); - let right = center_pos.x + (self.size.width / 2.0); - let bottom = center_pos.y - (self.size.height / 2.0); - let top = center_pos.y + (self.size.height / 2.0); - let near = center_pos.z - (self.size.depth / 2.0); - let far = center_pos.z + (self.size.depth / 2.0); + let size = match self.size { + OrthographicSize::FixedSize(fixed_size) => fixed_size, + OrthographicSize::WindowSize => window_size, + }; + + let origin_x = size.width * self.viewport_origin.x; + let origin_y = size.height * self.viewport_origin.y; + + let left = -origin_x; + let right = size.width - origin_x; + + let bottom = -origin_y; + let top = size.height - origin_y; + + let near = self.near; + let far = self.far; match clip_volume { ClipVolume::NegOneToOne => { @@ -108,13 +128,7 @@ impl Default for Orthographic { fn default() -> Self { - Self { - size: Dimens3 { - width: 10.0, - height: 7.0, - depth: 10.0, - }, - } + Self::builder().build() } } @@ -122,9 +136,12 @@ impl Default for OrthographicBuilder { fn default() -> Self { - let orthographic = Orthographic::default(); - - OrthographicBuilder { size: orthographic.size } + Self { + near: 0.0, + far: 1000.0, + viewport_origin: Vec2 { x: 0.5, y: 0.5 }, + size: OrthographicSize::WindowSize, + } } } diff --git a/engine/src/shader/default.rs b/engine/src/shader/default.rs index bc8202c..8690eb9 100644 --- a/engine/src/shader/default.rs +++ b/engine/src/shader/default.rs @@ -148,12 +148,7 @@ pub fn enqueue_set_shader_bindings( ), ( model_3d_shader_cursor.field("projection"), - create_projection_matrix( - &camera, - &camera_world_pos.position, - window.inner_size(), - ) - .into(), + create_projection_matrix(&camera, window.inner_size()).into(), ), ( lighting_shader_cursor.field("view_pos"), @@ -340,7 +335,6 @@ fn create_view_matrix(camera: &Camera, camera_world_pos: &Vec3<f32>) fn create_projection_matrix( camera: &Camera, - camera_world_pos: &Vec3<f32>, window_size: &Dimens<u32>, ) -> Matrix<f32, 4, 4> { @@ -349,8 +343,13 @@ fn create_projection_matrix( window_size.width as f32 / window_size.height as f32, ProjectionClipVolume::NegOneToOne, ), - Projection::Orthographic(orthographic_proj) => orthographic_proj - .to_matrix_rh(camera_world_pos, ProjectionClipVolume::NegOneToOne), + Projection::Orthographic(orthographic_proj) => orthographic_proj.to_matrix_rh( + Dimens { + width: window_size.width as f32, + height: window_size.height as f32, + }, + ProjectionClipVolume::NegOneToOne, + ), } } diff --git a/engine/src/windowing.rs b/engine/src/windowing.rs index 2bfdb31..03e0ff8 100644 --- a/engine/src/windowing.rs +++ b/engine/src/windowing.rs @@ -1,12 +1,12 @@ use std::sync::atomic::{AtomicBool, Ordering}; use std::sync::{Arc, Weak}; -use std::thread::{spawn, JoinHandle as ThreadJoinHandle}; +use std::thread::{JoinHandle as ThreadJoinHandle, spawn}; use crossbeam_channel::{ - bounded as bounded_channel, Receiver as ChannelReceiver, Sender as ChannelSender, TrySendError, + bounded as bounded_channel, }; use ecs::actions::Actions; use ecs::component::Component; @@ -17,7 +17,7 @@ use ecs::phase::{Phase, UPDATE as UPDATE_PHASE}; use ecs::sole::Single; use ecs::system::observer::Observe; use ecs::uid::Uid; -use ecs::{declare_entity, Query, Sole}; +use ecs::{Query, Sole, declare_entity}; use raw_window_handle::{DisplayHandle, HandleError, HasDisplayHandle, WindowHandle}; use winit::application::ApplicationHandler; use winit::dpi::PhysicalPosition; @@ -40,7 +40,7 @@ use crate::windowing::mouse::{ Button as MouseButton, ButtonState as MouseButtonState, Buttons as MouseButtons, - Motion as MouseMotion, + Mouse, }; use crate::windowing::window::{ Closed as WindowClosed, @@ -55,7 +55,7 @@ pub mod keyboard; pub mod mouse; pub mod window; -const MESSAGE_FROM_APP_CHANNEL_CAP: usize = 128; +const MESSAGE_FROM_APP_CHANNEL_CAP: usize = 512; const MESSAGE_TO_APP_CHANNEL_CAP: usize = 16; // Increase if more messages are added @@ -80,7 +80,7 @@ impl ecs::extension::Extension for Extension { collector.add_sole(Context::default()).ok(); collector.add_sole(Keyboard::default()).ok(); - collector.add_sole(MouseMotion::default()).ok(); + collector.add_sole(Mouse::default()).ok(); collector.add_sole(MouseButtons::default()).ok(); collector.add_declared_entity(&PHASE); @@ -122,7 +122,7 @@ fn handle_window_creation_ready( fn update_stuff( mut context: Single<Context>, mut keyboard: Single<Keyboard>, - mut mouse_motion: Single<MouseMotion>, + mut mouse: Single<Mouse>, mut mouse_buttons: Single<MouseButtons>, mut actions: Actions, entity_obtainer: EntityObtainer, @@ -130,7 +130,7 @@ fn update_stuff( { keyboard.make_key_states_previous(); mouse_buttons.make_states_previous(); - mouse_motion.position_delta = Vec2::default(); + mouse.curr_tick_position_delta = Vec2::default(); let Context { ref message_from_app_receiver, @@ -221,8 +221,11 @@ fn update_stuff( MessageFromApp::KeyboardKeyStateChanged(key, key_state) => { keyboard.set_key_state(key, key_state); } + MessageFromApp::MouseMovedTo { position } => { + mouse.position = position; + } MessageFromApp::MouseMoved { position_delta } => { - mouse_motion.position_delta += position_delta; + mouse.curr_tick_position_delta += position_delta; } MessageFromApp::MouseButtonStateChanged(mouse_button, mouse_button_state) => { mouse_buttons.set(mouse_button, mouse_button_state); @@ -430,6 +433,10 @@ enum MessageFromApp WindowCloseRequested(WindowId), WindowScaleFactorChanged(WindowId, f64), KeyboardKeyStateChanged(Key, KeyState), + MouseMovedTo + { + position: Vec2<f64>, + }, MouseMoved { position_delta: Vec2<f64>, @@ -616,6 +623,11 @@ impl ApplicationHandler for App keyboard_event.state.into(), )); } + WindowEvent::CursorMoved { device_id: _, position } => { + self.send_message(MessageFromApp::MouseMovedTo { + position: Vec2 { x: position.x, y: position.y }, + }); + } WindowEvent::MouseInput { device_id: _, state, button } => { self.send_message(MessageFromApp::MouseButtonStateChanged( button.into(), diff --git a/engine/src/windowing/mouse.rs b/engine/src/windowing/mouse.rs index 1afe594..0ea04e2 100644 --- a/engine/src/windowing/mouse.rs +++ b/engine/src/windowing/mouse.rs @@ -6,9 +6,17 @@ use crate::vector::Vec2; #[derive(Debug, Default, Clone, Sole)] #[non_exhaustive] -pub struct Motion +pub struct Mouse { - pub position_delta: Vec2<f64>, + /// Change in coordinates this tick. Unit is unspecified and platforms may use + /// different units. Updated automatically by the [`windowing extension`]. + /// + /// [`windowing extension`]: crate::windowing + pub curr_tick_position_delta: Vec2<f64>, + + /// Coordinates in pixels relative to the top-left corner of the window. May have + /// been affected by cursor acceleration + pub position: Vec2<f64>, } /// Mouse buttons. @@ -38,6 +46,15 @@ impl Buttons button_data.previous_state } + /// Returns a iterator that yields buttons and their current states. Only buttons with + /// states is included. + pub fn all_current(&self) -> impl Iterator<Item = (Button, ButtonState)> + { + self.map + .iter() + .map(|(button, button_data)| (button.clone(), button_data.current_state)) + } + pub fn set(&mut self, button: Button, button_state: ButtonState) { let button_data = self.map.entry(button).or_default(); |
