15#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
   26#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
   28    static constexpr Real cDrawScale = 10;
 
   65        inline          Triangle(
int inIdx0, 
int inIdx1, 
int inIdx2, 
const Vec3 *inPositions);
 
   84            return mEdge[(inIndex + 1) % 3];
 
   96#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  106        union alignas(Triangle) Block
 
  113        Block           mTriangles[cMaxTriangles];          
 
  114        Block *         mNextFree = 
nullptr;                
 
  115        int             mHighWatermark = 0;                 
 
  129            if (mNextFree != 
nullptr)
 
  132                t = 
reinterpret_cast<Triangle *
>(&mNextFree->mTriangle);
 
  133                mNextFree = mNextFree->mNextFree;
 
  138                if (mHighWatermark >= cMaxTriangles)
 
  140                t = 
reinterpret_cast<Triangle *
>(&mTriangles[mHighWatermark].mTriangle);
 
  145            new (t) 
Triangle(inIdx0, inIdx1, inIdx2, inPositions);
 
  156            memset(inT, 0xcd, 
sizeof(
Triangle));
 
  160            Block *tu = 
reinterpret_cast<Block *
>(inT);
 
  161            tu->mNextFree = mNextFree;
 
  194            Triangles::push_back(inT);
 
  200            std::push_heap(begin(), end(), sTriangleSorter);
 
  213            std::pop_heap(begin(), end(), sTriangleSorter);
 
  224        mPositions(inPositions)
 
  226#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  243        sLinkTriangle(t1, 0, t2, 2);
 
  244        sLinkTriangle(t1, 1, t2, 1);
 
  245        sLinkTriangle(t1, 2, t2, 0);
 
  248        mTriangleQueue.push_back(t1);
 
  249        mTriangleQueue.push_back(t2);
 
  251#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  263        return !mTriangleQueue.empty();
 
  269        return mTriangleQueue.PeekClosest();
 
  275        return mTriangleQueue.PopClosest();
 
  283        float best_dist_sq = 0.0f;
 
  288                float dot = t->
mNormal.
Dot(inPosition - t->mCentroid);
 
  291                    float dist_sq = dot * dot / t->mNormal.LengthSq();
 
  292                    if (dist_sq > best_dist_sq)
 
  295                        best_dist_sq = dist_sq;
 
  300        outBestDistSq = best_dist_sq;
 
  308        Vec3 pos = mPositions[inIdx];
 
  310#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  315#ifdef JPH_EPA_CONVEX_BUILDER_VALIDATE 
  322        if (!FindEdge(inFacingTriangle, pos, edges))
 
  326        int num_edges = edges.
size();
 
  327        for (
int i = 0; i < num_edges; ++i)
 
  338                mTriangleQueue.push_back(nt);
 
  342        for (
int i = 0; i < num_edges; ++i)
 
  344            sLinkTriangle(outTriangles[i], 0, edges[i].mNeighbourTriangle, edges[i].mNeighbourEdge);
 
  345            sLinkTriangle(outTriangles[i], 1, outTriangles[(i + 1) % num_edges], 2);
 
  348#ifdef JPH_EPA_CONVEX_BUILDER_VALIDATE 
  353#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  367#ifdef JPH_ENABLE_ASSERTS 
  374#if defined(JPH_EPA_CONVEX_BUILDER_VALIDATE) || defined(JPH_EPA_CONVEX_BUILDER_DRAW) 
  381        mFactory.FreeTriangle(inT);
 
  389        Triangle *t = mFactory.CreateTriangle(inIdx1, inIdx2, inIdx3, mPositions.data());
 
  393#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  395        t->mIteration = mIteration;
 
  398#if defined(JPH_EPA_CONVEX_BUILDER_VALIDATE) || defined(JPH_EPA_CONVEX_BUILDER_DRAW) 
  400        mTriangles.push_back(t);
 
  407    static void         sLinkTriangle(
Triangle *inT1, 
int inEdge1, 
Triangle *inT2, 
int inEdge2)
 
  411        Edge &e1 = inT1->mEdge[inEdge1];
 
  412        Edge &e2 = inT2->mEdge[inEdge2];
 
  419        JPH_ASSERT(e1.mStartIdx == inT2->GetNextEdge(inEdge2).mStartIdx);
 
  420        JPH_ASSERT(e2.mStartIdx == inT1->GetNextEdge(inEdge1).mStartIdx);
 
  423        e1.mNeighbourTriangle = inT2;
 
  424        e1.mNeighbourEdge = inEdge2;
 
  425        e2.mNeighbourTriangle = inT1;
 
  426        e2.mNeighbourEdge = inEdge1;
 
  433        for (
int i = 0; i < 3; ++i)
 
  435            Edge &edge = inT->mEdge[i];
 
  436            if (edge.mNeighbourTriangle != 
nullptr)
 
  438                Edge &neighbour_edge = edge.mNeighbourTriangle->mEdge[edge.mNeighbourEdge];
 
  441                JPH_ASSERT(neighbour_edge.mNeighbourTriangle == inT);
 
  442                JPH_ASSERT(neighbour_edge.mNeighbourEdge == i);
 
  445                neighbour_edge.mNeighbourTriangle = 
