diff options
Diffstat (limited to 'src/camera.rs')
| -rw-r--r-- | src/camera.rs | 112 |
1 files changed, 72 insertions, 40 deletions
diff --git a/src/camera.rs b/src/camera.rs index 695baf5..d10c92e 100644 --- a/src/camera.rs +++ b/src/camera.rs @@ -1,9 +1,10 @@ use crate::{ - config::{PIXEL_BUFFER_HEIGHT, PIXEL_BUFFER_WIDTH}, + Input, + config::{CAMERA_MOVEMENT_SPEED, PIXEL_BUFFER_HEIGHT, PIXEL_BUFFER_WIDTH}, sim::{board::Board, materials::MATERIALS}, }; -pub struct CameraState { +pub struct Camera { // centre coords pub x: f64, pub y: f64, @@ -11,48 +12,79 @@ pub struct CameraState { pub zoom: f64, } -pub fn screen_position_to_board( - board: &Board, - camera: &CameraState, - screen_x: f64, - screen_y: f64, -) -> (f64, f64) { - let camera_width = camera.zoom * f64::from(board.size_x); - let camera_height = camera.zoom * f64::from(board.size_y); - let camera_start_x = camera.x - camera_width / 2.0; - let camera_start_y = camera.y - camera_height / 2.0; - ( - (screen_x / PIXEL_BUFFER_WIDTH as f64 * camera_width) + camera_start_x, - (screen_y / PIXEL_BUFFER_HEIGHT as f64 * camera_height) + camera_start_y, - ) -} +impl Camera { + pub fn handle_camera_input(&mut self, input: &Input, delta_time: f32) { + // wasd movement + let x = if input.is_left_pressed { + -CAMERA_MOVEMENT_SPEED + } else if input.is_right_pressed { + CAMERA_MOVEMENT_SPEED + } else { + 0.0 + }; + let y = if input.is_down_pressed { + CAMERA_MOVEMENT_SPEED + } else if input.is_up_pressed { + -CAMERA_MOVEMENT_SPEED + } else { + 0.0 + }; + + if x == 0.0 && y == 0.0 { + return; + } + + let magnitude = (x.powi(2) + y.powi(2)).sqrt(); + let adjusted_x = x / magnitude * self.zoom as f32 * CAMERA_MOVEMENT_SPEED * delta_time; + let adjusted_y = y / magnitude * self.zoom as f32 * CAMERA_MOVEMENT_SPEED * delta_time; + + self.x += adjusted_x as f64; + self.y += adjusted_y as f64; + } + + pub fn screen_position_to_board( + &self, + board: &Board, + screen_x: f64, + screen_y: f64, + ) -> (f64, f64) { + let camera_width = self.zoom * f64::from(board.size_x); + let camera_height = self.zoom * f64::from(board.size_y); + let camera_start_x = self.x - camera_width / 2.0; + let camera_start_y = self.y - camera_height / 2.0; + ( + (screen_x / PIXEL_BUFFER_WIDTH as f64 * camera_width) + camera_start_x, + (screen_y / PIXEL_BUFFER_HEIGHT as f64 * camera_height) + camera_start_y, + ) + } -pub fn write_frame_view( - frame: &mut [u8], - board: &Board, - camera: &CameraState, - get_overlay: impl Fn(i32, i32) -> (u8, u8, u8, u8), -) { - for frame_y in 0..PIXEL_BUFFER_HEIGHT { - for frame_x in 0..PIXEL_BUFFER_WIDTH { - let (x_coord, y_coord) = - screen_position_to_board(board, camera, frame_x as f64, frame_y as f64); + pub fn write_frame_view( + &self, + frame: &mut [u8], + board: &Board, + get_overlay: impl Fn(i32, i32) -> (u8, u8, u8, u8), + ) { + for frame_y in 0..PIXEL_BUFFER_HEIGHT { + for frame_x in 0..PIXEL_BUFFER_WIDTH { + let (x_coord, y_coord) = + self.screen_position_to_board(board, frame_x as f64, frame_y as f64); - let cell = board.cell_at_position(x_coord as i32, y_coord as i32); - let cell_color: Option<(u8, u8, u8, u8)> = cell.map(|c| { - let m = MATERIALS[c.material as usize]; - (m.r, m.g, m.b, 0xFF) - }); - let off_grid_color: (u8, u8, u8, u8) = (0x00, 0x00, 0x00, 0xFF); + let cell = board.cell_at_position(x_coord as i32, y_coord as i32); + let cell_color: Option<(u8, u8, u8, u8)> = cell.map(|c| { + let m = MATERIALS[c.material as usize]; + (m.r, m.g, m.b, 0xFF) + }); + let off_grid_color: (u8, u8, u8, u8) = (0x00, 0x00, 0x00, 0xFF); - let target_color: (u8, u8, u8, u8) = cell_color.unwrap_or(off_grid_color); - let overlay = get_overlay(x_coord as i32, y_coord as i32); + let target_color: (u8, u8, u8, u8) = cell_color.unwrap_or(off_grid_color); + let overlay = get_overlay(x_coord as i32, y_coord as i32); - let frame_idx = ((frame_y * PIXEL_BUFFER_WIDTH + frame_x) * 4) as usize; - frame[frame_idx] = target_color.0.saturating_add(overlay.0); - frame[frame_idx + 1] = target_color.1.saturating_add(overlay.1); - frame[frame_idx + 2] = target_color.2.saturating_add(overlay.2); - frame[frame_idx + 3] = target_color.3.saturating_add(overlay.3); + let frame_idx = ((frame_y * PIXEL_BUFFER_WIDTH + frame_x) * 4) as usize; + frame[frame_idx] = target_color.0.saturating_add(overlay.0); + frame[frame_idx + 1] = target_color.1.saturating_add(overlay.1); + frame[frame_idx + 2] = target_color.2.saturating_add(overlay.2); + frame[frame_idx + 3] = target_color.3.saturating_add(overlay.3); + } } } } |
