pbrt/src/lights/point.rs

74 lines
2.2 KiB
Rust

use crate::core::light::{CreateLight, LightBaseTrait, lookup_spectrum};
use crate::core::spectrum::spectrum_to_photometric;
use crate::core::texture::FloatTexture;
use crate::utils::{Arena, FileLoc, ParameterDictionary};
use shared::core::geometry::VectorLike;
use shared::core::light::{Light, LightBase, LightType};
use shared::core::medium::{Medium, MediumInterface};
use shared::core::shape::Shape;
use shared::core::spectrum::Spectrum;
use shared::lights::PointLight;
use shared::spectra::RGBColorSpace;
use shared::utils::Transform;
use shared::{Float, PI};
pub trait CreatePointLight {
fn new(
render_from_light: Transform,
medium_interface: MediumInterface,
le: Spectrum,
scale: Float,
) -> Self;
}
impl CreatePointLight for PointLight {
fn new(
render_from_light: Transform,
medium_interface: MediumInterface,
le: Spectrum,
scale: Float,
) -> Self {
let base = LightBase::new(
LightType::DeltaPosition,
render_from_light,
medium_interface,
);
let i = lookup_spectrum(le);
Self { base, scale, i }
}
}
impl CreateLight for PointLight {
fn create(
arena: &mut Arena,
render_from_light: Transform,
medium: Medium,
parameters: &ParameterDictionary,
loc: &FileLoc,
shape: &Shape,
alpha_text: &FloatTexture,
colorspace: Option<&RGBColorSpace>,
) -> Result<Light, Error> {
let l = parameters
.get_one_spectrum(
"L",
colorspace.unwrap().illuminant,
SpectrumType::Illuminant,
)
.unwrap();
let mut scale = parameters.get_one_float("scale", 1);
scale /= spectrum_to_photometric(l.unwrap());
let phi_v = parameters.get_one_float("power", 1.);
if phi_v > 0. {
let k_e = 4. * PI;
sc *= phi_v / k_e;
}
let from = parameters.get_one_point3f("from", Point3f::zero());
let tf = Transform::translate(from.into());
let final_render = render_from_light * tf;
let specific = PointLight::new(final_render, medium.into(), l, scale);
Ok(Light::Point(specific))
}
}