|
|
@@ -0,0 +1,94 @@ |
|
|
|
use std::ops::*; |
|
|
|
use std::f32; |
|
|
|
use image::Rgb; |
|
|
|
|
|
|
|
#[derive(Clone, Copy, Debug)] |
|
|
|
pub struct Vec3(f32, f32, f32); |
|
|
|
|
|
|
|
impl Vec3 { |
|
|
|
pub fn new(x: f32, y: f32, z: f32) -> Vec3 { |
|
|
|
Vec3(x, y, z) |
|
|
|
} |
|
|
|
|
|
|
|
pub fn length(&self) -> f32 { |
|
|
|
(self.squared_length()).sqrt() |
|
|
|
} |
|
|
|
|
|
|
|
pub fn squared_length(&self) -> f32 { |
|
|
|
self.0 * self.0 + self.1 * self.1 + self.2 * self.2 |
|
|
|
} |
|
|
|
|
|
|
|
pub fn dot(&self, other: Vec3) -> f32 { |
|
|
|
self.0 * other.0 + self.1 * other.1 + self.2 * other.2 |
|
|
|
} |
|
|
|
|
|
|
|
pub fn cross(&self, other: Vec3) -> Vec3 { |
|
|
|
Vec3( |
|
|
|
self.1 * other.2 - self.2 * other.1, |
|
|
|
self.2 * other.0 - self.0 * other.2, |
|
|
|
self.0 * other.1 - self.1 * other.0, |
|
|
|
) |
|
|
|
} |
|
|
|
|
|
|
|
pub fn unit(&self) -> Vec3 { |
|
|
|
*self / self.length() |
|
|
|
} |
|
|
|
|
|
|
|
pub fn to_rgb(&self) -> Result<Rgb<u8>, &str> { |
|
|
|
if self.0 < 0.0 || self.0 > 1.0 || self.1 < 0.0 || self.1 > 1.0 || self.2 < 0.0 || self.2 > 1.0 { |
|
|
|
return Err("input out of bounds"); |
|
|
|
} |
|
|
|
let r = (self.0 * 255.99) as u8; |
|
|
|
let g = (self.1 * 255.99) as u8; |
|
|
|
let b = (self.2 * 255.99) as u8; |
|
|
|
Ok(Rgb([r, g, b])) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
impl Add for Vec3 { |
|
|
|
type Output = Vec3; |
|
|
|
|
|
|
|
fn add(self, other: Vec3) -> Vec3 { |
|
|
|
Vec3(self.0 + other.0, self.1 + other.1, self.2 + other.2) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
impl Sub for Vec3 { |
|
|
|
type Output = Vec3; |
|
|
|
|
|
|
|
fn sub(self, other:Vec3) -> Vec3 { |
|
|
|
Vec3(self.0 - other.0, self.1 - other.1, self.2 - other.2) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
impl Neg for Vec3 { |
|
|
|
type Output = Vec3; |
|
|
|
|
|
|
|
fn neg(self) -> Vec3 { |
|
|
|
Vec3(-self.0, -self.1, -self.2) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
impl Mul<f32> for Vec3 { |
|
|
|
type Output = Vec3; |
|
|
|
|
|
|
|
fn mul(self, k: f32) -> Vec3 { |
|
|
|
Vec3(self.0 * k, self.1 * k, self.2 * k) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
impl Div<f32> for Vec3 { |
|
|
|
type Output = Vec3; |
|
|
|
|
|
|
|
fn div(self, k: f32) -> Vec3 { |
|
|
|
Vec3(self.0 / k, self.1 / k, self.2 / k) |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
|
impl Mul<Vec3> for f32 { |
|
|
|
type Output = Vec3; |
|
|
|
|
|
|
|
fn mul(self, v: Vec3) -> Vec3 { |
|
|
|
v*self |
|
|
|
} |
|
|
|
} |