shapes: create generic Shape object with Sphere implementation.
All checks were successful
continuous-integration/drone/push Build is passing
All checks were successful
continuous-integration/drone/push Build is passing
This commit is contained in:
parent
7741766635
commit
c0e422a7eb
@ -4,7 +4,7 @@ use rtchallenge::{
|
|||||||
canvas::Canvas,
|
canvas::Canvas,
|
||||||
matrices::Matrix4x4,
|
matrices::Matrix4x4,
|
||||||
rays::Ray,
|
rays::Ray,
|
||||||
spheres::{intersect, Sphere},
|
shapes::{intersect, Shape},
|
||||||
tuples::{Color, Tuple},
|
tuples::{Color, Tuple},
|
||||||
Float,
|
Float,
|
||||||
};
|
};
|
||||||
@ -20,7 +20,7 @@ fn main() -> Result<()> {
|
|||||||
let pixel_size = wall_size / w as Float;
|
let pixel_size = wall_size / w as Float;
|
||||||
let half = wall_size / 2.;
|
let half = wall_size / 2.;
|
||||||
let color = Color::new(1., 0., 0.);
|
let color = Color::new(1., 0., 0.);
|
||||||
let mut shape = Sphere::default();
|
let mut shape = Shape::sphere();
|
||||||
shape.set_transform(
|
shape.set_transform(
|
||||||
Matrix4x4::shearing(1., 0., 0., 0., 0., 0.) * Matrix4x4::scaling(0.5, 1., 1.0),
|
Matrix4x4::shearing(1., 0., 0., 0., 0., 0.) * Matrix4x4::scaling(0.5, 1., 1.0),
|
||||||
);
|
);
|
||||||
|
|||||||
@ -5,7 +5,7 @@ use rtchallenge::{
|
|||||||
lights::PointLight,
|
lights::PointLight,
|
||||||
materials::{lighting, Material},
|
materials::{lighting, Material},
|
||||||
rays::Ray,
|
rays::Ray,
|
||||||
spheres::{intersect, Sphere},
|
shapes::{intersect, Shape},
|
||||||
tuples::{Color, Tuple},
|
tuples::{Color, Tuple},
|
||||||
Float, WHITE,
|
Float, WHITE,
|
||||||
};
|
};
|
||||||
@ -20,7 +20,7 @@ fn main() -> Result<()> {
|
|||||||
let wall_size = 7.;
|
let wall_size = 7.;
|
||||||
let pixel_size = wall_size / w as Float;
|
let pixel_size = wall_size / w as Float;
|
||||||
let half = wall_size / 2.;
|
let half = wall_size / 2.;
|
||||||
let mut shape = Sphere::default();
|
let mut shape = Shape::sphere();
|
||||||
shape.material = Material {
|
shape.material = Material {
|
||||||
color: Color::new(1., 0.2, 1.),
|
color: Color::new(1., 0.2, 1.),
|
||||||
specular: 0.5,
|
specular: 0.5,
|
||||||
|
|||||||
@ -9,7 +9,7 @@ use rtchallenge::{
|
|||||||
lights::PointLight,
|
lights::PointLight,
|
||||||
materials::Material,
|
materials::Material,
|
||||||
matrices::Matrix4x4,
|
matrices::Matrix4x4,
|
||||||
spheres::Sphere,
|
shapes::Shape,
|
||||||
transformations::view_transform,
|
transformations::view_transform,
|
||||||
tuples::{Color, Tuple},
|
tuples::{Color, Tuple},
|
||||||
world::World,
|
world::World,
|
||||||
@ -39,7 +39,7 @@ fn main() -> Result<()> {
|
|||||||
camera.set_transform(view_transform(from, to, up));
|
camera.set_transform(view_transform(from, to, up));
|
||||||
camera.render_strategy = opt.render_strategy;
|
camera.render_strategy = opt.render_strategy;
|
||||||
|
|
||||||
let mut floor = Sphere::default();
|
let mut floor = Shape::sphere();
|
||||||
floor.set_transform(Matrix4x4::scaling(10., 0.01, 10.));
|
floor.set_transform(Matrix4x4::scaling(10., 0.01, 10.));
|
||||||
floor.material = Material {
|
floor.material = Material {
|
||||||
color: Color::new(1., 0.9, 0.9),
|
color: Color::new(1., 0.9, 0.9),
|
||||||
@ -47,7 +47,7 @@ fn main() -> Result<()> {
|
|||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut left_wall = Sphere::default();
|
let mut left_wall = Shape::sphere();
|
||||||
left_wall.set_transform(
|
left_wall.set_transform(
|
||||||
Matrix4x4::translation(0., 0., 5.)
|
Matrix4x4::translation(0., 0., 5.)
|
||||||
* Matrix4x4::rotation_y(-PI / 4.)
|
* Matrix4x4::rotation_y(-PI / 4.)
|
||||||
@ -56,7 +56,7 @@ fn main() -> Result<()> {
|
|||||||
);
|
);
|
||||||
left_wall.material = floor.material.clone();
|
left_wall.material = floor.material.clone();
|
||||||
|
|
||||||
let mut right_wall = Sphere::default();
|
let mut right_wall = Shape::sphere();
|
||||||
right_wall.set_transform(
|
right_wall.set_transform(
|
||||||
Matrix4x4::translation(0., 0., 5.)
|
Matrix4x4::translation(0., 0., 5.)
|
||||||
* Matrix4x4::rotation_y(PI / 4.)
|
* Matrix4x4::rotation_y(PI / 4.)
|
||||||
@ -65,7 +65,7 @@ fn main() -> Result<()> {
|
|||||||
);
|
);
|
||||||
right_wall.material = floor.material.clone();
|
right_wall.material = floor.material.clone();
|
||||||
|
|
||||||
let mut middle = Sphere::default();
|
let mut middle = Shape::sphere();
|
||||||
middle.set_transform(Matrix4x4::translation(-0.5, 1., 0.5));
|
middle.set_transform(Matrix4x4::translation(-0.5, 1., 0.5));
|
||||||
middle.material = Material {
|
middle.material = Material {
|
||||||
color: Color::new(0.1, 1., 0.5),
|
color: Color::new(0.1, 1., 0.5),
|
||||||
@ -74,7 +74,7 @@ fn main() -> Result<()> {
|
|||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut right = Sphere::default();
|
let mut right = Shape::sphere();
|
||||||
right.set_transform(Matrix4x4::translation(1.5, 0.5, -0.5) * Matrix4x4::scaling(0.5, 0.5, 0.5));
|
right.set_transform(Matrix4x4::translation(1.5, 0.5, -0.5) * Matrix4x4::scaling(0.5, 0.5, 0.5));
|
||||||
right.material = Material {
|
right.material = Material {
|
||||||
color: Color::new(0.5, 1., 0.1),
|
color: Color::new(0.5, 1., 0.1),
|
||||||
@ -83,7 +83,7 @@ fn main() -> Result<()> {
|
|||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut left = Sphere::default();
|
let mut left = Shape::sphere();
|
||||||
left.set_transform(
|
left.set_transform(
|
||||||
Matrix4x4::translation(-1.5, 0.33, -0.75) * Matrix4x4::scaling(0.33, 0.33, 0.33),
|
Matrix4x4::translation(-1.5, 0.33, -0.75) * Matrix4x4::scaling(0.33, 0.33, 0.33),
|
||||||
);
|
);
|
||||||
|
|||||||
@ -9,7 +9,7 @@ use rtchallenge::{
|
|||||||
lights::PointLight,
|
lights::PointLight,
|
||||||
materials::Material,
|
materials::Material,
|
||||||
matrices::Matrix4x4,
|
matrices::Matrix4x4,
|
||||||
spheres::Sphere,
|
shapes::Shape,
|
||||||
transformations::view_transform,
|
transformations::view_transform,
|
||||||
tuples::{Color, Tuple},
|
tuples::{Color, Tuple},
|
||||||
world::World,
|
world::World,
|
||||||
@ -51,7 +51,7 @@ fn main() -> Result<()> {
|
|||||||
camera.render_strategy = opt.render_strategy;
|
camera.render_strategy = opt.render_strategy;
|
||||||
camera.samples_per_pixel = opt.samples;
|
camera.samples_per_pixel = opt.samples;
|
||||||
|
|
||||||
let mut floor = Sphere::default();
|
let mut floor = Shape::sphere();
|
||||||
floor.set_transform(Matrix4x4::scaling(10., 0.01, 10.));
|
floor.set_transform(Matrix4x4::scaling(10., 0.01, 10.));
|
||||||
floor.material = Material {
|
floor.material = Material {
|
||||||
color: Color::new(1., 0.9, 0.9),
|
color: Color::new(1., 0.9, 0.9),
|
||||||
@ -59,7 +59,7 @@ fn main() -> Result<()> {
|
|||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut left_wall = Sphere::default();
|
let mut left_wall = Shape::sphere();
|
||||||
left_wall.set_transform(
|
left_wall.set_transform(
|
||||||
Matrix4x4::translation(0., 0., 5.)
|
Matrix4x4::translation(0., 0., 5.)
|
||||||
* Matrix4x4::rotation_y(-PI / 4.)
|
* Matrix4x4::rotation_y(-PI / 4.)
|
||||||
@ -68,7 +68,7 @@ fn main() -> Result<()> {
|
|||||||
);
|
);
|
||||||
left_wall.material = floor.material.clone();
|
left_wall.material = floor.material.clone();
|
||||||
|
|
||||||
let mut right_wall = Sphere::default();
|
let mut right_wall = Shape::sphere();
|
||||||
right_wall.set_transform(
|
right_wall.set_transform(
|
||||||
Matrix4x4::translation(0., 0., 5.)
|
Matrix4x4::translation(0., 0., 5.)
|
||||||
* Matrix4x4::rotation_y(PI / 4.)
|
* Matrix4x4::rotation_y(PI / 4.)
|
||||||
@ -77,7 +77,7 @@ fn main() -> Result<()> {
|
|||||||
);
|
);
|
||||||
right_wall.material = floor.material.clone();
|
right_wall.material = floor.material.clone();
|
||||||
|
|
||||||
let mut middle = Sphere::default();
|
let mut middle = Shape::sphere();
|
||||||
middle.set_transform(Matrix4x4::translation(-0.5, 1., 0.5));
|
middle.set_transform(Matrix4x4::translation(-0.5, 1., 0.5));
|
||||||
middle.material = Material {
|
middle.material = Material {
|
||||||
color: Color::new(0.1, 1., 0.5),
|
color: Color::new(0.1, 1., 0.5),
|
||||||
@ -86,7 +86,7 @@ fn main() -> Result<()> {
|
|||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut right = Sphere::default();
|
let mut right = Shape::sphere();
|
||||||
right.set_transform(Matrix4x4::translation(1.5, 0.5, -0.5) * Matrix4x4::scaling(0.5, 0.5, 0.5));
|
right.set_transform(Matrix4x4::translation(1.5, 0.5, -0.5) * Matrix4x4::scaling(0.5, 0.5, 0.5));
|
||||||
right.material = Material {
|
right.material = Material {
|
||||||
color: Color::new(1., 1., 1.),
|
color: Color::new(1., 1., 1.),
|
||||||
@ -95,7 +95,7 @@ fn main() -> Result<()> {
|
|||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
|
|
||||||
let mut left = Sphere::default();
|
let mut left = Shape::sphere();
|
||||||
left.set_transform(
|
left.set_transform(
|
||||||
Matrix4x4::translation(-1.5, 0.33, -0.75) * Matrix4x4::scaling(0.33, 0.33, 0.33),
|
Matrix4x4::translation(-1.5, 0.33, -0.75) * Matrix4x4::scaling(0.33, 0.33, 0.33),
|
||||||
);
|
);
|
||||||
|
|||||||
@ -2,7 +2,7 @@ use std::ops::Index;
|
|||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
rays::Ray,
|
rays::Ray,
|
||||||
spheres::Sphere,
|
shapes::Shape,
|
||||||
tuples::{dot, Tuple},
|
tuples::{dot, Tuple},
|
||||||
Float, EPSILON,
|
Float, EPSILON,
|
||||||
};
|
};
|
||||||
@ -10,7 +10,7 @@ use crate::{
|
|||||||
#[derive(Debug, Clone, PartialEq)]
|
#[derive(Debug, Clone, PartialEq)]
|
||||||
pub struct Intersection<'i> {
|
pub struct Intersection<'i> {
|
||||||
pub t: Float,
|
pub t: Float,
|
||||||
pub object: &'i Sphere,
|
pub object: &'i Shape,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'i> Intersection<'i> {
|
impl<'i> Intersection<'i> {
|
||||||
@ -18,15 +18,15 @@ impl<'i> Intersection<'i> {
|
|||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
/// ```
|
/// ```
|
||||||
/// use rtchallenge::{intersections::Intersection, spheres::Sphere};
|
/// use rtchallenge::{intersections::Intersection, shapes::Shape};
|
||||||
///
|
///
|
||||||
/// // An intersection ecapsulates t and object.
|
/// // An intersection ecapsulates t and object.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let i = Intersection::new(3.5, &s);
|
/// let i = Intersection::new(3.5, &s);
|
||||||
/// assert_eq!(i.t, 3.5);
|
/// assert_eq!(i.t, 3.5);
|
||||||
/// assert_eq!(i.object, &s);
|
/// assert_eq!(i.object, &s);
|
||||||
/// ```
|
/// ```
|
||||||
pub fn new(t: Float, object: &Sphere) -> Intersection {
|
pub fn new(t: Float, object: &Shape) -> Intersection {
|
||||||
Intersection { t, object }
|
Intersection { t, object }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -38,11 +38,11 @@ impl<'i> Intersection<'i> {
|
|||||||
/// use rtchallenge::{
|
/// use rtchallenge::{
|
||||||
/// intersections::{Intersection, Intersections},
|
/// intersections::{Intersection, Intersections},
|
||||||
/// rays::Ray,
|
/// rays::Ray,
|
||||||
/// spheres::{intersect, Sphere},
|
/// shapes::{intersect, Shape},
|
||||||
/// tuples::Tuple,
|
/// tuples::Tuple,
|
||||||
/// };
|
/// };
|
||||||
///
|
///
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let i1 = Intersection::new(1., &s);
|
/// let i1 = Intersection::new(1., &s);
|
||||||
/// let i2 = Intersection::new(2., &s);
|
/// let i2 = Intersection::new(2., &s);
|
||||||
/// let xs = Intersections::new(vec![i1, i2]);
|
/// let xs = Intersections::new(vec![i1, i2]);
|
||||||
@ -73,12 +73,12 @@ impl<'i> Intersections<'i> {
|
|||||||
/// use rtchallenge::{
|
/// use rtchallenge::{
|
||||||
/// intersections::{Intersection, Intersections},
|
/// intersections::{Intersection, Intersections},
|
||||||
/// rays::Ray,
|
/// rays::Ray,
|
||||||
/// spheres::{intersect, Sphere},
|
/// shapes::{intersect, Shape},
|
||||||
/// tuples::Tuple,
|
/// tuples::Tuple,
|
||||||
/// };
|
/// };
|
||||||
///
|
///
|
||||||
/// // The hit, when all intersections have positive t.
|
/// // The hit, when all intersections have positive t.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let i1 = Intersection::new(1., &s);
|
/// let i1 = Intersection::new(1., &s);
|
||||||
/// let i2 = Intersection::new(2., &s);
|
/// let i2 = Intersection::new(2., &s);
|
||||||
/// let xs = Intersections::new(vec![i2, i1.clone()]);
|
/// let xs = Intersections::new(vec![i2, i1.clone()]);
|
||||||
@ -86,7 +86,7 @@ impl<'i> Intersections<'i> {
|
|||||||
/// assert_eq!(i, Some(&i1));
|
/// assert_eq!(i, Some(&i1));
|
||||||
///
|
///
|
||||||
/// // The hit, when some intersections have negative t.
|
/// // The hit, when some intersections have negative t.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let i1 = Intersection::new(-1., &s);
|
/// let i1 = Intersection::new(-1., &s);
|
||||||
/// let i2 = Intersection::new(1., &s);
|
/// let i2 = Intersection::new(1., &s);
|
||||||
/// let xs = Intersections::new(vec![i2.clone(), i1]);
|
/// let xs = Intersections::new(vec![i2.clone(), i1]);
|
||||||
@ -94,7 +94,7 @@ impl<'i> Intersections<'i> {
|
|||||||
/// assert_eq!(i, Some(&i2));
|
/// assert_eq!(i, Some(&i2));
|
||||||
///
|
///
|
||||||
/// // The hit, when all intersections have negative t.
|
/// // The hit, when all intersections have negative t.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let i1 = Intersection::new(-2., &s);
|
/// let i1 = Intersection::new(-2., &s);
|
||||||
/// let i2 = Intersection::new(-1., &s);
|
/// let i2 = Intersection::new(-1., &s);
|
||||||
/// let xs = Intersections::new(vec![i2, i1]);
|
/// let xs = Intersections::new(vec![i2, i1]);
|
||||||
@ -102,7 +102,7 @@ impl<'i> Intersections<'i> {
|
|||||||
/// assert_eq!(i, None);
|
/// assert_eq!(i, None);
|
||||||
///
|
///
|
||||||
/// // The hit is always the lowest nonnegative intersection.
|
/// // The hit is always the lowest nonnegative intersection.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let i1 = Intersection::new(5., &s);
|
/// let i1 = Intersection::new(5., &s);
|
||||||
/// let i2 = Intersection::new(7., &s);
|
/// let i2 = Intersection::new(7., &s);
|
||||||
/// let i3 = Intersection::new(-3., &s);
|
/// let i3 = Intersection::new(-3., &s);
|
||||||
@ -138,7 +138,7 @@ impl<'i> Index<usize> for Intersections<'i> {
|
|||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct PrecomputedData<'i> {
|
pub struct PrecomputedData<'i> {
|
||||||
pub t: Float,
|
pub t: Float,
|
||||||
pub object: &'i Sphere,
|
pub object: &'i Shape,
|
||||||
pub point: Tuple,
|
pub point: Tuple,
|
||||||
pub over_point: Tuple,
|
pub over_point: Tuple,
|
||||||
pub eyev: Tuple,
|
pub eyev: Tuple,
|
||||||
@ -154,14 +154,14 @@ pub struct PrecomputedData<'i> {
|
|||||||
/// intersections::{prepare_computations, Intersection, Intersections},
|
/// intersections::{prepare_computations, Intersection, Intersections},
|
||||||
/// rays::Ray,
|
/// rays::Ray,
|
||||||
/// matrices::Matrix4x4,
|
/// matrices::Matrix4x4,
|
||||||
/// spheres::{intersect, Sphere},
|
/// shapes::{intersect, Shape},
|
||||||
/// tuples::Tuple,
|
/// tuples::Tuple,
|
||||||
/// EPSILON
|
/// EPSILON
|
||||||
/// };
|
/// };
|
||||||
///
|
///
|
||||||
/// // Precomputing the state of an intersection.
|
/// // Precomputing the state of an intersection.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let shape = Sphere::default();
|
/// let shape = Shape::sphere();
|
||||||
/// let i = Intersection::new(4., &shape);
|
/// let i = Intersection::new(4., &shape);
|
||||||
/// let comps = prepare_computations(&i, &r);
|
/// let comps = prepare_computations(&i, &r);
|
||||||
/// assert_eq!(comps.t, i.t);
|
/// assert_eq!(comps.t, i.t);
|
||||||
@ -172,14 +172,14 @@ pub struct PrecomputedData<'i> {
|
|||||||
///
|
///
|
||||||
/// // The hit, when an intersection occurs on the outside.
|
/// // The hit, when an intersection occurs on the outside.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let shape = Sphere::default();
|
/// let shape = Shape::sphere();
|
||||||
/// let i = Intersection::new(4., &shape);
|
/// let i = Intersection::new(4., &shape);
|
||||||
/// let comps = prepare_computations(&i, &r);
|
/// let comps = prepare_computations(&i, &r);
|
||||||
/// assert_eq!(comps.inside, false);
|
/// assert_eq!(comps.inside, false);
|
||||||
///
|
///
|
||||||
/// // The hit, when an intersection occurs on the inside.
|
/// // The hit, when an intersection occurs on the inside.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., 0.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., 0.), Tuple::vector(0., 0., 1.));
|
||||||
/// let shape = Sphere::default();
|
/// let shape = Shape::sphere();
|
||||||
/// let i = Intersection::new(1., &shape);
|
/// let i = Intersection::new(1., &shape);
|
||||||
/// let comps = prepare_computations(&i, &r);
|
/// let comps = prepare_computations(&i, &r);
|
||||||
/// assert_eq!(comps.point, Tuple::point(0., 0., 1.));
|
/// assert_eq!(comps.point, Tuple::point(0., 0., 1.));
|
||||||
@ -190,7 +190,7 @@ pub struct PrecomputedData<'i> {
|
|||||||
///
|
///
|
||||||
/// // The hit should offset the point.
|
/// // The hit should offset the point.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let mut shape = Sphere::default();
|
/// let mut shape = Shape::sphere();
|
||||||
/// shape .set_transform(Matrix4x4::translation(0.,0.,1.));
|
/// shape .set_transform(Matrix4x4::translation(0.,0.,1.));
|
||||||
/// let i = Intersection::new(5., &shape);
|
/// let i = Intersection::new(5., &shape);
|
||||||
/// let comps = prepare_computations(&i, &r);
|
/// let comps = prepare_computations(&i, &r);
|
||||||
|
|||||||
@ -5,7 +5,7 @@ pub mod lights;
|
|||||||
pub mod materials;
|
pub mod materials;
|
||||||
pub mod matrices;
|
pub mod matrices;
|
||||||
pub mod rays;
|
pub mod rays;
|
||||||
pub mod spheres;
|
pub mod shapes;
|
||||||
pub mod transformations;
|
pub mod transformations;
|
||||||
pub mod tuples;
|
pub mod tuples;
|
||||||
pub mod world;
|
pub mod world;
|
||||||
|
|||||||
@ -7,71 +7,80 @@ use crate::{
|
|||||||
};
|
};
|
||||||
|
|
||||||
#[derive(Debug, PartialEq, Clone)]
|
#[derive(Debug, PartialEq, Clone)]
|
||||||
/// Sphere represents the unit-sphere (radius of unit 1.) at the origin 0., 0., 0.
|
enum Geometry {
|
||||||
pub struct Sphere {
|
/// Sphere represents the unit-sphere (radius of unit 1.) at the origin 0., 0., 0.
|
||||||
|
Sphere,
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Shape represents visible objects. A signal instance of Shape can generically represent one of
|
||||||
|
/// many different shapes based on the value of it's geometry field. Users chose the shape by
|
||||||
|
/// calling the appropriate constructor, i.e. [Shape::sphere].
|
||||||
|
#[derive(Debug, PartialEq, Clone)]
|
||||||
|
pub struct Shape {
|
||||||
transform: Matrix4x4,
|
transform: Matrix4x4,
|
||||||
inverse_transform: Matrix4x4,
|
inverse_transform: Matrix4x4,
|
||||||
pub material: Material,
|
pub material: Material,
|
||||||
|
geometry: Geometry,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Default for Sphere {
|
impl Shape {
|
||||||
/// # Examples
|
/// # Examples
|
||||||
/// ```
|
/// ```
|
||||||
/// use rtchallenge::{materials::Material, matrices::Matrix4x4, spheres::Sphere};
|
/// use rtchallenge::{materials::Material, matrices::Matrix4x4, shapes::Shape};
|
||||||
///
|
///
|
||||||
/// // A sphere's default transform is the identity matrix.
|
/// // A sphere's default transform is the identity matrix.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// assert_eq!(s.transform(), Matrix4x4::identity());
|
/// assert_eq!(s.transform(), Matrix4x4::identity());
|
||||||
///
|
///
|
||||||
/// // It can be changed by directly setting the transform member.
|
/// // It can be changed by directly setting the transform member.
|
||||||
/// let mut s = Sphere::default();
|
/// let mut s = Shape::sphere();
|
||||||
/// let t = Matrix4x4::translation(2., 3., 4.);
|
/// let t = Matrix4x4::translation(2., 3., 4.);
|
||||||
/// s.set_transform ( t.clone());
|
/// s.set_transform(t.clone());
|
||||||
/// assert_eq!(s.transform(), t);
|
/// assert_eq!(s.transform(), t);
|
||||||
///
|
///
|
||||||
/// // Default Sphere has the default material.
|
/// // Default Sphere has the default material.
|
||||||
/// assert_eq!(s.material, Material::default());
|
/// assert_eq!(s.material, Material::default());
|
||||||
/// // It can be overridden.
|
/// // It can be overridden.
|
||||||
/// let mut s = Sphere::default();
|
/// let mut s = Shape::sphere();
|
||||||
/// let mut m = Material::default();
|
/// let mut m = Material::default();
|
||||||
/// m.ambient = 1.;
|
/// m.ambient = 1.;
|
||||||
/// s.material = m.clone();
|
/// s.material = m.clone();
|
||||||
/// assert_eq!(s.material, m);
|
/// assert_eq!(s.material, m);
|
||||||
|
|
||||||
/// ```
|
/// ```
|
||||||
fn default() -> Sphere {
|
pub fn sphere() -> Shape {
|
||||||
Sphere {
|
Shape {
|
||||||
transform: Matrix4x4::identity(),
|
transform: Matrix4x4::identity(),
|
||||||
inverse_transform: Matrix4x4::identity(),
|
inverse_transform: Matrix4x4::identity(),
|
||||||
material: Material::default(),
|
material: Material::default(),
|
||||||
|
geometry: Geometry::Sphere,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
impl Sphere {
|
|
||||||
/// Find the normal at the point on the sphere.
|
/// Find the normal at the point on the sphere.
|
||||||
///
|
///
|
||||||
/// # Examples
|
/// # Examples
|
||||||
/// ```
|
/// ```
|
||||||
/// use rtchallenge::{matrices::Matrix4x4, spheres::Sphere, tuples::Tuple,Float};
|
/// use rtchallenge::{
|
||||||
|
/// float::consts::PI, materials::Material, matrices::Matrix4x4, shapes::Shape, tuples::Tuple,
|
||||||
|
/// Float,
|
||||||
|
/// };
|
||||||
///
|
///
|
||||||
/// // Normal on X-axis
|
/// // Normal on X-axis
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let n = s.normal_at(Tuple::point(1., 0., 0.));
|
/// let n = s.normal_at(Tuple::point(1., 0., 0.));
|
||||||
/// assert_eq!(n, Tuple::vector(1., 0., 0.));
|
/// assert_eq!(n, Tuple::vector(1., 0., 0.));
|
||||||
///
|
///
|
||||||
/// // Normal on Y-axis
|
/// // Normal on Y-axis
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let n = s.normal_at(Tuple::point(0., 1., 0.));
|
/// let n = s.normal_at(Tuple::point(0., 1., 0.));
|
||||||
/// assert_eq!(n, Tuple::vector(0., 1., 0.));
|
/// assert_eq!(n, Tuple::vector(0., 1., 0.));
|
||||||
///
|
///
|
||||||
/// // Normal on Z-axis
|
/// // Normal on Z-axis
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let n = s.normal_at(Tuple::point(0., 0., 1.));
|
/// let n = s.normal_at(Tuple::point(0., 0., 1.));
|
||||||
/// assert_eq!(n, Tuple::vector(0., 0., 1.));
|
/// assert_eq!(n, Tuple::vector(0., 0., 1.));
|
||||||
///
|
///
|
||||||
/// // Normal on a sphere at a nonaxial point.
|
/// // Normal on a sphere at a nonaxial point.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let n = s.normal_at(Tuple::point(
|
/// let n = s.normal_at(Tuple::point(
|
||||||
/// (3. as Float).sqrt() / 3.,
|
/// (3. as Float).sqrt() / 3.,
|
||||||
/// (3. as Float).sqrt() / 3.,
|
/// (3. as Float).sqrt() / 3.,
|
||||||
@ -79,10 +88,14 @@ impl Sphere {
|
|||||||
/// ));
|
/// ));
|
||||||
/// assert_eq!(
|
/// assert_eq!(
|
||||||
/// n,
|
/// n,
|
||||||
/// Tuple::vector((3. as Float).sqrt() / 3., (3. as Float).sqrt() / 3., (3. as Float).sqrt() / 3.,)
|
/// Tuple::vector(
|
||||||
|
/// (3. as Float).sqrt() / 3.,
|
||||||
|
/// (3. as Float).sqrt() / 3.,
|
||||||
|
/// (3. as Float).sqrt() / 3.,
|
||||||
|
/// )
|
||||||
/// );
|
/// );
|
||||||
/// // Normals returned are normalized.
|
/// // Normals returned are normalized.
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let n = s.normal_at(Tuple::point(
|
/// let n = s.normal_at(Tuple::point(
|
||||||
/// (3. as Float).sqrt() / 3.,
|
/// (3. as Float).sqrt() / 3.,
|
||||||
/// (3. as Float).sqrt() / 3.,
|
/// (3. as Float).sqrt() / 3.,
|
||||||
@ -91,23 +104,27 @@ impl Sphere {
|
|||||||
/// assert_eq!(n, n.normalize());
|
/// assert_eq!(n, n.normalize());
|
||||||
///
|
///
|
||||||
/// // Compute the normal on a translated sphere.
|
/// // Compute the normal on a translated sphere.
|
||||||
/// let mut s = Sphere::default();
|
/// let mut s = Shape::sphere();
|
||||||
/// s.set_transform ( Matrix4x4::translation(0., 1., 0.));
|
/// s.set_transform(Matrix4x4::translation(0., 1., 0.));
|
||||||
/// let n = s.normal_at(Tuple::point(0., 1.70711, -0.70711));
|
/// let n = s.normal_at(Tuple::point(0., 1.70711, -0.70711));
|
||||||
/// assert_eq!(n, Tuple::vector(0., 0.70711, -0.70711));
|
/// assert_eq!(n, Tuple::vector(0., 0.70711, -0.70711));
|
||||||
|
|
||||||
/// // Compute the normal on a transformed sphere.
|
|
||||||
/// use rtchallenge::float::consts::PI;
|
|
||||||
///
|
///
|
||||||
/// let mut s = Sphere::default();
|
/// // Compute the normal on a transformed sphere.
|
||||||
/// s.set_transform ( Matrix4x4::scaling(1.,0.5,1.) * Matrix4x4::rotation_z(PI/5.));
|
/// let mut s = Shape::sphere();
|
||||||
/// let n = s.normal_at(Tuple::point(0., (2. as Float).sqrt()/2., -(2. as Float).sqrt()/2.));
|
/// s.set_transform(Matrix4x4::scaling(1., 0.5, 1.) * Matrix4x4::rotation_z(PI / 5.));
|
||||||
|
/// let n = s.normal_at(Tuple::point(
|
||||||
|
/// 0.,
|
||||||
|
/// (2. as Float).sqrt() / 2.,
|
||||||
|
/// -(2. as Float).sqrt() / 2.,
|
||||||
|
/// ));
|
||||||
/// assert_eq!(n, Tuple::vector(0., 0.97014, -0.24254));
|
/// assert_eq!(n, Tuple::vector(0., 0.97014, -0.24254));
|
||||||
/// ```
|
/// ```
|
||||||
#[cfg(not(feature = "disable-inverse-cache"))]
|
#[cfg(not(feature = "disable-inverse-cache"))]
|
||||||
pub fn normal_at(&self, world_point: Tuple) -> Tuple {
|
pub fn normal_at(&self, world_point: Tuple) -> Tuple {
|
||||||
let object_point = self.inverse_transform * world_point;
|
let object_point = self.inverse_transform * world_point;
|
||||||
let object_normal = object_point - Tuple::point(0., 0., 0.);
|
let object_normal = match self.geometry {
|
||||||
|
Geometry::Sphere => object_point - Tuple::point(0., 0., 0.),
|
||||||
|
};
|
||||||
let mut world_normal = self.inverse_transform.transpose() * object_normal;
|
let mut world_normal = self.inverse_transform.transpose() * object_normal;
|
||||||
world_normal.w = 0.;
|
world_normal.w = 0.;
|
||||||
world_normal.normalize()
|
world_normal.normalize()
|
||||||
@ -115,7 +132,9 @@ impl Sphere {
|
|||||||
#[cfg(feature = "disable-inverse-cache")]
|
#[cfg(feature = "disable-inverse-cache")]
|
||||||
pub fn normal_at(&self, world_point: Tuple) -> Tuple {
|
pub fn normal_at(&self, world_point: Tuple) -> Tuple {
|
||||||
let object_point = self.transform.inverse() * world_point;
|
let object_point = self.transform.inverse() * world_point;
|
||||||
let object_normal = object_point - Tuple::point(0., 0., 0.);
|
let object_normal = match self.geometry {
|
||||||
|
Geometry::Sphere => object_point - Tuple::point(0., 0., 0.),
|
||||||
|
};
|
||||||
let mut world_normal = self.transform.inverse().transpose() * object_normal;
|
let mut world_normal = self.transform.inverse().transpose() * object_normal;
|
||||||
world_normal.w = 0.;
|
world_normal.w = 0.;
|
||||||
world_normal.normalize()
|
world_normal.normalize()
|
||||||
@ -124,6 +143,7 @@ impl Sphere {
|
|||||||
pub fn transform(&self) -> Matrix4x4 {
|
pub fn transform(&self) -> Matrix4x4 {
|
||||||
self.transform
|
self.transform
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn set_transform(&mut self, t: Matrix4x4) {
|
pub fn set_transform(&mut self, t: Matrix4x4) {
|
||||||
self.transform = t;
|
self.transform = t;
|
||||||
self.inverse_transform = t.inverse();
|
self.inverse_transform = t.inverse();
|
||||||
@ -138,13 +158,13 @@ impl Sphere {
|
|||||||
/// intersections::{Intersection, Intersections},
|
/// intersections::{Intersection, Intersections},
|
||||||
/// matrices::Matrix4x4,
|
/// matrices::Matrix4x4,
|
||||||
/// rays::Ray,
|
/// rays::Ray,
|
||||||
/// spheres::{intersect, Sphere},
|
/// shapes::{intersect, Shape},
|
||||||
/// tuples::Tuple,
|
/// tuples::Tuple,
|
||||||
/// };
|
/// };
|
||||||
///
|
///
|
||||||
/// // A ray intersects a sphere in two points.
|
/// // A ray intersects a sphere in two points.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let xs = intersect(&s, &r);
|
/// let xs = intersect(&s, &r);
|
||||||
/// assert_eq!(
|
/// assert_eq!(
|
||||||
/// xs,
|
/// xs,
|
||||||
@ -153,13 +173,13 @@ impl Sphere {
|
|||||||
///
|
///
|
||||||
/// // A ray intersects a sphere at a tangent.
|
/// // A ray intersects a sphere at a tangent.
|
||||||
/// let r = Ray::new(Tuple::point(0., 2., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 2., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let xs = intersect(&s, &r);
|
/// let xs = intersect(&s, &r);
|
||||||
/// assert_eq!(xs, Intersections::default());
|
/// assert_eq!(xs, Intersections::default());
|
||||||
///
|
///
|
||||||
/// // A ray originates inside a sphere.
|
/// // A ray originates inside a sphere.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., 0.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., 0.), Tuple::vector(0., 0., 1.));
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let xs = intersect(&s, &r);
|
/// let xs = intersect(&s, &r);
|
||||||
/// assert_eq!(
|
/// assert_eq!(
|
||||||
/// xs,
|
/// xs,
|
||||||
@ -168,7 +188,7 @@ impl Sphere {
|
|||||||
///
|
///
|
||||||
/// // A sphere is behind a ray.
|
/// // A sphere is behind a ray.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., 5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., 5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let s = Sphere::default();
|
/// let s = Shape::sphere();
|
||||||
/// let xs = intersect(&s, &r);
|
/// let xs = intersect(&s, &r);
|
||||||
/// assert_eq!(
|
/// assert_eq!(
|
||||||
/// xs,
|
/// xs,
|
||||||
@ -177,7 +197,7 @@ impl Sphere {
|
|||||||
///
|
///
|
||||||
/// // Intersect a scaled sphere with a ray.
|
/// // Intersect a scaled sphere with a ray.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let mut s = Sphere::default();
|
/// let mut s = Shape::sphere();
|
||||||
/// s.set_transform(Matrix4x4::scaling(2., 2., 2.));
|
/// s.set_transform(Matrix4x4::scaling(2., 2., 2.));
|
||||||
/// let xs = intersect(&s, &r);
|
/// let xs = intersect(&s, &r);
|
||||||
/// assert_eq!(xs.len(), 2, "xs {:?}", xs);
|
/// assert_eq!(xs.len(), 2, "xs {:?}", xs);
|
||||||
@ -186,17 +206,19 @@ impl Sphere {
|
|||||||
///
|
///
|
||||||
/// // Intersect a translated sphere with a ray.
|
/// // Intersect a translated sphere with a ray.
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., -5.), Tuple::vector(0., 0., 1.));
|
||||||
/// let mut s = Sphere::default();
|
/// let mut s = Shape::sphere();
|
||||||
/// s.set_transform(Matrix4x4::translation(5., 0., 0.));
|
/// s.set_transform(Matrix4x4::translation(5., 0., 0.));
|
||||||
/// let xs = intersect(&s, &r);
|
/// let xs = intersect(&s, &r);
|
||||||
/// assert_eq!(xs.len(), 0);
|
/// assert_eq!(xs.len(), 0);
|
||||||
/// ```
|
/// ```
|
||||||
pub fn intersect<'s>(sphere: &'s Sphere, ray: &Ray) -> Intersections<'s> {
|
pub fn intersect<'s>(shape: &'s Shape, ray: &Ray) -> Intersections<'s> {
|
||||||
intersect_rtc(sphere, ray)
|
match shape.geometry {
|
||||||
|
Geometry::Sphere => intersect_rtc(shape, ray),
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn intersect_rtc<'s>(sphere: &'s Sphere, ray: &Ray) -> Intersections<'s> {
|
fn intersect_rtc<'s>(shape: &'s Shape, ray: &Ray) -> Intersections<'s> {
|
||||||
let ray = ray.transform(sphere.inverse_transform);
|
let ray = ray.transform(shape.inverse_transform);
|
||||||
let sphere_to_ray = ray.origin - Tuple::point(0., 0., 0.);
|
let sphere_to_ray = ray.origin - Tuple::point(0., 0., 0.);
|
||||||
let a = dot(ray.direction, ray.direction);
|
let a = dot(ray.direction, ray.direction);
|
||||||
let b = 2. * dot(ray.direction, sphere_to_ray);
|
let b = 2. * dot(ray.direction, sphere_to_ray);
|
||||||
@ -206,12 +228,12 @@ fn intersect_rtc<'s>(sphere: &'s Sphere, ray: &Ray) -> Intersections<'s> {
|
|||||||
return Intersections::default();
|
return Intersections::default();
|
||||||
}
|
}
|
||||||
Intersections::new(vec![
|
Intersections::new(vec![
|
||||||
Intersection::new((-b - discriminant.sqrt()) / (2. * a), &sphere),
|
Intersection::new((-b - discriminant.sqrt()) / (2. * a), &shape),
|
||||||
Intersection::new((-b + discriminant.sqrt()) / (2. * a), &sphere),
|
Intersection::new((-b + discriminant.sqrt()) / (2. * a), &shape),
|
||||||
])
|
])
|
||||||
}
|
}
|
||||||
fn intersect_rtiow<'s>(sphere: &'s Sphere, ray: &Ray) -> Intersections<'s> {
|
fn intersect_rtiow<'s>(shape: &'s Shape, ray: &Ray) -> Intersections<'s> {
|
||||||
let ray = ray.transform(sphere.inverse_transform);
|
let ray = ray.transform(shape.inverse_transform);
|
||||||
let oc = ray.origin - Tuple::point(0., 0., 0.);
|
let oc = ray.origin - Tuple::point(0., 0., 0.);
|
||||||
let a = dot(ray.direction, ray.direction);
|
let a = dot(ray.direction, ray.direction);
|
||||||
let b = dot(oc, ray.direction);
|
let b = dot(oc, ray.direction);
|
||||||
@ -221,7 +243,7 @@ fn intersect_rtiow<'s>(sphere: &'s Sphere, ray: &Ray) -> Intersections<'s> {
|
|||||||
return Intersections::default();
|
return Intersections::default();
|
||||||
}
|
}
|
||||||
Intersections::new(vec![
|
Intersections::new(vec![
|
||||||
Intersection::new((-b - discriminant.sqrt()) / a, &sphere),
|
Intersection::new((-b - discriminant.sqrt()) / a, &shape),
|
||||||
Intersection::new((-b + discriminant.sqrt()) / a, &sphere),
|
Intersection::new((-b + discriminant.sqrt()) / a, &shape),
|
||||||
])
|
])
|
||||||
}
|
}
|
||||||
@ -4,7 +4,7 @@ use crate::{
|
|||||||
materials::{lighting, Material},
|
materials::{lighting, Material},
|
||||||
matrices::Matrix4x4,
|
matrices::Matrix4x4,
|
||||||
rays::Ray,
|
rays::Ray,
|
||||||
spheres::{intersect, Sphere},
|
shapes::{intersect, Shape},
|
||||||
tuples::{Color, Tuple},
|
tuples::{Color, Tuple},
|
||||||
Float, BLACK, WHITE,
|
Float, BLACK, WHITE,
|
||||||
};
|
};
|
||||||
@ -23,7 +23,7 @@ use crate::{
|
|||||||
#[derive(Clone, Debug, Default)]
|
#[derive(Clone, Debug, Default)]
|
||||||
pub struct World {
|
pub struct World {
|
||||||
pub lights: Vec<PointLight>,
|
pub lights: Vec<PointLight>,
|
||||||
pub objects: Vec<Sphere>,
|
pub objects: Vec<Shape>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl World {
|
impl World {
|
||||||
@ -39,14 +39,14 @@ impl World {
|
|||||||
/// ```
|
/// ```
|
||||||
pub fn test_world() -> World {
|
pub fn test_world() -> World {
|
||||||
let light = PointLight::new(Tuple::point(-10., 10., -10.), WHITE);
|
let light = PointLight::new(Tuple::point(-10., 10., -10.), WHITE);
|
||||||
let mut s1 = Sphere::default();
|
let mut s1 = Shape::sphere();
|
||||||
s1.material = Material {
|
s1.material = Material {
|
||||||
color: Color::new(0.8, 1., 0.6),
|
color: Color::new(0.8, 1., 0.6),
|
||||||
diffuse: 0.7,
|
diffuse: 0.7,
|
||||||
specular: 0.2,
|
specular: 0.2,
|
||||||
..Material::default()
|
..Material::default()
|
||||||
};
|
};
|
||||||
let mut s2 = Sphere::default();
|
let mut s2 = Shape::sphere();
|
||||||
s2.set_transform(Matrix4x4::scaling(0.5, 0.5, 0.5));
|
s2.set_transform(Matrix4x4::scaling(0.5, 0.5, 0.5));
|
||||||
World {
|
World {
|
||||||
lights: vec![light],
|
lights: vec![light],
|
||||||
@ -92,7 +92,7 @@ impl World {
|
|||||||
/// lights::PointLight,
|
/// lights::PointLight,
|
||||||
/// matrices::Matrix4x4,
|
/// matrices::Matrix4x4,
|
||||||
/// rays::Ray,
|
/// rays::Ray,
|
||||||
/// spheres::Sphere,
|
/// shapes::Shape,
|
||||||
/// tuples::{Color, Tuple},
|
/// tuples::{Color, Tuple},
|
||||||
/// world::World,
|
/// world::World,
|
||||||
/// WHITE,
|
/// WHITE,
|
||||||
@ -120,8 +120,8 @@ impl World {
|
|||||||
/// // Shading with an intersection in shadow.
|
/// // Shading with an intersection in shadow.
|
||||||
/// let mut w = World::default();
|
/// let mut w = World::default();
|
||||||
/// w.lights = vec![PointLight::new(Tuple::point(0., 0., -10.), WHITE)];
|
/// w.lights = vec![PointLight::new(Tuple::point(0., 0., -10.), WHITE)];
|
||||||
/// let s1 = Sphere::default();
|
/// let s1 = Shape::sphere();
|
||||||
/// let mut s2 = Sphere::default();
|
/// let mut s2 = Shape::sphere();
|
||||||
/// s2.set_transform(Matrix4x4::translation(0., 0., 10.));
|
/// s2.set_transform(Matrix4x4::translation(0., 0., 10.));
|
||||||
/// w.objects = vec![s1, s2.clone()];
|
/// w.objects = vec![s1, s2.clone()];
|
||||||
/// let r = Ray::new(Tuple::point(0., 0., 5.), Tuple::vector(0., 0., 1.));
|
/// let r = Ray::new(Tuple::point(0., 0., 5.), Tuple::vector(0., 0., 1.));
|
||||||
@ -155,6 +155,7 @@ impl World {
|
|||||||
/// intersections::{prepare_computations, Intersection},
|
/// intersections::{prepare_computations, Intersection},
|
||||||
/// lights::PointLight,
|
/// lights::PointLight,
|
||||||
/// rays::Ray,
|
/// rays::Ray,
|
||||||
|
/// shapes::Shape,
|
||||||
/// tuples::{Color, Tuple},
|
/// tuples::{Color, Tuple},
|
||||||
/// world::World,
|
/// world::World,
|
||||||
/// BLACK,
|
/// BLACK,
|
||||||
@ -176,7 +177,7 @@ impl World {
|
|||||||
/// let w = {
|
/// let w = {
|
||||||
/// let mut w = World::test_world();
|
/// let mut w = World::test_world();
|
||||||
/// let mut outer = &mut w.objects[0];
|
/// let mut outer = &mut w.objects[0];
|
||||||
/// outer.material.ambient = 1.;
|
/// let m = outer.material.ambient = 1.;
|
||||||
/// let inner = &mut w.objects[1];
|
/// let inner = &mut w.objects[1];
|
||||||
/// inner.material.ambient = 1.;
|
/// inner.material.ambient = 1.;
|
||||||
/// w
|
/// w
|
||||||
@ -202,6 +203,7 @@ impl World {
|
|||||||
/// ```
|
/// ```
|
||||||
/// use rtchallenge::{
|
/// use rtchallenge::{
|
||||||
/// tuples::{ Tuple},
|
/// tuples::{ Tuple},
|
||||||
|
/// shapes::Shape,
|
||||||
/// world::World,
|
/// world::World,
|
||||||
/// };
|
/// };
|
||||||
///
|
///
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user