diff --git a/rtchallenge/src/camera.rs b/rtchallenge/src/camera.rs new file mode 100644 index 0000000..55a8604 --- /dev/null +++ b/rtchallenge/src/camera.rs @@ -0,0 +1,73 @@ +use crate::matrices::Matrix4x4; + +pub struct Camera { + hsize: usize, + vsize: usize, + field_of_view: f32, + transform: Matrix4x4, + pixel_size: f32, + half_width: f32, + half_height: f32, +} + +impl Camera { + /// Create a camera with a canvas of pixel hsize (height) and vsize (width) + /// with the given field of view (in radians). + /// + /// # Examples + /// ``` + /// use std::f32::consts::PI; + /// + /// use rtchallenge::{camera::Camera, matrices::Matrix4x4}; + /// + /// let hsize = 160; + /// let vsize = 120; + /// let field_of_view = PI / 2.; + /// let c = Camera::new(hsize, vsize, field_of_view); + /// assert_eq!(c.hsize(), 160); + /// assert_eq!(c.vsize(), 120); + /// assert_eq!(c.transform(), Matrix4x4::identity()); + /// + /// // Pixel size for a horizontal canvas. + /// let c = Camera::new(200, 150, PI / 2.); + /// assert_eq!(c.pixel_size(), 0.01); + /// + /// // Pixel size for a horizontal canvas. + /// let c = Camera::new(150, 200, PI / 2.); + /// assert_eq!(c.pixel_size(), 0.01); + /// ``` + pub fn new(hsize: usize, vsize: usize, field_of_view: f32) -> Camera { + let half_view = (field_of_view / 2.).tan(); + let aspect = hsize as f32 / vsize as f32; + let (half_width, half_height) = if aspect >= 1. { + (half_view, half_view / aspect) + } else { + (half_view * aspect, half_view) + }; + let pixel_size = 2. * half_width / hsize as f32; + Camera { + hsize, + vsize, + field_of_view, + transform: Matrix4x4::identity(), + pixel_size, + half_height, + half_width, + } + } + pub fn hsize(&self) -> usize { + self.hsize + } + pub fn vsize(&self) -> usize { + self.vsize + } + pub fn field_of_view(&self) -> f32 { + self.field_of_view + } + pub fn transform(&self) -> Matrix4x4 { + self.transform + } + pub fn pixel_size(&self) -> f32 { + self.pixel_size + } +} diff --git a/rtchallenge/src/lib.rs b/rtchallenge/src/lib.rs index f4ff091..d941f0c 100644 --- a/rtchallenge/src/lib.rs +++ b/rtchallenge/src/lib.rs @@ -1,3 +1,4 @@ +pub mod camera; pub mod canvas; pub mod intersections; pub mod lights;