pbrt/src/core/interaction.rs

71 lines
2.6 KiB
Rust

use crate::globals::get_options;
use shared::core::interaction::{
InteractionBase, InteractionTrait, MediumInteraction, SimpleInteraction, SurfaceInteraction,
};
pub trait InteractionGetter {
fn get_bsdf(
&mut self,
r: &Ray,
lambda: &SampledWavelengths,
camera: &Camera,
sampler: &mut Sampler,
) -> Option<BSDF> {
self.compute_differentials(r, camera, sampler.samples_per_pixel() as i32);
let material = {
let root_mat = self.material;
let mut active_mat: &Material = &*root_mat;
let tex_eval = UniversalTextureEvaluator;
while let Material::Mix(mix) = active_mat {
// We need a context to evaluate the 'amount' texture
let ctx = MaterialEvalContext::from(&*self);
active_mat = mix.choose_material(&tex_eval, &ctx)?;
}
active_mat.clone()
};
let ctx = MaterialEvalContext::from(&*self);
let tex_eval = UniversalTextureEvaluator;
let displacement = material.get_displacement();
let normal_map = Ptr::from(material.get_normal_map().unwrap());
if !displacement.is_null() || !normal_map.is_null() {
// This calls the function defined above
self.compute_bump_geom(&tex_eval, displacement, normal_map);
}
let mut bsdf = material.get_bsdf(&tex_eval, &ctx, lambda);
if get_options().force_diffuse {
let r = bsdf.rho_wo(self.common.wo, &[sampler.get1d()], &[sampler.get2d()]);
let diff_bxdf = BxDF::Diffuse(DiffuseBxDF::new(r));
bsdf = BSDF::new(self.shading.n, self.shading.dpdu, Ptr::from(&diff_bxdf));
}
Some(bsdf)
}
fn get_bssrdf(
&self,
_ray: &Ray,
lambda: &SampledWavelengths,
_camera: &Camera,
) -> Option<BSSRDF> {
let material = {
let mut active_mat = unsafe { self.material.as_ref() };
let tex_eval = UniversalTextureEvaluator;
while let Material::Mix(mix) = active_mat {
// We need a context to evaluate the 'amount' texture
let ctx = MaterialEvalContext::from(self);
active_mat = mix.choose_material(&tex_eval, &ctx)?;
}
active_mat.clone()
};
let ctx = MaterialEvalContext::from(self);
let tex_eval = UniversalTextureEvaluator;
material.get_bssrdf(&tex_eval, &ctx, lambda)
}
}
impl InteractionGetter for SurfaceInteraction {}
impl InteractionGetter for MediumInteraction {}
impl InteractionGetter for SimpleInteraction {}