Fixed bug in new BVH4 traversal code.
This commit is contained in:
parent
a940630a27
commit
b135e8beb8
|
@ -9,7 +9,7 @@
|
||||||
|
|
||||||
use mem_arena::MemArena;
|
use mem_arena::MemArena;
|
||||||
|
|
||||||
use algorithm::partition_with_side;
|
use algorithm::{partition, partition_with_side};
|
||||||
use bbox::BBox;
|
use bbox::BBox;
|
||||||
use bbox4::BBox4;
|
use bbox4::BBox4;
|
||||||
use boundable::Boundable;
|
use boundable::Boundable;
|
||||||
|
@ -99,9 +99,9 @@ impl<'a> BVH4<'a> {
|
||||||
let mut unpopped = 0;
|
let mut unpopped = 0;
|
||||||
let mut first_loop = true;
|
let mut first_loop = true;
|
||||||
|
|
||||||
let ray_code = (rays[0].dir_inv.x().is_sign_negative() as u8) |
|
let ray_code = ((rays[0].dir_inv.x() < 0.0) as u8) |
|
||||||
((rays[0].dir_inv.y().is_sign_negative() as u8) << 1) |
|
(((rays[0].dir_inv.y() < 0.0) as u8) << 1) |
|
||||||
((rays[0].dir_inv.z().is_sign_negative() as u8) << 2);
|
(((rays[0].dir_inv.z() < 0.0) as u8) << 2);
|
||||||
|
|
||||||
while stack_ptr > 0 {
|
while stack_ptr > 0 {
|
||||||
match node_stack[stack_ptr] {
|
match node_stack[stack_ptr] {
|
||||||
|
@ -117,11 +117,10 @@ impl<'a> BVH4<'a> {
|
||||||
let mut all_hits = 0;
|
let mut all_hits = 0;
|
||||||
|
|
||||||
// Ray testing
|
// Ray testing
|
||||||
let part = filter_rays(&ray_i_stack[stack_ptr..],
|
let part;
|
||||||
&mut rays[..ray_i_stack[stack_ptr]],
|
{
|
||||||
unpopped,
|
// Common code for ray testing below
|
||||||
|r, pop_count| {
|
let mut test_ray = |r: &mut AccelRay| {
|
||||||
if (!r.is_done()) && (first_loop || r.trav_stack.pop_to_nth(pop_count)) {
|
|
||||||
let hits = lerp_slice(bounds, r.time)
|
let hits = lerp_slice(bounds, r.time)
|
||||||
.intersect_accel_ray(r)
|
.intersect_accel_ray(r)
|
||||||
.to_bitmask();
|
.to_bitmask();
|
||||||
|
@ -147,9 +146,33 @@ impl<'a> BVH4<'a> {
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
return false;
|
return false;
|
||||||
});
|
};
|
||||||
|
|
||||||
|
// Skip some tests if it's the first loop
|
||||||
|
part = if first_loop {
|
||||||
|
filter_rays(&ray_i_stack[stack_ptr..],
|
||||||
|
&mut rays[..ray_i_stack[stack_ptr]],
|
||||||
|
unpopped,
|
||||||
|
|r, _| {
|
||||||
|
if !r.is_done() {
|
||||||
|
return test_ray(r);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
})
|
||||||
|
} else {
|
||||||
|
filter_rays(&ray_i_stack[stack_ptr..],
|
||||||
|
&mut rays[..ray_i_stack[stack_ptr]],
|
||||||
|
unpopped,
|
||||||
|
|r, pop_count| {
|
||||||
|
if (!r.is_done()) && r.trav_stack.pop_to_nth(pop_count) {
|
||||||
|
return test_ray(r);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
})
|
||||||
|
};
|
||||||
|
}
|
||||||
unpopped = 0;
|
unpopped = 0;
|
||||||
|
|
||||||
// Update stack based on ray testing results
|
// Update stack based on ray testing results
|
||||||
|
@ -176,10 +199,13 @@ impl<'a> BVH4<'a> {
|
||||||
filter_rays(&ray_i_stack[stack_ptr..],
|
filter_rays(&ray_i_stack[stack_ptr..],
|
||||||
&mut rays[..ray_i_stack[stack_ptr]],
|
&mut rays[..ray_i_stack[stack_ptr]],
|
||||||
unpopped,
|
unpopped,
|
||||||
|r, pop_count| r.trav_stack.pop_to_nth(pop_count))
|
|r, pop_count| {
|
||||||
|
(!r.is_done()) && r.trav_stack.pop_to_nth(pop_count)
|
||||||
|
})
|
||||||
} else {
|
} else {
|
||||||
ray_i_stack[stack_ptr]
|
ray_i_stack[stack_ptr]
|
||||||
};
|
};
|
||||||
|
|
||||||
unpopped = 0;
|
unpopped = 0;
|
||||||
|
|
||||||
trav_time += timer.tick() as f64;
|
trav_time += timer.tick() as f64;
|
||||||
|
@ -195,10 +221,8 @@ impl<'a> BVH4<'a> {
|
||||||
|
|
||||||
None => {
|
None => {
|
||||||
if !first_loop {
|
if !first_loop {
|
||||||
// unpopped += 1;
|
unpopped += 1;
|
||||||
for r in (&mut rays[..ray_i_stack[stack_ptr]]).iter_mut() {
|
|
||||||
r.trav_stack.pop();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
stack_ptr -= 1;
|
stack_ptr -= 1;
|
||||||
}
|
}
|
||||||
|
@ -207,6 +231,14 @@ impl<'a> BVH4<'a> {
|
||||||
first_loop = false;
|
first_loop = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Pop any unpopped bits of the ray traversal stacks
|
||||||
|
if unpopped > 0 {
|
||||||
|
filter_rays(&ray_i_stack[1..],
|
||||||
|
&mut rays[..ray_i_stack[1]],
|
||||||
|
unpopped - 1,
|
||||||
|
|r, pop_count| r.trav_stack.pop_to_nth(pop_count));
|
||||||
|
}
|
||||||
|
|
||||||
trav_time += timer.tick() as f64;
|
trav_time += timer.tick() as f64;
|
||||||
ACCEL_TRAV_TIME.with(|att| {
|
ACCEL_TRAV_TIME.with(|att| {
|
||||||
let v = att.get();
|
let v = att.get();
|
||||||
|
@ -425,31 +457,31 @@ fn filter_rays<F>(ray_i_stack: &[usize],
|
||||||
-> usize
|
-> usize
|
||||||
where F: FnMut(&mut AccelRay, usize) -> bool
|
where F: FnMut(&mut AccelRay, usize) -> bool
|
||||||
{
|
{
|
||||||
// let part = if unpopped == 0 {
|
let part = if ray_i_stack[0] == ray_i_stack[unpopped] {
|
||||||
partition_with_side(rays, |r, _| ray_test(r, 1))
|
let pop_count = unpopped + 1;
|
||||||
// } else {
|
partition(rays, |r| ray_test(r, pop_count))
|
||||||
// let mut part_n = [0, rays.len()]; // Where we are in the partition
|
} else {
|
||||||
// let mut part_pop = [unpopped, 0]; // Number of bits to pop on the left and right side
|
let mut part_n = [0, rays.len() - 1]; // Where we are in the partition
|
||||||
|
let mut part_pop = [unpopped, 0]; // Number of bits to pop on the left and right side
|
||||||
|
|
||||||
// partition_with_side(rays, |r, side| {
|
partition_with_side(rays, |r, side| {
|
||||||
// let pop_count = 1 +
|
let pop_count = if !side {
|
||||||
// if side {
|
while part_n[0] >= ray_i_stack[part_pop[0]] {
|
||||||
// part_n[1] -= 1;
|
part_pop[0] -= 1;
|
||||||
// while part_n[1] < ray_i_stack[part_pop[1] + 1] && part_pop[1] < unpopped {
|
}
|
||||||
// part_pop[1] += 1;
|
part_n[0] += 1;
|
||||||
// }
|
part_pop[0]
|
||||||
// part_pop[1]
|
} else {
|
||||||
// } else {
|
while part_n[1] < ray_i_stack[part_pop[1] + 1] && part_pop[1] < unpopped {
|
||||||
// while part_n[0] >= ray_i_stack[part_pop[0]] {
|
part_pop[1] += 1;
|
||||||
// part_pop[0] -= 1;
|
}
|
||||||
// }
|
part_n[1] -= 1;
|
||||||
// part_n[0] += 1;
|
part_pop[1]
|
||||||
// part_pop[0]
|
};
|
||||||
// };
|
|
||||||
|
|
||||||
// return ray_test(r, pop_count);
|
return ray_test(r, pop_count + 1);
|
||||||
// })
|
})
|
||||||
// };
|
};
|
||||||
|
|
||||||
// part
|
part
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,7 @@ use color::XYZ;
|
||||||
use lerp::{lerp, lerp_slice, lerp_slice_with};
|
use lerp::{lerp, lerp_slice, lerp_slice_with};
|
||||||
use math::{Point, Matrix4x4, cross};
|
use math::{Point, Matrix4x4, cross};
|
||||||
use ray::{Ray, AccelRay};
|
use ray::{Ray, AccelRay};
|
||||||
use shading::surface_closure::{SurfaceClosureUnion, GTRClosure};
|
use shading::surface_closure::{SurfaceClosureUnion, GTRClosure, LambertClosure};
|
||||||
|
|
||||||
use super::{Surface, SurfaceIntersection, SurfaceIntersectionData};
|
use super::{Surface, SurfaceIntersection, SurfaceIntersectionData};
|
||||||
use super::triangle;
|
use super::triangle;
|
||||||
|
@ -106,16 +106,15 @@ impl<'a> Surface for TriangleMesh<'a> {
|
||||||
local_space: mat_space,
|
local_space: mat_space,
|
||||||
},
|
},
|
||||||
// TODO: get surface closure from surface shader.
|
// TODO: get surface closure from surface shader.
|
||||||
//closure: SurfaceClosureUnion::LambertClosure(
|
closure: SurfaceClosureUnion::LambertClosure(
|
||||||
// LambertClosure::new(XYZ::new(0.8, 0.8, 0.8))
|
LambertClosure::new(XYZ::new(0.8, 0.8, 0.8))
|
||||||
//),
|
),
|
||||||
closure:
|
// closure:
|
||||||
SurfaceClosureUnion::GTRClosure(GTRClosure::new(XYZ::new(0.8,
|
// SurfaceClosureUnion::GTRClosure(
|
||||||
0.8,
|
// GTRClosure::new(XYZ::new(0.8, 0.8, 0.8),
|
||||||
0.8),
|
// 0.1,
|
||||||
0.1,
|
// 2.0,
|
||||||
2.0,
|
// 1.0)),
|
||||||
1.0)),
|
|
||||||
};
|
};
|
||||||
r.max_t = t;
|
r.max_t = t;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in New Issue
Block a user