nullptr;
 
  446                edge.mNeighbourTriangle = 
nullptr;
 
  463        JPH_ASSERT(inFacingTriangle->IsFacing(inVertex));
 
  466        inFacingTriangle->mRemoved = 
true;
 
  476        int cur_stack_pos = 0;
 
  479        stack[0].mTriangle = inFacingTriangle;
 
  484        int next_expected_start_idx = -1;
 
  488            StackEntry &cur_entry = stack[cur_stack_pos];
 
  491            if (++cur_entry.mIter >= 3)
 
  494                UnlinkTriangle(cur_entry.mTriangle);
 
  497                if (--cur_stack_pos < 0)
 
  503                Edge &e = cur_entry.mTriangle->mEdge[(cur_entry.mEdge + cur_entry.mIter) % 3];
 
  505                if (n != 
nullptr && !n->mRemoved)
 
  508                    if (n->IsFacing(inVertex))
 
  516                        StackEntry &new_entry = stack[cur_stack_pos];
 
  517                        new_entry.mTriangle = n;
 
  518                        new_entry.mEdge = e.mNeighbourEdge;
 
  529                        if (e.mStartIdx != next_expected_start_idx && next_expected_start_idx != -1)
 
  533                        next_expected_start_idx = n->mEdge[e.mNeighbourEdge].mStartIdx;
 
  536                        outEdges.push_back(e);
 
  543        JPH_ASSERT(outEdges.empty() || outEdges[0].mStartIdx == next_expected_start_idx);
 
  545#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  547        for (
int i = 0; i < (int)outEdges.size(); ++i)
 
  549            RVec3 edge_start = cDrawScale * (mOffset + mPositions[outEdges[i].mStartIdx]);
 
  561        return outEdges.size() >= 3;
 
  564#ifdef JPH_EPA_CONVEX_BUILDER_VALIDATE 
  566    void                ValidateTriangle(
const Triangle *inT)
 const 
  571            for (
const Edge &my_edge : inT->mEdge)
 
  572                JPH_ASSERT(my_edge.mNeighbourTriangle == 
nullptr);
 
  576            for (
int i = 0; i < 3; ++i)
 
  578                const Edge &my_edge = inT->mEdge[i];
 
  581                const Triangle *nb = my_edge.mNeighbourTriangle;
 
  587                    const Edge &nb_edge = nb->mEdge[my_edge.mNeighbourEdge];
 
  588                    JPH_ASSERT(nb_edge.mNeighbourTriangle == inT);
 
  592                    const Edge &nb_next_edge = nb->GetNextEdge(my_edge.mNeighbourEdge);
 
  593                    JPH_ASSERT(nb_next_edge.mStartIdx == my_edge.mStartIdx);
 
  596                    const Edge &my_next_edge = inT->GetNextEdge(i);
 
  597                    JPH_ASSERT(my_next_edge.mStartIdx == nb_edge.mStartIdx);
 
  604    void                ValidateTriangles()
 const 
  606        for (
const Triangle *t : mTriangles)
 
  611#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  620        for (
