Recast: New API documentation, and standardized tab/space use.

Documented DetourAlloc.h and most members in DetourCommon.h.
Added warning related to issue 180. (Limitation on use of dtNavmeshQuery::findNearestPoly.)
Standardized the use of tab/space indenting in the API documentation.
This commit is contained in:
Stephen Pratt 2011-09-13 13:22:09 +00:00
parent 79a61cbdb1
commit 923098b43c
6 changed files with 762 additions and 497 deletions

View File

@ -19,18 +19,41 @@
#ifndef DETOURALLOCATOR_H #ifndef DETOURALLOCATOR_H
#define DETOURALLOCATOR_H #define DETOURALLOCATOR_H
/// Provides hint values to the memory allocator on how long the
/// memory is expected to be used.
enum dtAllocHint enum dtAllocHint
{ {
DT_ALLOC_PERM, ///< Memory persist after a function call. DT_ALLOC_PERM, ///< Memory persist after a function call.
DT_ALLOC_TEMP ///< Memory used temporarily within a function. DT_ALLOC_TEMP ///< Memory used temporarily within a function.
}; };
/// A memory allocation function.
// @param[in] size The size, in bytes of memory, to allocate.
// @param[in] rcAllocHint A hint to the allocator on how long the memory is expected to be in use.
// @return A pointer to the beginning of the allocated memory block, or null if the allocation failed.
/// @see dtAllocSetCustom
typedef void* (dtAllocFunc)(int size, dtAllocHint hint); typedef void* (dtAllocFunc)(int size, dtAllocHint hint);
/// A memory deallocation function.
/// @param[in] ptr A pointer to a memory block previously allocated using #dtAllocFunc.
/// @see dtAllocSetCustom
typedef void (dtFreeFunc)(void* ptr); typedef void (dtFreeFunc)(void* ptr);
/// Sets the base custom allocation functions to be used by Detour.
/// @param[in] allocFunc The memory allocation function to be used by #dtAlloc
/// @param[in] freeFunc The memory de-allocation function to be used by #dtFree
void dtAllocSetCustom(dtAllocFunc *allocFunc, dtFreeFunc *freeFunc); void dtAllocSetCustom(dtAllocFunc *allocFunc, dtFreeFunc *freeFunc);
/// Allocates a memory block.
/// @param[in] size The size, in bytes of memory, to allocate.
/// @param[in] hint A hint to the allocator on how long the memory is expected to be in use.
/// @return A pointer to the beginning of the allocated memory block, or null if the allocation failed.
/// @see dtFree
void* dtAlloc(int size, dtAllocHint hint); void* dtAlloc(int size, dtAllocHint hint);
/// Deallocates a memory block.
/// @param[in] ptr A pointer to a memory block previously allocated using #dtAlloc.
/// @see dtAlloc
void dtFree(void* ptr); void dtFree(void* ptr);
#endif #endif

View File

