From 0880a0f19d5646459220dfbbe54b485b43d22474 Mon Sep 17 00:00:00 2001 From: Nathan Vegdahl Date: Thu, 7 Jul 2016 19:51:19 -0700 Subject: [PATCH] Make renderer actually use the material system properly. The intersection code still isn't using any kind of shading, and materials aren't parsed by the parser, but the renderer class itself is using them. --- src/renderer.rs | 8 ++++---- src/shading/surface_closure.rs | 17 ++++++++++++++++- src/surface/mod.rs | 3 ++- src/surface/triangle_mesh.rs | 9 +++++++-- 4 files changed, 29 insertions(+), 8 deletions(-) diff --git a/src/renderer.rs b/src/renderer.rs index d1177b4..295ef29 100644 --- a/src/renderer.rs +++ b/src/renderer.rs @@ -234,7 +234,7 @@ impl LightPath { pos, nor, local_space: _, - uv: _ } = isect { + closure } = isect { // Hit something! Do the stuff self.interaction = *isect; // Store interaction for use in next phase @@ -267,7 +267,7 @@ impl LightPath { // Calculate and store the light that will be contributed // to the film plane if the light is not in shadow. self.pending_color_addition = { - let material = LambertClosure::new(XYZ::new(0.8, 0.8, 0.8)); + let material = closure.as_surface_closure(); let la = material.evaluate(ray.dir, shadow_vec, nor, self.wavelength); light_color * la * self.light_attenuation / light_pdf }; @@ -307,10 +307,10 @@ impl LightPath { incoming, nor, local_space: _, - uv: _ } = self.interaction { + closure } = self.interaction { // Sample material let (dir, filter, pdf) = { - let material = LambertClosure::new(XYZ::new(0.8, 0.8, 0.8)); + let material = closure.as_surface_closure(); let u = self.next_lds_samp(); let v = self.next_lds_samp(); material.sample(incoming, nor, (u, v), self.wavelength) diff --git a/src/shading/surface_closure.rs b/src/shading/surface_closure.rs index 1ef4d80..ae995e1 100644 --- a/src/shading/surface_closure.rs +++ b/src/shading/surface_closure.rs @@ -4,8 +4,23 @@ use sampling::cosine_sample_hemisphere; use std::f32::consts::PI as PI_32; const INV_PI: f32 = 1.0 / PI_32; +#[derive(Debug, Copy, Clone)] +pub enum SurfaceClosureUnion { + EmitClosure(EmitClosure), + LambertClosure(LambertClosure), +} + +impl SurfaceClosureUnion { + pub fn as_surface_closure(&self) -> &SurfaceClosure { + match self { + &SurfaceClosureUnion::EmitClosure(ref closure) => closure as &SurfaceClosure, + &SurfaceClosureUnion::LambertClosure(ref closure) => closure as &SurfaceClosure, + } + } +} + /// Trait for surface closures. -pub trait SurfaceClosure: Copy { +pub trait SurfaceClosure { /// Returns whether the closure has a delta distribution or not. fn is_delta(&self) -> bool; diff --git a/src/surface/mod.rs b/src/surface/mod.rs index 561da71..cb1e1c0 100644 --- a/src/surface/mod.rs +++ b/src/surface/mod.rs @@ -4,6 +4,7 @@ use std::fmt::Debug; pub mod triangle_mesh; +use shading::surface_closure::SurfaceClosureUnion; use ray::{Ray, AccelRay}; use math::{Point, Vector, Normal, Matrix4x4}; use boundable::Boundable; @@ -19,7 +20,7 @@ pub enum SurfaceIntersection { incoming: Vector, nor: Normal, local_space: Matrix4x4, - uv: (f32, f32), + closure: SurfaceClosureUnion, }, } diff --git a/src/surface/triangle_mesh.rs b/src/surface/triangle_mesh.rs index 4f89b79..c5118c8 100644 --- a/src/surface/triangle_mesh.rs +++ b/src/surface/triangle_mesh.rs @@ -7,6 +7,8 @@ use triangle; use bbox::BBox; use boundable::Boundable; use bvh::BVH; +use shading::surface_closure::{SurfaceClosureUnion, LambertClosure}; +use color::XYZ; use super::{Surface, SurfaceIntersection}; @@ -76,7 +78,7 @@ impl Surface for TriangleMesh { let mat_space = lerp_slice(space, wr.time); let mat_inv = mat_space.inverse(); let tri = (tri.0 * mat_inv, tri.1 * mat_inv, tri.2 * mat_inv); - if let Some((t, tri_u, tri_v)) = triangle::intersect_ray(wr, tri) { + if let Some((t, _, _)) = triangle::intersect_ray(wr, tri) { if t < r.max_t { if r.is_occlusion() { isects[r.id as usize] = SurfaceIntersection::Occlude; @@ -88,7 +90,10 @@ impl Surface for TriangleMesh { incoming: wr.dir, nor: cross(tri.0 - tri.1, tri.0 - tri.2).into_normal(), local_space: mat_space, - uv: (tri_u, tri_v), + // TODO + closure: SurfaceClosureUnion::LambertClosure( + LambertClosure::new(XYZ::new(0.8, 0.8, 0.8)) + ), }; r.max_t = t; }