const Triangle *t : mTriangles)
 
  624                RVec3 p1 = cDrawScale * (mOffset + mPositions[t->mEdge[0].mStartIdx]);
 
  625                RVec3 p2 = cDrawScale * (mOffset + mPositions[t->mEdge[1].mStartIdx]);
 
  626                RVec3 p3 = cDrawScale * (mOffset + mPositions[t->mEdge[2].mStartIdx]);
 
  633                RVec3 centroid = cDrawScale * (mOffset + t->mCentroid);
 
  634                float len = t->mNormal.Length();
 
  640        float min_x = FLT_MAX;
 
  641        float max_x = -FLT_MAX;
 
  642        for (
Vec3 p : mPositions)
 
  644            min_x = min(min_x, p.GetX());
 
  645            max_x = max(max_x, p.GetX());
 
  649        mOffset += 
Vec3(max_x - min_x + 0.5f, 0.0f, 0.0f);
 
  653    void                DrawLabel(
const string_view &inText)
 
  657        mOffset += 
Vec3(5.0f, 0.0f, 0.0f);
 
  666        mOffset += 
Vec3(inGeometry->mBounds.GetSize().GetX(), 0, 0);
 
  672        RVec3 prev = cDrawScale * (mOffset + mPositions[inTriangle.mEdge[2].mStartIdx]);
 
  673        for (
const Edge &edge : inTriangle.mEdge)
 
  675            RVec3 cur = cDrawScale * (mOffset + mPositions[edge.mStartIdx]);
 
  695    TriangleFactory     mFactory;                           
 
  696    const Points &      mPositions;                         
 
  697    TriangleQueue       mTriangleQueue;                     
 
  699#if defined(JPH_EPA_CONVEX_BUILDER_VALIDATE) || defined(JPH_EPA_CONVEX_BUILDER_DRAW) 
  703#ifdef JPH_EPA_CONVEX_BUILDER_DRAW 
  716    JPH_ASSERT(inIdx0 != inIdx1 && inIdx0 != inIdx2 && inIdx1 != inIdx2);
 
  717    mEdge[0].mStartIdx = inIdx0;
 
  718    mEdge[1].mStartIdx = inIdx1;
 
  719    mEdge[2].mStartIdx = inIdx2;
 
  722    mEdge[0].mNeighbourTriangle = 
nullptr;
 
  723    mEdge[1].mNeighbourTriangle = 
nullptr;
 
  724    mEdge[2].mNeighbourTriangle = 
nullptr;
 
  727    Vec3 y0 = inPositions[inIdx0];
 
  728    Vec3 y1 = inPositions[inIdx1];
 
  729    Vec3 y2 = inPositions[inIdx2];
 
  732    mCentroid = (y0 + y1 + y2) / 3.0f;
 
  744    float y20_dot_y20 = y20.
Dot(y20);
 
  745    float y21_dot_y21 = y21.
Dot(y21);
 
  746    if (y20_dot_y20 < y21_dot_y21)
 
  749        mNormal = y10.
Cross(y20);
 
  752        float normal_len_sq = mNormal.
LengthSq();
 
  758            float c_dot_n = mCentroid.Dot(mNormal);
 
  759            mClosestLenSq = abs(c_dot_n) * c_dot_n / normal_len_sq;
 
  776            float y10_dot_y20 = y10.
Dot(y20);
 
  777            float determinant = y10_dot_y10 * y20_dot_y20 - y10_dot_y20 * y10_dot_y20;
 
  778            if (determinant > 0.0f) 
 
  780                float y0_dot_y10 = y0.
Dot(y10);
 
  781                float y0_dot_y20 = y0.