@ -20,21 +20,65 @@
#define DETOURCOMMON_H #define DETOURCOMMON_H
/** /**
* @defgroup detour Detour @defgroup detour Detour
* Classes and functions related to path planning.
* @note This is a summary list. Use the index or documentation search Members in this module are used to create, manipulate, and query navigation
* functionality to find minor elements. meshes.
@note This is a summary list of members. Use the index or search
feature to find minor members.
*/ */
/// @name General helper functions
/// @{
/// Swaps the values of the two parameters.
/// @param[in,out] a Value A
/// @param[in,out] b Value B
template<class T> inline void dtSwap(T& a, T& b) { T t = a; a = b; b = t; } template<class T> inline void dtSwap(T& a, T& b) { T t = a; a = b; b = t; }
/// Returns the minimum of two values.
/// @param[in] a Value A
/// @param[in] b Value B
/// @return The minimum of the two values.
template<class T> inline T dtMin(T a, T b) { return a < b ? a : b; } template<class T> inline T dtMin(T a, T b) { return a < b ? a : b; }
/// Returns the maximum of two values.
/// @param[in] a Value A
/// @param[in] b Value B
/// @return The maximum of the two values.
template<class T> inline T dtMax(T a, T b) { return a > b ? a : b; } template<class T> inline T dtMax(T a, T b) { return a > b ? a : b; }
/// Returns the absolute value.
/// @param[in] a The value.
/// @return The absolute value of the specified value.
template<class T> inline T dtAbs(T a) { return a < 0 ? -a : a; } template<class T> inline T dtAbs(T a) { return a < 0 ? -a : a; }
/// Returns the square of the value.
/// @param[in] a The value.
/// @return The square of the value.
template<class T> inline T dtSqr(T a) { return a*a; } template<class T> inline T dtSqr(T a) { return a*a; }
/// Clamps the value to the specified range.
/// @param[in] v The value to clamp.
/// @param[in] mn The minimum permitted return value.
/// @param[in] mx The maximum permitted return value.
/// @return The value, clamped to the specified range.
template<class T> inline T dtClamp(T v, T mn, T mx) { return v < mn ? mn : (v > mx ? mx : v); } template<class T> inline T dtClamp(T v, T mn, T mx) { return v < mn ? mn : (v > mx ? mx : v); }
/// Returns the square root of the value.
/// @param[in] x The value.
/// @return The square root of the vlaue.
float dtSqrt(float x); float dtSqrt(float x);
/// @}
/// @name Vector helper functions.
/// @{
/// Derives the cross product of two vectors. (@p v1 x @p v2)
/// @param[out] dest The cross product. [(x, y, z)]
/// @param[in] v1 A Vector [(x, y, z)]
/// @param[in] v2 A vector [(x, y, z)]
inline void dtVcross(float* dest, const float* v1, const float* v2) inline void dtVcross(float* dest, const float* v1, const float* v2)
{ {
dest[0] = v1[1]*v2[2] - v1[2]*v2[1]; dest[0] = v1[1]*v2[2] - v1[2]*v2[1];
@ -42,11 +86,20 @@ inline void dtVcross(float* dest, const float* v1, const float* v2)
dest[2] = v1[0]*v2[1] - v1[1]*v2[0]; dest[2] = v1[0]*v2[1] - v1[1]*v2[0];
} }
/// Derives the dot product of two vectors. (@p v1 . @p v2)
/// @param[in] v1 A Vector [(x, y, z)]
/// @param[in] v2 A vector [(x, y, z)]
/// @return The dot product.
inline float dtVdot(const float* v1, const float* v2) inline float dtVdot(const float* v1, const float* v2)
{ {
return v1[0]*v2[0] + v1[1]*v2[1] + v1[2]*v2[2]; return v1[0]*v2[0] + v1[1]*v2[1] + v1[2]*v2[2];
} }
/// Performs a scaled vector addition. (@p v1 + (@p v2 * @p s))
/// @param[out] dest The result vector. [(x, y, z)]
/// @param[in] v1 The base vector. [(x, y, z)]
/// @param[in] v2 The vector to scale and add to @p v1. [(x, y, z)]
/// @param[in] s The amount to scale @p v2 by before adding to @p v1.
inline void dtVmad(float* dest, const float* v1, const float* v2, const float s) inline void dtVmad(float* dest, const float* v1, const float* v2, const float s)
{ {
dest[0] = v1[0]+v2[0]*s; dest[0] = v1[0]+v2[0]*s;
@ -54,6 +107,11 @@ inline void dtVmad(float* dest, const float* v1, const float* v2, const float s)
dest[2] = v1[2]+v2[2]*s; dest[2] = v1[2]+v2[2]*s;
} }
/// Performs a linear interpolation between two vectors. (@p v1 toward @p v2)
/// @param[out] dest The result vector. [(x, y, x)]
/// @param[in] v1 The starting vector.
/// @param[in] v2 The destination vector.
/// @param[in] t The interpolation factor. [Limits: 0 <= value <= 1.0]
inline void dtVlerp(float* dest, const float* v1, const float* v2, const float t) inline void dtVlerp(float* dest, const float* v1, const float* v2, const float t)
{ {
dest[0] = v1[0]+(v2[0]-v1[0])*t; dest[0] = v1[0]+(v2[0]-v1[0])*t;
@ -61,6 +119,10 @@ inline void dtVlerp(float* dest, const float* v1, const float* v2, const float t
dest[2] = v1[2]+(v2[2]-v1[2])*t; dest[2] = v1[2]+(v2[2]-v1[2])*t;
} }
/// Performs a vector addition. (@p v1 + @p v2)
/// @param[out] dest The result vector. [(x, y, z)]
/// @param[in] v1 The base vector. [(x, y, z)]
/// @param[in] v2 The vector to add to @p v1. [(x, y, z)]
inline void dtVadd(float* dest, const float* v1, const float* v2) inline void dtVadd(float* dest, const float* v1, const float* v2)
{ {
dest[0] = v1[0]+v2[0]; dest[0] = v1[0]+v2[0];
@ -68,6 +130,10 @@ inline void dtVadd(float* dest, const float* v1, const float* v2)
dest[2] = v1[2]+v2[2]; dest[2] = v1[2]+v2[2];
} }
/// Performs a vector subtraction. (@p v1 - @p v2)
/// @param[out] dest The result vector. [(x, y, z)]
/// @param[in] v1 The base vector. [(x, y, z)]
/// @param[in] v2 The vector to subtract from @p v1. [(x, y, z)]
inline void dtVsub(float* dest, const float* v1, const float* v2) inline void dtVsub(float* dest, const float* v1, const float* v2)
{ {
dest[0] = v1[0]-v2[0]; dest[0] = v1[0]-v2[0];
@ -75,6 +141,10 @@ inline void dtVsub(float* dest, const float* v1, const float* v2)
dest[2] = v1[2]-v2[2]; dest[2] = v1[2]-v2[2];
} }
/// Scales the vector by the specified value. (@p v * @p t)
/// @param[out] dest The result vector. [(x, y, z)]
/// @param[in] v The vector to scale. [(x, y, z)]
/// @param[in] t The scaling factor.
inline void dtVscale(float* dest, const float* v, const float t) inline void dtVscale(float* dest, const float* v, const float t)
{ {
dest[0] = v[0]*t; dest[0] = v[0]*t;
@ -82,6 +152,9 @@ inline void dtVscale(float* dest, const float* v, const float t)
dest[2] = v[2]*t; dest[2] = v[2]*t;
} }
/// Selects the minimum value of each element from the specified vectors.
/// @param[in,out] mn A vector. (Will be updated with the result.) [(x, y, z)]
/// @param[in] v A vector. [(x, y, z)]
inline void dtVmin(float* mn, const float* v) inline void dtVmin(float* mn, const float* v)
{ {
mn[0] = dtMin(mn[0], v[0]); mn[0] = dtMin(mn[0], v[0]);
@ -89,6 +162,9 @@ inline void dtVmin(float* mn, const float* v)
mn[2] = dtMin(mn[2], v[2]); mn[2] = dtMin(mn[2], v[2]);
} }
/// Selects the maximum value of each element from the specified vectors.
/// @param[in,out] mx A vector. (Will be updated with the result.) [(x, y, z)]
/// @param[in] v A vector. [(x, y, z)]
inline void dtVmax(float* mx, const float* v) inline void dtVmax(float* mx, const float* v)
{ {
mx[0] = dtMax(mx[0], v[0]); mx[0] = dtMax(mx[0], v[0]);
@ -96,11 +172,19 @@ inline void dtVmax(float* mx, const float* v)
mx[2] = dtMax(mx[2], v[2]); mx[2] = dtMax(mx[2], v[2]);
} }
/// Sets the vector elements to the specified values.
/// @param[out] dest The result vector. [(x, y, z)]
/// @param[in] x The x-value of the vector.
/// @param[in] y The y-value of the vector.
/// @param[in] z The z-value of the vector.
inline void dtVset(float* dest, const float x, const float y, const float z) inline void dtVset(float* dest, const float x, const float y, const float z)
{ {
dest[0] = x; dest[1] = y; dest[2] = z; dest[0] = x; dest[1] = y; dest[2] = z;
} }
/// Performs a vector copy.
/// @param[out] dest The result. [(x, y, z)]
/// @param[in] a The vector to copy. [(x, y, z)]
inline void dtVcopy(float* dest, const float* a) inline void dtVcopy(float* dest, const float* a)
{ {
dest[0] = a[0]; dest[0] = a[0];
@ -108,16 +192,26 @@ inline void dtVcopy(float* dest, const float* a)
dest[2] = a[2]; dest[2] = a[2];
} }
/// Derives the scalar length of the vector.
/// @param[in] v The vector. [(x, y, z)]
/// @return The scalar length of the vector.
inline float dtVlen(const float* v) inline float dtVlen(const float* v)
{ {
return dtSqrt(v[0]*v[0] + v[1]*v[1] + v[2]*v[2]); return dtSqrt(v[0]*v[0] + v[1]*v[1] + v[2]*v[2]);
} }
/// Derives the square of the scalar length of the vector. (len * len)
/// @param[in] v The vector. [(x, y, z)]
/// @return The square of the scalar length of the vector.
inline float dtVlenSqr(const float* v) inline float dtVlenSqr(const float* v)
{ {
return v[0]*v[0] + v[1]*v[1] + v[2]*v[2]; return v[0]*v[0] + v[1]*v[1] + v[2]*v[2];
} }
/// Returns the distance between two points.
/// @param[in] v1 A point. [(x, y, z)]
/// @param[in] v2 A point. [(x, y, z)]
/// @return The distance between the two points.
inline float dtVdist(const float* v1, const float* v2) inline float dtVdist(const float* v1, const float* v2)
{ {
const float dx = v2[0] - v1[0]; const float dx = v2[0] - v1[0];
@ -126,6 +220,10 @@ inline float dtVdist(const float* v1, const float* v2)
return dtSqrt(dx*dx + dy*dy + dz*dz); return dtSqrt(dx*dx + dy*dy + dz*dz);
} }
/// Returns the square of the distance between two points.
/// @param[in] v1 A point. [(x, y, z)]
/// @param[in] v2 A point. [(x, y, z)]
/// @return The square of the distance between the two points.
inline float dtVdistSqr(const float* v1, const float* v2) inline float dtVdistSqr(const float* v1, const float* v2)
{ {
const float dx = v2[0] - v1[0]; const float dx = v2[0] - v1[0];
@ -134,6 +232,12 @@ inline float dtVdistSqr(const float* v1, const float* v2)
return dx*dx + dy*dy + dz*dz; return dx*dx + dy*dy + dz*dz;
} }
/// Derives the distance between the specified points on the xz-plane.
/// @param[in] v1 A point. [(x, y, z)]
/// @param[in] v2 A point. [(x, y, z)]
/// @return The distance between the point on the xz-plane.
///
/// The vectors are projected onto the xz-plane, so the y-values are ignored.
inline float dtVdist2D(const float* v1, const float* v2) inline float dtVdist2D(const float* v1, const float* v2)
{ {
const float dx = v2[0] - v1[0]; const float dx = v2[0] - v1[0];
@ -141,6 +245,10 @@ inline float dtVdist2D(const float* v1, const float* v2)
return dtSqrt(dx*dx + dz*dz); return dtSqrt(dx*dx + dz*dz);
} }
/// Derives the square of the distance between the specified points on the xz-plane.
/// @param[in] v1 A point. [(x, y, z)]
/// @param[in] v2 A point. [(x, y, z)]
/// @return The square of the distance between the point on the xz-plane.
inline float dtVdist2DSqr(const float* v1, const float* v2) inline float dtVdist2DSqr(const float* v1, const float* v2)
{ {
const float dx = v2[0] - v1[0]; const float dx = v2[0] - v1[0];
@ -148,6 +256,8 @@ inline float dtVdist2DSqr(const float* v1, const float* v2)
return dx*dx + dz*dz; return dx*dx + dz*dz;
} }
/// Normalizes the vector.
/// @param[in,out] v The vector to normalize. [(x, y, z)]
inline void dtVnormalize(float* v) inline void dtVnormalize(float* v)
{ {
float d = 1.0f / dtSqrt(dtSqr(v[0]) + dtSqr(v[1]) + dtSqr(v[2])); float d = 1.0f / dtSqrt(dtSqr(v[0]) + dtSqr(v[1]) + dtSqr(v[2]));
@ -156,6 +266,13 @@ inline void dtVnormalize(float* v)
v[2] *= d; v[2] *= d;
} }
/// Performs a 'sloppy' colocation check of the specified points.
/// @param[in] p0 A point. [(x, y, z)]
/// @param[in] p1 A point. [(x, y, z)]
/// @return True if the points are considered to be at the same location.
///
/// Basically, this function will return true if the specified points are
/// close enough to eachother to be considered colocated.
inline bool dtVequal(const float* p0, const float* p1) inline bool dtVequal(const float* p0, const float* p1)
{ {
static const float thr = dtSqr(1.0f/16384.0f); static const float thr = dtSqr(1.0f/16384.0f);
@ -163,6 +280,134 @@ inline bool dtVequal(const float* p0, const float* p1)
return d < thr; return d < thr;
} }
/// Derives the dot product of two vectors on the xz-plane. (@p u . @p v)
/// @param[in] u A vector [(x, y, z)]
/// @param[in] v A vector [(x, y, z)]
/// @return The dot product on the xz-plane.
///
/// The vectors are projected onto the xz-plane, so the y-values are ignored.
inline float dtVdot2D(const float* u, const float* v)
{
return u[0]*v[0] + u[2]*v[2];
}
/// Derives the xz-plane 2D perp product of the two vectors. (uz*vx - ux*vz)
/// @param[in] u The LHV vector [(x, y, z)]
/// @param[in] v The RHV vector [(x, y, z)]
/// @return The dot product on the xz-plane.
///
/// The vectors are projected onto the xz-plane, so the y-values are ignored.
inline float dtVperp2D(const float* u, const float* v)
{
return u[2]*v[0] - u[0]*v[2];
}
/// @}
/// @name Computational geometry helper functions.
/// @{
/// Derives the signed xz-plane area of the triangle ABC, or the relationship of line AB to point C.
/// @param[in] a Vertex A. [(x, y, z)]
/// @param[in] b Vertex B. [(x, y, z)]
/// @param[in] c Vertex C. [(x, y, z)]
/// @return The signed xz-plane area of the triangle.
inline float dtTriArea2D(const float* a, const float* b, const float* c)
{
const float abx = b[0] - a[0];
const float abz = b[2] - a[2];
const float acx = c[0] - a[0];
const float acz = c[2] - a[2];
return acx*abz - abx*acz;
}
/// Determines if two axis-aligned bounding boxes overlap.
/// @param[in] amin Minimum bounds of box A. [(x, y, z)]
/// @param[in] amax Maximum bounds of box A. [(x, y, z)]
/// @param[in] bmin Minimum bounds of box B. [(x, y, z)]
/// @param[in] bmax Maximum bounds of box B. [(x, y, z)]
/// @return True if the two AABB's overlap.
/// @see dtOverlapBounds
inline bool dtOverlapQuantBounds(const unsigned short amin[3], const unsigned short amax[3],
const unsigned short bmin[3], const unsigned short bmax[3])
{
bool overlap = true;
overlap = (amin[0] > bmax[0] || amax[0] < bmin[0]) ? false : overlap;
overlap = (amin[1] > bmax[1] || amax[1] < bmin[1]) ? false : overlap;
overlap = (amin[2] > bmax[2] || amax[2] < bmin[2]) ? false : overlap;
return overlap;
}
/// Determines if two axis-aligned bounding boxes overlap.
/// @param[in] amin Minimum bounds of box A. [(x, y, z)]
/// @param[in] amax Maximum bounds of box A. [(x, y, z)]
/// @param[in] bmin Minimum bounds of box B. [(x, y, z)]
/// @param[in] bmax Maximum bounds of box B. [(x, y, z)]
/// @return True if the two AABB's overlap.
/// @see dtOverlapQuantBounds
inline bool dtOverlapBounds(const float* amin, const float* amax,
const float* bmin, const float* bmax)
{
bool overlap = true;
overlap = (amin[0] > bmax[0] || amax[0] < bmin[0]) ? false : overlap;
overlap = (amin[1] > bmax[1] || amax[1] < bmin[1]) ? false : overlap;
overlap = (amin[2] > bmax[2] || amax[2] < bmin[2]) ? false : overlap;
return overlap;
}
/// Derives the closest point on a triangle from the specified reference point.
/// @param[out] closest The closest point on the triangle.
/// @param[in] p The reference point from which to test. [(x, y, z)]
/// @param[in] a Vertex A of triangle ABC. [(x, y, z)]
/// @param[in] b Vertex B of triangle ABC. [(x, y, z)]
/// @param[in] c Vertex C of triangle ABC. [(x, y, z)]
void dtClosestPtPointTriangle(float* closest, const float* p,
const float* a, const float* b, const float* c);
/// Derives the y-axis height of the closest point on the triangle from the specified reference point.
/// @param[in] p The reference point from which to test. [(x, y, z)]
/// @param[in] a Vertex A of triangle ABC. [(x, y, z)]
/// @param[in] b Vertex B of triangle ABC. [(x, y, z)]
/// @param[in] c Vertex C of triangle ABC. [(x, y, z)]
/// @param[out] h The resulting height.
bool dtClosestHeightPointTriangle(const float* p, const float* a, const float* b, const float* c, float& h);
bool dtIntersectSegmentPoly2D(const float* p0, const float* p1,
const float* verts, int nverts,
float& tmin, float& tmax,
int& segMin, int& segMax);
/// Determines if the specified point is inside the convex polygon on the xz-plane.
/// @param[in] pt The point to check. [(x, y, z)]
/// @param[in] verts The polygon vertices. [(x, y, z) * @p nverts]
/// @param[in] nverts The number of vertices. [Limit: >= 3]
/// @return True if the point is inside the polygon.
bool dtPointInPolygon(const float* pt, const float* verts, const int nverts);
bool dtDistancePtPolyEdgesSqr(const float* pt, const float* verts, const int nverts,
float* ed, float* et);
float dtDistancePtSegSqr2D(const float* pt, const float* p, const float* q, float& t);
/// Derives the centroid of a convex polygon.
/// @param[out] tc The centroid of the polgyon. [(x, y, z)]
/// @param[in] idx The polygon indices. [(vertIndex) * @p nidx]
/// @param[in] nidx The number of indices in the polygon. [Limit: >= 3]
/// @param[in] verts The polygon vertices. [(x, y, z) * vertCount]
void dtCalcPolyCenter(float* tc, const unsigned short* idx, int nidx, const float* verts);
/// Determines if the two convex polygons overlap on the xz-plane.
/// @param[in] polya Polygon A vertices. [(x, y, z) * @p npolya]
/// @param[in] npolya The number of vertices in polygon A.
/// @param[in] polyb Polygon B vertices. [(x, y, z) * @p npolyb]
/// @param[in] npolyb The number of vertices in polygon B.
/// @return True if the two polygons overlap.
bool dtOverlapPolyPoly2D(const float* polya, const int npolya,
const float* polyb, const int npolyb);
/// @}
/// @name Miscellanious functions.
/// @{
inline unsigned int dtNextPow2(unsigned int v) inline unsigned int dtNextPow2(unsigned int v)
{ {
v--; v--;
@ -191,65 +436,51 @@ inline int dtAlign4(int x) { return (x+3) & ~3; }
inline int dtOppositeTile(int side) { return (side+4) & 0x7; } inline int dtOppositeTile(int side) { return (side+4) & 0x7; }
inline float dtVdot2D(const float* u, const float* v) /// @}
{
return u[0]*v[0] + u[2]*v[2];
}
inline float dtVperp2D(const float* u, const float* v)
{
return u[2]*v[0] - u[0]*v[2];
}
inline float dtTriArea2D(const float* a, const float* b, const float* c)
{
const float abx = b[0] - a[0];
const float abz = b[2] - a[2];
const float acx = c[0] - a[0];
const float acz = c[2] - a[2];
return acx*abz - abx*acz;
}
inline bool dtOverlapQuantBounds(const unsigned short amin[3], const unsigned short amax[3],
const unsigned short bmin[3], const unsigned short bmax[3])
{
bool overlap = true;
overlap = (amin[0] > bmax[0] || amax[0] < bmin[0]) ? false : overlap;
overlap = (amin[1] > bmax[1] || amax[1] < bmin[1]) ? false : overlap;
overlap = (amin[2] > bmax[2] || amax[2] < bmin[2]) ? false : overlap;
return overlap;
}
inline bool dtOverlapBounds(const float* amin, const float* amax,
const float* bmin, const float* bmax)
{
bool overlap = true;
overlap = (amin[0] > bmax[0] || amax[0] < bmin[0]) ? false : overlap;
overlap = (amin[1] > bmax[1] || amax[1] < bmin[1]) ? false : overlap;
overlap = (amin[2] > bmax[2] || amax[2] < bmin[2]) ? false : overlap;
return overlap;
}
void dtClosestPtPointTriangle(float* closest, const float* p,
const float* a, const float* b, const float* c);
bool dtClosestHeightPointTriangle(const float* p, const float* a, const float* b, const float* c, float& h);
bool dtIntersectSegmentPoly2D(const float* p0, const float* p1,
const float* verts, int nverts,
float& tmin, float& tmax,
int& segMin, int& segMax);
bool dtPointInPolygon(const float* pt, const float* verts, const int nverts);
bool dtDistancePtPolyEdgesSqr(const float* pt, const float* verts, const int nverts,
float* ed, float* et);
float dtDistancePtSegSqr2D(const float* pt, const float* p, const float* q, float& t);
void dtCalcPolyCenter(float* tc, const unsigned short* idx, int nidx, const float* verts);
bool dtOverlapPolyPoly2D(const float* polya, const int npolya,
const float* polyb, const int npolyb);
#endif // DETOURCOMMON_H #endif // DETOURCOMMON_H
///////////////////////////////////////////////////////////////////////////
// This section contains detailed documentation for members that don't have
// a source file. It reduces clutter in the main section of the header.
/**
@fn float dtTriArea2D(const float* a, const float* b, const float* c)
@par
The vertices are projected onto the xz-plane, so the y-values are ignored.
This is a low cost function than can be used for various purposes. Its main purpose
is for point/line relationship testing.
In all cases: A value of zero indicates that all vertices are collinear or represent the same point.
(On the xz-plane.)
When used for point/line relationship tests, AB usually represents a line against which
the C point is to be tested. In this case:
A positive value indicates that point C is to the left of line AB, looking from A toward B.<br/>
A negative value indicates that point C is to the right of lineAB, looking from A toward B.
When used for evaluating a triangle:
The absolute value of the return value is two times the area of the triangle when it is
projected onto the xz-plane.
A positive return value indicates:
<ul>
<li>The vertices are wrapped in the normal Detour wrap direction.</li>
<li>The triangle's 3D face normal is in the general up direction.</li>
</ul>
A negative return value indicates:
<ul>
<li>The vertices are reverse wrapped. (Wrapped opposite the normal Detour wrap direction.)</li>
<li>The triangle's 3D face normal is in the general down direction.</li>
</ul>
*/

View File

@ -22,9 +22,8 @@
#include "DetourAlloc.h" #include "DetourAlloc.h"
#include "DetourStatus.h" #include "DetourStatus.h"
// Note: If you want to use 64-bit refs, change the types of both dtPolyRef & dtTileRef. // Note: If you want to use 64-bit refs, change the types of both dtPolyRef & dtTileRef.
// It is also recommended to change dtHashRef() to proper 64-bit hash too. // It is also recommended that you change dtHashRef() to a proper 64-bit hash.
/// A handle to a polygon within a navigation mesh tile. /// A handle to a polygon within a navigation mesh tile.
/// @ingroup detour /// @ingroup detour
@ -589,92 +588,95 @@ void dtFreeNavMesh(dtNavMesh* navmesh);
/////////////////////////////////////////////////////////////////////////// ///////////////////////////////////////////////////////////////////////////
// This section contains detailed documentation for types that don't have // This section contains detailed documentation for members that don't have
// a source file. It reduces clutter in the main section of the header. // a source file. It reduces clutter in the main section of the header.
/// @typedef dtPolyRef /**
/// @par
///
/// Polygon references are subject to the same invalidate/preserve/restore
/// rules that apply to #dtTileRef's. If the #dtTileRef for the polygon's
/// tile changes, the polygon reference becomes invalid.
///
/// Changing a polygon's flags, area id, etc. does not impact its polygon
/// reference.
/// @typedef dtTileRef @typedef dtPolyRef
/// @par @par
///
/// The following changes will invalidate a tile reference:
///
/// - The referenced tile has been removed from the navigation mesh.
/// - The navigation mesh has been initialized using a different set
/// of #dtNavMeshParams.
///
/// A tile reference is preserved/restored if the tile is added to a navigation
/// mesh initialized with the original #dtNavMeshParams and is added at the
/// original reference location. (E.g. The lastRef parameter is used with
/// dtNavMesh::addTile.)
///
/// Basically, if the storage structure of a tile changes, its associated
/// tile reference changes.
///
/// @var unsigned short dtPoly::neis[DT_VERTS_PER_POLYGON] Polygon references are subject to the same invalidate/preserve/restore
/// @par rules that apply to #dtTileRef's. If the #dtTileRef for the polygon's
/// tile changes, the polygon reference becomes invalid.
/// Each entry represents data for the edge starting at the vertex of the same index.
/// E.g. The entry at index n represents the edge data for vertex[n] to vertex[n+1].
///
/// A value of zero indicates the edge has no polygon connection. (It makes up the
/// border of the navigation mesh.)
///
/// The information can be extracted as follows:
/// @code
/// neighborRef = neis[n] & 0xff; // Get the neighbor polygon reference.
///
/// if (neis[n] & #DT_EX_LINK)
/// {
/// // The edge is an external (portal) edge.
/// }
/// @endcode
/// @var float dtMeshHeader::bvQuantFactor Changing a polygon's flags, area id, etc. does not impact its polygon
/// @par reference.
///
/// This value is used for converting between world and bounding volume coordinates.
/// For example:
/// @code
/// const float cs = 1.0f / tile->header->bvQuantFactor;
/// const dtBVNode* n = &tile->bvTree[i];
/// if (n->i >= 0)
/// {
/// // This is a leaf node.
/// float worldMinX = tile->header->bmin[0] + n->bmin[0]*cs;
/// float worldMinY = tile->header->bmin[0] + n->bmin[1]*cs;
/// // Etc...
/// }
/// @endcode
/// @struct dtMeshTile @typedef dtTileRef
/// @par @par
///
/// Tiles generally only exist within the context of a dtNavMesh object.
///
/// Some tile content is optional. For example, a tile may not contain any
/// off-mesh connections. In this case the associated pointer will be null.
///
/// If a detail mesh exists it will share vertices with the base polygon mesh.
/// Only the vertices unique to the detail mesh will be stored in #detailVerts.
///
/// @warning Tiles returned by a dtNavMesh object are not guarenteed to be populated.
/// For example: The tile at a location might not have been loaded yet, or may have been removed.
/// In this case, pointers will be null. So if in doubt, check the polygon count in the
/// tile's header to determine if a tile has polygons defined.
/// @var float dtOffMeshConnection::pos[6] The following changes will invalidate a tile reference:
/// @par
/// - The referenced tile has been removed from the navigation mesh.
/// For a properly built navigation mesh, vertex A will always be within the bounds of the mesh. - The navigation mesh has been initialized using a different set
/// Vertex B is not required to be within the bounds of the mesh. of #dtNavMeshParams.
///
A tile reference is preserved/restored if the tile is added to a navigation
mesh initialized with the original #dtNavMeshParams and is added at the
original reference location. (E.g. The lastRef parameter is used with
dtNavMesh::addTile.)
Basically, if the storage structure of a tile changes, its associated
tile reference changes.
@var unsigned short dtPoly::neis[DT_VERTS_PER_POLYGON]
@par
Each entry represents data for the edge starting at the vertex of the same index.
E.g. The entry at index n represents the edge data for vertex[n] to vertex[n+1].
A value of zero indicates the edge has no polygon connection. (It makes up the
border of the navigation mesh.)
The information can be extracted as follows:
@code
neighborRef = neis[n] & 0xff; // Get the neighbor polygon reference.
if (neis[n] & #DT_EX_LINK)
{
// The edge is an external (portal) edge.
}
@endcode
@var float dtMeshHeader::bvQuantFactor
@par
This value is used for converting between world and bounding volume coordinates.
For example:
@code
const float cs = 1.0f / tile->header->bvQuantFactor;
const dtBVNode* n = &tile->bvTree[i];
if (n->i >= 0)
{
// This is a leaf node.
float worldMinX = tile->header->bmin[0] + n->bmin[0]*cs;
float worldMinY = tile->header->bmin[0] + n->bmin[1]*cs;
// Etc...
}
@endcode
@struct dtMeshTile
@par
Tiles generally only exist within the context of a dtNavMesh object.
Some tile content is optional. For example, a tile may not contain any
off-mesh connections. In this case the associated pointer will be null.
If a detail mesh exists it will share vertices with the base polygon mesh.
Only the vertices unique to the detail mesh will be stored in #detailVerts.
@warning Tiles returned by a dtNavMesh object are not guarenteed to be populated.
For example: The tile at a location might not have been loaded yet, or may have been removed.
In this case, pointers will be null. So if in doubt, check the polygon count in the
tile's header to determine if a tile has polygons defined.
@var float dtOffMeshConnection::pos[6]
@par
For a properly built navigation mesh, vertex A will always be within the bounds of the mesh.
Vertex B is not required to be within the bounds of the mesh.
*/

View File

@ -238,6 +238,9 @@ bool dtClosestHeightPointTriangle(const float* p, const float* a, const float* b
return false; return false;
} }
/// @par
///
/// All points are projected onto the xz-plane, so the y-values are ignored.
bool dtPointInPolygon(const float* pt, const float* verts, const int nverts) bool dtPointInPolygon(const float* pt, const float* verts, const int nverts)
{ {
// TODO: Replace pnpoly with triArea2D tests? // TODO: Replace pnpoly with triArea2D tests?
@ -291,6 +294,9 @@ inline bool overlapRange(const float amin, const float amax,
return ((amin+eps) > bmax || (amax-eps) < bmin) ? false : true; return ((amin+eps) > bmax || (amax-eps) < bmin) ? false : true;
} }
/// @par
///
/// All vertices are projected onto the xz-plane, so the y-values are ignored.
bool dtOverlapPolyPoly2D(const float* polya, const int npolya, bool dtOverlapPolyPoly2D(const float* polya, const int npolya,
const float* polyb, const int npolyb) const float* polyb, const int npolyb)
{ {

View File

@ -439,6 +439,9 @@ dtStatus dtNavMeshQuery::getPolyHeight(dtPolyRef ref, const float* pos, float* h
/// return #DT_SUCCESS, but @p nearestRef will be zero. So if in doubt, check /// return #DT_SUCCESS, but @p nearestRef will be zero. So if in doubt, check
/// @p nearestRef before using @p nearestPt. /// @p nearestRef before using @p nearestPt.
/// ///
/// @warning This function is not suitable for large area searches. If the search
/// extents overlaps more than 128 polygons it may return an invalid result.
///
dtStatus dtNavMeshQuery::findNearestPoly(const float* center, const float* extents, dtStatus dtNavMeshQuery::findNearestPoly(const float* center, const float* extents,
const dtQueryFilter* filter, const dtQueryFilter* filter,
dtPolyRef* nearestRef, float* nearestPt) const dtPolyRef* nearestRef, float* nearestPt) const