Extract iteration limiting into a function
This commit is contained in:
parent
1c283a6fbe
commit
b10d30c902
|
|
@ -171,22 +171,35 @@ impl Space {
|
|||
}
|
||||
}
|
||||
|
||||
/// Like [`std::iter::successors`] but with an upper limit on iteration count.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// Panics if the sequence doesn’t terminate in `max_iters` calls of `succ`.
|
||||
fn iterate_with_limit<T>(max_iters: usize, init: T, mut succ: impl FnMut(T) -> Option<T>) {
|
||||
let mut state = init;
|
||||
for _ in 0..max_iters {
|
||||
match succ(state) {
|
||||
Some(next) => state = next,
|
||||
None => return,
|
||||
}
|
||||
}
|
||||
panic!("iteration limit exceeded");
|
||||
}
|
||||
|
||||
impl Traceable for Space {
|
||||
fn trace(&self, camera: Location, ray: Ray) -> Vec<Hit> {
|
||||
let ray = self.camera_ray_to_abs(camera, ray);
|
||||
let mut hits = vec![];
|
||||
std::iter::successors(Some(ray), |ray: &Ray| {
|
||||
iterate_with_limit(100, ray, |ray| {
|
||||
let ret = self
|
||||
.trace_iter(*ray)
|
||||
.trace_iter(ray)
|
||||
.skip(1)
|
||||
.find_map(|ray| self.obj_hitter(ray.pos).map(|hitter| hitter(self, ray)))
|
||||
.expect("Space::trace_iter does not terminate");
|
||||
hits.extend(ret.objects); // TODO fix distance
|
||||
ret.end
|
||||
})
|
||||
.nth(100)
|
||||
.is_some()
|
||||
.then(|| panic!("tracing didn't terminate"));
|
||||
});
|
||||
hits
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user