Dot(y20);
 
  782                float l0 = (y10_dot_y20 * y0_dot_y20 - y20_dot_y20 * y0_dot_y10) / determinant;
 
  783                float l1 = (y10_dot_y20 * y0_dot_y10 - y10_dot_y10 * y0_dot_y20) / determinant;
 
  786                mLambdaRelativeTo0 = 
true;
 
  792                    mClosestPointInterior = 
true;
 
  799        mNormal = y10.
Cross(y21);
 
  802        float normal_len_sq = mNormal.
LengthSq();
 
  806            float c_dot_n = mCentroid.Dot(mNormal);
 
  807            mClosestLenSq = abs(c_dot_n) * c_dot_n / normal_len_sq;
 
  822            float y10_dot_y21 = y10.
Dot(y21);
 
  823            float determinant = y10_dot_y10 * y21_dot_y21 - y10_dot_y21 * y10_dot_y21;
 
  824            if (determinant > 0.0f)
 
  826                float y1_dot_y10 = y1.
Dot(y10);
 
  827                float y1_dot_y21 = y1.
Dot(y21);
 
  828                float l0 = (y21_dot_y21 * y1_dot_y10 - y10_dot_y21 * y1_dot_y21) / determinant;
 
  829                float l1 = (y10_dot_y21 * y1_dot_y10 - y10_dot_y10 * y1_dot_y21) / determinant;
 
  832                mLambdaRelativeTo0 = 
false;
 
  836                    mClosestPointInterior = 
true;
 
std::uint8_t uint8
Definition: Core.h:453
 
#define JPH_NAMESPACE_END
Definition: Core.h:378
 
#define JPH_NAMESPACE_BEGIN
Definition: Core.h:372
 
#define JPH_ASSERT(...)
Definition: IssueReporting.h:33
 
float Real
Definition: Real.h:27
 
Class that holds an RGBA color with 8-bits per component.
Definition: Color.h:16
 
static const Color sWhite
Definition: Color.h:67
 
static Color sGetDistinctColor(int inIndex)
Get a visually distinct color.
Definition: Color.cpp:31
 
static const Color sDarkGreen
Definition: Color.h:56
 
static const Color sGrey
Definition: Color.h:65
 
static const Color sYellow
Definition: Color.h:60
 
virtual void DrawText3D(RVec3Arg inPosition, const string_view &inString, ColorArg inColor=Color::sWhite, float inHeight=0.5f)=0
Draw text.
 
void DrawMarker(RVec3Arg inPosition, ColorArg inColor, float inSize)
Draw a marker on a position.
Definition: DebugRenderer.cpp:172
 
void DrawWireTriangle(RVec3Arg inV1, RVec3Arg inV2, RVec3Arg inV3, ColorArg inColor)
Draw wireframe triangle.
Definition: DebugRenderer.cpp:242
 
void DrawCoordinateSystem(RMat44Arg inTransform, float inSize=1.0f)
Draw coordinate system (3 arrows, x = red, y = green, z = blue)
Definition: DebugRenderer.cpp:206
 
virtual void DrawGeometry(RMat44Arg inModelMatrix, const AABox &inWorldSpaceBounds, float inLODScaleSq, ColorArg inModelColor, const GeometryRef &inGeometry, ECullMode inCullMode=ECullMode::CullBackFace, ECastShadow inCastShadow=ECastShadow::On, EDrawMode inDrawMode=EDrawMode::Solid)=0
 
static DebugRenderer * sInstance
Singleton instance.
Definition: DebugRenderer.h:179
 
void DrawArrow(RVec3Arg inFrom, RVec3Arg inTo, ColorArg inColor, float inSize)
Draw an arrow.
Definition: DebugRenderer.cpp:184
 
virtual void DrawTriangle(RVec3Arg inV1, RVec3Arg inV2, RVec3Arg inV3, ColorArg inColor, ECastShadow inCastShadow=ECastShadow::Off)=0
Draw a single back face culled triangle.
 
