Provide a tangent at each traced point

This commit is contained in:
numzero 2024-09-23 22:24:43 +03:00
parent 1d57ca8a93
commit b8f0ce0b68
4 changed files with 22 additions and 21 deletions

View File

@ -166,13 +166,13 @@ fn draw_ray_2(gc: &mut Vec<Draw>, space: &Space, camera: Location, dir: Vec3) {
gc.new_path(); gc.new_path();
gc.move_to(pos.x, pos.y); gc.move_to(pos.x, pos.y);
for pt in &path.points[1..] { for pt in &path.points[1..] {
gc.line_to(pt.x, pt.y); gc.line_to(pt.pos.x, pt.pos.y);
} }
let end_pos = *path let end_pos = *path
.points .points
.last() .last()
.expect("the starting point is always in the path"); .expect("the starting point is always in the path");
let dir_pos = end_pos + 1000.0 * path.end_dir; let dir_pos = end_pos.forward(1000. / DT).pos;
gc.line_to(dir_pos.x, dir_pos.y); gc.line_to(dir_pos.x, dir_pos.y);
gc.stroke(); gc.stroke();
} }

View File

@ -1,5 +1,5 @@
use glam::*; use glam::*;
use itertools::{chain, iproduct}; use itertools::{chain, iproduct, Itertools};
use refraction::ifaces::{DebugTraceable, Traceable}; use refraction::ifaces::{DebugTraceable, Traceable};
use refraction::tube::metric::Tube; use refraction::tube::metric::Tube;
@ -107,9 +107,9 @@ fn draw_ray_2(gc: &mut Vec<Line>, space: &Space, camera: Location, dir: Vec3) {
let end_pos = *pts let end_pos = *pts
.last() .last()
.expect("the starting point is always in the path"); .expect("the starting point is always in the path");
let dir_pos = end_pos + 10000.0 * path.end_dir; let dir_pos = end_pos.forward(10000.0);
pts.push(dir_pos); pts.push(dir_pos);
gc.push(Line::Strip(pts)); gc.push(Line::Strip(pts.into_iter().map(|r| r.pos).collect()));
} }
fn draw_fan_2(space: &Space, camera: Location, spread: f32) -> Vec<Line> { fn draw_fan_2(space: &Space, camera: Location, spread: f32) -> Vec<Line> {

View File

@ -1,5 +1,4 @@
use crate::types::{Hit, Location, Ray}; use crate::types::{Hit, Location, Ray};
use glam::Vec3;
pub trait Traceable { pub trait Traceable {
/// Traces a ray from a given starting point. `ray` is relative to the camera. /// Traces a ray from a given starting point. `ray` is relative to the camera.
@ -19,8 +18,7 @@ pub trait OptimizedTraceable: Traceable {
} }
pub struct RayPath { pub struct RayPath {
pub points: Vec<Vec3>, pub points: Vec<Ray>,
pub end_dir: Vec3,
} }
pub trait DebugTraceable: Traceable { pub trait DebugTraceable: Traceable {

View File

@ -146,16 +146,25 @@ impl Space {
.collect() .collect()
} }
pub fn line(&self, a: Vec3, b: Vec3, step: f32) -> Vec<Vec3> { pub fn line(&self, a: Vec3, b: Vec3, step: f32) -> Vec<Ray> {
match self.which_subspace(a) { match self.which_subspace(a) {
Outer => vec![b], Outer => vec![Ray {
pos: b,
dir: (b - a).normalize(),
}],
Inner => { Inner => {
let cs = InnerCS(self.tube); let cs = InnerCS(self.tube);
let n = ((b - a).length() / step) as usize + 1; let n = ((b - a).length() / step) as usize + 1;
let a = cs.global_to_flat(a); let a = cs.global_to_flat(a);
let b = cs.global_to_flat(b); let b = cs.global_to_flat(b);
let dir = (b - a).normalize();
(1..=n) (1..=n)
.map(|k| cs.flat_to_global(a.lerp(b, k as f32 / n as f32))) .map(|k| {
cs.flat_to_global(Ray {
pos: a.lerp(b, k as f32 / n as f32),
dir,
})
})
.collect() .collect()
} }
Boundary => panic!("Can't draw a line here!"), Boundary => panic!("Can't draw a line here!"),
@ -210,9 +219,9 @@ impl DebugTraceable for Space {
let mut hits = vec![]; let mut hits = vec![];
let mut ray = self.camera_ray_to_abs(camera, ray); let mut ray = self.camera_ray_to_abs(camera, ray);
let trace_to_flat = |points: &mut Vec<Vec3>, ray| { let trace_to_flat = |points: &mut Vec<Ray>, ray| {
for ray in self.trace_iter(ray).skip(1) { for ray in self.trace_iter(ray).skip(1) {
points.push(ray.pos); points.push(ray);
if let Some(hitter) = self.obj_hitter(ray.pos) { if let Some(hitter) = self.obj_hitter(ray.pos) {
return (ray, hitter(self, ray)); return (ray, hitter(self, ray));
} }
@ -220,18 +229,12 @@ impl DebugTraceable for Space {
unreachable!("Space::trace_iter terminated!") unreachable!("Space::trace_iter terminated!")
}; };
points.push(ray.pos); points.push(ray);
for _ in 0..100 { for _ in 0..100 {
let (ray_into_flat, ret) = trace_to_flat(&mut points, ray); let (ray_into_flat, ret) = trace_to_flat(&mut points, ray);
hits.extend(ret.objects); // TODO fix distance hits.extend(ret.objects); // TODO fix distance
let Some(ray_outta_flat) = ret.end else { let Some(ray_outta_flat) = ret.end else {
return ( return (hits, RayPath { points });
hits,
RayPath {
points,
end_dir: ray_into_flat.dir.normalize(),
},
);
}; };
points.extend(self.line(ray_into_flat.pos, ray_outta_flat.pos, 10.0)); points.extend(self.line(ray_into_flat.pos, ray_outta_flat.pos, 10.0));
ray = ray_outta_flat; ray = ray_outta_flat;