9 #define REAL_infinity 1.0e30
10 #define REAL_EQUAL(a,b) (((a < b + EPSILON) && (a > b - EPSILON)) ? true : false)
11 #define REAL_GREAT(a,b) ((a > EPSILON + b)? true: false)
12 #define REAL_LESS(a,b) ((a + EPSILON < b)? true: false)
19 template<
typename Real>
25 template<
typename Real>
38 template<
typename Real>
55 template<
typename Real>
68 axisNormal = normal * l;
92 template<
typename Real>
94 DYN_FUNC
void computeReferenceEdgesAndBasis(
unsigned char*
out,
SquareMatrix<Real, 3>* basis,
Vector<Real, 3>* e,
const Vector<Real, 3>& eR,
const Transform<Real, 3>& rtx,
Vector<Real, 3> n,
int axis)
96 n = rtx.rotation().transpose()*n;
101 auto rot_t = rtx.rotation();
116 outB.setCol(0, rot_t.col(1));
117 outB.setCol(1, rot_t.col(2));
118 outB.setCol(2, rot_t.col(0));
129 outB.setCol(0, rot_t.col(2));
130 outB.setCol(1, rot_t.col(1));
131 outB.setCol(2, -rot_t.col(0));
145 outB.setCol(0, rot_t.col(2));
146 outB.setCol(1, rot_t.col(0));
147 outB.setCol(2, rot_t.col(1));
158 outB.setCol(0, rot_t.col(2));
159 outB.setCol(1, -rot_t.col(0));
160 outB.setCol(2, -rot_t.col(1));
174 outB.setCol(0, -rot_t.col(1));
175 outB.setCol(1, rot_t.col(0));
176 outB.setCol(2, rot_t.col(2));
187 outB.setCol(0, -rot_t.col(1));
188 outB.setCol(1, -rot_t.col(0));
189 outB.setCol(2, -rot_t.col(2));
198 template<
typename Real>
201 n = -itx.rotation().transpose()*n;
204 if (absN.x > absN.y && absN.x > absN.z)
221 else if (absN.y > absN.x && absN.y > absN.z)
256 for (
int i = 0; i < 4; ++i)
257 out[i].v = itx *
out[i].v;
261#define InFront( a ) \
265 ((a) >= float( 0.0 ))
268 ((a) < float( 0.005 ) && (a) > -float( 0.005 ))
270 template<
typename Real>
276 for (
int i = 0; i < inCount; ++i)
286 if (
On(da) ||
On(db))
298 cv.
v = a.
v + (b.
v - a.
v) * (da / (da - db));
299 out[outCount++] = cv;
305 cv.
v = a.
v + (b.
v - a.
v) * (da / (da - db));
306 out[outCount++] = cv;
319 template<
typename Real>
327 for (
int i = 0; i < 4; ++i)
328 in[i].v = basis.transpose()*(incident[i].
v - rPos);
349 for (
int i = 0; i < inCount; ++i)
355 outVerts[outCount].
v = basis *
in[i].v + rPos;
356 outDepths[outCount++] = d;
365 template<
typename Real>
373 for (
int i = 0; i < inCount; ++i)
374 in[i].v = basis.transpose() * (incident[i].
v - rPos);
395 for (
int i = 0; i < inCount; ++i)
401 outVerts[outCount].
v = basis *
in[i].v + rPos;
402 outDepths[outCount++] = d;
410 template<
typename Real>
411 DYN_FUNC
inline void edgesContact(
Vector<Real, 3>& CA,
Vector<Real, 3>& CB,
const Vector<Real, 3>& PA,
const Vector<Real, 3>& QA,
const Vector<Real, 3>& PB,
const Vector<Real, 3>& QB)
422 Real denom = a * e - b * b;
424 Real TA = (b * f - c * e) / denom;
425 Real TB = (b * TA + f) / e;
432 template<
typename Real>
438 Real& intersectionDistance,
443 if (!((lowerBoundaryA > upperBoundaryB) || (lowerBoundaryB > upperBoundaryA)))
447 if (lowerBoundaryA < lowerBoundaryB)
449 if (upperBoundaryA > upperBoundaryB)
453 if (upperBoundaryB - lowerBoundaryA > upperBoundaryA - lowerBoundaryB)
457 boundaryA = upperBoundaryA;
458 boundaryB = lowerBoundaryB;
459 intersectionDistance = - (upperBoundaryA - lowerBoundaryB);
465 boundaryA = lowerBoundaryA;
466 boundaryB = upperBoundaryB;
467 intersectionDistance = - (upperBoundaryB - lowerBoundaryA);
474 boundaryA = upperBoundaryA;
475 boundaryB = lowerBoundaryB;
476 intersectionDistance = - (upperBoundaryA - lowerBoundaryB);
481 if (upperBoundaryA > upperBoundaryB)
485 boundaryA = lowerBoundaryA;
486 boundaryB = upperBoundaryB;
487 intersectionDistance = - (upperBoundaryB - lowerBoundaryA);
494 if (upperBoundaryB - lowerBoundaryA > upperBoundaryA - lowerBoundaryB)
498 boundaryA = upperBoundaryA;
499 boundaryB = lowerBoundaryB;
500 intersectionDistance = - (upperBoundaryA - lowerBoundaryB);
506 boundaryA = lowerBoundaryA;
507 boundaryB = upperBoundaryB;
508 intersectionDistance = - (upperBoundaryB - lowerBoundaryA);
518 if (upperBoundaryA < lowerBoundaryB)
520 boundaryA = upperBoundaryA;
521 boundaryB = lowerBoundaryB;
522 intersectionDistance = (lowerBoundaryB - upperBoundaryA);
525 if (upperBoundaryB < lowerBoundaryA)
527 boundaryA = lowerBoundaryA;
528 boundaryB = upperBoundaryB;
529 intersectionDistance = (lowerBoundaryA - upperBoundaryB);
534 template<
typename Real>
541 template<
typename Real>
547 Real currentBoundaryA,
548 Real currentBoundaryB,
556 currentN = ( (currentBoundaryB < currentBoundaryA) ^ (
REAL_LESS(currentDepth, 0)) ) ? -currentN : currentN;
559 depth = currentDepth;
561 boundaryA = currentBoundaryA;
562 boundaryB = currentBoundaryB;
566 template<
typename Real,
typename ShapeA,
typename ShapeB>
570 Real lowerBoundaryA, upperBoundaryA, lowerBoundaryB, upperBoundaryB;
573 projectOnAxis(lowerBoundaryA, upperBoundaryA, axisNormal, shapeA, radiusA);
574 projectOnAxis(lowerBoundaryB, upperBoundaryB, axisNormal, shapeB, radiusB);
576 checkSignedDistance(lowerBoundaryA, upperBoundaryA, lowerBoundaryB, upperBoundaryB, intersectionDistance, BoundaryA, BoundaryB);
580 template<
typename Real,
typename ShapeA,
typename ShapeB>
596 if (
N.norm() >
EPSILON)
N /=
N.norm();
else return;
604 template<
typename Real,
typename ShapeA,
typename ShapeB>
618 Vec3f N = dirA.cross(dirB);
621 if (
N.norm() >
EPSILON)
N /=
N.norm();
else return;
628 template<
typename Real,
typename ShapeA,
typename ShapeB>
642 if (
N.norm() >
EPSILON)
N /=
N.norm();
else return;
646 for (
int i = 0; i < 3; ++i)
648 sat.
update(type, bA, bB, D,
N, tri.
v[0], tri.
v[1], tri.
v[2]);
651 template<
typename Real,
typename ShapeA,
typename ShapeB>
665 if (
N.norm() >
EPSILON)
N /=
N.norm();
else return;
669 for (
int i = 0; i < 4; ++i)
671 sat.
update(type, bA, bB, D,
N, rect.
center, rect.
axis[0], rect.
axis[1],
Vec3f(rect.
extent[0], rect.
extent[1], 0.f));
675 template<
typename Real>
679 const Vec3f axisNormal,
684 lowerBoundary = upperBoundary = sphere.
center.dot(axisNormal);
686 lowerBoundary -= radius + sphere.
radius;
687 upperBoundary += radius + sphere.
radius;
690 template<
typename Real>
702 template<
typename Real>
714 template<
typename Real>
727 template<
typename Real>
731 const Vec3f axisNormal,
736 Real t = seg.
v0.dot(axisNormal); lowerBoundary = upperBoundary = t;
737 t = seg.
v1.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
739 lowerBoundary -= radius;
740 upperBoundary += radius;
743 template<
typename Real>
766 template<
typename Real>
788 template<
typename Real>
805 transA = m.
normal * (radiusA + depth);
806 transB = -m.
normal * radiusB;
808 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
813 transA = m.
normal * (radiusA + depth);
814 transB = -m.
normal * radiusB;
816 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
918 template<
typename Real>
922 const Vec3f axisNormal,
927 Real t = tri.
v[0].dot(axisNormal); lowerBoundary = upperBoundary = t;
928 t = tri.
v[1].dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
929 t = tri.
v[2].dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
931 lowerBoundary -= radius;
932 upperBoundary += radius;
935 template<
typename Real>
958 template<
typename Real>
980 template<
typename Real,
typename Shape>
998 transA = m.
normal * (radiusA + depth);
999 transB = -m.
normal * radiusB;
1001 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1006 transA = m.
normal * (radiusA + depth);
1007 transB = -m.
normal * radiusB;
1009 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1014 transA = m.
normal * (radiusA + depth);
1015 transB = -m.
normal * (radiusB);
1017 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1022 template<
typename Real>
1024 Real& lowerBoundary,
1025 Real& upperBoundary,
1026 const Vec3f axisNormal,
1031 Real t = tet.
v[0].dot(axisNormal); lowerBoundary = upperBoundary = t;
1032 t = tet.
v[1].dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1033 t = tet.
v[2].dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1034 t = tet.
v[3].dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1036 lowerBoundary -= radius;
1037 upperBoundary += radius;
1040 template<
typename Real>
1050 Tet3D tetTB =
Tet3D(tetB.
v[0] + transB, tetB.
v[1] + transB, tetB.
v[2] + transB, tetB.
v[3] + transB);
1063 template<
typename Real>
1073 Tet3D tetT =
Tet3D(tetB.
v[0] + transB, tetB.
v[1] + transB, tetB.
v[2] + transB, tetB.
v[3] + transB);
1085 template<
typename Real,
typename Shape>
1089 const Shape& shapeA,
1103 transA = m.
normal * (radiusA + depth);
1104 transB = -m.
normal * radiusB;
1106 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1111 transA = m.
normal * (radiusA + depth);
1112 transB = -m.
normal * radiusB;
1114 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1119 transA = m.
normal * (radiusA + depth);
1120 transB = -m.
normal * (radiusB);
1122 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1127 template<
typename Real>
1129 Real& lowerBoundary,
1130 Real& upperBoundary,
1131 const Vec3f axisNormal,
1143 p = (center - u * extent[0] - v * extent[1] - w * extent[2]);
1144 Real t = p.dot(axisNormal); lowerBoundary = upperBoundary = t;
1146 p = (center - u * extent[0] - v * extent[1] + w * extent[2]);
1147 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1149 p = (center - u * extent[0] + v * extent[1] - w * extent[2]);
1150 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1152 p = (center - u * extent[0] + v * extent[1] + w * extent[2]);
1153 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1155 p = (center + u * extent[0] - v * extent[1] - w * extent[2]);
1156 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1158 p = (center + u * extent[0] - v * extent[1] + w * extent[2]);
1159 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1161 p = (center + u * extent[0] + v * extent[1] - w * extent[2]);
1162 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1164 p = (center + u * extent[0] + v * extent[1] + w * extent[2]);
1165 t = p.dot(axisNormal); lowerBoundary = glm::min(lowerBoundary, t); upperBoundary = glm::max(upperBoundary, t);
1167 lowerBoundary -= radius;
1168 upperBoundary += radius;
1171 template<
typename Real>
1194 template<
typename Real>
1217 template<
typename Real,
typename Shape>
1221 const Shape& shapeA,
1235 transA = m.
normal * (radiusA + depth);
1236 transB = -m.
normal * radiusB;
1238 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1243 transA = m.
normal * (radiusA + depth);
1244 transB = -m.
normal * radiusB;
1246 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1251 transA = m.
normal * (radiusA + depth);
1252 transB = -m.
normal * (radiusB);
1254 for (
int i = 0; i < num; ++i) m.
pushContact(q[i], depth);
1260 template<
typename Real>
1272 template<
typename Real>
1277 MSDF(sat, sphereA, sphereB, radiusA, radiusB);
1290 template<
typename Real>
1300 checkAxisP(projP.
origin, pB);
1304 template<
typename Real>
1309 MSDF(sat, segB, sphereA, radiusB, radiusA);
1330 template<
typename Real>
1335 MSDF(sat, segA, sphereB, radiusA, radiusB);
1356 template<
typename Real>
1366 checkAxisP(projP.
origin, pB);
1371 template<
typename Real>
1376 MSDF(sat, triB, sphereA, radiusB, radiusA);
1389 template<
typename Real>
1394 MSDF(sat, triA, sphereB, radiusA, radiusB);
1415 template<
typename Real>
1425 checkAxisP(projP.
origin, pB);
1428 template<
typename Real>
1433 MSDF(sat, tetB, sphereA, radiusB, radiusA);
1447 template<
typename Real>
1452 MSDF(sat, tetA, sphereB, radiusA, radiusB);
1473 template<
typename Real>
1483 checkAxisP(projP.
origin, pB);
1486 template<
typename Real>
1491 MSDF(sat, boxB, sphereA, radiusB, radiusA);
1504 template<
typename Real>
1509 MSDF(sat, boxA, sphereB, radiusA, radiusB);
1523 template<
typename Real>
1531 for (
int j = 0; j < 2; j++)
1533 Vec3f pB = (j == 0) ? (segB.
v0) : (segB.
v1);
1536 checkAxisP(projP.
origin, pB);
1538 for (
int j = 0; j < 2; j++)
1540 Vec3f pA = (j == 0) ? (segA.
v0) : (segA.
v1);
1543 checkAxisP(pA, projP.
origin);
1548 checkAxisE(segA, segB);
1588 template<
typename Real>
1593 MSDF(sat, segA, segB, radiusA, radiusB);
1614 template<
typename Real>
1627 checkAxisE(
Segment3D(triA.
v[0], triA.
v[1]), segB);
1628 checkAxisE(
Segment3D(triA.
v[0], triA.
v[2]), segB);
1629 checkAxisE(
Segment3D(triA.
v[1], triA.
v[2]), segB);
1634 for (
int j = 0; j < 2; j++)
1636 Vec3f pB = (j == 0) ? (segB.
v0) : (segB.
v1);
1639 checkAxisP(projP.
origin, pB);
1642 for (
int j = 0; j < 3; j++)
1647 checkAxisP(pA, projP.
origin);
1699 template<
typename Real>
1704 MSDF(sat, triA, segB, radiusA, radiusB);
1718 template<
typename Real>
1723 MSDF(sat, triB, segA, radiusB, radiusA);
1738 template<
typename Real>
1747 checkAxisT(tetA.
face(0));
1748 checkAxisT(tetA.
face(1));
1749 checkAxisT(tetA.
face(2));
1750 checkAxisT(tetA.
face(3));
1754 checkAxisE(
Segment3D(tetA.
v[0], tetA.
v[1]), segB);
1755 checkAxisE(
Segment3D(tetA.
v[0], tetA.
v[2]), segB);
1756 checkAxisE(
Segment3D(tetA.
v[1], tetA.
v[2]), segB);
1757 checkAxisE(
Segment3D(tetA.
v[0], tetA.
v[3]), segB);
1758 checkAxisE(
Segment3D(tetA.
v[1], tetA.
v[3]), segB);
1759 checkAxisE(
Segment3D(tetA.
v[2], tetA.
v[3]), segB);
1764 for (
int j = 0; j < 2; j++)
1766 Vec3f pB = (j == 0) ? (segB.
v0) : (segB.
v1);
1769 checkAxisP(projP.
origin, pB);
1772 for (
int j = 0; j < 4; j++)
1777 checkAxisP(pA, projP.
origin);
1891 template<
typename Real>
1896 MSDF(sat, tetB, segA, radiusB, radiusA);
1909 template<
typename Real>
1914 MSDF(sat, tetA, segB, radiusA, radiusB);
1930 template<
typename Real>
1940 for (
int j = 0; j < 6; j++)
1948 for (
int j = 0; j < 12; j++)
1951 checkAxisE(edgeA, segB);
1956 for (
int j = 0; j < 2; j++)
1958 Vec3f pB = (j == 0) ? (segB.
v0) : (segB.
v1);
1961 checkAxisP(projP.
origin, pB);
1964 for (
int j = 0; j < 8; j++)
1969 checkAxisP(pA, projP.
origin);
2094 template<
typename Real>
2099 MSDF(sat, boxB, segA, radiusB, radiusA);
2113 template<
typename Real>
2118 MSDF(sat, boxA, segB, radiusA, radiusB);
2134 template<
typename Real>
2139 auto checkAxisT = [&](
Triangle3D face,
auto type) {
checkAxisTri(sat, triA, triB, radiusA, radiusB, face, type); };
2149 for (
int i = 0; i < 3; i++)
2150 for (
int j = 0; j < 3; j++)
2152 int ni = (i == 2) ? 0 : i + 1;
2153 int nj = (j == 2) ? 0 : j + 1;
2158 for (
int j = 0; j < 3; j++)
2163 checkAxisP(pA, projP.
origin);
2166 for (
int j = 0; j < 3; j++)
2171 checkAxisP(projP.
origin, pB);
2224 template<
typename Real>
2229 MSDF(sat, triA, triB, radiusA, radiusB);
2244 template<
typename Real>
2249 auto checkAxisT = [&](
Triangle3D face,
auto type) {
checkAxisTri(sat, tetA, triB, radiusA, radiusB, face, type); };
2262 for (
int i = 0; i < 6; i++)
2263 for (
int j = 0; j < 3; j++)
2265 int nj = (j == 2) ? 0 : j + 1;
2270 for (
int j = 0; j < 4; j++)
2275 checkAxisP(pA, projP.
origin);
2278 for (
int j = 0; j < 3; j++)
2283 checkAxisP(projP.
origin, pB);
2342 template<
typename Real>
2347 MSDF(sat, tetB, triA, radiusA, radiusB);
2360 template<
typename Real>
2365 MSDF(sat, tetA, triB, radiusA, radiusB);
2379 template<
typename Real>
2389 for (
int j = 0; j < 6; j++) checkAxisR(boxA.
face(j));
2394 for (
int i = 0; i < 12; i++)
2395 for (
int j = 0; j < 3; j++)
2397 int nj = (j == 2) ? 0 : j + 1;
2402 for (
int j = 0; j < 8; j++)
2407 checkAxisP(pA, projP.
origin);
2410 for (
int j = 0; j < 3; j++)
2415 checkAxisP(projP.
origin, pB);
2472 template<
typename Real>
2477 MSDF(sat, boxB, triA, radiusA, radiusB);
2490 template<
typename Real>
2495 MSDF(sat, boxA, triB, radiusA, radiusB);
2509 template<
typename Real>
2514 auto checkAxisT = [&](
Triangle3D face,
auto type) {
checkAxisTri(sat, tetA, tetB, radiusA, radiusB, face, type); };
2530 for (
int i = 0; i < 6; i++)
2531 for (
int j = 0; j < 6; j++)
2535 checkAxisE(edgeA, edgeB);
2540 for (
int j = 0; j < 4; j++)
2545 checkAxisP(pA, projP.
origin);
2548 for (
int j = 0; j < 4; j++)
2553 checkAxisP(pA, projP.
origin);
2616 template<
typename Real>
2621 MSDF(sat, tetA, tetB, radiusA, radiusB);
2635 template<
typename Real>
2646 for (
int j = 0; j < 6; j++) checkAxisR(boxA.
face(j));
2647 checkAxisT(tetB.
face(0));
2648 checkAxisT(tetB.
face(1));
2649 checkAxisT(tetB.
face(2));
2650 checkAxisT(tetB.
face(3));
2655 for (
int i = 0; i < 12; i++)
2656 for (
int j = 0; j < 6; j++)
2658 checkAxisE(boxA.
edge(i), tetB.
edge(j));
2662 for (
int j = 0; j < 8; j++)
2667 checkAxisP(pA, projP.
origin);
2670 for (
int j = 0; j < 4; j++)
2675 checkAxisP(projP.
origin, pB);
2735 template<
typename Real>
2740 MSDF(sat, boxB, tetA, radiusA, radiusB);
2753 template<
typename Real>
2758 MSDF(sat, boxA, tetB, radiusA, radiusB);
2772 template<
typename Real>
2777 auto checkAxisR = [&](
Rectangle3D face,
auto type) {
checkAxisRect(sat, boxA, boxB, radiusA, radiusB, face, type); };
2782 for (
int j = 0; j < 6; j++) checkAxisR(boxA.
face(j),
CT_RECTA);
2783 for (
int j = 0; j < 6; j++) checkAxisR(boxB.
face(j),
CT_RECTB);
2788 for (
int i = 0; i < 12; i++)
2789 for (
int j = 0; j < 12; j++)
2791 checkAxisE(boxA.
edge(i), boxB.
edge(j));
2795 for (
int j = 0; j < 8; j++)
2800 checkAxisP(pA, projP.
origin);
2803 for (
int j = 0; j < 8; j++)
2808 checkAxisP(projP.
origin, pB);
2867 template<
typename Real>
2872 MSDF(sat, boxA, boxB, radiusA, radiusB);
2886 template<
typename Real>
2887 DYN_FUNC
void computeSupportEdge(
Vector<Real, 3>& aOut,
Vector<Real, 3>& bOut,
const SquareMatrix<Real, 3>& rot,
const Vector<Real, 3>& trans,
const Vector<Real, 3>& e,
Vector<Real, 3> n)
2889 n = rot.transpose()*n;
2894 if (absN.x > absN.y)
2897 if (absN.y > absN.z)
2914 if (absN.x > absN.z)
2938 aOut = rot * a + trans;
2939 bOut = rot * b + trans;
2942 template<
typename Real>
2953 rotA.setCol(0, box0.
u);
2954 rotA.setCol(1, box0.
v);
2955 rotA.setCol(2, box0.
w);
2958 rotB.setCol(0, box1.
u);
2959 rotB.setCol(1, box1.
v);
2960 rotB.setCol(2, box1.
w);
2963 Matrix3D C = rotA.transpose() * rotB;
2965 bool parallel =
false;
2966 const float kCosTol = float(1.0e-6);
2967 for (
int i = 0; i < 3; ++i)
2969 for (
int j = 0; j < 3; ++j)
2971 float val =
abs(C(i, j));
2974 if (val + kCosTol >=
float(1.0))
2980 Matrix3D absC_t = absC.transpose();
3036 rA = eA.y * absC(2, 0) + eA.z * absC(1, 0);
3037 rB = eB.y * absC(0, 2) + eB.z * absC(0, 1);
3038 s =
abs(t.z * C(1, 0) - t.y * C(2, 0)) - (rA + rB);
3039 if (
trackEdgeAxis(eAxis, eMax, nE, 6, s,
Vector<Real, 3>(
float(0.0), -C(2, 0), C(1, 0))))
3043 rA = eA.y * absC(2, 1) + eA.z * absC(1, 1);
3044 rB = eB.x * absC(0, 2) + eB.z * absC(0, 0);
3045 s =
abs(t.z * C(1, 1) - t.y * C(2, 1)) - (rA + rB);
3046 if (
trackEdgeAxis(eAxis, eMax, nE, 7, s,
Vector<Real, 3>(
float(0.0), -C(2, 1), C(1, 1))))
3050 rA = eA.y * absC(2, 2) + eA.z * absC(1, 2);
3051 rB = eB.x * absC(0, 1) + eB.y * absC(0, 0);
3052 s =
abs(t.z * C(1, 2) - t.y * C(2, 2)) - (rA + rB);
3053 if (
trackEdgeAxis(eAxis, eMax, nE, 8, s,
Vector<Real, 3>(
float(0.0), -C(2, 2), C(1, 2))))
3057 rA = eA.x * absC(2, 0) + eA.z * absC(0, 0);
3058 rB = eB.y * absC(1, 2) + eB.z * absC(1, 1);
3059 s =
abs(t.x * C(2, 0) - t.z * C(0, 0)) - (rA + rB);
3060 if (
trackEdgeAxis(eAxis, eMax, nE, 9, s,
Vector<Real, 3>(C(2, 0),
float(0.0), -C(0, 0))))
3064 rA = eA.x * absC(2, 1) + eA.z * absC(0, 1);
3065 rB = eB.x * absC(1, 2) + eB.z * absC(1, 0);
3066 s =
abs(t.x * C(2, 1) - t.z * C(0, 1)) - (rA + rB);
3067 if (
trackEdgeAxis(eAxis, eMax, nE, 10, s,
Vector<Real, 3>(C(2, 1),
float(0.0), -C(0, 1))))
3071 rA = eA.x * absC(2, 2) + eA.z * absC(0, 2);
3072 rB = eB.x * absC(1, 1) + eB.y * absC(1, 0);
3073 s =
abs(t.x * C(2, 2) - t.z * C(0, 2)) - (rA + rB);
3074 if (
trackEdgeAxis(eAxis, eMax, nE, 11, s,
Vector<Real, 3>(C(2, 2),
float(0.0), -C(0, 2))))
3078 rA = eA.x * absC(1, 0) + eA.y * absC(0, 0);
3079 rB = eB.y * absC(2, 2) + eB.z * absC(2, 1);
3080 s =
abs(t.y * C(0, 0) - t.x * C(1, 0)) - (rA + rB);
3081 if (
trackEdgeAxis(eAxis, eMax, nE, 12, s,
Vector<Real, 3>(-C(1, 0), C(0, 0),
float(0.0))))
3085 rA = eA.x * absC(1, 1) + eA.y * absC(0, 1);
3086 rB = eB.x * absC(2, 2) + eB.z * absC(2, 0);
3087 s =
abs(t.y * C(0, 1) - t.x * C(1, 1)) - (rA + rB);
3088 if (
trackEdgeAxis(eAxis, eMax, nE, 13, s,
Vector<Real, 3>(-C(1, 1), C(0, 1),
float(0.0))))
3092 rA = eA.x * absC(1, 2) + eA.y * absC(0, 2);
3093 rB = eB.x * absC(2, 1) + eB.y * absC(2, 0);
3094 s =
abs(t.y * C(0, 2) - t.x * C(1, 2)) - (rA + rB);
3095 if (
trackEdgeAxis(eAxis, eMax, nE, 14, s,
Vector<Real, 3>(-C(1, 2), C(0, 2),
float(0.0))))
3100 const float kRelTol = float(0.95);
3101 const float kAbsTol = float(0.01);
3105 float faceMax = std::max(aMax, bMax);
3106 if (kRelTol * eMax > faceMax + kAbsTol)
3114 if (kRelTol * bMax > aMax + kAbsTol)
3128 if (n.dot(v) <
float(0.0))
3166 unsigned char clipEdges[4];
3175 outNum =
clip(
out, depths, rtx.translation(), e, clipEdges, basis, incident);
3180 m.
normal = flip ? -n : n;
3182 for (
int i = 0; i < outNum; ++i)
3185 m.
contacts[i].penetration = depths[i];
3193 if (n.dot(v) <
float(0.0))
3212 template<
typename Real>
3221 bool bInside = c0.
inside(box);
3223 Segment3D dir = bInside ? c0 - vproj : vproj - c0;
3236 template<
typename Real>
3252 bool parallel = s0xs1.norm() < absTol ? true :
false;
3253 bool overlap =
true;
3263 Real d = dir.norm();
3264 Real interpenetration = d - r0;
3266 if (interpenetration >= 0)
3274 if (!interval.isEmpty())
3279 m.
normal = dir.normalize();
3280 m.
contacts[0].penetration = interpenetration;
3282 m.
contacts[1].penetration = interpenetration;
3292 if (!parallel || (parallel && !overlap))
3311 template<
typename Real>
3335 template<
typename Real>
3343 template<
typename Real>
3345 Real& lowerBoundary1,
3346 Real& upperBoundary1,
3347 Real& lowerBoundary2,
3348 Real& upperBoundary2,
3349 Real& intersectionDistance,
3361 lowerBoundary1 = seg.
v0.dot(axisNormal) - cap.
radius;
3362 upperBoundary1 = seg.
v0.dot(axisNormal) + cap.
radius;
3363 lowerBoundary1 = glm::min(lowerBoundary1, seg.
v1.dot(axisNormal) - cap.
radius);
3364 upperBoundary1 = glm::max(upperBoundary1, seg.
v1.dot(axisNormal) + cap.
radius);
3373 p = (center - u * extent[0] - v * extent[1] - w * extent[2]);
3374 lowerBoundary2 = upperBoundary2 = p.dot(axisNormal);
3376 p = (center - u * extent[0] - v * extent[1] + w * extent[2]);
3377 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3378 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3380 p = (center - u * extent[0] + v * extent[1] - w * extent[2]);
3381 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3382 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3384 p = (center - u * extent[0] + v * extent[1] + w * extent[2]);
3385 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3386 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3388 p = (center + u * extent[0] - v * extent[1] - w * extent[2]);
3389 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3390 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3392 p = (center + u * extent[0] - v * extent[1] + w * extent[2]);
3393 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3394 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3396 p = (center + u * extent[0] + v * extent[1] - w * extent[2]);
3397 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3398 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3400 p = (center + u * extent[0] + v * extent[1] + w * extent[2]);
3401 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
3402 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
3404 return checkOverlap(lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2, intersectionDistance, boundary1, boundary2);
3407 template<
typename Real>
3409 Real lowerBoundary1,
3410 Real upperBoundary1,
3411 Real lowerBoundary2,
3412 Real upperBoundary2,
3413 Real& intersectionDistance,
3418 if (!((lowerBoundary1 > upperBoundary2) || (lowerBoundary2 > upperBoundary1)))
3420 if (lowerBoundary1 < lowerBoundary2)
3422 if (upperBoundary1 > upperBoundary2)
3424 if (upperBoundary2 - lowerBoundary1 > upperBoundary1 - lowerBoundary2)
3426 boundary1 = upperBoundary1;
3427 boundary2 = lowerBoundary2;
3428 intersectionDistance =
abs(boundary1 - boundary2);
3432 boundary1 = lowerBoundary1;
3433 boundary2 = upperBoundary2;
3434 intersectionDistance =
abs(boundary1 - boundary2);
3439 intersectionDistance = upperBoundary1 - lowerBoundary2;
3440 boundary1 = upperBoundary1;
3441 boundary2 = lowerBoundary2;
3446 if (upperBoundary1 > upperBoundary2)
3448 intersectionDistance = upperBoundary2 - lowerBoundary1;
3449 boundary1 = lowerBoundary1;
3450 boundary2 = upperBoundary2;
3455 if (upperBoundary2 - lowerBoundary1 > upperBoundary1 - lowerBoundary2)
3457 boundary1 = upperBoundary1;
3458 boundary2 = lowerBoundary2;
3459 intersectionDistance =
abs(boundary1 - boundary2);
3463 boundary1 = lowerBoundary1;
3464 boundary2 = upperBoundary2;
3465 intersectionDistance =
abs(boundary1 - boundary2);
3471 intersectionDistance =
Real(0.0f);
3475 template<
typename Real>
3477 Real& lowerBoundary1,
3478 Real& upperBoundary1,
3479 Real& lowerBoundary2,
3480 Real& upperBoundary2,
3481 Real& intersectionDistance,
3492 lowerBoundary1 = seg.
v0.dot(axisNormal) - cap.
radius;
3493 upperBoundary1 = seg.
v0.dot(axisNormal) + cap.
radius;
3494 lowerBoundary1 = glm::min(lowerBoundary1, seg.
v1.dot(axisNormal) - cap.
radius);
3495 upperBoundary1 = glm::max(upperBoundary1, seg.
v1.dot(axisNormal) + cap.
radius);
3497 for (
int i = 0; i < 4; i++)
3502 lowerBoundary2 = upperBoundary2 = tet.
v[0].dot(axisNormal);
3506 lowerBoundary2 = glm::min(lowerBoundary2, tet.
v[i].dot(axisNormal));
3507 upperBoundary2 = glm::max(upperBoundary2, tet.
v[i].dot(axisNormal));
3512 return checkOverlapTetTri(lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2, intersectionDistance, boundary1, boundary2);
3516 template<
typename Real>
3538 Real boundaryMin = glm::min(boundary1, boundary2);
3539 Real boundaryMax = glm::max(boundary1, boundary2);
3542 if (
abs(cap.
endPoint().dot(axisNormal) - boundaryMin) <
abs(depth))
3543 boundaryPoints1[cnt1++] = cap.
endPoint();
3552 p = (center - u * extent[0] - v * extent[1] - w * extent[2]);
3553 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3554 boundaryPoints2[cnt2++] = p;
3556 p = (center - u * extent[0] - v * extent[1] + w * extent[2]);
3557 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3558 boundaryPoints2[cnt2++] = p;
3560 p = (center - u * extent[0] + v * extent[1] - w * extent[2]);
3561 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3562 boundaryPoints2[cnt2++] = p;
3564 p = (center - u * extent[0] + v * extent[1] + w * extent[2]);
3565 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3566 boundaryPoints2[cnt2++] = p;
3568 p = (center + u * extent[0] - v * extent[1] - w * extent[2]);
3569 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3570 boundaryPoints2[cnt2++] = p;
3572 p = (center + u * extent[0] - v * extent[1] + w * extent[2]);
3573 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3574 boundaryPoints2[cnt2++] = p;
3576 p = (center + u * extent[0] + v * extent[1] - w * extent[2]);
3577 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3578 boundaryPoints2[cnt2++] = p;
3580 p = (center + u * extent[0] + v * extent[1] + w * extent[2]);
3581 if (
abs(p.dot(axisNormal) - boundaryMin) <
abs(depth))
3582 boundaryPoints2[cnt2++] = p;
3585 if (cnt1 == 1 || cnt2 == 1)
3587 m.
normal = (boundary1 < boundary2) ? -axisNormal : axisNormal;
3589 m.
contacts[0].position = (cnt1 == 1) ? boundaryPoints1[0] : boundaryPoints2[0];
3599 Segment3D s2(boundaryPoints2[0], boundaryPoints2[1]);
3601 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3613 for (
int tmp_i = 1; tmp_i < 4; tmp_i++)
3614 for (
int tmp_j = tmp_i + 1; tmp_j < 4; tmp_j++)
3616 if ((boundaryPoints2[tmp_i] - boundaryPoints2[0]).
dot(boundaryPoints2[tmp_j] - boundaryPoints2[0]) <
EPSILON)
3618 int tmp_k = 1 + 2 + 3 - tmp_i - tmp_j;
3622 boundaryPoints2[1] = p2;
3623 boundaryPoints2[2] = p3;
3624 boundaryPoints2[3] = p4;
3635 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3636 Triangle3D t2(boundaryPoints2[0], boundaryPoints2[1], boundaryPoints2[2]);
3645 if (dirTmp1.cross(axisNormal).norm() < 1e-4)
3651 if (dirTmp2.cross(axisNormal).norm() < 1e-4)
3657 t2 =
Triangle3D(boundaryPoints2[3], boundaryPoints2[1], boundaryPoints2[2]);
3664 if (dirTmp1.cross(axisNormal).norm() < 1e-4)
3670 if (dirTmp2.cross(axisNormal).norm() < 1e-4)
3676 for (
int i = 0; i < 4; i++)
3680 s2 =
Segment3D(boundaryPoints2[0], boundaryPoints2[i]);
3682 s2 =
Segment3D(boundaryPoints2[3], boundaryPoints2[i - 2]);
3688 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-4)
3691 if ((dir.
v0 - s1.
v0).norm() > 1e-4 && (dir.
v0 - s1.
v1).norm() > 1e-4)
3704 template<
typename Real>
3715 unsigned char boundaryPoints1[4], boundaryPoints2[4];
3720 for (
unsigned char i = 0; i < 4; i++)
3722 if (
abs(tet.
v[i].dot(axisNormal) - boundary1) <
abs(sMax))
3723 boundaryPoints1[cnt1 ++] = i;
3729 boundaryPoints2[cnt2 ++] = 0;
3734 boundaryPoints2[cnt2++] = 1;
3738 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3740 m.
contacts[0].position = tet.
v[boundaryPoints1[0]];
3746 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3754 Segment3D s1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]]);
3760 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3769 Triangle3D t1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]], tet.
v[boundaryPoints1[2]]);
3775 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3779 if (dirTmp1.cross(axisNormal).norm() < 1e-5)
3785 if (dirTmp2.cross(axisNormal).norm() < 1e-5)
3791 for (
int i = 0; i < 3; i++)
3793 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
3795 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-5)
3797 if ((dir.
v0 - s2.
v0).norm() > 1e-5 && (dir.
v0 - s2.
v1).norm() > 1e-5)
3811 template<
typename Real>
3822 unsigned char boundaryPoints1[4], boundaryPoints2[4];
3827 for (
unsigned char i = 0; i < 4; i++)
3829 if (
abs(tet.
v[i].dot(axisNormal) - boundary1) <
abs(sMax) +
EPSILON)
3830 boundaryPoints1[cnt1++] = i;
3833 for (
unsigned char i = 0; i < 3; i++)
3835 if (
abs(triangle.
v[i].dot(axisNormal) - boundary2) <
abs(sMax) +
EPSILON)
3836 boundaryPoints2[cnt2++] = i;
3841 if (cnt1 == 1 || cnt2 == 1)
3843 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3845 m.
contacts[0].position = (cnt1 == 1) ? tet.
v[boundaryPoints1[0]] : triangle.
v[boundaryPoints2[0]];
3851 Segment3D s1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]]);
3855 Segment3D s2(triangle.
v[boundaryPoints2[0]], triangle.
v[boundaryPoints2[1]]);
3857 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3866 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3867 Triangle3D t2(triangle.
v[boundaryPoints2[0]], triangle.
v[boundaryPoints2[1]], triangle.
v[boundaryPoints2[2]]);
3870 if (dirTmp1.cross(axisNormal).norm() < 1e-5)
3876 if (dirTmp2.cross(axisNormal).norm() < 1e-5)
3882 for (
int i = 0; i < 3; i++)
3884 Segment3D s2(t2.
v[(i + 1) % 3], t2.
v[(i + 2) % 3]);
3887 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-5)
3890 if ((dir.
v0 - s1.
v0).norm() > 1e-5 && (dir.
v0 - s1.
v1).norm() > 1e-5)
3902 Triangle3D t1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]], tet.
v[boundaryPoints1[2]]);
3906 Segment3D s2(triangle.
v[boundaryPoints2[0]], triangle.
v[boundaryPoints2[1]]);
3908 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3912 if (dirTmp1.cross(axisNormal).norm() < 1e-5)
3918 if (dirTmp2.cross(axisNormal).norm() < 1e-5)
3924 for (
int i = 0; i < 3; i++)
3926 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
3928 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-5)
3930 if ((dir.
v0 - s2.
v0).norm() > 1e-5 && (dir.
v0 - s2.
v1).norm() > 1e-5)
3941 Triangle3D t1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]], tet.
v[boundaryPoints1[2]]);
3945 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
3947 for (
int i = 0; i < 3; i++)
3962 for (
int j = 0; j < 3; j++)
3964 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
3965 Segment3D s2(t2.
v[(j + 1) % 3], t2.
v[(j + 2) % 3]);
3967 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-5)
3969 if ((dir.
v0 - s1.
v0).norm() > 1e-5 && (dir.
v0 - s1.
v1).norm() > 1e-5)
3983 template<
typename Real>
3997 rotBox.setCol(0, box.
u);
3998 rotBox.setCol(1, box.
v);
3999 rotBox.setCol(2, box.
w);
4005 Matrix3D C = rotBox.transpose() * rotCap;
4007 auto centerline = cap.
centerline().direction();
4008 Vector<Real, 3> nCapLocal = rotBox.transpose() * centerline.normalize();
4010 bool parallel =
false;
4011 const float kCosTol = float(1.0e-6);
4013 for (
int i = 0; i < 3; ++i)
4015 float val =
abs(nCapLocal[i]);
4019 for (
int j = 0; j < 3; ++j)
4021 absC(i, j) =
abs(C(i, j));
4025 Matrix3D absC_t = absC.transpose();
4063 rA = boxExt.y *
abs(nCapLocal.z) + boxExt.z *
abs(nCapLocal.y);
4064 rB = radius * eSepAxis.norm();
4065 s =
abs(t.z * nCapLocal.y - t.y * nCapLocal.z) - (rA + rB);
4071 rA = boxExt.x *
abs(nCapLocal.z) + boxExt.z *
abs(nCapLocal.x);
4072 rB = radius * eSepAxis.norm();
4073 s =
abs(t.x * nCapLocal.z - t.z * nCapLocal.x) - (rA + rB);
4079 rA = boxExt.x *
abs(nCapLocal.y) + boxExt.y *
abs(nCapLocal.x);
4080 rB = radius * eSepAxis.norm();
4081 s =
abs(t.y * nCapLocal.x - t.x * nCapLocal.y) - (rA + rB);
4088 auto num = capCenterline.
intersect(box, interSeg);
4089 bool intersected = num > 0 ? true :
false;
4097 s = dirSepAxis.norm() * dirSepAxis.norm() - radius * dirSepAxis.norm();
4103 const float kRelTol = float(0.95);
4104 const float kAbsTol = float(0.01);
4105 const float kAbsTol2 = float(0.00001);
4108 float ebMax = std::max(eMax, bMax);
4119 if (dirMax > ebMax + kAbsTol2)
4127 if (kRelTol * eMax > bMax + kAbsTol)
4142 if (n.dot(v) <
float(0.0))
4154 auto num = centerline_translated.
intersect(box, centerline_inter);
4162 unsigned char clipEdges[4];
4178 for (
int i = 0; i < outNum; ++i)
4181 m.
contacts[i].penetration = depths[i];
4202 m.
contacts[0].position = CB - radius * n;
4210 m.
contacts[0].position = prox.
v0 - radius * n;
4214 template<
typename Real>
4222 template<
typename Real>
4229 Real lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2;
4230 Real l1, u1, l2, u2;
4234 Real boundary1, boundary2, b1, b2;
4238 for (
int i = 0; i < 4; i++)
4241 axisTmp = tet.
face(i).normal();
4242 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, tri) ==
false)
4250 if (sIntersect < sMax)
4253 lowerBoundary1 = l1;
4254 lowerBoundary2 = l2;
4255 upperBoundary1 = u1;
4256 upperBoundary2 = u2;
4267 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, tri) ==
false)
4275 if (sIntersect < sMax)
4278 lowerBoundary1 = l1;
4279 lowerBoundary2 = l2;
4280 upperBoundary1 = u1;
4281 upperBoundary2 = u2;
4288 const int segmentIndex[6][2] = {
4297 const int triIndex[6][2] = {
4303 for (
int i = 0; i < 6; i++)
4304 for(
int j = 0; j < 3; j ++)
4308 dirTri /= dirTri.norm();
4309 dirTet /= dirTet.norm();
4310 axisTmp = dirTet.cross(dirTri);
4313 axisTmp /= axisTmp.norm();
4321 axisTmp /= axisTmp.norm();
4323 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, tri) ==
false)
4331 if (sIntersect < sMax)
4334 lowerBoundary1 = l1;
4335 lowerBoundary2 = l2;
4336 upperBoundary1 = u1;
4337 upperBoundary2 = u2;
4345 axisTmp = (tet.
v[0] + tet.
v[1] + tet.
v[2] + tet.
v[3]) / 4.0f - (tri.
v[0] + tri.
v[1] + tri.
v[2]) / 3.0f;
4346 axisTmp /= axisTmp.norm();
4347 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, tri) ==
false)
4355 if (sIntersect < sMax)
4358 lowerBoundary1 = l1;
4359 lowerBoundary2 = l2;
4360 upperBoundary1 = u1;
4361 upperBoundary2 = u2;
4372 template<
typename Real>
4380 template<
typename Real>
4387 Real lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2;
4388 Real l1, u1, l2, u2;
4392 Real boundary1, boundary2, b1, b2;
4395 for (
int i = 0; i < 4; i++)
4398 axisTmp = tet.
face(i).normal();
4399 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, cap) ==
false)
4406 if (sIntersect < sMax)
4409 lowerBoundary1 = l1;
4410 lowerBoundary2 = l2;
4411 upperBoundary1 = u1;
4412 upperBoundary2 = u2;
4419 axisTmp = tet.
face(i).normal();
4420 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, cap) ==
false)
4427 if (sIntersect < sMax)
4430 lowerBoundary1 = l1;
4431 lowerBoundary2 = l2;
4432 upperBoundary1 = u1;
4433 upperBoundary2 = u2;
4441 const int segmentIndex[6][2] = {
4453 axisTmp /= axisTmp.norm();
4455 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, cap) ==
false)
4462 if (sIntersect < sMax)
4465 lowerBoundary1 = l1;
4466 lowerBoundary2 = l2;
4467 upperBoundary1 = u1;
4468 upperBoundary2 = u2;
4475 for (
int i = 0; i < 6; i++)
4482 axisTmp = dirTet.cross(dirCap);
4485 axisTmp /= axisTmp.norm();
4493 axisTmp /= axisTmp.norm();
4495 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, cap) ==
false)
4502 if (sIntersect < sMax)
4505 lowerBoundary1 = l1;
4506 lowerBoundary2 = l2;
4507 upperBoundary1 = u1;
4508 upperBoundary2 = u2;
4524 template<
typename Real>
4532 template<
typename Real>
4540 template<
typename Real>
4545 auto c0 = sphere0.
center;
4546 auto c1 = sphere1.
center;
4552 Real sMax = dir.norm() - r0 - r1;
4556 m.
normal = dir.normalize();
4562 template<
typename Real>
4564 Real lowerBoundary1,
4565 Real upperBoundary1,
4566 Real lowerBoundary2,
4567 Real upperBoundary2,
4568 Real& intersectionDistance,
4573 if (!((lowerBoundary1 > upperBoundary2) || (lowerBoundary2 > upperBoundary1)))
4575 if (lowerBoundary1 < lowerBoundary2)
4577 if (upperBoundary1 > upperBoundary2)
4582 if (upperBoundary2 - lowerBoundary1 > upperBoundary1 - lowerBoundary2)
4586 boundary1 = upperBoundary1;
4587 boundary2 = lowerBoundary2;
4588 intersectionDistance = upperBoundary1 - lowerBoundary2;
4594 boundary1 = lowerBoundary1;
4595 boundary2 = upperBoundary2;
4596 intersectionDistance = upperBoundary2 - lowerBoundary1;
4603 intersectionDistance = upperBoundary1 - lowerBoundary2;
4604 boundary1 = upperBoundary1;
4605 boundary2 = lowerBoundary2;
4610 if (upperBoundary1 > upperBoundary2)
4614 intersectionDistance = upperBoundary2 - lowerBoundary1;
4615 boundary1 = lowerBoundary1;
4616 boundary2 = upperBoundary2;
4623 if (upperBoundary2 - lowerBoundary1 > upperBoundary1 - lowerBoundary2)
4627 boundary1 = upperBoundary1;
4628 boundary2 = lowerBoundary2;
4629 intersectionDistance = upperBoundary1 - lowerBoundary2;
4635 boundary1 = lowerBoundary1;
4636 boundary2 = upperBoundary2;
4637 intersectionDistance = upperBoundary2 - lowerBoundary1;
4645 intersectionDistance =
Real(0.0f);
4649 template<
typename Real>
4651 Real& lowerBoundary1,
4652 Real& upperBoundary1,
4653 Real& lowerBoundary2,
4654 Real& upperBoundary2,
4655 Real& intersectionDistance,
4664 for (
int i = 0; i < 4; i++)
4668 lowerBoundary1 = upperBoundary1 = tet1.
v[0].dot(axisNormal);
4669 lowerBoundary2 = upperBoundary2 = tet2.
v[0].dot(axisNormal);
4673 lowerBoundary1 = glm::min(lowerBoundary1, tet1.
v[i].dot(axisNormal));
4674 lowerBoundary2 = glm::min(lowerBoundary2, tet2.
v[i].dot(axisNormal));
4675 upperBoundary1 = glm::max(upperBoundary1, tet1.
v[i].dot(axisNormal));
4676 upperBoundary2 = glm::max(upperBoundary2, tet2.
v[i].dot(axisNormal));
4685 return checkOverlap(lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2, intersectionDistance, boundary1, boundary2);
4689 template<
typename Real>
4691 Real& lowerBoundary1,
4692 Real& upperBoundary1,
4693 Real& lowerBoundary2,
4694 Real& upperBoundary2,
4695 Real& intersectionDistance,
4704 for (
int i = 0; i < 4; i++)
4708 lowerBoundary1 = upperBoundary1 = tet.
v[0].dot(axisNormal);
4712 lowerBoundary1 = glm::min(lowerBoundary1, tet.
v[i].dot(axisNormal));
4713 upperBoundary1 = glm::max(upperBoundary1, tet.
v[i].dot(axisNormal));
4717 for (
int i = 0; i < 3; i++)
4720 lowerBoundary2 = upperBoundary2 = tri.
v[i].dot(axisNormal);
4723 lowerBoundary2 = glm::min(lowerBoundary2, tri.
v[i].dot(axisNormal));
4724 upperBoundary2 = glm::max(upperBoundary2, tri.
v[i].dot(axisNormal));
4732 template<
typename Real>
4734 Real& lowerBoundary1,
4735 Real& upperBoundary1,
4736 Real& lowerBoundary2,
4737 Real& upperBoundary2,
4738 Real& intersectionDistance,
4747 for (
int i = 0; i < 4; i++)
4750 lowerBoundary1 = upperBoundary1 = tet.
v[0].dot(axisNormal);
4753 lowerBoundary1 = glm::min(lowerBoundary1, tet.
v[i].dot(axisNormal));
4754 upperBoundary1 = glm::max(upperBoundary1, tet.
v[i].dot(axisNormal));
4764 p = (center - u * extent[0] - v * extent[1] - w * extent[2]);
4765 lowerBoundary2 = upperBoundary2 = p.dot(axisNormal);
4767 p = (center - u * extent[0] - v * extent[1] + w * extent[2]);
4768 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4769 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4771 p = (center - u * extent[0] + v * extent[1] - w * extent[2]);
4772 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4773 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4775 p = (center - u * extent[0] + v * extent[1] + w * extent[2]);
4776 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4777 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4779 p = (center + u * extent[0] - v * extent[1] - w * extent[2]);
4780 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4781 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4783 p = (center + u * extent[0] - v * extent[1] + w * extent[2]);
4784 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4785 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4787 p = (center + u * extent[0] + v * extent[1] - w * extent[2]);
4788 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4789 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4791 p = (center + u * extent[0] + v * extent[1] + w * extent[2]);
4792 lowerBoundary2 = glm::min(lowerBoundary2, p.dot(axisNormal));
4793 upperBoundary2 = glm::max(upperBoundary2, p.dot(axisNormal));
4795 return checkOverlap(lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2, intersectionDistance, boundary1, boundary2);
4799 template<
typename Real>
4810 unsigned char boundaryPoints1[4], boundaryPoints2[4];
4815 for (
unsigned char i = 0; i < 4; i++)
4817 if (
abs(tet1.
v[i].dot(axisNormal) - boundary1) <
abs(sMax))
4818 boundaryPoints1[cnt1 ++] = i;
4819 if (
abs(tet2.
v[i].dot(axisNormal) - boundary2) <
abs(sMax))
4820 boundaryPoints2[cnt2 ++] = i;
4823 if (cnt1 == 1 || cnt2 == 1)
4826 m.
normal = (boundary1 > boundary2) ? axisNormal : - axisNormal;
4828 m.
contacts[0].position = (cnt1 == 1) ? tet1.
v[boundaryPoints1[0]] : tet2.
v[boundaryPoints2[0]];
4834 Segment3D s1(tet1.
v[boundaryPoints1[0]], tet1.
v[boundaryPoints1[1]]);
4838 Segment3D s2(tet2.
v[boundaryPoints2[0]], tet2.
v[boundaryPoints2[1]]);
4840 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
4849 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
4850 Triangle3D t2(tet2.
v[boundaryPoints2[0]], tet2.
v[boundaryPoints2[1]], tet2.
v[boundaryPoints2[2]]);
4854 if (dirTmp1.cross(axisNormal).norm() < 1e-5)
4860 if (dirTmp2.cross(axisNormal).norm() < 1e-5)
4867 for (
int i = 0; i < 3; i++)
4869 Segment3D s2(t2.
v[(i + 1) % 3], t2.
v[(i + 2) % 3]);
4882 if ((dir.
v0 - s1.
v0).norm() > 1e-5 && (dir.
v0 - s1.
v1).norm() > 1e-5)
4894 Triangle3D t1(tet1.
v[boundaryPoints1[0]], tet1.
v[boundaryPoints1[1]], tet1.
v[boundaryPoints1[2]]);
4898 Segment3D s2(tet2.
v[boundaryPoints2[0]], tet2.
v[boundaryPoints2[1]]);
4900 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
4904 if (dirTmp1.cross(axisNormal).norm() < 1e-5)
4911 if (dirTmp2.cross(axisNormal).norm() < 1e-5)
4918 for (
int i = 0; i < 3; i++)
4920 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
4927 if ((dir.
v0 - s2.
v0).norm() > 1e-5 && (dir.
v0 - s2.
v1).norm() > 1e-5)
4938 Triangle3D t1(tet1.
v[boundaryPoints1[0]], tet1.
v[boundaryPoints1[1]], tet1.
v[boundaryPoints1[2]]);
4939 Triangle3D t2(tet2.
v[boundaryPoints2[0]], tet2.
v[boundaryPoints2[1]], tet2.
v[boundaryPoints2[2]]);
4942 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
4944 for (
int i = 0; i < 3; i++)
4959 for (
int j = 0; j < 3; j++)
4961 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
4962 Segment3D s2(t2.
v[(j + 1) % 3], t2.
v[(j + 2) % 3]);
4972 if ((dir.
v0 - s1.
v0).norm() > 1e-5 && (dir.
v0 - s1.
v1).norm() > 1e-5)
4988 template<
typename Real>
4999 unsigned char boundaryPoints1[4];
5005 for (
unsigned char i = 0; i < 4; i++)
5007 if (
abs(tet.
v[i].dot(axisNormal) - boundary1) <
abs(sMax))
5008 boundaryPoints1[cnt1++] = i;
5017 p = (center - u * extent[0] - v * extent[1] - w * extent[2]);
5018 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5019 boundaryPoints2[cnt2++] = p;
5021 p = (center - u * extent[0] - v * extent[1] + w * extent[2]);
5022 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5023 boundaryPoints2[cnt2++] = p;
5025 p = (center - u * extent[0] + v * extent[1] - w * extent[2]);
5026 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5027 boundaryPoints2[cnt2++] = p;
5029 p = (center - u * extent[0] + v * extent[1] + w * extent[2]);
5030 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5031 boundaryPoints2[cnt2++] = p;
5033 p = (center + u * extent[0] - v * extent[1] - w * extent[2]);
5034 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5035 boundaryPoints2[cnt2++] = p;
5037 p = (center + u * extent[0] - v * extent[1] + w * extent[2]);
5038 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5039 boundaryPoints2[cnt2++] = p;
5041 p = (center + u * extent[0] + v * extent[1] - w * extent[2]);
5042 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5043 boundaryPoints2[cnt2++] = p;
5045 p = (center + u * extent[0] + v * extent[1] + w * extent[2]);
5046 if (
abs(p.dot(axisNormal) - boundary2) <
abs(sMax))
5047 boundaryPoints2[cnt2++] = p;
5050 if (cnt1 == 1 || cnt2 == 1)
5052 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
5054 m.
contacts[0].position = (cnt1 == 1) ? tet.
v[boundaryPoints1[0]] : boundaryPoints2[0];
5060 Segment3D s1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]]);
5064 Segment3D s2(boundaryPoints2[0], boundaryPoints2[1]);
5066 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
5078 for(
int tmp_i = 1; tmp_i < 4; tmp_i ++)
5079 for (
int tmp_j = tmp_i + 1; tmp_j < 4; tmp_j++)
5081 if ((boundaryPoints2[tmp_i] - boundaryPoints2[0]).
dot(boundaryPoints2[tmp_j] - boundaryPoints2[0]) <
EPSILON)
5083 int tmp_k = 1 + 2 + 3 - tmp_i - tmp_j;
5087 boundaryPoints2[1] = p2;
5088 boundaryPoints2[2] = p3;
5089 boundaryPoints2[3] = p4;
5100 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
5101 Triangle3D t2(boundaryPoints2[0], boundaryPoints2[1], boundaryPoints2[2]);
5110 if (dirTmp1.cross(axisNormal).norm() < 1e-4)
5116 if (dirTmp2.cross(axisNormal).norm() < 1e-4)
5122 t2 =
Triangle3D(boundaryPoints2[3], boundaryPoints2[1], boundaryPoints2[2]);
5129 if (dirTmp1.cross(axisNormal).norm() < 1e-4)
5135 if (dirTmp2.cross(axisNormal).norm() < 1e-4)
5141 for (
int i = 0; i < 4; i++)
5145 s2 =
Segment3D(boundaryPoints2[0], boundaryPoints2[i]);
5147 s2 =
Segment3D(boundaryPoints2[3], boundaryPoints2[i - 2]);
5153 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-4)
5156 if ((dir.
v0 - s1.
v0).norm() > 1e-4 && (dir.
v0 - s1.
v1).norm() > 1e-4)
5168 Triangle3D t1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]], tet.
v[boundaryPoints1[2]]);
5175 Segment3D s2(boundaryPoints2[0], boundaryPoints2[1]);
5177 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
5181 if (dirTmp1.cross(axisNormal).norm() < 1e-4)
5187 if (dirTmp2.cross(axisNormal).norm() < 1e-4)
5193 for (
int i = 0; i < 3; i++)
5195 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
5197 if ((!dir.
isValid()) || dir.
direction().normalize().cross(axisNormal).norm() < 1e-4)
5199 if ((dir.
v0 - s2.
v0).norm() > 1e-4 && (dir.
v0 - s2.
v1).norm() > 1e-4)
5210 Triangle3D t1(tet.
v[boundaryPoints1[0]], tet.
v[boundaryPoints1[1]], tet.
v[boundaryPoints1[2]]);
5217 for (
int tmp_i = 1; tmp_i < 4; tmp_i++)
5218 for (
int tmp_j = tmp_i + 1; tmp_j < 4; tmp_j++)
5220 if ((boundaryPoints2[tmp_i] - boundaryPoints2[0]).
dot(boundaryPoints2[tmp_j] - boundaryPoints2[0]) <
EPSILON)
5222 int tmp_k = 1 + 2 + 3 - tmp_i - tmp_j;
5226 boundaryPoints2[1] = p2;
5227 boundaryPoints2[2] = p3;
5228 boundaryPoints2[3] = p4;
5234 m.
normal = (boundary1 > boundary2) ? axisNormal : -axisNormal;
5236 for(
int i = 0; i < 4; i ++)
5237 if ((
Point3D(boundaryPoints2[i]).project(t1).origin - boundaryPoints2[i]).
cross(t1.
normal()).norm() < 1e-4)
5245 for (
int i = 0; i < 3; i++)
5247 Triangle3D t2(boundaryPoints2[0], boundaryPoints2[1], boundaryPoints2[2]);
5255 t2 =
Triangle3D(boundaryPoints2[3], boundaryPoints2[1], boundaryPoints2[2]);
5265 Segment3D s1(t1.
v[(i + 1) % 3], t1.
v[(i + 2) % 3]);
5266 Segment3D s2(boundaryPoints2[0], boundaryPoints2[1]);
5270 if ((dir.
v0 - s1.
v0).norm() > 1e-4 && (dir.
v0 - s1.
v1).norm() > 1e-4)
5280 s2 =
Segment3D(boundaryPoints2[0], boundaryPoints2[2]);
5284 if ((dir.
v0 - s1.
v0).norm() > 1e-4 && (dir.
v0 - s1.
v1).norm() > 1e-4)
5292 s2 =
Segment3D(boundaryPoints2[3], boundaryPoints2[2]);
5296 if ((dir.
v0 - s1.
v0).norm() > 1e-4 && (dir.
v0 - s1.
v1).norm() > 1e-4)
5304 s2 =
Segment3D(boundaryPoints2[3], boundaryPoints2[1]);
5308 if ((dir.
v0 - s1.
v0).norm() > 1e-4 && (dir.
v0 - s1.
v1).norm() > 1e-4)
5324 template<
typename Real>
5331 Real lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2;
5332 Real l1, u1, l2, u2;
5336 Real boundary1, boundary2, b1, b2;
5343 for(
int i = 0; i < 4; i ++)
5346 axisTmp = tet0.
face(i).normal();
5347 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet0, tet1) ==
false)
5354 if (sIntersect < sMax)
5357 lowerBoundary1 = l1;
5358 lowerBoundary2 = l2;
5359 upperBoundary1 = u1;
5360 upperBoundary2 = u2;
5367 axisTmp = tet1.
face(i).normal();
5368 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet0, tet1) ==
false)
5375 if (sIntersect < sMax)
5378 lowerBoundary1 = l1;
5379 lowerBoundary2 = l2;
5380 upperBoundary1 = u1;
5381 upperBoundary2 = u2;
5389 const int segmentIndex[6][2] = {
5398 for(
int i = 0; i < 6; i ++)
5399 for (
int j = 0; j < 6; j++)
5401 Vector<Real, 3> dirTet1 = tet0.
v[segmentIndex[i][0]] - tet0.
v[segmentIndex[i][1]];
5402 Vector<Real, 3> dirTet2 = tet1.
v[segmentIndex[j][0]] - tet1.
v[segmentIndex[j][1]];
5403 axisTmp = dirTet1.cross(dirTet2);
5406 axisTmp /= axisTmp.norm();
5414 axisTmp /= axisTmp.norm();
5416 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet0, tet1) ==
false)
5423 if (sIntersect < sMax)
5426 lowerBoundary1 = l1;
5427 lowerBoundary2 = l2;
5428 upperBoundary1 = u1;
5429 upperBoundary2 = u2;
5443 template<
typename Real>
5450 Real lowerBoundary1, upperBoundary1, lowerBoundary2, upperBoundary2;
5451 Real l1, u1, l2, u2;
5455 Real boundary1, boundary2, b1, b2;
5457 for (
int i = 0; i < 4; i++)
5460 axisTmp = tet.
face(i).normal();
5461 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, box) ==
false)
5468 if (sIntersect < sMax)
5471 lowerBoundary1 = l1;
5472 lowerBoundary2 = l2;
5473 upperBoundary1 = u1;
5474 upperBoundary2 = u2;
5483 axisTmp = box.
u / box.
u.norm();
5484 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, box) ==
false)
5491 if (sIntersect < sMax)
5494 lowerBoundary1 = l1;
5495 lowerBoundary2 = l2;
5496 upperBoundary1 = u1;
5497 upperBoundary2 = u2;
5506 axisTmp = box.
v / box.
v.norm();
5507 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, box) ==
false)
5514 if (sIntersect < sMax)
5517 lowerBoundary1 = l1;
5518 lowerBoundary2 = l2;
5519 upperBoundary1 = u1;
5520 upperBoundary2 = u2;
5528 axisTmp = box.
w / box.
w.norm();
5529 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, box) ==
false)
5536 if (sIntersect < sMax)
5539 lowerBoundary1 = l1;
5540 lowerBoundary2 = l2;
5541 upperBoundary1 = u1;
5542 upperBoundary2 = u2;
5549 const int segmentIndex[6][2] = {
5559 for (
int i = 0; i < 6; i++)
5562 for(
int j = 0; j < 3; j ++)
5565 axisTmp = dirTet.cross(boxDir);
5568 axisTmp /= axisTmp.norm();
5576 axisTmp /= axisTmp.norm();
5578 if (
checkOverlapAxis(l1, u1, l2, u2, sIntersect, b1, b2, axisTmp, tet, box) ==
false)
5585 if (sIntersect < sMax)
5588 lowerBoundary1 = l1;
5589 lowerBoundary2 = l2;
5590 upperBoundary1 = u1;
5591 upperBoundary2 = u2;
5602 template<
typename Real>
5610 template<
typename Real>
5619 bool bInside = c0.
inside(tet);
5621 Segment3D dir = bInside ? c0 - vproj : vproj - c0;
5633 template<
typename Real>
5641 template<
typename Real>
5670 template<
typename Real>
TSeparationData< Real > SeparationData
SquareMatrix< Real, 3 > Matrix3D
static DYN_FUNC void MSDF(SeparationData &sat, const Sphere3D &sphereA, const Sphere3D &sphereB, const Real radiusA, const Real radiusB)
TSegment3D< Real > Segment3D
TCapsule3D< Real > Capsule3D
TSphere3D< Real > Sphere3D
Transform< Real, 3 > Transform3D
TOrientedBox3D< Real > OBox3D
TTriangle3D< Real > Triangle3D
static DYN_FUNC void request(Manifold &m, const Sphere3D &sphereA, const Sphere3D &sphereB, const Real radiusA, const Real radiusB)
TManifold< Real > Manifold
DYN_FUNC Interval< Real > intersect(const Interval< Real > &itv) const
DYN_FUNC TSegment3D< Real > centerline() const
DYN_FUNC Coord3D endPoint() const
DYN_FUNC Coord3D startPoint() const
1D geometric primitives in three-dimensional space
Coord3D u
three unit vectors u, v and w forming a right-handed orthornormal basis
DYN_FUNC TPoint3D< Real > vertex(const int i) const
DYN_FUNC TSegment3D< Real > edge(const int i) const
DYN_FUNC TRectangle3D< Real > face(const int i) const
Coord3D extent
half the dimension in each of the u, v, and w directions
Coord3D center
centerpoint
0D geometric primitive in three-dimensional space
DYN_FUNC TPoint3D< Real > project(const TLine3D< Real > &line) const
project a point onto linear components – lines, rays and segments
DYN_FUNC bool inside(const TLine3D< Real > &line) const
check whether a point strictly lies inside (excluding boundary) a 1D geometric primitive
Coord3D axis[2]
two orthonormal unit axis
DYN_FUNC TPoint3D< Real > vertex(const int i) const
DYN_FUNC Coord3D normal() const
DYN_FUNC Coord3D & endPoint()
DYN_FUNC Real parameter(const Coord3D &pos) const
DYN_FUNC Coord3D direction() const
DYN_FUNC TSegment3D< Real > proximity(const TSegment3D< Real > &segment) const
return a segment pointing from the input segment to the other primitive
DYN_FUNC bool isValid() const
DYN_FUNC bool intersect(const TPlane3D< Real > &plane, TPoint3D< Real > &interPt) const
DYN_FUNC Coord3D & startPoint()
DYN_FUNC Rectangle3D rect()
DYN_FUNC Vector< Real, 3 > pointB()
DYN_FUNC SeparationType face()
DYN_FUNC Triangle3D tri()
DYN_FUNC SeparationType type()
DYN_FUNC void update(SeparationType type, Real BoundaryA, Real BoundaryB, Real Depth, Vec3f N, Vec3f a0, Vec3f a1, Vec3f a2=Vec3f(0.), Vec3f a3=Vec3f(0.))
DYN_FUNC Vector< Real, 3 > normal()
3D geometric primitives in three-dimensional space
vertices are ordered so that the normal vectors for the triangular faces point outwards 3 / | \ 0 - 2...
DYN_FUNC TSegment3D< Real > edge(const int index) const
DYN_FUNC TTriangle3D< Real > face(const int index) const
DYN_FUNC Real volume() const
DYN_FUNC Coord3D normal() const
DYN_FUNC int intrSegWithPlane(Vec3f *q, Vec3f oA, Vec3f nA, Vec3f b0, Vec3f b1)
DYN_FUNC int intrBoxWithPlane(Vec3f *q, Vec3f oA, Vec3f nA, Vec3f center, Vec3f halfU, Vec3f halfV, Vec3f halfW)
DYN_FUNC int intrPolyWithRect(Vec3f *q, int n, Vec3f *p, Vec3f a0, Vec3f a1, Vec3f a2, Vec3f a3)
DYN_FUNC int intrTetWithPlane(Vec3f *q, Vec3f oA, Vec3f nA, Vec3f b0, Vec3f b1, Vec3f b2, Vec3f b3)
DYN_FUNC int intrPolyWithTri(Vec3f *q, int n, Vec3f *p, Vec3f a0, Vec3f a1, Vec3f a2)
DYN_FUNC int intrTriWithPlane(Vec3f *q, Vec3f oA, Vec3f nA, Vec3f b0, Vec3f b1, Vec3f b2)
This is an implementation of AdditiveCCD based on peridyno.
DYN_FUNC void computeSupportEdge(Vector< Real, 3 > &aOut, Vector< Real, 3 > &bOut, const SquareMatrix< Real, 3 > &rot, const Vector< Real, 3 > &trans, const Vector< Real, 3 > &e, Vector< Real, 3 > n)
DYN_FUNC int sign(T const &a, T const EPS=EPSILON)
DYN_FUNC void checkAxisPoint(TSeparationData< Real > &sat, ShapeA &shapeA, ShapeB &shapeB, const Real radiusA, const Real radiusB, Vec3f pA, Vec3f pB, const Real rA=0.f, const Real rB=0.f)
DYN_FUNC void computeReferenceEdgesAndBasis(unsigned char *out, SquareMatrix< Real, 3 > *basis, Vector< Real, 3 > *e, const Vector< Real, 3 > &eR, const Transform< Real, 3 > &rtx, Vector< Real, 3 > n, int axis)
DYN_FUNC void setupContactOnSphere(TManifold< Real > &m, TSeparationData< Real > &sat, const TSphere3D< Real > &sphereB, const Real radiusA, const Real radiusB)
DYN_FUNC void updateSDF(Real &boundaryA, Real &boundaryB, Real &depth, Vec3f &normal, Real currentBoundaryA, Real currentBoundaryB, Real currentDepth, Vec3f currentN)
DYN_FUNC Vector< T, 3 > cross(Vector< T, 3 > const &U, Vector< T, 3 > const &V)
DYN_FUNC void setupContactTets(Real boundary1, Real boundary2, const Vector< Real, 3 > axisNormal, Tet3D tet, Capsule3D cap, Real sMax, TManifold< Real > &m)
DYN_FUNC int clipEdgeAgainstRectangle(ClipVertex *outVerts, float *outDepths, const Vector< Real, 3 > &rPos, const Vector< Real, 3 > &e, unsigned char *clipEdges, const SquareMatrix< Real, 3 > &basis, ClipVertex *incident)
DYN_FUNC T dot(Vector< T, 2 > const &U, Vector< T, 2 > const &V)
DYN_FUNC void checkAxisRect(TSeparationData< Real > &sat, ShapeA &shapeA, ShapeB &shapeB, const Real radiusA, const Real radiusB, Rectangle3D rect, SeparationType type)
DYN_FUNC void computeIncidentFace(ClipVertex *out, const Transform< Real, 3 > &itx, const Vector< Real, 3 > &e, Vector< Real, 3 > n)
DYN_FUNC void projectOnAxis(Real &lowerBoundary, Real &upperBoundary, const Vec3f axisNormal, Sphere3D sphere, const Real radius)
TRectangle3D< double > Rectangle3D
DYN_FUNC void setupContactOnBox(TManifold< Real > &m, TSeparationData< Real > &sat, const Shape &shapeA, const TOrientedBox3D< Real > &boxB, const Real radiusA, const Real radiusB)
DYN_FUNC T abs(const T &v)
TTriangle3D< double > Triangle3D
DYN_FUNC void checkAxisEdge(TSeparationData< Real > &sat, ShapeA &shapeA, ShapeB &shapeB, const Real radiusA, const Real radiusB, Segment3D edgeA, Segment3D edgeB)
DYN_FUNC bool checkPointInBoundary(const Vec3f &p, const Vec3f &N, const Real &b, const Real &r)
DYN_FUNC int ClippingWithRect(Vector< Real, 3 > *q, const TRectangle3D< Real > &rectA, const TSphere3D< Real > &sphereB, const Vector< Real, 3 > &transA, const Vector< Real, 3 > &transB)
DYN_FUNC void setupContactCaps(Real boundary1, Real boundary2, const Vector< Real, 3 > axisNormal, TCapsule3D< Real > cap, TOrientedBox3D< Real > box, Real depth, TManifold< Real > &m)
DYN_FUNC int ClippingWithTri(Vector< Real, 3 > *q, const TTriangle3D< Real > &triA, const TSphere3D< Real > &sphereB, const Vector< Real, 3 > &transA, const Vector< Real, 3 > &transB)
DYN_FUNC void setupContactTetTri(Real boundary1, Real boundary2, const Vector< Real, 3 > axisNormal, Tet3D tet, Triangle3D triangle, Real sMax, TManifold< Real > &m)
TOrientedBox3D< double > OrientedBox3D
DYN_FUNC void checkSignedDistance(Real lowerBoundaryA, Real upperBoundaryA, Real lowerBoundaryB, Real upperBoundaryB, Real &intersectionDistance, Real &boundaryA, Real &boundaryB)
DYN_FUNC void setupContactOnSeg(TManifold< Real > &m, TSeparationData< Real > &sat, const TSegment3D< Real > &segB, const Real radiusA, const Real radiusB)
DYN_FUNC void swapContactPair(TManifold< Real > &m)
TCapsule3D< double > Capsule3D
DYN_FUNC bool checkOverlapTetTri(Real lowerBoundary1, Real upperBoundary1, Real lowerBoundary2, Real upperBoundary2, Real &intersectionDistance, Real &boundary1, Real &boundary2)
TPoint3D< double > Point3D
DYN_FUNC void setupContactOnTri(TManifold< Real > &m, TSeparationData< Real > &sat, const Shape &shapeA, const TTriangle3D< Real > &triB, const Real radiusA, const Real radiusB)
DYN_FUNC void edgesContact(Vector< Real, 3 > &CA, Vector< Real, 3 > &CB, const Vector< Real, 3 > &PA, const Vector< Real, 3 > &QA, const Vector< Real, 3 > &PB, const Vector< Real, 3 > &QB)
DYN_FUNC void checkSignedDistanceAxis(Real &intersectionDistance, Real &BoundaryA, Real &BoundaryB, const Vec3f axisNormal, ShapeA &shapeA, ShapeB &shapeB, const Real radiusA, const Real radiusB)
DYN_FUNC float fsign(Real v)
DYN_FUNC int orthographic(ClipVertex *out, Real sign, Real e, int axis, int clipEdge, ClipVertex *in, int inCount)
DYN_FUNC bool trackFaceAxis(int &axis, Real &sMax, Vector< Real, 3 > &axisNormal, int n, Real s, const Vector< Real, 3 > &normal)
DYN_FUNC bool trackEdgeAxis(int &axis, Real &sMax, Vector< Real, 3 > &axisNormal, int n, Real s, const Vector< Real, 3 > &normal)
TSphere3D< double > Sphere3D
DYN_FUNC void setupContactOnTet(TManifold< Real > &m, TSeparationData< Real > &sat, const Shape &shapeA, const TTet3D< Real > &tetB, const Real radiusA, const Real radiusB)
TSegment3D< double > Segment3D
DYN_FUNC void checkAxisTri(TSeparationData< Real > &sat, ShapeA &shapeA, ShapeB &shapeB, const Real radiusA, const Real radiusB, Triangle3D tri, SeparationType type)
DYN_FUNC int clip(ClipVertex *outVerts, float *outDepths, const Vector< Real, 3 > &rPos, const Vector< Real, 3 > &e, unsigned char *clipEdges, const SquareMatrix< Real, 3 > &basis, ClipVertex *incident)
DYN_FUNC bool checkOverlapAxis(Real &lowerBoundary1, Real &upperBoundary1, Real &lowerBoundary2, Real &upperBoundary2, Real &intersectionDistance, Real &boundary1, Real &boundary2, const Vector< Real, 3 > axisNormal, OrientedBox3D box, Capsule3D cap)
DYN_FUNC bool checkOverlap(Real lowerBoundary1, Real upperBoundary1, Real lowerBoundary2, Real upperBoundary2, Real &intersectionDistance, Real &boundary1, Real &boundary2)
DYN_FUNC void pushContact(const Vector< Real, 3 > &pos, const Real &dep)
TContact< Real > contacts[8]