Class that holds the information of an edge.
Definition: EPAConvexHullBuilder.h:48
 
int mStartIdx
Vertex index in mPositions that indicates the start vertex of this edge.
Definition: EPAConvexHullBuilder.h:54
 
Triangle * mNeighbourTriangle
Information about neighbouring triangle.
Definition: EPAConvexHullBuilder.h:51
 
int mNeighbourEdge
Index in mEdge that specifies edge that this Edge is connected to.
Definition: EPAConvexHullBuilder.h:52
 
Specialized points list that allows direct access to the size.
Definition: EPAConvexHullBuilder.h:172
 
size_type & GetSizeRef()
Definition: EPAConvexHullBuilder.h:174
 
Factory that creates triangles in a fixed size buffer.
Definition: EPAConvexHullBuilder.h:103
 
Triangle * CreateTriangle(int inIdx0, int inIdx1, int inIdx2, const Vec3 *inPositions)
Allocate a new triangle with 3 indexes.
Definition: EPAConvexHullBuilder.h:126
 
void FreeTriangle(Triangle *inT)
Free a triangle.
Definition: EPAConvexHullBuilder.h:151
 
void Clear()
Return all triangles to the free pool.
Definition: EPAConvexHullBuilder.h:119
 
Class that holds the information of one triangle.
Definition: EPAConvexHullBuilder.h:62
 
Vec3 mCentroid
Center of the triangle.
Definition: EPAConvexHullBuilder.h:89
 
bool mClosestPointInterior
Flag that indicates that the closest point from this triangle to the origin is an interior point.
Definition: EPAConvexHullBuilder.h:93
 
bool IsFacing(Vec3Arg inPosition) const
Check if triangle is facing inPosition.
Definition: EPAConvexHullBuilder.h:68
 
const Edge & GetNextEdge(int inIndex) const
Get the next edge of edge inIndex.
Definition: EPAConvexHullBuilder.h:82
 
Vec3 mNormal
Normal of this triangle, length is 2 times area of triangle.
Definition: EPAConvexHullBuilder.h:88
 
Edge mEdge[3]
3 edges of this triangle
Definition: EPAConvexHullBuilder.h:87
 
bool IsFacingOrigin() const
Check if triangle is facing the origin.
Definition: EPAConvexHullBuilder.h:75
 
float mClosestLenSq
Closest distance^2 from origin to triangle.
Definition: EPAConvexHullBuilder.h:90
 
Triangle(int inIdx0, int inIdx1, int inIdx2, const Vec3 *inPositions)
Constructor.
Definition: EPAConvexHullBuilder.h:713
 
