23#ifndef VCL_ALGORITHMS_CORE_INTERSECTION_INTERSECT_H
24#define VCL_ALGORITHMS_CORE_INTERSECTION_INTERSECT_H
26#include <vclib/space/core.h>
38template<PlaneConcept PlaneType, Segment3Concept SegmentType>
39void projectSegmentEndPoints(
42 typename SegmentType::ScalarType& p0Proj,
43 typename SegmentType::ScalarType& p1Proj)
45 using ScalarType = SegmentType::ScalarType;
48 p0Proj = s.p1() * p.direction() - p.offset();
49 p1Proj = s.p0() * p.direction() - p.offset();
56template<
typename ScalarType>
57inline void findMinMax(
76template<
typename ScalarType, Po
intConcept Po
intType>
77inline bool axisTestX01(
84 const PointType& bHalfSize)
86 ScalarType p0 = a * v0.y() - b * v0.z();
87 ScalarType p2 = a * v2.y() - b * v2.z();
97 ScalarType rad = fa * bHalfSize.y() + fb * bHalfSize.z();
98 if (
min > rad ||
max < -rad)
103template<
typename ScalarType, Po
intConcept Po
intType>
104inline bool axisTestX2(
111 const PointType& bHalfSize)
113 ScalarType p0 = a * v0.y() - b * v0.z();
114 ScalarType p1 = a * v1.y() - b * v1.z();
124 ScalarType rad = fa * bHalfSize.y() + fb * bHalfSize.z();
125 if (
min > rad ||
max < -rad)
131template<
typename ScalarType, Po
intConcept Po
intType>
132inline bool axisTestY02(
139 const PointType& bHalfSize)
141 ScalarType p0 = -a * v0.x() + b * v0.z();
142 ScalarType p2 = -a * v2.x() + b * v2.z();
152 ScalarType rad = fa * bHalfSize.x() + fb * bHalfSize.z();
153 if (
min > rad ||
max < -rad)
158template<
typename ScalarType, Po
intConcept Po
intType>
159inline bool axisTestY1(
166 const PointType& bHalfSize)
168 ScalarType p0 = -a * v0.x() + b * v0.z();
169 ScalarType p1 = -a * v1.x() + b * v1.z();
179 ScalarType rad = fa * bHalfSize.x() + fb * bHalfSize.z();
180 if (
min > rad ||
max < -rad)
186template<
typename ScalarType, Po
intConcept Po
intType>
187inline bool axisTestZ12(
194 const PointType& bHalfSize)
196 ScalarType p1 = a * v1.x() - b * v1.y();
197 ScalarType p2 = a * v2.x() - b * v2.y();
207 ScalarType rad = fa * bHalfSize.x() + fb * bHalfSize.y();
208 if (
min > rad ||
max < -rad)
213template<
typename ScalarType, Po
intConcept Po
intType>
214inline bool axisTestZ0(
221 const PointType& bHalfSize)
223 ScalarType p0 = a * v0.x() - b * v0.y();
224 ScalarType p1 = a * v1.x() - b * v1.y();
234 ScalarType rad = fa * bHalfSize.x() + fb * bHalfSize.y();
235 if (
min > rad ||
max < -rad)
257template<PlaneConcept PlaneType, Box3Concept BoxType>
260 using PointType = BoxType::PointType;
261 using ScalarType = PointType::ScalarType;
265 PointType e =
box.
max() - c;
267 PointType
n =
plane.direction();
270 e[0] * std::abs(
n[0]) + e[1] * std::abs(
n[1]) + e[2] * std::abs(
n[2]);
273 ScalarType s =
n.dot(c) -
plane.offset();
276 return std::abs(s) <=
r;
284template<Box3Concept BoxType, PlaneConcept PlaneType>
307template<PlaneConcept PlaneType, Segment3Concept SegmentType>
310 using ScalarType = SegmentType::ScalarType;
335template<Segment3Concept SegmentType, PlaneConcept PlaneType>
363template<PlaneConcept PlaneType, Segment3Concept SegmentType>
368 std::optional<typename SegmentType::PointType>
intersection;
370 using ScalarType = SegmentType::ScalarType;
407template<SphereConcept SphereType, Box3Concept BoxType>
418template<Box3Concept BoxType, SphereConcept SphereType>
444template<Triangle2Concept TriangleType, Po
int2Concept Po
intType>
447 using TP = TriangleType::PointType;
448 using ScalarType = TP::ScalarType;
455 ScalarType
sign = A < 0 ? -1 : 1;
458 (p0.y() *
p2.x() - p0.x() *
p2.y() + (
p2.y() - p0.y()) * point.x() +
459 (p0.x() -
p2.x()) * point.y()) *
462 (p0.x() * p1.y() - p0.y() * p1.x() + (p0.y() - p1.y()) * point.x() +
463 (p1.x() - p0.x()) * point.y()) *
466 return s > 0 &&
tt > 0 && (s +
tt) < 2 * A *
sign;
474template<Po
int2Concept Po
intType, Triangle2Concept TriangleType>
494template<Triangle3Concept TriangleType, Po
int3Concept Po
intType>
495bool intersect(
const TriangleType& triangle,
const PointType& point)
497 PointType v1 = triangle.point(1) - triangle.point(0);
498 PointType v2 = triangle.point(2) - triangle.point(0);
499 PointType v3 = point - triangle.point(0);
501 return v1.dot(v2.cross(v3)) > 0;
509template<Po
int3Concept Po
intType, Triangle3Concept TriangleType>
510bool intersect(
const PointType& point,
const TriangleType& triangle)
537template<Triangle3Concept TriangleType, Box3Concept BoxType>
540 using PointType = TriangleType::PointType;
541 using ScalarType = PointType::ScalarType;
564 PointType
e0 = v1 -
v0;
565 PointType
e1 = v2 - v1;
566 PointType
e2 =
v0 - v2;
570 ScalarType
fex = std::abs(
e0.x());
571 ScalarType
fey = std::abs(
e0.y());
572 ScalarType
fez = std::abs(
e0.z());
581 fex = std::abs(
e1.x());
582 fey = std::abs(
e1.y());
583 fez = std::abs(
e1.z());
592 fex = std::abs(
e2.x());
593 fey = std::abs(
e2.y());
594 fez = std::abs(
e2.z());
610 detail::findMinMax(
v0.x(), v1.x(), v2.x(),
min,
max);
615 detail::findMinMax(
v0.y(), v1.y(), v2.y(),
min,
max);
620 detail::findMinMax(
v0.z(), v1.z(), v2.z(),
min,
max);
628 normal =
e0.cross(
e1);
642template<Box3Concept BoxType, Triangle3Concept TriangleType>
663 Triangle3Concept TriangleType,
664 SphereConcept SphereType,
665 Point3Concept PointType,
671 std::pair<ScalarType, ScalarType>&
res)
675 ScalarType radius =
sphere.radius();
677 PointType p0 =
triangle.point0() - center;
678 PointType p1 =
triangle.point1() - center;
681 PointType
p10 = p1 - p0;
682 PointType
p21 =
p2 - p1;
683 PointType
p20 =
p2 - p0;
741 res.first = std::max<ScalarType>(
witness_norm - radius, ScalarType(0.0));
742 res.second = std::max<ScalarType>(radius -
witness_norm, ScalarType(0.0));
758template<Triangle3Concept TriangleType, SphereConcept SphereType>
761 using SScalar = SphereType::ScalarType;
762 typename TriangleType::PointType
witness;
763 std::pair<SScalar, SScalar>
res;
772template<SphereConcept SphereType, Triangle3Concept TriangleType>
A class representing a box in N-dimensional space.
Definition box.h:46
bool intersects(const Box< PointT > &b) const
Same as Box::overlap.
Definition box.h:239
PointT & max()
Returns a reference to the maximum point of the box.
Definition box.h:104
PointT center() const
Calculates the center point of the box.
Definition box.h:259
PointT size() const
Computes the size of the box.
Definition box.h:267
constexpr auto max(const T &p1, const T &p2)
Returns the maximum between the two parameters.
Definition min_max.h:81
constexpr auto min(const T &p1, const T &p2)
Returns the minimum between the two parameters.
Definition min_max.h:40
bool intersect(const PlaneType &plane, const BoxType &box)
Checks if a plane intersects with a box.
Definition intersect.h:258
std::optional< typename SegmentType::PointType > intersection(const PlaneType &plane, const SegmentType &segment)
Returns the intersection point between a plane and a segment, if it exists.
Definition intersect.h:364