mirror of
https://gitlab.com/veloren/veloren.git
synced 2024-08-30 18:12:32 +00:00
Moved closest_line_seg_line_seg to common/systems/src/phys.rs and renamed to closest_points_ls3
This commit is contained in:
parent
b9239cf603
commit
c86f000881
@ -2200,6 +2200,43 @@ fn closest_points(n: LineSegment2<f32>, m: LineSegment2<f32>) -> (Vec2<f32>, Vec
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Get closest point between 2 3D line segments https://math.stackexchange.com/a/4289668
|
||||||
|
pub fn closest_points_ls3(n: LineSegment3<f32>, m: LineSegment3<f32>) -> (Vec3<f32>, Vec3<f32>) {
|
||||||
|
let p1 = n.start;
|
||||||
|
let p2 = n.end;
|
||||||
|
let p3 = m.start;
|
||||||
|
let p4 = m.end;
|
||||||
|
|
||||||
|
let d1 = p2 - p1;
|
||||||
|
let d2 = p4 - p3;
|
||||||
|
let d21 = p3 - p1;
|
||||||
|
|
||||||
|
let v22 = d2.dot(d2);
|
||||||
|
let v11 = d1.dot(d1);
|
||||||
|
let v21 = d2.dot(d1);
|
||||||
|
let v21_1 = d21.dot(d1);
|
||||||
|
let v21_2 = d21.dot(d2);
|
||||||
|
|
||||||
|
let denom = v21 * v21 - v22 * v11;
|
||||||
|
|
||||||
|
let (s, t) = if denom == 0.0 {
|
||||||
|
let s = 0.0;
|
||||||
|
let t = (v11 * s - v21_1) / v21;
|
||||||
|
(s, t)
|
||||||
|
} else {
|
||||||
|
let s = (v21_2 * v21 - v22 * v21_1) / denom;
|
||||||
|
let t = (-v21_1 * v21 + v11 * v21_2) / denom;
|
||||||
|
(s, t)
|
||||||
|
};
|
||||||
|
|
||||||
|
let (s, t) = (s.clamp(0.0, 1.0), t.clamp(0.0, 1.0));
|
||||||
|
|
||||||
|
let p_a = p1 + s * d1;
|
||||||
|
let p_b = p3 + t * d2;
|
||||||
|
|
||||||
|
(p_a, p_b)
|
||||||
|
}
|
||||||
|
|
||||||
/// Find pushback vector and collision_distance we assume between this
|
/// Find pushback vector and collision_distance we assume between this
|
||||||
/// colliders assuming that only one of them is capsule prism.
|
/// colliders assuming that only one of them is capsule prism.
|
||||||
fn capsule2cylinder(c0: ColliderContext, c1: ColliderContext) -> (Vec2<f32>, f32) {
|
fn capsule2cylinder(c0: ColliderContext, c1: ColliderContext) -> (Vec2<f32>, f32) {
|
||||||
|
@ -13,6 +13,7 @@ use common::{
|
|||||||
vol::ReadVol,
|
vol::ReadVol,
|
||||||
};
|
};
|
||||||
use common_base::span;
|
use common_base::span;
|
||||||
|
use common_systems::phys::closest_points_ls3;
|
||||||
|
|
||||||
#[derive(Clone, Copy, Debug)]
|
#[derive(Clone, Copy, Debug)]
|
||||||
pub struct Target<T> {
|
pub struct Target<T> {
|
||||||
@ -305,12 +306,7 @@ pub(super) fn ray_entities(
|
|||||||
start: world_p0,
|
start: world_p0,
|
||||||
end: world_p1,
|
end: world_p1,
|
||||||
};
|
};
|
||||||
closest_line_seg_line_seg(
|
closest_points_ls3(seg_ray, seg_capsule)
|
||||||
seg_ray.start,
|
|
||||||
seg_ray.end,
|
|
||||||
seg_capsule.start,
|
|
||||||
seg_capsule.end,
|
|
||||||
)
|
|
||||||
} else {
|
} else {
|
||||||
let nearest = seg_ray.projected_point(world_p0);
|
let nearest = seg_ray.projected_point(world_p0);
|
||||||
(nearest, world_p0)
|
(nearest, world_p0)
|
||||||
@ -338,48 +334,3 @@ pub(super) fn ray_entities(
|
|||||||
|
|
||||||
entity
|
entity
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get closest point between 2 line segments https://math.stackexchange.com/a/4289668
|
|
||||||
fn closest_line_seg_line_seg(
|
|
||||||
p1: Vec3<f32>,
|
|
||||||
p2: Vec3<f32>,
|
|
||||||
p3: Vec3<f32>,
|
|
||||||
p4: Vec3<f32>,
|
|
||||||
) -> (Vec3<f32>, Vec3<f32>) {
|
|
||||||
let p1 = Vec3::new(p1.x as f64, p1.y as f64, p1.z as f64);
|
|
||||||
let p2 = Vec3::new(p2.x as f64, p2.y as f64, p2.z as f64);
|
|
||||||
let p3 = Vec3::new(p3.x as f64, p3.y as f64, p3.z as f64);
|
|
||||||
let p4 = Vec3::new(p4.x as f64, p4.y as f64, p4.z as f64);
|
|
||||||
|
|
||||||
let d1 = p2 - p1;
|
|
||||||
let d2 = p4 - p3;
|
|
||||||
let d21 = p3 - p1;
|
|
||||||
|
|
||||||
let v22 = d2.dot(d2);
|
|
||||||
let v11 = d1.dot(d1);
|
|
||||||
let v21 = d2.dot(d1);
|
|
||||||
let v21_1 = d21.dot(d1);
|
|
||||||
let v21_2 = d21.dot(d2);
|
|
||||||
|
|
||||||
let denom = v21 * v21 - v22 * v11;
|
|
||||||
|
|
||||||
let (s, t) = if denom == 0.0 {
|
|
||||||
let s = 0.0;
|
|
||||||
let t = (v11 * s - v21_1) / v21;
|
|
||||||
(s, t)
|
|
||||||
} else {
|
|
||||||
let s = (v21_2 * v21 - v22 * v21_1) / denom;
|
|
||||||
let t = (-v21_1 * v21 + v11 * v21_2) / denom;
|
|
||||||
(s, t)
|
|
||||||
};
|
|
||||||
|
|
||||||
let (s, t) = (s.clamp(0.0, 1.0), t.clamp(0.0, 1.0));
|
|
||||||
|
|
||||||
let p_a = p1 + s * d1;
|
|
||||||
let p_b = p3 + t * d2;
|
|
||||||
|
|
||||||
(
|
|
||||||
Vec3::new(p_a.x as f32, p_a.y as f32, p_a.z as f32),
|
|
||||||
Vec3::new(p_b.x as f32, p_b.y as f32, p_b.z as f32),
|
|
||||||
)
|
|
||||||
}
|
|
||||||
|
Loading…
Reference in New Issue
Block a user