~ttt/ray_tracing_in_one_weekend

69f8f7997ce9ad1197aaee3be96dbea077bc7fd6 — Tomasz Kłak 4 years ago 5d3c6c4
ch 6.4 done
3 files changed, 41 insertions(+), 16 deletions(-)

M src/hittable.rs
M src/main.rs
M src/sphere.rs
M src/hittable.rs => src/hittable.rs +13 -1
@@ 1,11 1,23 @@
use crate::vec3::*;
use crate::ray::*;
use crate::vec3::*;

#[derive(Debug, Clone, Copy, Default)]
pub struct HitRecord {
    pub p: Point3,
    pub normal: Vec3,
    pub t: f64,
    pub front_face: bool,
}

impl HitRecord {
    pub fn set_face_normal(&mut self, r: &Ray, outward_normal: &Vec3) {
        self.front_face = dot(&r.direction(), outward_normal) < 0.0;
        self.normal = if self.front_face {
            *outward_normal
        } else {
            -outward_normal
        };
    }
}

pub trait Hittable {

M src/main.rs => src/main.rs +5 -6
@@ 14,14 14,13 @@ fn hit_sphere(center: &Point3, radius: f64, r: &Ray) -> f64 {
    let oc = r.origin() - *center;
    let a = r.direction().length_squared();
    let half_b = dot(&oc, &r.direction());
    let c = oc.length_squared() - radius*radius;
    let discriminant = half_b*half_b - a*c;

    let c = oc.length_squared() - radius * radius;
    let discriminant = half_b * half_b - a * c;

    if discriminant < 0.0 {
        -1.0
    } else {
        (-half_b - discriminant.sqrt() ) / a
        (-half_b - discriminant.sqrt()) / a
    }
}



@@ 29,7 28,7 @@ fn ray_color(r: &Ray) -> Color {
    let t = hit_sphere(&Point3::new(0.0, 0.0, -1f64), 0.5, r);
    if t > 0.0 {
        let N = unit_vector(r.at(t) - Vec3::new(0.0, 0.0, -1.0));
        return 0.5*Color::new(N.x()+1.0, N.y()+1.0, N.z()+1.0);
        return 0.5 * Color::new(N.x() + 1.0, N.y() + 1.0, N.z() + 1.0);
    }
    let unit_direction = unit_vector(r.direction());
    let t = 0.5 * (unit_direction.y() + 1.0);


@@ 69,7 68,7 @@ fn main() {
            let v = j as f64 / (image_height - 1) as f64;
            let r = Ray::new(
                &origin,
                &(lower_left_corner + u * horizontal + v * vertical - origin)
                &(lower_left_corner + u * horizontal + v * vertical - origin),
            );
            let pixel_color = ray_color(&r);
            write_color(&mut handle, pixel_color);

M src/sphere.rs => src/sphere.rs +23 -9
@@ 1,6 1,6 @@
use crate::vec3::*;
use crate::ray::*;
use crate::hittable::*;
use crate::ray::*;
use crate::vec3::*;

#[derive(Debug, Clone, Copy, Default)]
pub struct Sphere {


@@ 10,7 10,7 @@ pub struct Sphere {

impl Sphere {
    fn new(center: Point3, radius: f64) -> Self {
        Self{center, radius}
        Self { center, radius }
    }
}



@@ 19,8 19,8 @@ impl Hittable for Sphere {
        let oc = r.origin() - self.center;
        let a = r.direction().length_squared();
        let half_b = dot(&oc, &r.direction());
        let c = oc.length_squared() - self.radius*self.radius;
        let discriminant = half_b*half_b - a*c;
        let c = oc.length_squared() - self.radius * self.radius;
        let discriminant = half_b * half_b - a * c;

        if discriminant > 0.0 {
            let root = discriminant.sqrt();


@@ 29,16 29,30 @@ impl Hittable for Sphere {
            if temp < t_max && temp > t_min {
                let t = temp;
                let p = r.at(t);
                let normal = (p - self.center) / self.radius;
                return Some(HitRecord{t, p, normal})
                let mut rec = HitRecord {
                    t: temp,
                    p,
                    normal: (p - self.center) / self.radius,
                    front_face: false,
                };
                let outward_normal = (rec.p - self.center) / self.radius;
                rec.set_face_normal(r, &outward_normal);
                return Some(rec);
            }

            let temp = (-half_b + root) / a;
            if temp < t_max && temp > t_min {
                let t = temp;
                let p = r.at(t);
                let normal = (p - self.center) / self.radius;
                return Some(HitRecord{t, p, normal})
                let mut rec = HitRecord {
                    t: temp,
                    p,
                    normal: (p - self.center) / self.radius,
                    front_face: false,
                };
                let outward_normal = (rec.p - self.center) / self.radius;
                rec.set_face_normal(r, &outward_normal);
                return Some(rec);
            }
        }