bool mInQueue
Flag that indicates that this triangle was placed in the sorted heap (stays true after it is popped b...
Definition: EPAConvexHullBuilder.h:95
 
float mLambda[2]
Barycentric coordinates of closest point to origin on triangle.
Definition: EPAConvexHullBuilder.h:91
 
bool mLambdaRelativeTo0
How to calculate the closest point, true: y0 + l0 * (y1 - y0) + l1 * (y2 - y0), false: y1 + l0 * (y0 ...
Definition: EPAConvexHullBuilder.h:92
 
bool mRemoved
Flag that indicates that triangle has been removed.
Definition: EPAConvexHullBuilder.h:94
 
Specialized triangles list that keeps them sorted on closest distance to origin.
Definition: EPAConvexHullBuilder.h:182
 
void push_back(Triangle *inT)
Add triangle to the list.
Definition: EPAConvexHullBuilder.h:191
 
Triangle * PeekClosest()
Peek the next closest triangle without removing it.
Definition: EPAConvexHullBuilder.h:204
 
Triangle * PopClosest()
Get next closest triangle.
Definition: EPAConvexHullBuilder.h:210
 
static bool sTriangleSorter(const Triangle *inT1, const Triangle *inT2)
Function to sort triangles on closest distance to origin.
Definition: EPAConvexHullBuilder.h:185
 
A convex hull builder specifically made for the EPA penetration depth calculation....
Definition: EPAConvexHullBuilder.h:24
 
Triangle * PeekClosestTriangleInQueue()
Access to the next closest triangle to the origin (won't remove it from the queue).
Definition: EPAConvexHullBuilder.h:267
 
bool HasNextTriangle() const
Check if there's another triangle to process from the queue.
Definition: EPAConvexHullBuilder.h:261
 
static constexpr int cMaxTriangles
Max triangles in hull.
Definition: EPAConvexHullBuilder.h:35
 
StaticArray< Edge, cMaxEdgeLength > Edges
Definition: EPAConvexHullBuilder.h:57
 
static constexpr float cMinTriangleArea
Minimum area of a triangle before, if smaller than this it will not be added to the priority queue.
Definition: EPAConvexHullBuilder.h:40
 
static constexpr float cBarycentricEpsilon
Epsilon value used to determine if a point is in the interior of a triangle.
Definition: EPAConvexHullBuilder.h:41
 
static constexpr int cMaxPoints
Max number of points in hull.
Definition: EPAConvexHullBuilder.h:36
 
Triangle * PopClosestTriangleFromQueue()
Access to the next closest triangle to the origin and remove it from the queue.
Definition: EPAConvexHullBuilder.h:273
 
static constexpr int cMaxEdgeLength
Max number of edges in FindEdge.
Definition: EPAConvexHullBuilder.h:39
 
void FreeTriangle(Triangle *inT)
Free a triangle.
Definition: EPAConvexHullBuilder.h:365
 
Triangle * FindFacingTriangle(Vec3Arg inPosition, float &outBestDistSq)
Definition: EPAConvexHullBuilder.h:280
 
void Initialize(int inIdx1, int inIdx2, int inIdx3)
Initialize the hull with 3 points.
Definition: EPAConvexHullBuilder.h:233
 
bool AddPoint(Triangle *inFacingTriangle, int inIdx, float inClosestDistSq, NewTriangles &outTriangles)
Add a new point to the convex hull.
Definition: EPAConvexHullBuilder.h:305
 
EPAConvexHullBuilder(const Points &inPositions)
Constructor.
Definition: EPAConvexHullBuilder.h:223
 
StaticArray< Triangle *, cMaxTriangles > Triangles
Definition: EPAConvexHullBuilder.h:168
 
Holds a 4x4 matrix of floats, but supports also operations on the 3x3 upper left part of the matrix.
Definition: Mat44.h:13
 
static JPH_INLINE Mat44 sScale(float inScale)
Get matrix that scales uniformly.
Definition: Mat44.inl:163
 
static JPH_INLINE Mat44 sTranslation(Vec3Arg inV)
Get matrix that translates.
Definition: Mat44.inl:144
 
Class that makes another class non-copyable. Usage: Inherit from NonCopyable.
Definition: NonCopyable.h:11
 
Simple variable length array backed by a fixed size buffer.
Definition: StaticArray.h:14
 
void push_back(const T &inElement)
Add element to the back of the array.
Definition: StaticArray.h:61
 
T * iterator
Definition: StaticArray.h:126
 
uint size_type
Definition: StaticArray.h:18
 
size_type size() const
Returns amount of elements in the array.
Definition: StaticArray.h:89
 
A simple triangle and its material.
Definition: Triangle.h:11
 
JPH_INLINE float Dot(Vec3Arg inV2) const
Dot product.
Definition: Vec3.inl:649
 
JPH_INLINE Vec3 Cross(Vec3Arg inV2) const
Cross product.
Definition: Vec3.inl:594
 
JPH_INLINE float LengthSq() const
Squared length of vector.
Definition: Vec3.inl:665
 
static JPH_INLINE Vec3 sZero()
Vector with all zeros.
Definition: Vec3.inl:107
 
static JPH_INLINE Vec3 sReplicate(float inV)
Replicate inV across all components.
Definition: Vec3.inl:118