From f1fcbe7449f8373d78eae6b7bc5ec7da2d74819b Mon Sep 17 00:00:00 2001 From: Bill Thiede Date: Sun, 23 Sep 2018 22:00:52 -0700 Subject: [PATCH] Add empty cornell box with light and flipped normals. --- rtiow/src/flip_normals.rs | 30 +++++++++ rtiow/src/lib.rs | 1 + rtiow/src/renderer.rs | 7 +- rtiow/src/scenes/cornell_box.rs | 116 ++++++++++++++++++++++++++++++++ rtiow/src/scenes/mod.rs | 1 + rtiow/src/scenes/test.rs | 1 - 6 files changed, 153 insertions(+), 3 deletions(-) create mode 100644 rtiow/src/flip_normals.rs create mode 100644 rtiow/src/scenes/cornell_box.rs diff --git a/rtiow/src/flip_normals.rs b/rtiow/src/flip_normals.rs new file mode 100644 index 0000000..2214d75 --- /dev/null +++ b/rtiow/src/flip_normals.rs @@ -0,0 +1,30 @@ +use aabb::AABB; +use hitable::Hit; +use hitable::HitRecord; +use ray::Ray; + +pub struct FlipNormals { + hitable: Box, +} + +impl FlipNormals { + pub fn new(hitable: Box) -> FlipNormals { + FlipNormals { hitable } + } +} + +impl Hit for FlipNormals { + fn hit(&self, r: Ray, t_min: f32, t_max: f32) -> Option { + if let Some(rec) = self.hitable.hit(r, t_min, t_max) { + return Some(HitRecord { + normal: -rec.normal, + ..rec + }); + }; + None + } + + fn bounding_box(&self, t_min: f32, t_max: f32) -> Option { + self.hitable.bounding_box(t_min, t_max) + } +} diff --git a/rtiow/src/lib.rs b/rtiow/src/lib.rs index 912a780..fee5d69 100644 --- a/rtiow/src/lib.rs +++ b/rtiow/src/lib.rs @@ -1,6 +1,7 @@ pub mod aabb; pub mod bvh; pub mod camera; +pub mod flip_normals; pub mod hitable; pub mod hitable_list; pub mod kdtree; diff --git a/rtiow/src/renderer.rs b/rtiow/src/renderer.rs index cf3bc2c..b416608 100644 --- a/rtiow/src/renderer.rs +++ b/rtiow/src/renderer.rs @@ -26,6 +26,7 @@ pub enum Model { Tutorial, BVH, Test, + CornellBox, } impl Model { @@ -36,6 +37,7 @@ impl Model { Model::Tutorial => scenes::tutorial::new(&opt), Model::BVH => scenes::bvh::new(&opt), Model::Test => scenes::test::new(&opt), + Model::CornellBox => scenes::cornell_box::new(&opt), } } } @@ -58,6 +60,7 @@ impl str::FromStr for Model { "tutorial" => Ok(Model::Tutorial), "bvh" => Ok(Model::BVH), "test" => Ok(Model::Test), + "cornell_box" => Ok(Model::CornellBox), _ => Err(ModelParseError(s.to_owned())), } } @@ -75,8 +78,8 @@ pub struct Opt { /// Sub-samples per pixel #[structopt(short = "s", long = "subsample", default_value = "8")] pub subsamples: usize, - /// Select scene to render, one of: "bench", "book", "tutorial", "bvh", "test" - #[structopt(long = "model", default_value = "test")] + /// Select scene to render, one of: "bench", "book", "tutorial", "bvh", "test", "cornell_box" + #[structopt(long = "model", default_value = "cornell_box")] pub model: Model, /// Path to store pprof profile data, i.e. /tmp/cpuprofile.pprof #[structopt(long = "pprof", parse(from_os_str))] diff --git a/rtiow/src/scenes/cornell_box.rs b/rtiow/src/scenes/cornell_box.rs new file mode 100644 index 0000000..af4aacb --- /dev/null +++ b/rtiow/src/scenes/cornell_box.rs @@ -0,0 +1,116 @@ +use camera::Camera; +use flip_normals::FlipNormals; +use hitable::Hit; +use hitable_list::HitableList; +use kdtree::KDTree; +use material::DiffuseLight; +use material::Lambertian; +use rect::XYRect; +use rect::XZRect; +use rect::YZRect; +use renderer::Opt; +use renderer::Scene; +use texture::ConstantTexture; +use vec3::Vec3; + +pub fn new(opt: &Opt) -> Scene { + let lookfrom = Vec3::new(278., 278., -800.); + let lookat = Vec3::new(278., 278., 0.); + let dist_to_focus = 10.0; + let aperture = 0.0; + let time_min = 0.; + let time_max = 1.; + let camera = Camera::new( + lookfrom, + lookat, + Vec3::new(0., 1., 0.), + 40., + opt.width as f32 / opt.height as f32, + aperture, + dist_to_focus, + time_min, + time_max, + ); + + let objects: Vec> = vec![ + // Green wall left + Box::new(FlipNormals::new(Box::new(YZRect::new( + 0., + 555., + 0., + 555., + 555., + Box::new(Lambertian::new(Box::new(ConstantTexture::new(Vec3::new( + 0.12, 0.45, 0.15, + ))))), + )))), + // Red floor right + Box::new(YZRect::new( + 0., + 555., + 0., + 555., + 0., + Box::new(Lambertian::new(Box::new(ConstantTexture::new(Vec3::new( + 0.65, 0.05, 0.05, + ))))), + )), + // Light in ceiling + Box::new(XZRect::new( + 213., + 343., + 227., + 332., + 554., + Box::new(DiffuseLight::new(Box::new(ConstantTexture::new( + Vec3::new(15., 15., 15.), + )))), + )), + // Grey ceiling + Box::new(FlipNormals::new(Box::new(XZRect::new( + 0., + 555., + 0., + 555., + 555., + Box::new(Lambertian::new(Box::new(ConstantTexture::new(Vec3::new( + 0.73, 0.73, 0.73, + ))))), + )))), + // Grey floor + Box::new(XZRect::new( + 0., + 555., + 0., + 555., + 0., + Box::new(Lambertian::new(Box::new(ConstantTexture::new(Vec3::new( + 0.73, 0.73, 0.73, + ))))), + )), + // Grey back wall + Box::new(FlipNormals::new(Box::new(XYRect::new( + 0., + 555., + 0., + 555., + 555., + Box::new(Lambertian::new(Box::new(ConstantTexture::new(Vec3::new( + 0.73, 0.73, 0.73, + ))))), + )))), + ]; + let world: Box = if opt.use_accel { + Box::new(KDTree::new(objects, time_min, time_max)) + } else { + Box::new(HitableList::new(objects)) + }; + Scene { + camera, + world, + subsamples: opt.subsamples, + width: opt.width, + height: opt.height, + global_illumination: false, + } +} diff --git a/rtiow/src/scenes/mod.rs b/rtiow/src/scenes/mod.rs index 2ccfcef..2dd5240 100644 --- a/rtiow/src/scenes/mod.rs +++ b/rtiow/src/scenes/mod.rs @@ -1,5 +1,6 @@ pub mod bench; pub mod book; pub mod bvh; +pub mod cornell_box; pub mod test; pub mod tutorial; diff --git a/rtiow/src/scenes/test.rs b/rtiow/src/scenes/test.rs index fe97e53..6d493ff 100644 --- a/rtiow/src/scenes/test.rs +++ b/rtiow/src/scenes/test.rs @@ -43,7 +43,6 @@ pub fn new(opt: &Opt) -> Scene { let world_image_bytes = include_bytes!("../../images/world.jpg"); let it = ImageTexture::new(image::load_from_memory(world_image_bytes).unwrap().to_rgb()); - let it2 = ImageTexture::new(image::load_from_memory(world_image_bytes).unwrap().to_rgb()); let objects: Vec> = vec![ // Big sphere Box::new(Sphere::new(