Update psychopath code to work with RMath changes.
This commit is contained in:
parent
6dbdcba91a
commit
d55ec9b025
20
src/bbox.rs
20
src/bbox.rs
|
@ -7,7 +7,7 @@ use std::{
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
lerp::{lerp, lerp_slice, Lerp},
|
lerp::{lerp, lerp_slice, Lerp},
|
||||||
math::{fast_minf32, Point, Vector, Xform, XformFull},
|
math::{fast_minf32, Point, Vector, Xform},
|
||||||
};
|
};
|
||||||
|
|
||||||
const BBOX_MAXT_ADJUST: f32 = 1.000_000_24;
|
const BBOX_MAXT_ADJUST: f32 = 1.000_000_24;
|
||||||
|
@ -57,7 +57,7 @@ impl BBox {
|
||||||
// Creates a new BBox transformed from its local space to the
|
// Creates a new BBox transformed from its local space to the
|
||||||
// given space.
|
// given space.
|
||||||
#[must_use]
|
#[must_use]
|
||||||
pub fn xform(&self, xform: &XformFull) -> BBox {
|
pub fn xform(&self, xform: &Xform) -> BBox {
|
||||||
// BBox corners
|
// BBox corners
|
||||||
let vs = [
|
let vs = [
|
||||||
Point::new(self.min.x(), self.min.y(), self.min.z()),
|
Point::new(self.min.x(), self.min.y(), self.min.z()),
|
||||||
|
@ -73,7 +73,7 @@ impl BBox {
|
||||||
// Transform BBox corners and make new bbox
|
// Transform BBox corners and make new bbox
|
||||||
let mut b = BBox::new();
|
let mut b = BBox::new();
|
||||||
for v in &vs {
|
for v in &vs {
|
||||||
let v = v.xform(&xform);
|
let v = v.xform(xform);
|
||||||
b.min = v.min(b.min);
|
b.min = v.min(b.min);
|
||||||
b.max = v.max(b.max);
|
b.max = v.max(b.max);
|
||||||
}
|
}
|
||||||
|
@ -141,11 +141,7 @@ impl Lerp for BBox {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn transform_bbox_slice_from(
|
pub fn transform_bbox_slice_from(bbs_in: &[BBox], xforms: &[Xform], bbs_out: &mut Vec<BBox>) {
|
||||||
bbs_in: &[BBox],
|
|
||||||
xforms: &[Xform],
|
|
||||||
bbs_out: &mut Vec<BBox>,
|
|
||||||
) -> Result<(), ()> {
|
|
||||||
bbs_out.clear();
|
bbs_out.clear();
|
||||||
|
|
||||||
// Transform the bounding boxes
|
// Transform the bounding boxes
|
||||||
|
@ -153,19 +149,17 @@ pub fn transform_bbox_slice_from(
|
||||||
bbs_out.extend_from_slice(bbs_in);
|
bbs_out.extend_from_slice(bbs_in);
|
||||||
} else if bbs_in.len() == xforms.len() {
|
} else if bbs_in.len() == xforms.len() {
|
||||||
for (bb, xf) in Iterator::zip(bbs_in.iter(), xforms.iter()) {
|
for (bb, xf) in Iterator::zip(bbs_in.iter(), xforms.iter()) {
|
||||||
bbs_out.push(bb.xform(&xf.into_full().ok_or(())?));
|
bbs_out.push(bb.xform(&xf));
|
||||||
}
|
}
|
||||||
} else if bbs_in.len() > xforms.len() {
|
} else if bbs_in.len() > xforms.len() {
|
||||||
let s = (bbs_in.len() - 1) as f32;
|
let s = (bbs_in.len() - 1) as f32;
|
||||||
for (i, bb) in bbs_in.iter().enumerate() {
|
for (i, bb) in bbs_in.iter().enumerate() {
|
||||||
bbs_out.push(bb.xform(&lerp_slice(xforms, i as f32 / s).into_full().ok_or(())?));
|
bbs_out.push(bb.xform(&lerp_slice(xforms, i as f32 / s)));
|
||||||
}
|
}
|
||||||
} else if bbs_in.len() < xforms.len() {
|
} else if bbs_in.len() < xforms.len() {
|
||||||
let s = (xforms.len() - 1) as f32;
|
let s = (xforms.len() - 1) as f32;
|
||||||
for (i, xf) in xforms.iter().enumerate() {
|
for (i, xf) in xforms.iter().enumerate() {
|
||||||
bbs_out.push(lerp_slice(bbs_in, i as f32 / s).xform(&xf.into_full().ok_or(())?));
|
bbs_out.push(lerp_slice(bbs_in, i as f32 / s).xform(&xf));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -73,7 +73,7 @@ impl<'a> Camera<'a> {
|
||||||
|
|
||||||
pub fn generate_ray(&self, x: f32, y: f32, time: f32, wavelength: f32, u: f32, v: f32) -> Ray {
|
pub fn generate_ray(&self, x: f32, y: f32, time: f32, wavelength: f32, u: f32, v: f32) -> Ray {
|
||||||
// Get time-interpolated camera settings
|
// Get time-interpolated camera settings
|
||||||
let transform = lerp_slice(self.transforms, time).into_full_fast().unwrap();
|
let transform = lerp_slice(self.transforms, time).to_full_fast().unwrap();
|
||||||
let tfov = lerp_slice(self.tfovs, time);
|
let tfov = lerp_slice(self.tfovs, time);
|
||||||
let aperture_radius = lerp_slice(self.aperture_radii, time);
|
let aperture_radius = lerp_slice(self.aperture_radii, time);
|
||||||
let focus_distance = lerp_slice(self.focus_distances, time);
|
let focus_distance = lerp_slice(self.focus_distances, time);
|
||||||
|
|
|
@ -271,7 +271,7 @@ impl<'a> Surface for RectangleLight<'a> {
|
||||||
let dim = lerp_slice(self.dimensions, time);
|
let dim = lerp_slice(self.dimensions, time);
|
||||||
let xform = lerp_slice(space, time);
|
let xform = lerp_slice(space, time);
|
||||||
|
|
||||||
let space = if let Some(xform) = xform.into_full() {
|
let space = if let Some(xform) = xform.to_full() {
|
||||||
xform
|
xform
|
||||||
} else {
|
} else {
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -215,7 +215,7 @@ impl<'a> Surface for SphereLight<'a> {
|
||||||
let time = rays.time(ray_idx);
|
let time = rays.time(ray_idx);
|
||||||
|
|
||||||
// Get the transform space
|
// Get the transform space
|
||||||
let xform = if let Some(xform) = lerp_slice(space, time).into_full() {
|
let xform = if let Some(xform) = lerp_slice(space, time).to_full() {
|
||||||
xform
|
xform
|
||||||
} else {
|
} else {
|
||||||
return;
|
return;
|
||||||
|
|
|
@ -3,8 +3,8 @@
|
||||||
use std::f32;
|
use std::f32;
|
||||||
|
|
||||||
pub use rmath::{
|
pub use rmath::{
|
||||||
cross, cross_fast, dot, dot_fast, wide4::Float4, CrossProduct, DotProduct, Normal, Point,
|
cross, cross_fast, dot, dot_fast, wide4::Float4, AsXform, CrossProduct, DotProduct, Normal,
|
||||||
Vector, Xform, XformFull,
|
Point, Vector, Xform, XformFull,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// Clamps a value between a min and max.
|
/// Clamps a value between a min and max.
|
||||||
|
|
|
@ -58,7 +58,7 @@ impl<'a> Assembly<'a> {
|
||||||
} = *intr
|
} = *intr
|
||||||
{
|
{
|
||||||
let sel_xform = if !xform_stack.top().is_empty() {
|
let sel_xform = if !xform_stack.top().is_empty() {
|
||||||
if let Some(xform) = lerp_slice(xform_stack.top(), time).into_full() {
|
if let Some(xform) = lerp_slice(xform_stack.top(), time).to_full() {
|
||||||
xform
|
xform
|
||||||
} else {
|
} else {
|
||||||
return None;
|
return None;
|
||||||
|
@ -98,7 +98,7 @@ impl<'a> Assembly<'a> {
|
||||||
Xform::identity()
|
Xform::identity()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
.into_full();
|
.to_full();
|
||||||
|
|
||||||
// Sample the light
|
// Sample the light
|
||||||
if let Some(xform) = xform {
|
if let Some(xform) = xform {
|
||||||
|
@ -390,7 +390,7 @@ impl<'a> AssemblyBuilder<'a> {
|
||||||
// Transform the bounding boxes, if necessary
|
// Transform the bounding boxes, if necessary
|
||||||
if let Some((xstart, xend)) = inst.transform_indices {
|
if let Some((xstart, xend)) = inst.transform_indices {
|
||||||
let xf = &self.xforms[xstart..xend];
|
let xf = &self.xforms[xstart..xend];
|
||||||
transform_bbox_slice_from(&bbs, xf, &mut bbs2).unwrap();
|
transform_bbox_slice_from(&bbs, xf, &mut bbs2);
|
||||||
} else {
|
} else {
|
||||||
bbs2.clear();
|
bbs2.clear();
|
||||||
bbs2.extend(bbs);
|
bbs2.extend(bbs);
|
||||||
|
|
|
@ -9,7 +9,7 @@ use crate::{
|
||||||
bbox::BBox,
|
bbox::BBox,
|
||||||
boundable::Boundable,
|
boundable::Boundable,
|
||||||
lerp::lerp_slice,
|
lerp::lerp_slice,
|
||||||
math::{cross, dot, Normal, Point, Xform, XformFull},
|
math::{cross, dot, Normal, Point, Xform},
|
||||||
ray::{RayBatch, RayStack},
|
ray::{RayBatch, RayStack},
|
||||||
shading::SurfaceClosure,
|
shading::SurfaceClosure,
|
||||||
};
|
};
|
||||||
|
@ -154,13 +154,9 @@ impl<'a> MicropolyBatch<'a> {
|
||||||
) {
|
) {
|
||||||
// Precalculate transform for non-motion blur cases
|
// Precalculate transform for non-motion blur cases
|
||||||
let static_mat_space = if space.len() == 1 {
|
let static_mat_space = if space.len() == 1 {
|
||||||
if let Some(xform) = space[0].into_full() {
|
space[0]
|
||||||
xform
|
|
||||||
} else {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
XformFull::identity()
|
Xform::identity()
|
||||||
};
|
};
|
||||||
|
|
||||||
self.accel
|
self.accel
|
||||||
|
@ -209,11 +205,7 @@ impl<'a> MicropolyBatch<'a> {
|
||||||
// Calculate the ray space, if necessary.
|
// Calculate the ray space, if necessary.
|
||||||
let mat_space = if space.len() > 1 {
|
let mat_space = if space.len() > 1 {
|
||||||
// Per-ray transform, for motion blur
|
// Per-ray transform, for motion blur
|
||||||
if let Some(xform) = lerp_slice(space, ray_time).into_full() {
|
lerp_slice(space, ray_time)
|
||||||
xform
|
|
||||||
} else {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
static_mat_space
|
static_mat_space
|
||||||
};
|
};
|
||||||
|
@ -292,6 +284,13 @@ impl<'a> MicropolyBatch<'a> {
|
||||||
|
|
||||||
// Calculate intersection data if necessary.
|
// Calculate intersection data if necessary.
|
||||||
if non_shadow_hit {
|
if non_shadow_hit {
|
||||||
|
// Get the full space data.
|
||||||
|
let mat_space = if let Some(space) = mat_space.to_full() {
|
||||||
|
space
|
||||||
|
} else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
let hit_tri = unsafe { hit_tri.assume_init() };
|
let hit_tri = unsafe { hit_tri.assume_init() };
|
||||||
let hit_tri_indices = unsafe { hit_tri_indices.assume_init() };
|
let hit_tri_indices = unsafe { hit_tri_indices.assume_init() };
|
||||||
let (t, b0, b1, b2) = unsafe { hit_tri_data.assume_init() };
|
let (t, b0, b1, b2) = unsafe { hit_tri_data.assume_init() };
|
||||||
|
|
|
@ -7,7 +7,7 @@ use crate::{
|
||||||
bbox::BBox,
|
bbox::BBox,
|
||||||
boundable::Boundable,
|
boundable::Boundable,
|
||||||
lerp::lerp_slice,
|
lerp::lerp_slice,
|
||||||
math::{cross, dot, Normal, Point, Xform, XformFull},
|
math::{cross, dot, Normal, Point, Xform},
|
||||||
ray::{RayBatch, RayStack},
|
ray::{RayBatch, RayStack},
|
||||||
shading::SurfaceShader,
|
shading::SurfaceShader,
|
||||||
};
|
};
|
||||||
|
@ -132,13 +132,9 @@ impl<'a> Surface for TriangleMesh<'a> {
|
||||||
) {
|
) {
|
||||||
// Precalculate transform for non-motion blur cases
|
// Precalculate transform for non-motion blur cases
|
||||||
let static_mat_space = if space.len() == 1 {
|
let static_mat_space = if space.len() == 1 {
|
||||||
if let Some(xform) = lerp_slice(space, 0.0).into_full() {
|
space[0]
|
||||||
xform
|
|
||||||
} else {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
XformFull::identity()
|
Xform::identity()
|
||||||
};
|
};
|
||||||
|
|
||||||
self.accel
|
self.accel
|
||||||
|
@ -187,11 +183,7 @@ impl<'a> Surface for TriangleMesh<'a> {
|
||||||
// Calculate the ray space, if necessary.
|
// Calculate the ray space, if necessary.
|
||||||
let mat_space = if space.len() > 1 {
|
let mat_space = if space.len() > 1 {
|
||||||
// Per-ray transform, for motion blur
|
// Per-ray transform, for motion blur
|
||||||
if let Some(xform) = lerp_slice(space, ray_time).into_full() {
|
lerp_slice(space, ray_time)
|
||||||
xform
|
|
||||||
} else {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
} else {
|
} else {
|
||||||
static_mat_space
|
static_mat_space
|
||||||
};
|
};
|
||||||
|
@ -270,6 +262,13 @@ impl<'a> Surface for TriangleMesh<'a> {
|
||||||
|
|
||||||
// Calculate intersection data if necessary.
|
// Calculate intersection data if necessary.
|
||||||
if non_shadow_hit {
|
if non_shadow_hit {
|
||||||
|
// Get the full space data.
|
||||||
|
let mat_space = if let Some(space) = mat_space.to_full() {
|
||||||
|
space
|
||||||
|
} else {
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
let hit_tri = unsafe { hit_tri.assume_init() };
|
let hit_tri = unsafe { hit_tri.assume_init() };
|
||||||
let (t, b0, b1, b2) = unsafe { hit_tri_data.assume_init() };
|
let (t, b0, b1, b2) = unsafe { hit_tri_data.assume_init() };
|
||||||
|
|
||||||
|
|
|
@ -103,16 +103,27 @@ impl<'a> TracerInner<'a> {
|
||||||
// Do transforms
|
// Do transforms
|
||||||
// TODO: re-divide rays based on direction (maybe?).
|
// TODO: re-divide rays based on direction (maybe?).
|
||||||
let xforms = self.xform_stack.top();
|
let xforms = self.xform_stack.top();
|
||||||
|
let static_xform = if xforms.len() == 1 {
|
||||||
|
if let Some(xform) = xforms[0].to_full() {
|
||||||
|
Some(xform)
|
||||||
|
} else {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} else if xforms.len() == 0 {
|
||||||
|
Some(XformFull::identity())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
};
|
||||||
ray_stack.do_next_task(|ray_idx| {
|
ray_stack.do_next_task(|ray_idx| {
|
||||||
let t = rays.time(ray_idx);
|
let t = rays.time(ray_idx);
|
||||||
rays.update_local(
|
rays.update_local(
|
||||||
ray_idx,
|
ray_idx,
|
||||||
&if let Some(xform) = lerp_slice(xforms, t).into_full() {
|
&static_xform.unwrap_or_else(|| {
|
||||||
xform
|
lerp_slice(xforms, t).to_full().unwrap_or(
|
||||||
} else {
|
// TODO: filter out ray instead.
|
||||||
// TODO: filter out ray instead.
|
XformFull::identity(),
|
||||||
XformFull::identity()
|
)
|
||||||
},
|
}),
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
ray_stack.duplicate_next_task();
|
ray_stack.duplicate_next_task();
|
||||||
|
@ -142,17 +153,28 @@ impl<'a> TracerInner<'a> {
|
||||||
|
|
||||||
// Undo transforms
|
// Undo transforms
|
||||||
let xforms = self.xform_stack.top();
|
let xforms = self.xform_stack.top();
|
||||||
|
let static_xform = if xforms.len() == 1 {
|
||||||
|
if let Some(xform) = xforms[0].to_full() {
|
||||||
|
Some(xform)
|
||||||
|
} else {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
} else if xforms.len() == 0 {
|
||||||
|
Some(XformFull::identity())
|
||||||
|
} else {
|
||||||
|
None
|
||||||
|
};
|
||||||
if !xforms.is_empty() {
|
if !xforms.is_empty() {
|
||||||
ray_stack.pop_do_next_task(|ray_idx| {
|
ray_stack.pop_do_next_task(|ray_idx| {
|
||||||
let t = rays.time(ray_idx);
|
let t = rays.time(ray_idx);
|
||||||
rays.update_local(
|
rays.update_local(
|
||||||
ray_idx,
|
ray_idx,
|
||||||
&if let Some(xform) = lerp_slice(xforms, t).into_full() {
|
&static_xform.unwrap_or_else(|| {
|
||||||
xform
|
lerp_slice(xforms, t).to_full().unwrap_or(
|
||||||
} else {
|
// TODO: filter out ray instead.
|
||||||
// TODO: filter out ray instead.
|
XformFull::identity(),
|
||||||
XformFull::identity()
|
)
|
||||||
},
|
}),
|
||||||
);
|
);
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
|
|
Loading…
Reference in New Issue
Block a user