diff --git a/src/main.rs b/src/main.rs index 160fd99..f8df5a0 100644 --- a/src/main.rs +++ b/src/main.rs @@ -39,22 +39,7 @@ struct Vector3f { x: f32, y: f32, z: f32 } #[derive(Clone, Copy, Debug, Default)] struct Vector4f { x: f32, y: f32, z: f32, w: f32 } -#[derive(Clone, Copy, Debug, Default)] -struct Lighting -{ - diffuse: Vector3f, - specular: Vector3f, -} -#[derive(Clone, Copy, Debug, Default)] -struct PointLight -{ - position : Vector3f, - diffuseColor : Vector3f, - diffusePower : f32, - specularColor : Vector3f, - specularPower : f32, -} fn saturate(v: f32) -> f32 { f32::min(f32::max(v, 0.0), 1.0) @@ -174,16 +159,34 @@ fn get_surface_data(phit: Vector3f, sphere_center: Vector3f) -> (Vector2f, Vecto }, nhit) } +#[derive(Clone, Copy, Debug, Default)] +struct Lighting +{ + diffuse: Vector3f, + specular: Vector3f, + distance: f32, +} +#[derive(Clone, Copy, Debug, Default)] +struct PointLight +{ + position : Vector3f, + diffuseColor : Vector3f, + diffusePower : f32, + specularColor : Vector3f, + specularPower : f32, +} + +// returns the diffuse and specular fn get_point_light(light: PointLight, pos3D: Vector3f, viewDir: Vector3f, normal: Vector3f) -> Lighting { let mut out = Lighting::default(); if (light.diffusePower > 0.0) { let lightDir = sub(light.position, pos3D); //3D position in space of the surface - let distance = len(lightDir); - let lightDir = div(lightDir, distance); // = normalize(lightDir); - let distance = distance * distance; //This line may be optimised using Inverse square root + out.distance = len(lightDir); + let lightDir = div(lightDir, out.distance); // = normalize(lightDir); + let distance = out.distance * out.distance; //This line may be optimised using Inverse square root //Intensity of the diffuse light. Saturate to keep within the 0-1 range. let NdotL = dot(normal, lightDir); @@ -251,7 +254,7 @@ fn main() { // Create a new ImgBuf with width: imgx and height: imgy let mut imgbuf = image::ImageBuffer::new(view_res.x as u32, view_res.y as u32); - let sphere_center = Vector3f { x: -70.0, y: 20.0, z: -10.0 }; + let sphere_center = Vector3f { x: -10.0, y: 0.0, z: 0.0 }; let sphere_color = Vector3f { x: 78.0, y: 22.0, @@ -292,8 +295,24 @@ fn main() { z: -dir.z, }; + let light = PointLight { + position : Vector3f{x:0.0,y:0.0,z:0.0}, + diffuseColor : Vector3f{x:255.0,y:255.0,z:255.0}, + diffusePower : 100.0, + specularColor : Vector3f{x:255.0,y:255.0,z:255.0}, + specularPower : 70.0, + }; - let hit_color = mult(mix(sphere_color, mult(sphere_color, 0.8), f32::max(0.0, dot(nhit, ndir))), pattern); + let red = Vector3f {x:255.0, y:0.0, z:0.0}; + let color2 = Vector3f {x:200.0, y:90.0, z:120.0}; + + let lighting = get_point_light(light, add(phit, sphere_center), dir, nhit); + + let mut hit_color = add(lighting.diffuse, lighting.specular); + + println!("{:?}", hit_color); + println!("{:?}", add(nhit, sphere_center)); +// println!("{:?}", lighting); *pixel = image::Rgb([hit_color.x as u8, hit_color.y as u8, hit_color.z as u8]); } };