22#include "DetourMath.h"
41template<
class T>
void dtIgnoreUnused(
const T&) { }
46template<
class T>
inline void dtSwap(T& a, T& b) { T t = a; a = b; b = t; }
52template<
class T>
inline T dtMin(T a, T b) {
return a < b ? a : b; }
58template<
class T>
inline T dtMax(T a, T b) {
return a > b ? a : b; }
63template<
class T>
inline T dtAbs(T a) {
return a < 0 ? -a : a; }
68template<
class T>
inline T dtSqr(T a) {
return a*a; }
75template<
class T>
inline T dtClamp(T v, T mn, T mx) {
return v < mn ? mn : (v > mx ? mx : v); }
85inline void dtVcross(
float* dest,
const float* v1,
const float* v2)
87 dest[0] = v1[1]*v2[2] - v1[2]*v2[1];
88 dest[1] = v1[2]*v2[0] - v1[0]*v2[2];
89 dest[2] = v1[0]*v2[1] - v1[1]*v2[0];
96inline float dtVdot(
const float* v1,
const float* v2)
98 return v1[0]*v2[0] + v1[1]*v2[1] + v1[2]*v2[2];
106inline void dtVmad(
float* dest,
const float* v1,
const float* v2,
const float s)
108 dest[0] = v1[0]+v2[0]*s;
109 dest[1] = v1[1]+v2[1]*s;
110 dest[2] = v1[2]+v2[2]*s;
118inline void dtVlerp(
float* dest,
const float* v1,
const float* v2,
const float t)
120 dest[0] = v1[0]+(v2[0]-v1[0])*t;
121 dest[1] = v1[1]+(v2[1]-v1[1])*t;
122 dest[2] = v1[2]+(v2[2]-v1[2])*t;
129inline void dtVadd(
float* dest,
const float* v1,
const float* v2)
131 dest[0] = v1[0]+v2[0];
132 dest[1] = v1[1]+v2[1];
133 dest[2] = v1[2]+v2[2];
140inline void dtVsub(
float* dest,
const float* v1,
const float* v2)
142 dest[0] = v1[0]-v2[0];
143 dest[1] = v1[1]-v2[1];
144 dest[2] = v1[2]-v2[2];
151inline void dtVscale(
float* dest,
const float* v,
const float t)
161inline void dtVmin(
float* mn,
const float* v)
163 mn[0] = dtMin(mn[0], v[0]);
164 mn[1] = dtMin(mn[1], v[1]);
165 mn[2] = dtMin(mn[2], v[2]);
171inline void dtVmax(
float* mx,
const float* v)
173 mx[0] = dtMax(mx[0], v[0]);
174 mx[1] = dtMax(mx[1], v[1]);
175 mx[2] = dtMax(mx[2], v[2]);
183inline void dtVset(
float* dest,
const float x,
const float y,
const float z)
185 dest[0] = x; dest[1] = y; dest[2] = z;
191inline void dtVcopy(
float* dest,
const float* a)
201inline float dtVlen(
const float* v)
203 return dtMathSqrtf(v[0] * v[0] + v[1] * v[1] + v[2] * v[2]);
209inline float dtVlenSqr(
const float* v)
211 return v[0]*v[0] + v[1]*v[1] + v[2]*v[2];
218inline float dtVdist(
const float* v1,
const float* v2)
220 const float dx = v2[0] - v1[0];
221 const float dy = v2[1] - v1[1];
222 const float dz = v2[2] - v1[2];
223 return dtMathSqrtf(dx*dx + dy*dy + dz*dz);
230inline float dtVdistSqr(
const float* v1,
const float* v2)
232 const float dx = v2[0] - v1[0];
233 const float dy = v2[1] - v1[1];
234 const float dz = v2[2] - v1[2];
235 return dx*dx + dy*dy + dz*dz;
244inline float dtVdist2D(
const float* v1,
const float* v2)
246 const float dx = v2[0] - v1[0];
247 const float dz = v2[2] - v1[2];
248 return dtMathSqrtf(dx*dx + dz*dz);
255inline float dtVdist2DSqr(
const float* v1,
const float* v2)
257 const float dx = v2[0] - v1[0];
258 const float dz = v2[2] - v1[2];
259 return dx*dx + dz*dz;
264inline void dtVnormalize(
float* v)
266 float d = 1.0f / dtMathSqrtf(dtSqr(v[0]) + dtSqr(v[1]) + dtSqr(v[2]));
279inline bool dtVequal(
const float* p0,
const float* p1)
281 static const float thr = dtSqr(1.0f/16384.0f);
282 const float d = dtVdistSqr(p0, p1);
290inline bool dtVisfinite(
const float* v)
293 dtMathIsfinite(v[0]) &&
294 dtMathIsfinite(v[1]) &&
295 dtMathIsfinite(v[2]);
302inline bool dtVisfinite2D(
const float* v)
304 bool result = dtMathIsfinite(v[0]) && dtMathIsfinite(v[2]);
314inline float dtVdot2D(
const float* u,
const float* v)
316 return u[0]*v[0] + u[2]*v[2];
325inline float dtVperp2D(
const float* u,
const float* v)
327 return u[2]*v[0] - u[0]*v[2];
339inline float dtTriArea2D(
const float* a,
const float* b,
const float* c)
341 const float abx = b[0] - a[0];
342 const float abz = b[2] - a[2];
343 const float acx = c[0] - a[0];
344 const float acz = c[2] - a[2];
345 return acx*abz - abx*acz;
355inline bool dtOverlapQuantBounds(
const unsigned short amin[3],
const unsigned short amax[3],
356 const unsigned short bmin[3],
const unsigned short bmax[3])
359 overlap = (amin[0] > bmax[0] || amax[0] < bmin[0]) ?
false : overlap;
360 overlap = (amin[1] > bmax[1] || amax[1] < bmin[1]) ?
false : overlap;
361 overlap = (amin[2] > bmax[2] || amax[2] < bmin[2]) ?
false : overlap;
372inline bool dtOverlapBounds(
const float* amin,
const float* amax,
373 const float* bmin,
const float* bmax)
376 overlap = (amin[0] > bmax[0] || amax[0] < bmin[0]) ?
false : overlap;
377 overlap = (amin[1] > bmax[1] || amax[1] < bmin[1]) ?
false : overlap;
378 overlap = (amin[2] > bmax[2] || amax[2] < bmin[2]) ?
false : overlap;
388void dtClosestPtPointTriangle(
float* closest,
const float* p,
389 const float* a,
const float* b,
const float* c);
397bool dtClosestHeightPointTriangle(
const float* p,
const float* a,
const float* b,
const float* c,
float& h);
399bool dtIntersectSegmentPoly2D(
const float* p0,
const float* p1,
400 const float* verts,
int nverts,
401 float& tmin,
float& tmax,
402 int& segMin,
int& segMax);
404bool dtIntersectSegSeg2D(
const float* ap,
const float* aq,
405 const float* bp,
const float* bq,
413bool dtPointInPolygon(
const float* pt,
const float* verts,
const int nverts);
415bool dtDistancePtPolyEdgesSqr(
const float* pt,
const float* verts,
const int nverts,
416 float* ed,
float* et);
418float dtDistancePtSegSqr2D(
const float* pt,
const float* p,
const float* q,
float& t);
425void dtCalcPolyCenter(
float* tc,
const unsigned short* idx,
int nidx,
const float* verts);
433bool dtOverlapPolyPoly2D(
const float* polya,
const int npolya,
434 const float* polyb,
const int npolyb);
440inline unsigned int dtNextPow2(
unsigned int v)
452inline unsigned int dtIlog2(
unsigned int v)
456 r = (v > 0xffff) << 4; v >>= r;
457 shift = (v > 0xff) << 3; v >>= shift; r |= shift;
458 shift = (v > 0xf) << 2; v >>= shift; r |= shift;
459 shift = (v > 0x3) << 1; v >>= shift; r |= shift;
464inline int dtAlign4(
int x) {
return (x+3) & ~3; }
466inline int dtOppositeTile(
int side) {
return (side+4) & 0x7; }
468inline void dtSwapByte(
unsigned char* a,
unsigned char* b)
470 unsigned char tmp = *a;
475inline void dtSwapEndian(
unsigned short* v)
477 unsigned char* x = (
unsigned char*)v;
478 dtSwapByte(x+0, x+1);
481inline void dtSwapEndian(
short* v)
483 unsigned char* x = (
unsigned char*)v;
484 dtSwapByte(x+0, x+1);
487inline void dtSwapEndian(
unsigned int* v)
489 unsigned char* x = (
unsigned char*)v;
490 dtSwapByte(x+0, x+3); dtSwapByte(x+1, x+2);
493inline void dtSwapEndian(
int* v)
495 unsigned char* x = (
unsigned char*)v;
496 dtSwapByte(x+0, x+3); dtSwapByte(x+1, x+2);
499inline void dtSwapEndian(
float* v)
501 unsigned char* x = (
unsigned char*)v;
502 dtSwapByte(x+0, x+3); dtSwapByte(x+1, x+2);
505void dtRandomPointInConvexPoly(
const float* pts,
const int npts,
float* areas,
506 const float s,
const float t,
float* out);
508template<
typename TypeToRetrieveAs>
509TypeToRetrieveAs* dtGetThenAdvanceBufferPointer(
const unsigned char*& buffer,
const size_t distanceToAdvance)
511 TypeToRetrieveAs* returnPointer =
reinterpret_cast<TypeToRetrieveAs*
>(buffer);
512 buffer += distanceToAdvance;
513 return returnPointer;
516template<
typename TypeToRetrieveAs>
517TypeToRetrieveAs* dtGetThenAdvanceBufferPointer(
unsigned char*& buffer,
const size_t distanceToAdvance)
519 TypeToRetrieveAs* returnPointer =
reinterpret_cast<TypeToRetrieveAs*
>(buffer);
520 buffer += distanceToAdvance;
521 return returnPointer;