DistTriangle3Rectangle3.h 3.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586
  1. // David Eberly, Geometric Tools, Redmond WA 98052
  2. // Copyright (c) 1998-2020
  3. // Distributed under the Boost Software License, Version 1.0.
  4. // https://www.boost.org/LICENSE_1_0.txt
  5. // https://www.geometrictools.com/License/Boost/LICENSE_1_0.txt
  6. // Version: 4.0.2019.08.13
  7. #pragma once
  8. #include <Mathematics/DistSegment3Rectangle3.h>
  9. #include <Mathematics/DistSegment3Triangle3.h>
  10. namespace WwiseGTE
  11. {
  12. template <typename Real>
  13. class DCPQuery<Real, Triangle3<Real>, Rectangle3<Real>>
  14. {
  15. public:
  16. struct Result
  17. {
  18. Real distance, sqrDistance;
  19. Real triangleParameter[3], rectangleParameter[2];
  20. Vector3<Real> closestPoint[2];
  21. };
  22. Result operator()(Triangle3<Real> const& triangle, Rectangle3<Real> const& rectangle)
  23. {
  24. Result result;
  25. result.sqrDistance = std::numeric_limits<Real>::max();
  26. // Compare edges of triangle to the interior of rectangle.
  27. for (int i0 = 2, i1 = 0; i1 < 3; i0 = i1++)
  28. {
  29. Vector3<Real> segCenter = (Real)0.5 * (triangle.v[i0] + triangle.v[i1]);
  30. Vector3<Real> segDirection = triangle.v[i1] - triangle.v[i0];
  31. Real segExtent = (Real)0.5 * Normalize(segDirection);
  32. Segment3<Real> edge(segCenter, segDirection, segExtent);
  33. DCPQuery<Real, Segment3<Real>, Rectangle3<Real>> srQuery;
  34. auto srResult = srQuery(edge, rectangle);
  35. if (srResult.sqrDistance < result.sqrDistance)
  36. {
  37. result.distance = srResult.distance;
  38. result.sqrDistance = srResult.sqrDistance;
  39. // ratio is in [-1,1]
  40. Real ratio = srResult.segmentParameter / segExtent;
  41. result.triangleParameter[i0] = (Real)0.5 * ((Real)1 - ratio);
  42. result.triangleParameter[i1] = (Real)1 - result.triangleParameter[i0];
  43. result.triangleParameter[3 - i0 - i1] = (Real)0;
  44. result.rectangleParameter[0] = srResult.rectangleParameter[0];
  45. result.rectangleParameter[1] = srResult.rectangleParameter[1];
  46. result.closestPoint[0] = srResult.closestPoint[0];
  47. result.closestPoint[1] = srResult.closestPoint[1];
  48. }
  49. }
  50. // Compare edges of rectangle to the interior of triangle.
  51. for (int i1 = 0; i1 < 2; ++i1)
  52. {
  53. for (int i0 = -1; i0 <= 1; i0 += 2)
  54. {
  55. Real s = i0 * rectangle.extent[1 - i1];
  56. Vector3<Real> segCenter = rectangle.center + s * rectangle.axis[1 - i1];
  57. Segment3<Real> edge(segCenter, rectangle.axis[i1], rectangle.extent[i1]);
  58. DCPQuery<Real, Segment3<Real>, Triangle3<Real>> stQuery;
  59. auto stResult = stQuery(edge, triangle);
  60. if (stResult.sqrDistance < result.sqrDistance)
  61. {
  62. result.distance = stResult.distance;
  63. result.sqrDistance = stResult.sqrDistance;
  64. result.triangleParameter[0] = stResult.triangleParameter[0];
  65. result.triangleParameter[1] = stResult.triangleParameter[1];
  66. result.triangleParameter[2] = stResult.triangleParameter[2];
  67. result.rectangleParameter[i1] = s;
  68. result.rectangleParameter[1 - i1] = stResult.segmentParameter;
  69. result.closestPoint[0] = stResult.closestPoint[1];
  70. result.closestPoint[1] = stResult.closestPoint[0];
  71. }
  72. }
  73. }
  74. return result;
  75. }
  76. };
  77. }