add missing files
only report fail if there are actual failures
This commit is contained in:
@@ -5,7 +5,6 @@
|
||||
#include "parallel_primitives/host/btQuickprof.h"
|
||||
#include "../basic_initialize/btOpenCLUtils.h"
|
||||
|
||||
#include "../kernels/integrateKernel.h"
|
||||
|
||||
#include "../kernels/sapKernels.h"
|
||||
#include "../kernels/sapFastKernels.h"
|
||||
|
||||
@@ -81,8 +81,9 @@ inline void broadphaseTest()
|
||||
int usrPtr = 1;
|
||||
sap->createProxy(aabbMin,aabbMax,usrPtr,group,mask);
|
||||
|
||||
// aabbMin.setValue(2,2,2);
|
||||
// aabbMax.setValue(3,3,3);
|
||||
aabbMin.setValue(1,1,1);
|
||||
aabbMax.setValue(2,2,2);
|
||||
|
||||
usrPtr = 2;
|
||||
sap->createProxy(aabbMin,aabbMax,usrPtr,group,mask);
|
||||
sap->writeAabbsToGpu();
|
||||
@@ -113,8 +114,13 @@ int main(int argc, char** argv)
|
||||
|
||||
broadphaseTest();
|
||||
|
||||
printf("%d tests passed, %d tests failed\n",g_nPassed, g_nFailed);
|
||||
printf("%d tests passed\n",g_nPassed, g_nFailed);
|
||||
if (g_nFailed)
|
||||
{
|
||||
printf("%d tests failed\n",g_nFailed);
|
||||
}
|
||||
printf("End, press <enter>\n");
|
||||
|
||||
getchar();
|
||||
|
||||
exitCL();
|
||||
|
||||
232
opencl/parallel_primitives/host/btAabbUtil2.h
Normal file
232
opencl/parallel_primitives/host/btAabbUtil2.h
Normal file
@@ -0,0 +1,232 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#ifndef BT_AABB_UTIL2
|
||||
#define BT_AABB_UTIL2
|
||||
|
||||
#include "btTransform.h"
|
||||
#include "btVector3.h"
|
||||
#include "btMinMax.h"
|
||||
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE void AabbExpand (btVector3& aabbMin,
|
||||
btVector3& aabbMax,
|
||||
const btVector3& expansionMin,
|
||||
const btVector3& expansionMax)
|
||||
{
|
||||
aabbMin = aabbMin + expansionMin;
|
||||
aabbMax = aabbMax + expansionMax;
|
||||
}
|
||||
|
||||
/// conservative test for overlap between two aabbs
|
||||
SIMD_FORCE_INLINE bool TestPointAgainstAabb2(const btVector3 &aabbMin1, const btVector3 &aabbMax1,
|
||||
const btVector3 &point)
|
||||
{
|
||||
bool overlap = true;
|
||||
overlap = (aabbMin1.getX() > point.getX() || aabbMax1.getX() < point.getX()) ? false : overlap;
|
||||
overlap = (aabbMin1.getZ() > point.getZ() || aabbMax1.getZ() < point.getZ()) ? false : overlap;
|
||||
overlap = (aabbMin1.getY() > point.getY() || aabbMax1.getY() < point.getY()) ? false : overlap;
|
||||
return overlap;
|
||||
}
|
||||
|
||||
|
||||
/// conservative test for overlap between two aabbs
|
||||
SIMD_FORCE_INLINE bool TestAabbAgainstAabb2(const btVector3 &aabbMin1, const btVector3 &aabbMax1,
|
||||
const btVector3 &aabbMin2, const btVector3 &aabbMax2)
|
||||
{
|
||||
bool overlap = true;
|
||||
overlap = (aabbMin1.getX() > aabbMax2.getX() || aabbMax1.getX() < aabbMin2.getX()) ? false : overlap;
|
||||
overlap = (aabbMin1.getZ() > aabbMax2.getZ() || aabbMax1.getZ() < aabbMin2.getZ()) ? false : overlap;
|
||||
overlap = (aabbMin1.getY() > aabbMax2.getY() || aabbMax1.getY() < aabbMin2.getY()) ? false : overlap;
|
||||
return overlap;
|
||||
}
|
||||
|
||||
/// conservative test for overlap between triangle and aabb
|
||||
SIMD_FORCE_INLINE bool TestTriangleAgainstAabb2(const btVector3 *vertices,
|
||||
const btVector3 &aabbMin, const btVector3 &aabbMax)
|
||||
{
|
||||
const btVector3 &p1 = vertices[0];
|
||||
const btVector3 &p2 = vertices[1];
|
||||
const btVector3 &p3 = vertices[2];
|
||||
|
||||
if (btMin(btMin(p1[0], p2[0]), p3[0]) > aabbMax[0]) return false;
|
||||
if (btMax(btMax(p1[0], p2[0]), p3[0]) < aabbMin[0]) return false;
|
||||
|
||||
if (btMin(btMin(p1[2], p2[2]), p3[2]) > aabbMax[2]) return false;
|
||||
if (btMax(btMax(p1[2], p2[2]), p3[2]) < aabbMin[2]) return false;
|
||||
|
||||
if (btMin(btMin(p1[1], p2[1]), p3[1]) > aabbMax[1]) return false;
|
||||
if (btMax(btMax(p1[1], p2[1]), p3[1]) < aabbMin[1]) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE int btOutcode(const btVector3& p,const btVector3& halfExtent)
|
||||
{
|
||||
return (p.getX() < -halfExtent.getX() ? 0x01 : 0x0) |
|
||||
(p.getX() > halfExtent.getX() ? 0x08 : 0x0) |
|
||||
(p.getY() < -halfExtent.getY() ? 0x02 : 0x0) |
|
||||
(p.getY() > halfExtent.getY() ? 0x10 : 0x0) |
|
||||
(p.getZ() < -halfExtent.getZ() ? 0x4 : 0x0) |
|
||||
(p.getZ() > halfExtent.getZ() ? 0x20 : 0x0);
|
||||
}
|
||||
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE bool btRayAabb2(const btVector3& rayFrom,
|
||||
const btVector3& rayInvDirection,
|
||||
const unsigned int raySign[3],
|
||||
const btVector3 bounds[2],
|
||||
btScalar& tmin,
|
||||
btScalar lambda_min,
|
||||
btScalar lambda_max)
|
||||
{
|
||||
btScalar tmax, tymin, tymax, tzmin, tzmax;
|
||||
tmin = (bounds[raySign[0]].getX() - rayFrom.getX()) * rayInvDirection.getX();
|
||||
tmax = (bounds[1-raySign[0]].getX() - rayFrom.getX()) * rayInvDirection.getX();
|
||||
tymin = (bounds[raySign[1]].getY() - rayFrom.getY()) * rayInvDirection.getY();
|
||||
tymax = (bounds[1-raySign[1]].getY() - rayFrom.getY()) * rayInvDirection.getY();
|
||||
|
||||
if ( (tmin > tymax) || (tymin > tmax) )
|
||||
return false;
|
||||
|
||||
if (tymin > tmin)
|
||||
tmin = tymin;
|
||||
|
||||
if (tymax < tmax)
|
||||
tmax = tymax;
|
||||
|
||||
tzmin = (bounds[raySign[2]].getZ() - rayFrom.getZ()) * rayInvDirection.getZ();
|
||||
tzmax = (bounds[1-raySign[2]].getZ() - rayFrom.getZ()) * rayInvDirection.getZ();
|
||||
|
||||
if ( (tmin > tzmax) || (tzmin > tmax) )
|
||||
return false;
|
||||
if (tzmin > tmin)
|
||||
tmin = tzmin;
|
||||
if (tzmax < tmax)
|
||||
tmax = tzmax;
|
||||
return ( (tmin < lambda_max) && (tmax > lambda_min) );
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE bool btRayAabb(const btVector3& rayFrom,
|
||||
const btVector3& rayTo,
|
||||
const btVector3& aabbMin,
|
||||
const btVector3& aabbMax,
|
||||
btScalar& param, btVector3& normal)
|
||||
{
|
||||
btVector3 aabbHalfExtent = (aabbMax-aabbMin)* btScalar(0.5);
|
||||
btVector3 aabbCenter = (aabbMax+aabbMin)* btScalar(0.5);
|
||||
btVector3 source = rayFrom - aabbCenter;
|
||||
btVector3 target = rayTo - aabbCenter;
|
||||
int sourceOutcode = btOutcode(source,aabbHalfExtent);
|
||||
int targetOutcode = btOutcode(target,aabbHalfExtent);
|
||||
if ((sourceOutcode & targetOutcode) == 0x0)
|
||||
{
|
||||
btScalar lambda_enter = btScalar(0.0);
|
||||
btScalar lambda_exit = param;
|
||||
btVector3 r = target - source;
|
||||
int i;
|
||||
btScalar normSign = 1;
|
||||
btVector3 hitNormal(0,0,0);
|
||||
int bit=1;
|
||||
|
||||
for (int j=0;j<2;j++)
|
||||
{
|
||||
for (i = 0; i != 3; ++i)
|
||||
{
|
||||
if (sourceOutcode & bit)
|
||||
{
|
||||
btScalar lambda = (-source[i] - aabbHalfExtent[i]*normSign) / r[i];
|
||||
if (lambda_enter <= lambda)
|
||||
{
|
||||
lambda_enter = lambda;
|
||||
hitNormal.setValue(0,0,0);
|
||||
hitNormal[i] = normSign;
|
||||
}
|
||||
}
|
||||
else if (targetOutcode & bit)
|
||||
{
|
||||
btScalar lambda = (-source[i] - aabbHalfExtent[i]*normSign) / r[i];
|
||||
btSetMin(lambda_exit, lambda);
|
||||
}
|
||||
bit<<=1;
|
||||
}
|
||||
normSign = btScalar(-1.);
|
||||
}
|
||||
if (lambda_enter <= lambda_exit)
|
||||
{
|
||||
param = lambda_enter;
|
||||
normal = hitNormal;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE void btTransformAabb(const btVector3& halfExtents, btScalar margin,const btTransform& t,btVector3& aabbMinOut,btVector3& aabbMaxOut)
|
||||
{
|
||||
btVector3 halfExtentsWithMargin = halfExtents+btVector3(margin,margin,margin);
|
||||
btMatrix3x3 abs_b = t.getBasis().absolute();
|
||||
btVector3 center = t.getOrigin();
|
||||
btVector3 extent = halfExtentsWithMargin.dot3( abs_b[0], abs_b[1], abs_b[2] );
|
||||
aabbMinOut = center - extent;
|
||||
aabbMaxOut = center + extent;
|
||||
}
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE void btTransformAabb(const btVector3& localAabbMin,const btVector3& localAabbMax, btScalar margin,const btTransform& trans,btVector3& aabbMinOut,btVector3& aabbMaxOut)
|
||||
{
|
||||
btAssert(localAabbMin.getX() <= localAabbMax.getX());
|
||||
btAssert(localAabbMin.getY() <= localAabbMax.getY());
|
||||
btAssert(localAabbMin.getZ() <= localAabbMax.getZ());
|
||||
btVector3 localHalfExtents = btScalar(0.5)*(localAabbMax-localAabbMin);
|
||||
localHalfExtents+=btVector3(margin,margin,margin);
|
||||
|
||||
btVector3 localCenter = btScalar(0.5)*(localAabbMax+localAabbMin);
|
||||
btMatrix3x3 abs_b = trans.getBasis().absolute();
|
||||
btVector3 center = trans(localCenter);
|
||||
btVector3 extent = localHalfExtents.dot3( abs_b[0], abs_b[1], abs_b[2] );
|
||||
aabbMinOut = center-extent;
|
||||
aabbMaxOut = center+extent;
|
||||
}
|
||||
|
||||
#define USE_BANCHLESS 1
|
||||
#ifdef USE_BANCHLESS
|
||||
//This block replaces the block below and uses no branches, and replaces the 8 bit return with a 32 bit return for improved performance (~3x on XBox 360)
|
||||
SIMD_FORCE_INLINE unsigned testQuantizedAabbAgainstQuantizedAabb(const unsigned short int* aabbMin1,const unsigned short int* aabbMax1,const unsigned short int* aabbMin2,const unsigned short int* aabbMax2)
|
||||
{
|
||||
return static_cast<unsigned int>(btSelect((unsigned)((aabbMin1[0] <= aabbMax2[0]) & (aabbMax1[0] >= aabbMin2[0])
|
||||
& (aabbMin1[2] <= aabbMax2[2]) & (aabbMax1[2] >= aabbMin2[2])
|
||||
& (aabbMin1[1] <= aabbMax2[1]) & (aabbMax1[1] >= aabbMin2[1])),
|
||||
1, 0));
|
||||
}
|
||||
#else
|
||||
SIMD_FORCE_INLINE bool testQuantizedAabbAgainstQuantizedAabb(const unsigned short int* aabbMin1,const unsigned short int* aabbMax1,const unsigned short int* aabbMin2,const unsigned short int* aabbMax2)
|
||||
{
|
||||
bool overlap = true;
|
||||
overlap = (aabbMin1[0] > aabbMax2[0] || aabbMax1[0] < aabbMin2[0]) ? false : overlap;
|
||||
overlap = (aabbMin1[2] > aabbMax2[2] || aabbMax1[2] < aabbMin2[2]) ? false : overlap;
|
||||
overlap = (aabbMin1[1] > aabbMax2[1] || aabbMax1[1] < aabbMin2[1]) ? false : overlap;
|
||||
return overlap;
|
||||
}
|
||||
#endif //USE_BANCHLESS
|
||||
|
||||
#endif //BT_AABB_UTIL2
|
||||
|
||||
|
||||
1167
opencl/parallel_primitives/host/btConvexHull.cpp
Normal file
1167
opencl/parallel_primitives/host/btConvexHull.cpp
Normal file
File diff suppressed because it is too large
Load Diff
241
opencl/parallel_primitives/host/btConvexHull.h
Normal file
241
opencl/parallel_primitives/host/btConvexHull.h
Normal file
@@ -0,0 +1,241 @@
|
||||
|
||||
/*
|
||||
Stan Melax Convex Hull Computation
|
||||
Copyright (c) 2008 Stan Melax http://www.melax.com/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
///includes modifications/improvements by John Ratcliff, see BringOutYourDead below.
|
||||
|
||||
#ifndef BT_CD_HULL_H
|
||||
#define BT_CD_HULL_H
|
||||
|
||||
#include "btVector3.h"
|
||||
#include "btAlignedObjectArray.h"
|
||||
|
||||
typedef btAlignedObjectArray<unsigned int> TUIntArray;
|
||||
|
||||
class HullResult
|
||||
{
|
||||
public:
|
||||
HullResult(void)
|
||||
{
|
||||
mPolygons = true;
|
||||
mNumOutputVertices = 0;
|
||||
mNumFaces = 0;
|
||||
mNumIndices = 0;
|
||||
}
|
||||
bool mPolygons; // true if indices represents polygons, false indices are triangles
|
||||
unsigned int mNumOutputVertices; // number of vertices in the output hull
|
||||
btAlignedObjectArray<btVector3> m_OutputVertices; // array of vertices
|
||||
unsigned int mNumFaces; // the number of faces produced
|
||||
unsigned int mNumIndices; // the total number of indices
|
||||
btAlignedObjectArray<unsigned int> m_Indices; // pointer to indices.
|
||||
|
||||
// If triangles, then indices are array indexes into the vertex list.
|
||||
// If polygons, indices are in the form (number of points in face) (p1, p2, p3, ..) etc..
|
||||
};
|
||||
|
||||
enum HullFlag
|
||||
{
|
||||
QF_TRIANGLES = (1<<0), // report results as triangles, not polygons.
|
||||
QF_REVERSE_ORDER = (1<<1), // reverse order of the triangle indices.
|
||||
QF_DEFAULT = QF_TRIANGLES
|
||||
};
|
||||
|
||||
|
||||
class HullDesc
|
||||
{
|
||||
public:
|
||||
HullDesc(void)
|
||||
{
|
||||
mFlags = QF_DEFAULT;
|
||||
mVcount = 0;
|
||||
mVertices = 0;
|
||||
mVertexStride = sizeof(btVector3);
|
||||
mNormalEpsilon = 0.001f;
|
||||
mMaxVertices = 4096; // maximum number of points to be considered for a convex hull.
|
||||
mMaxFaces = 4096;
|
||||
};
|
||||
|
||||
HullDesc(HullFlag flag,
|
||||
unsigned int vcount,
|
||||
const btVector3 *vertices,
|
||||
unsigned int stride = sizeof(btVector3))
|
||||
{
|
||||
mFlags = flag;
|
||||
mVcount = vcount;
|
||||
mVertices = vertices;
|
||||
mVertexStride = stride;
|
||||
mNormalEpsilon = btScalar(0.001);
|
||||
mMaxVertices = 4096;
|
||||
}
|
||||
|
||||
bool HasHullFlag(HullFlag flag) const
|
||||
{
|
||||
if ( mFlags & flag ) return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
void SetHullFlag(HullFlag flag)
|
||||
{
|
||||
mFlags|=flag;
|
||||
}
|
||||
|
||||
void ClearHullFlag(HullFlag flag)
|
||||
{
|
||||
mFlags&=~flag;
|
||||
}
|
||||
|
||||
unsigned int mFlags; // flags to use when generating the convex hull.
|
||||
unsigned int mVcount; // number of vertices in the input point cloud
|
||||
const btVector3 *mVertices; // the array of vertices.
|
||||
unsigned int mVertexStride; // the stride of each vertex, in bytes.
|
||||
btScalar mNormalEpsilon; // the epsilon for removing duplicates. This is a normalized value, if normalized bit is on.
|
||||
unsigned int mMaxVertices; // maximum number of vertices to be considered for the hull!
|
||||
unsigned int mMaxFaces;
|
||||
};
|
||||
|
||||
enum HullError
|
||||
{
|
||||
QE_OK, // success!
|
||||
QE_FAIL // failed.
|
||||
};
|
||||
|
||||
class btPlane
|
||||
{
|
||||
public:
|
||||
btVector3 normal;
|
||||
btScalar dist; // distance below origin - the D from plane equasion Ax+By+Cz+D=0
|
||||
btPlane(const btVector3 &n,btScalar d):normal(n),dist(d){}
|
||||
btPlane():normal(),dist(0){}
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
class ConvexH
|
||||
{
|
||||
public:
|
||||
class HalfEdge
|
||||
{
|
||||
public:
|
||||
short ea; // the other half of the edge (index into edges list)
|
||||
unsigned char v; // the vertex at the start of this edge (index into vertices list)
|
||||
unsigned char p; // the facet on which this edge lies (index into facets list)
|
||||
HalfEdge(){}
|
||||
HalfEdge(short _ea,unsigned char _v, unsigned char _p):ea(_ea),v(_v),p(_p){}
|
||||
};
|
||||
ConvexH()
|
||||
{
|
||||
}
|
||||
~ConvexH()
|
||||
{
|
||||
}
|
||||
btAlignedObjectArray<btVector3> vertices;
|
||||
btAlignedObjectArray<HalfEdge> edges;
|
||||
btAlignedObjectArray<btPlane> facets;
|
||||
ConvexH(int vertices_size,int edges_size,int facets_size);
|
||||
};
|
||||
|
||||
|
||||
class int4
|
||||
{
|
||||
public:
|
||||
int x,y,z,w;
|
||||
int4(){};
|
||||
int4(int _x,int _y, int _z,int _w){x=_x;y=_y;z=_z;w=_w;}
|
||||
const int& operator[](int i) const {return (&x)[i];}
|
||||
int& operator[](int i) {return (&x)[i];}
|
||||
};
|
||||
|
||||
class PHullResult
|
||||
{
|
||||
public:
|
||||
|
||||
PHullResult(void)
|
||||
{
|
||||
mVcount = 0;
|
||||
mIndexCount = 0;
|
||||
mFaceCount = 0;
|
||||
mVertices = 0;
|
||||
}
|
||||
|
||||
unsigned int mVcount;
|
||||
unsigned int mIndexCount;
|
||||
unsigned int mFaceCount;
|
||||
btVector3* mVertices;
|
||||
TUIntArray m_Indices;
|
||||
};
|
||||
|
||||
|
||||
|
||||
///The HullLibrary class can create a convex hull from a collection of vertices, using the ComputeHull method.
|
||||
///The btShapeHull class uses this HullLibrary to create a approximate convex mesh given a general (non-polyhedral) convex shape.
|
||||
class HullLibrary
|
||||
{
|
||||
|
||||
btAlignedObjectArray<class btHullTriangle*> m_tris;
|
||||
|
||||
public:
|
||||
|
||||
btAlignedObjectArray<int> m_vertexIndexMapping;
|
||||
|
||||
|
||||
HullError CreateConvexHull(const HullDesc& desc, // describes the input request
|
||||
HullResult& result); // contains the resulst
|
||||
HullError ReleaseResult(HullResult &result); // release memory allocated for this result, we are done with it.
|
||||
|
||||
private:
|
||||
|
||||
bool ComputeHull(unsigned int vcount,const btVector3 *vertices,PHullResult &result,unsigned int vlimit);
|
||||
|
||||
class btHullTriangle* allocateTriangle(int a,int b,int c);
|
||||
void deAllocateTriangle(btHullTriangle*);
|
||||
void b2bfix(btHullTriangle* s,btHullTriangle*t);
|
||||
|
||||
void removeb2b(btHullTriangle* s,btHullTriangle*t);
|
||||
|
||||
void checkit(btHullTriangle *t);
|
||||
|
||||
btHullTriangle* extrudable(btScalar epsilon);
|
||||
|
||||
int calchull(btVector3 *verts,int verts_count, TUIntArray& tris_out, int &tris_count,int vlimit);
|
||||
|
||||
int calchullgen(btVector3 *verts,int verts_count, int vlimit);
|
||||
|
||||
int4 FindSimplex(btVector3 *verts,int verts_count,btAlignedObjectArray<int> &allow);
|
||||
|
||||
class ConvexH* ConvexHCrop(ConvexH& convex,const btPlane& slice);
|
||||
|
||||
void extrude(class btHullTriangle* t0,int v);
|
||||
|
||||
ConvexH* test_cube();
|
||||
|
||||
//BringOutYourDead (John Ratcliff): When you create a convex hull you hand it a large input set of vertices forming a 'point cloud'.
|
||||
//After the hull is generated it give you back a set of polygon faces which index the *original* point cloud.
|
||||
//The thing is, often times, there are many 'dead vertices' in the point cloud that are on longer referenced by the hull.
|
||||
//The routine 'BringOutYourDead' find only the referenced vertices, copies them to an new buffer, and re-indexes the hull so that it is a minimal representation.
|
||||
void BringOutYourDead(const btVector3* verts,unsigned int vcount, btVector3* overts,unsigned int &ocount,unsigned int* indices,unsigned indexcount);
|
||||
|
||||
bool CleanupVertices(unsigned int svcount,
|
||||
const btVector3* svertices,
|
||||
unsigned int stride,
|
||||
unsigned int &vcount, // output number of vertices
|
||||
btVector3* vertices, // location to store the results.
|
||||
btScalar normalepsilon,
|
||||
btVector3& scale);
|
||||
};
|
||||
|
||||
|
||||
#endif //BT_CD_HULL_H
|
||||
|
||||
2751
opencl/parallel_primitives/host/btConvexHullComputer.cpp
Normal file
2751
opencl/parallel_primitives/host/btConvexHullComputer.cpp
Normal file
File diff suppressed because it is too large
Load Diff
103
opencl/parallel_primitives/host/btConvexHullComputer.h
Normal file
103
opencl/parallel_primitives/host/btConvexHullComputer.h
Normal file
@@ -0,0 +1,103 @@
|
||||
/*
|
||||
Copyright (c) 2011 Ole Kniemeyer, MAXON, www.maxon.net
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
#ifndef BT_CONVEX_HULL_COMPUTER_H
|
||||
#define BT_CONVEX_HULL_COMPUTER_H
|
||||
|
||||
#include "btVector3.h"
|
||||
#include "btAlignedObjectArray.h"
|
||||
|
||||
/// Convex hull implementation based on Preparata and Hong
|
||||
/// See http://code.google.com/p/bullet/issues/detail?id=275
|
||||
/// Ole Kniemeyer, MAXON Computer GmbH
|
||||
class btConvexHullComputer
|
||||
{
|
||||
private:
|
||||
btScalar compute(const void* coords, bool doubleCoords, int stride, int count, btScalar shrink, btScalar shrinkClamp);
|
||||
|
||||
public:
|
||||
|
||||
class Edge
|
||||
{
|
||||
private:
|
||||
int next;
|
||||
int reverse;
|
||||
int targetVertex;
|
||||
|
||||
friend class btConvexHullComputer;
|
||||
|
||||
public:
|
||||
int getSourceVertex() const
|
||||
{
|
||||
return (this + reverse)->targetVertex;
|
||||
}
|
||||
|
||||
int getTargetVertex() const
|
||||
{
|
||||
return targetVertex;
|
||||
}
|
||||
|
||||
const Edge* getNextEdgeOfVertex() const // clockwise list of all edges of a vertex
|
||||
{
|
||||
return this + next;
|
||||
}
|
||||
|
||||
const Edge* getNextEdgeOfFace() const // counter-clockwise list of all edges of a face
|
||||
{
|
||||
return (this + reverse)->getNextEdgeOfVertex();
|
||||
}
|
||||
|
||||
const Edge* getReverseEdge() const
|
||||
{
|
||||
return this + reverse;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
// Vertices of the output hull
|
||||
btAlignedObjectArray<btVector3> vertices;
|
||||
|
||||
// Edges of the output hull
|
||||
btAlignedObjectArray<Edge> edges;
|
||||
|
||||
// Faces of the convex hull. Each entry is an index into the "edges" array pointing to an edge of the face. Faces are planar n-gons
|
||||
btAlignedObjectArray<int> faces;
|
||||
|
||||
/*
|
||||
Compute convex hull of "count" vertices stored in "coords". "stride" is the difference in bytes
|
||||
between the addresses of consecutive vertices. If "shrink" is positive, the convex hull is shrunken
|
||||
by that amount (each face is moved by "shrink" length units towards the center along its normal).
|
||||
If "shrinkClamp" is positive, "shrink" is clamped to not exceed "shrinkClamp * innerRadius", where "innerRadius"
|
||||
is the minimum distance of a face to the center of the convex hull.
|
||||
|
||||
The returned value is the amount by which the hull has been shrunken. If it is negative, the amount was so large
|
||||
that the resulting convex hull is empty.
|
||||
|
||||
The output convex hull can be found in the member variables "vertices", "edges", "faces".
|
||||
*/
|
||||
btScalar compute(const float* coords, int stride, int count, btScalar shrink, btScalar shrinkClamp)
|
||||
{
|
||||
return compute(coords, false, stride, count, shrink, shrinkClamp);
|
||||
}
|
||||
|
||||
// same as above, but double precision
|
||||
btScalar compute(const double* coords, int stride, int count, btScalar shrink, btScalar shrinkClamp)
|
||||
{
|
||||
return compute(coords, true, stride, count, shrink, shrinkClamp);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#endif //BT_CONVEX_HULL_COMPUTER_H
|
||||
|
||||
42
opencl/parallel_primitives/host/btDefaultMotionState.h
Normal file
42
opencl/parallel_primitives/host/btDefaultMotionState.h
Normal file
@@ -0,0 +1,42 @@
|
||||
#ifndef BT_DEFAULT_MOTION_STATE_H
|
||||
#define BT_DEFAULT_MOTION_STATE_H
|
||||
|
||||
#include "btMotionState.h"
|
||||
|
||||
///The btDefaultMotionState provides a common implementation to synchronize world transforms with offsets.
|
||||
ATTRIBUTE_ALIGNED16(struct) btDefaultMotionState : public btMotionState
|
||||
{
|
||||
btTransform m_graphicsWorldTrans;
|
||||
btTransform m_centerOfMassOffset;
|
||||
btTransform m_startWorldTrans;
|
||||
void* m_userPointer;
|
||||
|
||||
BT_DECLARE_ALIGNED_ALLOCATOR();
|
||||
|
||||
btDefaultMotionState(const btTransform& startTrans = btTransform::getIdentity(),const btTransform& centerOfMassOffset = btTransform::getIdentity())
|
||||
: m_graphicsWorldTrans(startTrans),
|
||||
m_centerOfMassOffset(centerOfMassOffset),
|
||||
m_startWorldTrans(startTrans),
|
||||
m_userPointer(0)
|
||||
|
||||
{
|
||||
}
|
||||
|
||||
///synchronizes world transform from user to physics
|
||||
virtual void getWorldTransform(btTransform& centerOfMassWorldTrans ) const
|
||||
{
|
||||
centerOfMassWorldTrans = m_centerOfMassOffset.inverse() * m_graphicsWorldTrans ;
|
||||
}
|
||||
|
||||
///synchronizes world transform from physics to user
|
||||
///Bullet only calls the update of worldtransform for active objects
|
||||
virtual void setWorldTransform(const btTransform& centerOfMassWorldTrans)
|
||||
{
|
||||
m_graphicsWorldTrans = centerOfMassWorldTrans * m_centerOfMassOffset ;
|
||||
}
|
||||
|
||||
|
||||
|
||||
};
|
||||
|
||||
#endif //BT_DEFAULT_MOTION_STATE_H
|
||||
185
opencl/parallel_primitives/host/btGeometryUtil.cpp
Normal file
185
opencl/parallel_primitives/host/btGeometryUtil.cpp
Normal file
@@ -0,0 +1,185 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#include "btGeometryUtil.h"
|
||||
|
||||
|
||||
/*
|
||||
Make sure this dummy function never changes so that it
|
||||
can be used by probes that are checking whether the
|
||||
library is actually installed.
|
||||
*/
|
||||
extern "C"
|
||||
{
|
||||
void btBulletMathProbe ();
|
||||
|
||||
void btBulletMathProbe () {}
|
||||
}
|
||||
|
||||
|
||||
bool btGeometryUtil::isPointInsidePlanes(const btAlignedObjectArray<btVector3>& planeEquations, const btVector3& point, btScalar margin)
|
||||
{
|
||||
int numbrushes = planeEquations.size();
|
||||
for (int i=0;i<numbrushes;i++)
|
||||
{
|
||||
const btVector3& N1 = planeEquations[i];
|
||||
btScalar dist = btScalar(N1.dot(point))+btScalar(N1[3])-margin;
|
||||
if (dist>btScalar(0.))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
|
||||
bool btGeometryUtil::areVerticesBehindPlane(const btVector3& planeNormal, const btAlignedObjectArray<btVector3>& vertices, btScalar margin)
|
||||
{
|
||||
int numvertices = vertices.size();
|
||||
for (int i=0;i<numvertices;i++)
|
||||
{
|
||||
const btVector3& N1 = vertices[i];
|
||||
btScalar dist = btScalar(planeNormal.dot(N1))+btScalar(planeNormal[3])-margin;
|
||||
if (dist>btScalar(0.))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool notExist(const btVector3& planeEquation,const btAlignedObjectArray<btVector3>& planeEquations);
|
||||
|
||||
bool notExist(const btVector3& planeEquation,const btAlignedObjectArray<btVector3>& planeEquations)
|
||||
{
|
||||
int numbrushes = planeEquations.size();
|
||||
for (int i=0;i<numbrushes;i++)
|
||||
{
|
||||
const btVector3& N1 = planeEquations[i];
|
||||
if (planeEquation.dot(N1) > btScalar(0.999))
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void btGeometryUtil::getPlaneEquationsFromVertices(btAlignedObjectArray<btVector3>& vertices, btAlignedObjectArray<btVector3>& planeEquationsOut )
|
||||
{
|
||||
const int numvertices = vertices.size();
|
||||
// brute force:
|
||||
for (int i=0;i<numvertices;i++)
|
||||
{
|
||||
const btVector3& N1 = vertices[i];
|
||||
|
||||
|
||||
for (int j=i+1;j<numvertices;j++)
|
||||
{
|
||||
const btVector3& N2 = vertices[j];
|
||||
|
||||
for (int k=j+1;k<numvertices;k++)
|
||||
{
|
||||
|
||||
const btVector3& N3 = vertices[k];
|
||||
|
||||
btVector3 planeEquation,edge0,edge1;
|
||||
edge0 = N2-N1;
|
||||
edge1 = N3-N1;
|
||||
btScalar normalSign = btScalar(1.);
|
||||
for (int ww=0;ww<2;ww++)
|
||||
{
|
||||
planeEquation = normalSign * edge0.cross(edge1);
|
||||
if (planeEquation.length2() > btScalar(0.0001))
|
||||
{
|
||||
planeEquation.normalize();
|
||||
if (notExist(planeEquation,planeEquationsOut))
|
||||
{
|
||||
planeEquation[3] = -planeEquation.dot(N1);
|
||||
|
||||
//check if inside, and replace supportingVertexOut if needed
|
||||
if (areVerticesBehindPlane(planeEquation,vertices,btScalar(0.01)))
|
||||
{
|
||||
planeEquationsOut.push_back(planeEquation);
|
||||
}
|
||||
}
|
||||
}
|
||||
normalSign = btScalar(-1.);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void btGeometryUtil::getVerticesFromPlaneEquations(const btAlignedObjectArray<btVector3>& planeEquations , btAlignedObjectArray<btVector3>& verticesOut )
|
||||
{
|
||||
const int numbrushes = planeEquations.size();
|
||||
// brute force:
|
||||
for (int i=0;i<numbrushes;i++)
|
||||
{
|
||||
const btVector3& N1 = planeEquations[i];
|
||||
|
||||
|
||||
for (int j=i+1;j<numbrushes;j++)
|
||||
{
|
||||
const btVector3& N2 = planeEquations[j];
|
||||
|
||||
for (int k=j+1;k<numbrushes;k++)
|
||||
{
|
||||
|
||||
const btVector3& N3 = planeEquations[k];
|
||||
|
||||
btVector3 n2n3; n2n3 = N2.cross(N3);
|
||||
btVector3 n3n1; n3n1 = N3.cross(N1);
|
||||
btVector3 n1n2; n1n2 = N1.cross(N2);
|
||||
|
||||
if ( ( n2n3.length2() > btScalar(0.0001) ) &&
|
||||
( n3n1.length2() > btScalar(0.0001) ) &&
|
||||
( n1n2.length2() > btScalar(0.0001) ) )
|
||||
{
|
||||
//point P out of 3 plane equations:
|
||||
|
||||
// d1 ( N2 * N3 ) + d2 ( N3 * N1 ) + d3 ( N1 * N2 )
|
||||
//P = -------------------------------------------------------------------------
|
||||
// N1 . ( N2 * N3 )
|
||||
|
||||
|
||||
btScalar quotient = (N1.dot(n2n3));
|
||||
if (btFabs(quotient) > btScalar(0.000001))
|
||||
{
|
||||
quotient = btScalar(-1.) / quotient;
|
||||
n2n3 *= N1[3];
|
||||
n3n1 *= N2[3];
|
||||
n1n2 *= N3[3];
|
||||
btVector3 potentialVertex = n2n3;
|
||||
potentialVertex += n3n1;
|
||||
potentialVertex += n1n2;
|
||||
potentialVertex *= quotient;
|
||||
|
||||
//check if inside, and replace supportingVertexOut if needed
|
||||
if (isPointInsidePlanes(planeEquations,potentialVertex,btScalar(0.01)))
|
||||
{
|
||||
verticesOut.push_back(potentialVertex);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
42
opencl/parallel_primitives/host/btGeometryUtil.h
Normal file
42
opencl/parallel_primitives/host/btGeometryUtil.h
Normal file
@@ -0,0 +1,42 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef BT_GEOMETRY_UTIL_H
|
||||
#define BT_GEOMETRY_UTIL_H
|
||||
|
||||
#include "btVector3.h"
|
||||
#include "btAlignedObjectArray.h"
|
||||
|
||||
///The btGeometryUtil helper class provides a few methods to convert between plane equations and vertices.
|
||||
class btGeometryUtil
|
||||
{
|
||||
public:
|
||||
|
||||
|
||||
static void getPlaneEquationsFromVertices(btAlignedObjectArray<btVector3>& vertices, btAlignedObjectArray<btVector3>& planeEquationsOut );
|
||||
|
||||
static void getVerticesFromPlaneEquations(const btAlignedObjectArray<btVector3>& planeEquations , btAlignedObjectArray<btVector3>& verticesOut );
|
||||
|
||||
static bool isInside(const btAlignedObjectArray<btVector3>& vertices, const btVector3& planeNormal, btScalar margin);
|
||||
|
||||
static bool isPointInsidePlanes(const btAlignedObjectArray<btVector3>& planeEquations, const btVector3& point, btScalar margin);
|
||||
|
||||
static bool areVerticesBehindPlane(const btVector3& planeNormal, const btAlignedObjectArray<btVector3>& vertices, btScalar margin);
|
||||
|
||||
};
|
||||
|
||||
|
||||
#endif //BT_GEOMETRY_UTIL_H
|
||||
|
||||
117
opencl/parallel_primitives/host/btGrahamScan2dConvexHull.h
Normal file
117
opencl/parallel_primitives/host/btGrahamScan2dConvexHull.h
Normal file
@@ -0,0 +1,117 @@
|
||||
/*
|
||||
Bullet Continuous Collision Detection and Physics Library
|
||||
Copyright (c) 2011 Advanced Micro Devices, Inc. http://bulletphysics.org
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef GRAHAM_SCAN_2D_CONVEX_HULL_H
|
||||
#define GRAHAM_SCAN_2D_CONVEX_HULL_H
|
||||
|
||||
|
||||
#include "btVector3.h"
|
||||
#include "btAlignedObjectArray.h"
|
||||
|
||||
struct GrahamVector3 : public btVector3
|
||||
{
|
||||
GrahamVector3(const btVector3& org, int orgIndex)
|
||||
:btVector3(org),
|
||||
m_orgIndex(orgIndex)
|
||||
{
|
||||
}
|
||||
btScalar m_angle;
|
||||
int m_orgIndex;
|
||||
};
|
||||
|
||||
|
||||
struct btAngleCompareFunc {
|
||||
btVector3 m_anchor;
|
||||
btAngleCompareFunc(const btVector3& anchor)
|
||||
: m_anchor(anchor)
|
||||
{
|
||||
}
|
||||
bool operator()(const GrahamVector3& a, const GrahamVector3& b) const {
|
||||
if (a.m_angle != b.m_angle)
|
||||
return a.m_angle < b.m_angle;
|
||||
else
|
||||
{
|
||||
btScalar al = (a-m_anchor).length2();
|
||||
btScalar bl = (b-m_anchor).length2();
|
||||
if (al != bl)
|
||||
return al < bl;
|
||||
else
|
||||
{
|
||||
return a.m_orgIndex < b.m_orgIndex;
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
inline void GrahamScanConvexHull2D(btAlignedObjectArray<GrahamVector3>& originalPoints, btAlignedObjectArray<GrahamVector3>& hull, const btVector3& normalAxis)
|
||||
{
|
||||
btVector3 axis0,axis1;
|
||||
btPlaneSpace1(normalAxis,axis0,axis1);
|
||||
|
||||
|
||||
if (originalPoints.size()<=1)
|
||||
{
|
||||
for (int i=0;i<originalPoints.size();i++)
|
||||
hull.push_back(originalPoints[0]);
|
||||
return;
|
||||
}
|
||||
//step1 : find anchor point with smallest projection on axis0 and move it to first location
|
||||
for (int i=0;i<originalPoints.size();i++)
|
||||
{
|
||||
// const btVector3& left = originalPoints[i];
|
||||
// const btVector3& right = originalPoints[0];
|
||||
btScalar projL = originalPoints[i].dot(axis0);
|
||||
btScalar projR = originalPoints[0].dot(axis0);
|
||||
if (projL < projR)
|
||||
{
|
||||
originalPoints.swap(0,i);
|
||||
}
|
||||
}
|
||||
|
||||
//also precompute angles
|
||||
originalPoints[0].m_angle = -1e30f;
|
||||
for (int i=1;i<originalPoints.size();i++)
|
||||
{
|
||||
btVector3 xvec = axis0;
|
||||
btVector3 ar = originalPoints[i]-originalPoints[0];
|
||||
originalPoints[i].m_angle = btCross(xvec, ar).dot(normalAxis) / ar.length();
|
||||
}
|
||||
|
||||
//step 2: sort all points, based on 'angle' with this anchor
|
||||
btAngleCompareFunc comp(originalPoints[0]);
|
||||
originalPoints.quickSortInternal(comp,1,originalPoints.size()-1);
|
||||
|
||||
int i;
|
||||
for (i = 0; i<2; i++)
|
||||
hull.push_back(originalPoints[i]);
|
||||
|
||||
//step 3: keep all 'convex' points and discard concave points (using back tracking)
|
||||
for (; i != originalPoints.size(); i++)
|
||||
{
|
||||
bool isConvex = false;
|
||||
while (!isConvex&& hull.size()>1) {
|
||||
btVector3& a = hull[hull.size()-2];
|
||||
btVector3& b = hull[hull.size()-1];
|
||||
isConvex = btCross(a-b,a-originalPoints[i]).dot(normalAxis)> 0;
|
||||
if (!isConvex)
|
||||
hull.pop_back();
|
||||
else
|
||||
hull.push_back(originalPoints[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif //GRAHAM_SCAN_2D_CONVEX_HULL_H
|
||||
411
opencl/parallel_primitives/host/btIDebugDraw.h
Normal file
411
opencl/parallel_primitives/host/btIDebugDraw.h
Normal file
@@ -0,0 +1,411 @@
|
||||
/*
|
||||
Bullet Continuous Collision Detection and Physics Library
|
||||
Copyright (c) 2003-2009 Erwin Coumans http://bulletphysics.org
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef BT_IDEBUG_DRAW__H
|
||||
#define BT_IDEBUG_DRAW__H
|
||||
|
||||
#include "btVector3.h"
|
||||
#include "btTransform.h"
|
||||
|
||||
|
||||
///The btIDebugDraw interface class allows hooking up a debug renderer to visually debug simulations.
|
||||
///Typical use case: create a debug drawer object, and assign it to a btCollisionWorld or btDynamicsWorld using setDebugDrawer and call debugDrawWorld.
|
||||
///A class that implements the btIDebugDraw interface has to implement the drawLine method at a minimum.
|
||||
///For color arguments the X,Y,Z components refer to Red, Green and Blue each in the range [0..1]
|
||||
class btIDebugDraw
|
||||
{
|
||||
public:
|
||||
|
||||
enum DebugDrawModes
|
||||
{
|
||||
DBG_NoDebug=0,
|
||||
DBG_DrawWireframe = 1,
|
||||
DBG_DrawAabb=2,
|
||||
DBG_DrawFeaturesText=4,
|
||||
DBG_DrawContactPoints=8,
|
||||
DBG_NoDeactivation=16,
|
||||
DBG_NoHelpText = 32,
|
||||
DBG_DrawText=64,
|
||||
DBG_ProfileTimings = 128,
|
||||
DBG_EnableSatComparison = 256,
|
||||
DBG_DisableBulletLCP = 512,
|
||||
DBG_EnableCCD = 1024,
|
||||
DBG_DrawConstraints = (1 << 11),
|
||||
DBG_DrawConstraintLimits = (1 << 12),
|
||||
DBG_FastWireframe = (1<<13),
|
||||
DBG_DrawNormals = (1<<14),
|
||||
DBG_DrawBroadphasePairs= (1<<15),
|
||||
|
||||
DBG_MAX_DEBUG_DRAW_MODE
|
||||
};
|
||||
|
||||
virtual ~btIDebugDraw() {};
|
||||
|
||||
virtual void drawLine(const btVector3& from,const btVector3& to,const btVector3& color)=0;
|
||||
|
||||
virtual void drawLine(const btVector3& from,const btVector3& to, const btVector3& fromColor, const btVector3& toColor)
|
||||
{
|
||||
(void) toColor;
|
||||
drawLine (from, to, fromColor);
|
||||
}
|
||||
|
||||
virtual void drawSphere(btScalar radius, const btTransform& transform, const btVector3& color)
|
||||
{
|
||||
|
||||
btVector3 start = transform.getOrigin();
|
||||
|
||||
|
||||
const btVector3 xoffs = transform.getBasis() * btVector3(1,0,0);
|
||||
const btVector3 yoffs = transform.getBasis() * btVector3(0,1,0);
|
||||
const btVector3 zoffs = transform.getBasis() * btVector3(0,0,1);
|
||||
|
||||
drawArc(start,xoffs,yoffs,radius,radius,0,SIMD_2_PI,color,true,btScalar(10.0));
|
||||
drawArc(start,yoffs,zoffs,radius,radius,0,SIMD_2_PI,color,true,btScalar(10.0));
|
||||
drawArc(start,zoffs,xoffs,radius,radius,0,SIMD_2_PI,color,true,btScalar(10.0));
|
||||
// drawArc(start,zoffs,yoffs,radius,radius,0,SIMD_2_PI,color,false,btScalar(10.0));
|
||||
|
||||
}
|
||||
|
||||
virtual void drawSphere (const btVector3& p, btScalar radius, const btVector3& color)
|
||||
{
|
||||
btTransform tr;
|
||||
tr.setIdentity();
|
||||
tr.setOrigin(p);
|
||||
drawSphere(radius,tr,color);
|
||||
}
|
||||
|
||||
virtual void drawTriangle(const btVector3& v0,const btVector3& v1,const btVector3& v2,const btVector3& /*n0*/,const btVector3& /*n1*/,const btVector3& /*n2*/,const btVector3& color, btScalar alpha)
|
||||
{
|
||||
drawTriangle(v0,v1,v2,color,alpha);
|
||||
}
|
||||
virtual void drawTriangle(const btVector3& v0,const btVector3& v1,const btVector3& v2,const btVector3& color, btScalar /*alpha*/)
|
||||
{
|
||||
drawLine(v0,v1,color);
|
||||
drawLine(v1,v2,color);
|
||||
drawLine(v2,v0,color);
|
||||
}
|
||||
|
||||
virtual void drawContactPoint(const btVector3& PointOnB,const btVector3& normalOnB,btScalar distance,int lifeTime,const btVector3& color)=0;
|
||||
|
||||
virtual void reportErrorWarning(const char* warningString) = 0;
|
||||
|
||||
virtual void draw3dText(const btVector3& location,const char* textString) = 0;
|
||||
|
||||
virtual void setDebugMode(int debugMode) =0;
|
||||
|
||||
virtual int getDebugMode() const = 0;
|
||||
|
||||
virtual void drawAabb(const btVector3& from,const btVector3& to,const btVector3& color)
|
||||
{
|
||||
|
||||
btVector3 halfExtents = (to-from)* 0.5f;
|
||||
btVector3 center = (to+from) *0.5f;
|
||||
int i,j;
|
||||
|
||||
btVector3 edgecoord(1.f,1.f,1.f),pa,pb;
|
||||
for (i=0;i<4;i++)
|
||||
{
|
||||
for (j=0;j<3;j++)
|
||||
{
|
||||
pa = btVector3(edgecoord[0]*halfExtents[0], edgecoord[1]*halfExtents[1],
|
||||
edgecoord[2]*halfExtents[2]);
|
||||
pa+=center;
|
||||
|
||||
int othercoord = j%3;
|
||||
edgecoord[othercoord]*=-1.f;
|
||||
pb = btVector3(edgecoord[0]*halfExtents[0], edgecoord[1]*halfExtents[1],
|
||||
edgecoord[2]*halfExtents[2]);
|
||||
pb+=center;
|
||||
|
||||
drawLine(pa,pb,color);
|
||||
}
|
||||
edgecoord = btVector3(-1.f,-1.f,-1.f);
|
||||
if (i<3)
|
||||
edgecoord[i]*=-1.f;
|
||||
}
|
||||
}
|
||||
virtual void drawTransform(const btTransform& transform, btScalar orthoLen)
|
||||
{
|
||||
btVector3 start = transform.getOrigin();
|
||||
drawLine(start, start+transform.getBasis() * btVector3(orthoLen, 0, 0), btVector3(0.7f,0,0));
|
||||
drawLine(start, start+transform.getBasis() * btVector3(0, orthoLen, 0), btVector3(0,0.7f,0));
|
||||
drawLine(start, start+transform.getBasis() * btVector3(0, 0, orthoLen), btVector3(0,0,0.7f));
|
||||
}
|
||||
|
||||
virtual void drawArc(const btVector3& center, const btVector3& normal, const btVector3& axis, btScalar radiusA, btScalar radiusB, btScalar minAngle, btScalar maxAngle,
|
||||
const btVector3& color, bool drawSect, btScalar stepDegrees = btScalar(10.f))
|
||||
{
|
||||
const btVector3& vx = axis;
|
||||
btVector3 vy = normal.cross(axis);
|
||||
btScalar step = stepDegrees * SIMD_RADS_PER_DEG;
|
||||
int nSteps = (int)((maxAngle - minAngle) / step);
|
||||
if(!nSteps) nSteps = 1;
|
||||
btVector3 prev = center + radiusA * vx * btCos(minAngle) + radiusB * vy * btSin(minAngle);
|
||||
if(drawSect)
|
||||
{
|
||||
drawLine(center, prev, color);
|
||||
}
|
||||
for(int i = 1; i <= nSteps; i++)
|
||||
{
|
||||
btScalar angle = minAngle + (maxAngle - minAngle) * btScalar(i) / btScalar(nSteps);
|
||||
btVector3 next = center + radiusA * vx * btCos(angle) + radiusB * vy * btSin(angle);
|
||||
drawLine(prev, next, color);
|
||||
prev = next;
|
||||
}
|
||||
if(drawSect)
|
||||
{
|
||||
drawLine(center, prev, color);
|
||||
}
|
||||
}
|
||||
virtual void drawSpherePatch(const btVector3& center, const btVector3& up, const btVector3& axis, btScalar radius,
|
||||
btScalar minTh, btScalar maxTh, btScalar minPs, btScalar maxPs, const btVector3& color, btScalar stepDegrees = btScalar(10.f))
|
||||
{
|
||||
btVector3 vA[74];
|
||||
btVector3 vB[74];
|
||||
btVector3 *pvA = vA, *pvB = vB, *pT;
|
||||
btVector3 npole = center + up * radius;
|
||||
btVector3 spole = center - up * radius;
|
||||
btVector3 arcStart;
|
||||
btScalar step = stepDegrees * SIMD_RADS_PER_DEG;
|
||||
const btVector3& kv = up;
|
||||
const btVector3& iv = axis;
|
||||
btVector3 jv = kv.cross(iv);
|
||||
bool drawN = false;
|
||||
bool drawS = false;
|
||||
if(minTh <= -SIMD_HALF_PI)
|
||||
{
|
||||
minTh = -SIMD_HALF_PI + step;
|
||||
drawN = true;
|
||||
}
|
||||
if(maxTh >= SIMD_HALF_PI)
|
||||
{
|
||||
maxTh = SIMD_HALF_PI - step;
|
||||
drawS = true;
|
||||
}
|
||||
if(minTh > maxTh)
|
||||
{
|
||||
minTh = -SIMD_HALF_PI + step;
|
||||
maxTh = SIMD_HALF_PI - step;
|
||||
drawN = drawS = true;
|
||||
}
|
||||
int n_hor = (int)((maxTh - minTh) / step) + 1;
|
||||
if(n_hor < 2) n_hor = 2;
|
||||
btScalar step_h = (maxTh - minTh) / btScalar(n_hor - 1);
|
||||
bool isClosed = false;
|
||||
if(minPs > maxPs)
|
||||
{
|
||||
minPs = -SIMD_PI + step;
|
||||
maxPs = SIMD_PI;
|
||||
isClosed = true;
|
||||
}
|
||||
else if((maxPs - minPs) >= SIMD_PI * btScalar(2.f))
|
||||
{
|
||||
isClosed = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
isClosed = false;
|
||||
}
|
||||
int n_vert = (int)((maxPs - minPs) / step) + 1;
|
||||
if(n_vert < 2) n_vert = 2;
|
||||
btScalar step_v = (maxPs - minPs) / btScalar(n_vert - 1);
|
||||
for(int i = 0; i < n_hor; i++)
|
||||
{
|
||||
btScalar th = minTh + btScalar(i) * step_h;
|
||||
btScalar sth = radius * btSin(th);
|
||||
btScalar cth = radius * btCos(th);
|
||||
for(int j = 0; j < n_vert; j++)
|
||||
{
|
||||
btScalar psi = minPs + btScalar(j) * step_v;
|
||||
btScalar sps = btSin(psi);
|
||||
btScalar cps = btCos(psi);
|
||||
pvB[j] = center + cth * cps * iv + cth * sps * jv + sth * kv;
|
||||
if(i)
|
||||
{
|
||||
drawLine(pvA[j], pvB[j], color);
|
||||
}
|
||||
else if(drawS)
|
||||
{
|
||||
drawLine(spole, pvB[j], color);
|
||||
}
|
||||
if(j)
|
||||
{
|
||||
drawLine(pvB[j-1], pvB[j], color);
|
||||
}
|
||||
else
|
||||
{
|
||||
arcStart = pvB[j];
|
||||
}
|
||||
if((i == (n_hor - 1)) && drawN)
|
||||
{
|
||||
drawLine(npole, pvB[j], color);
|
||||
}
|
||||
if(isClosed)
|
||||
{
|
||||
if(j == (n_vert-1))
|
||||
{
|
||||
drawLine(arcStart, pvB[j], color);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(((!i) || (i == (n_hor-1))) && ((!j) || (j == (n_vert-1))))
|
||||
{
|
||||
drawLine(center, pvB[j], color);
|
||||
}
|
||||
}
|
||||
}
|
||||
pT = pvA; pvA = pvB; pvB = pT;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
virtual void drawBox(const btVector3& bbMin, const btVector3& bbMax, const btVector3& color)
|
||||
{
|
||||
drawLine(btVector3(bbMin[0], bbMin[1], bbMin[2]), btVector3(bbMax[0], bbMin[1], bbMin[2]), color);
|
||||
drawLine(btVector3(bbMax[0], bbMin[1], bbMin[2]), btVector3(bbMax[0], bbMax[1], bbMin[2]), color);
|
||||
drawLine(btVector3(bbMax[0], bbMax[1], bbMin[2]), btVector3(bbMin[0], bbMax[1], bbMin[2]), color);
|
||||
drawLine(btVector3(bbMin[0], bbMax[1], bbMin[2]), btVector3(bbMin[0], bbMin[1], bbMin[2]), color);
|
||||
drawLine(btVector3(bbMin[0], bbMin[1], bbMin[2]), btVector3(bbMin[0], bbMin[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMax[0], bbMin[1], bbMin[2]), btVector3(bbMax[0], bbMin[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMax[0], bbMax[1], bbMin[2]), btVector3(bbMax[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMin[0], bbMax[1], bbMin[2]), btVector3(bbMin[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMin[0], bbMin[1], bbMax[2]), btVector3(bbMax[0], bbMin[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMax[0], bbMin[1], bbMax[2]), btVector3(bbMax[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMax[0], bbMax[1], bbMax[2]), btVector3(bbMin[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(btVector3(bbMin[0], bbMax[1], bbMax[2]), btVector3(bbMin[0], bbMin[1], bbMax[2]), color);
|
||||
}
|
||||
virtual void drawBox(const btVector3& bbMin, const btVector3& bbMax, const btTransform& trans, const btVector3& color)
|
||||
{
|
||||
drawLine(trans * btVector3(bbMin[0], bbMin[1], bbMin[2]), trans * btVector3(bbMax[0], bbMin[1], bbMin[2]), color);
|
||||
drawLine(trans * btVector3(bbMax[0], bbMin[1], bbMin[2]), trans * btVector3(bbMax[0], bbMax[1], bbMin[2]), color);
|
||||
drawLine(trans * btVector3(bbMax[0], bbMax[1], bbMin[2]), trans * btVector3(bbMin[0], bbMax[1], bbMin[2]), color);
|
||||
drawLine(trans * btVector3(bbMin[0], bbMax[1], bbMin[2]), trans * btVector3(bbMin[0], bbMin[1], bbMin[2]), color);
|
||||
drawLine(trans * btVector3(bbMin[0], bbMin[1], bbMin[2]), trans * btVector3(bbMin[0], bbMin[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMax[0], bbMin[1], bbMin[2]), trans * btVector3(bbMax[0], bbMin[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMax[0], bbMax[1], bbMin[2]), trans * btVector3(bbMax[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMin[0], bbMax[1], bbMin[2]), trans * btVector3(bbMin[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMin[0], bbMin[1], bbMax[2]), trans * btVector3(bbMax[0], bbMin[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMax[0], bbMin[1], bbMax[2]), trans * btVector3(bbMax[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMax[0], bbMax[1], bbMax[2]), trans * btVector3(bbMin[0], bbMax[1], bbMax[2]), color);
|
||||
drawLine(trans * btVector3(bbMin[0], bbMax[1], bbMax[2]), trans * btVector3(bbMin[0], bbMin[1], bbMax[2]), color);
|
||||
}
|
||||
|
||||
virtual void drawCapsule(btScalar radius, btScalar halfHeight, int upAxis, const btTransform& transform, const btVector3& color)
|
||||
{
|
||||
btVector3 capStart(0.f,0.f,0.f);
|
||||
capStart[upAxis] = -halfHeight;
|
||||
|
||||
btVector3 capEnd(0.f,0.f,0.f);
|
||||
capEnd[upAxis] = halfHeight;
|
||||
|
||||
// Draw the ends
|
||||
{
|
||||
|
||||
btTransform childTransform = transform;
|
||||
childTransform.getOrigin() = transform * capStart;
|
||||
drawSphere(radius, childTransform, color);
|
||||
}
|
||||
|
||||
{
|
||||
btTransform childTransform = transform;
|
||||
childTransform.getOrigin() = transform * capEnd;
|
||||
drawSphere(radius, childTransform, color);
|
||||
}
|
||||
|
||||
// Draw some additional lines
|
||||
btVector3 start = transform.getOrigin();
|
||||
|
||||
capStart[(upAxis+1)%3] = radius;
|
||||
capEnd[(upAxis+1)%3] = radius;
|
||||
drawLine(start+transform.getBasis() * capStart,start+transform.getBasis() * capEnd, color);
|
||||
capStart[(upAxis+1)%3] = -radius;
|
||||
capEnd[(upAxis+1)%3] = -radius;
|
||||
drawLine(start+transform.getBasis() * capStart,start+transform.getBasis() * capEnd, color);
|
||||
|
||||
capStart[(upAxis+1)%3] = 0.f;
|
||||
capEnd[(upAxis+1)%3] = 0.f;
|
||||
|
||||
capStart[(upAxis+2)%3] = radius;
|
||||
capEnd[(upAxis+2)%3] = radius;
|
||||
drawLine(start+transform.getBasis() * capStart,start+transform.getBasis() * capEnd, color);
|
||||
capStart[(upAxis+2)%3] = -radius;
|
||||
capEnd[(upAxis+2)%3] = -radius;
|
||||
drawLine(start+transform.getBasis() * capStart,start+transform.getBasis() * capEnd, color);
|
||||
}
|
||||
|
||||
virtual void drawCylinder(btScalar radius, btScalar halfHeight, int upAxis, const btTransform& transform, const btVector3& color)
|
||||
{
|
||||
btVector3 start = transform.getOrigin();
|
||||
btVector3 offsetHeight(0,0,0);
|
||||
offsetHeight[upAxis] = halfHeight;
|
||||
btVector3 offsetRadius(0,0,0);
|
||||
offsetRadius[(upAxis+1)%3] = radius;
|
||||
drawLine(start+transform.getBasis() * (offsetHeight+offsetRadius),start+transform.getBasis() * (-offsetHeight+offsetRadius),color);
|
||||
drawLine(start+transform.getBasis() * (offsetHeight-offsetRadius),start+transform.getBasis() * (-offsetHeight-offsetRadius),color);
|
||||
|
||||
// Drawing top and bottom caps of the cylinder
|
||||
btVector3 yaxis(0,0,0);
|
||||
yaxis[upAxis] = btScalar(1.0);
|
||||
btVector3 xaxis(0,0,0);
|
||||
xaxis[(upAxis+1)%3] = btScalar(1.0);
|
||||
drawArc(start-transform.getBasis()*(offsetHeight),transform.getBasis()*yaxis,transform.getBasis()*xaxis,radius,radius,0,SIMD_2_PI,color,false,btScalar(10.0));
|
||||
drawArc(start+transform.getBasis()*(offsetHeight),transform.getBasis()*yaxis,transform.getBasis()*xaxis,radius,radius,0,SIMD_2_PI,color,false,btScalar(10.0));
|
||||
}
|
||||
|
||||
virtual void drawCone(btScalar radius, btScalar height, int upAxis, const btTransform& transform, const btVector3& color)
|
||||
{
|
||||
|
||||
btVector3 start = transform.getOrigin();
|
||||
|
||||
btVector3 offsetHeight(0,0,0);
|
||||
offsetHeight[upAxis] = height * btScalar(0.5);
|
||||
btVector3 offsetRadius(0,0,0);
|
||||
offsetRadius[(upAxis+1)%3] = radius;
|
||||
btVector3 offset2Radius(0,0,0);
|
||||
offset2Radius[(upAxis+2)%3] = radius;
|
||||
|
||||
drawLine(start+transform.getBasis() * (offsetHeight),start+transform.getBasis() * (-offsetHeight+offsetRadius),color);
|
||||
drawLine(start+transform.getBasis() * (offsetHeight),start+transform.getBasis() * (-offsetHeight-offsetRadius),color);
|
||||
drawLine(start+transform.getBasis() * (offsetHeight),start+transform.getBasis() * (-offsetHeight+offset2Radius),color);
|
||||
drawLine(start+transform.getBasis() * (offsetHeight),start+transform.getBasis() * (-offsetHeight-offset2Radius),color);
|
||||
|
||||
// Drawing the base of the cone
|
||||
btVector3 yaxis(0,0,0);
|
||||
yaxis[upAxis] = btScalar(1.0);
|
||||
btVector3 xaxis(0,0,0);
|
||||
xaxis[(upAxis+1)%3] = btScalar(1.0);
|
||||
drawArc(start-transform.getBasis()*(offsetHeight),transform.getBasis()*yaxis,transform.getBasis()*xaxis,radius,radius,0,SIMD_2_PI,color,false,10.0);
|
||||
}
|
||||
|
||||
virtual void drawPlane(const btVector3& planeNormal, btScalar planeConst, const btTransform& transform, const btVector3& color)
|
||||
{
|
||||
btVector3 planeOrigin = planeNormal * planeConst;
|
||||
btVector3 vec0,vec1;
|
||||
btPlaneSpace1(planeNormal,vec0,vec1);
|
||||
btScalar vecLen = 100.f;
|
||||
btVector3 pt0 = planeOrigin + vec0*vecLen;
|
||||
btVector3 pt1 = planeOrigin - vec0*vecLen;
|
||||
btVector3 pt2 = planeOrigin + vec1*vecLen;
|
||||
btVector3 pt3 = planeOrigin - vec1*vecLen;
|
||||
drawLine(transform*pt0,transform*pt1,color);
|
||||
drawLine(transform*pt2,transform*pt3,color);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
#endif //BT_IDEBUG_DRAW__H
|
||||
|
||||
73
opencl/parallel_primitives/host/btList.h
Normal file
73
opencl/parallel_primitives/host/btList.h
Normal file
@@ -0,0 +1,73 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#ifndef BT_GEN_LIST_H
|
||||
#define BT_GEN_LIST_H
|
||||
|
||||
class btGEN_Link {
|
||||
public:
|
||||
btGEN_Link() : m_next(0), m_prev(0) {}
|
||||
btGEN_Link(btGEN_Link *next, btGEN_Link *prev) : m_next(next), m_prev(prev) {}
|
||||
|
||||
btGEN_Link *getNext() const { return m_next; }
|
||||
btGEN_Link *getPrev() const { return m_prev; }
|
||||
|
||||
bool isHead() const { return m_prev == 0; }
|
||||
bool isTail() const { return m_next == 0; }
|
||||
|
||||
void insertBefore(btGEN_Link *link) {
|
||||
m_next = link;
|
||||
m_prev = link->m_prev;
|
||||
m_next->m_prev = this;
|
||||
m_prev->m_next = this;
|
||||
}
|
||||
|
||||
void insertAfter(btGEN_Link *link) {
|
||||
m_next = link->m_next;
|
||||
m_prev = link;
|
||||
m_next->m_prev = this;
|
||||
m_prev->m_next = this;
|
||||
}
|
||||
|
||||
void remove() {
|
||||
m_next->m_prev = m_prev;
|
||||
m_prev->m_next = m_next;
|
||||
}
|
||||
|
||||
private:
|
||||
btGEN_Link *m_next;
|
||||
btGEN_Link *m_prev;
|
||||
};
|
||||
|
||||
class btGEN_List {
|
||||
public:
|
||||
btGEN_List() : m_head(&m_tail, 0), m_tail(0, &m_head) {}
|
||||
|
||||
btGEN_Link *getHead() const { return m_head.getNext(); }
|
||||
btGEN_Link *getTail() const { return m_tail.getPrev(); }
|
||||
|
||||
void addHead(btGEN_Link *link) { link->insertAfter(&m_head); }
|
||||
void addTail(btGEN_Link *link) { link->insertBefore(&m_tail); }
|
||||
|
||||
private:
|
||||
btGEN_Link m_head;
|
||||
btGEN_Link m_tail;
|
||||
};
|
||||
|
||||
#endif //BT_GEN_LIST_H
|
||||
|
||||
|
||||
|
||||
1362
opencl/parallel_primitives/host/btMatrix3x3.h
Normal file
1362
opencl/parallel_primitives/host/btMatrix3x3.h
Normal file
File diff suppressed because it is too large
Load Diff
40
opencl/parallel_primitives/host/btMotionState.h
Normal file
40
opencl/parallel_primitives/host/btMotionState.h
Normal file
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
Bullet Continuous Collision Detection and Physics Library
|
||||
Copyright (c) 2003-2006 Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
#ifndef BT_MOTIONSTATE_H
|
||||
#define BT_MOTIONSTATE_H
|
||||
|
||||
#include "btTransform.h"
|
||||
|
||||
///The btMotionState interface class allows the dynamics world to synchronize and interpolate the updated world transforms with graphics
|
||||
///For optimizations, potentially only moving objects get synchronized (using setWorldPosition/setWorldOrientation)
|
||||
class btMotionState
|
||||
{
|
||||
public:
|
||||
|
||||
virtual ~btMotionState()
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
virtual void getWorldTransform(btTransform& worldTrans ) const =0;
|
||||
|
||||
//Bullet only calls the update of worldtransform for active objects
|
||||
virtual void setWorldTransform(const btTransform& worldTrans)=0;
|
||||
|
||||
|
||||
};
|
||||
|
||||
#endif //BT_MOTIONSTATE_H
|
||||
99
opencl/parallel_primitives/host/btPolarDecomposition.cpp
Normal file
99
opencl/parallel_primitives/host/btPolarDecomposition.cpp
Normal file
@@ -0,0 +1,99 @@
|
||||
#include "btPolarDecomposition.h"
|
||||
#include "btMinMax.h"
|
||||
|
||||
namespace
|
||||
{
|
||||
btScalar abs_column_sum(const btMatrix3x3& a, int i)
|
||||
{
|
||||
return btFabs(a[0][i]) + btFabs(a[1][i]) + btFabs(a[2][i]);
|
||||
}
|
||||
|
||||
btScalar abs_row_sum(const btMatrix3x3& a, int i)
|
||||
{
|
||||
return btFabs(a[i][0]) + btFabs(a[i][1]) + btFabs(a[i][2]);
|
||||
}
|
||||
|
||||
btScalar p1_norm(const btMatrix3x3& a)
|
||||
{
|
||||
const btScalar sum0 = abs_column_sum(a,0);
|
||||
const btScalar sum1 = abs_column_sum(a,1);
|
||||
const btScalar sum2 = abs_column_sum(a,2);
|
||||
return btMax(btMax(sum0, sum1), sum2);
|
||||
}
|
||||
|
||||
btScalar pinf_norm(const btMatrix3x3& a)
|
||||
{
|
||||
const btScalar sum0 = abs_row_sum(a,0);
|
||||
const btScalar sum1 = abs_row_sum(a,1);
|
||||
const btScalar sum2 = abs_row_sum(a,2);
|
||||
return btMax(btMax(sum0, sum1), sum2);
|
||||
}
|
||||
}
|
||||
|
||||
const btScalar btPolarDecomposition::DEFAULT_TOLERANCE = btScalar(0.0001);
|
||||
const unsigned int btPolarDecomposition::DEFAULT_MAX_ITERATIONS = 16;
|
||||
|
||||
btPolarDecomposition::btPolarDecomposition(btScalar tolerance, unsigned int maxIterations)
|
||||
: m_tolerance(tolerance)
|
||||
, m_maxIterations(maxIterations)
|
||||
{
|
||||
}
|
||||
|
||||
unsigned int btPolarDecomposition::decompose(const btMatrix3x3& a, btMatrix3x3& u, btMatrix3x3& h) const
|
||||
{
|
||||
// Use the 'u' and 'h' matrices for intermediate calculations
|
||||
u = a;
|
||||
h = a.inverse();
|
||||
|
||||
for (unsigned int i = 0; i < m_maxIterations; ++i)
|
||||
{
|
||||
const btScalar h_1 = p1_norm(h);
|
||||
const btScalar h_inf = pinf_norm(h);
|
||||
const btScalar u_1 = p1_norm(u);
|
||||
const btScalar u_inf = pinf_norm(u);
|
||||
|
||||
const btScalar h_norm = h_1 * h_inf;
|
||||
const btScalar u_norm = u_1 * u_inf;
|
||||
|
||||
// The matrix is effectively singular so we cannot invert it
|
||||
if (btFuzzyZero(h_norm) || btFuzzyZero(u_norm))
|
||||
break;
|
||||
|
||||
const btScalar gamma = btPow(h_norm / u_norm, 0.25f);
|
||||
const btScalar inv_gamma = 1.0 / gamma;
|
||||
|
||||
// Determine the delta to 'u'
|
||||
const btMatrix3x3 delta = (u * (gamma - 2.0) + h.transpose() * inv_gamma) * 0.5;
|
||||
|
||||
// Update the matrices
|
||||
u += delta;
|
||||
h = u.inverse();
|
||||
|
||||
// Check for convergence
|
||||
if (p1_norm(delta) <= m_tolerance * u_1)
|
||||
{
|
||||
h = u.transpose() * a;
|
||||
h = (h + h.transpose()) * 0.5;
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
// The algorithm has failed to converge to the specified tolerance, but we
|
||||
// want to make sure that the matrices returned are in the right form.
|
||||
h = u.transpose() * a;
|
||||
h = (h + h.transpose()) * 0.5;
|
||||
|
||||
return m_maxIterations;
|
||||
}
|
||||
|
||||
unsigned int btPolarDecomposition::maxIterations() const
|
||||
{
|
||||
return m_maxIterations;
|
||||
}
|
||||
|
||||
unsigned int polarDecompose(const btMatrix3x3& a, btMatrix3x3& u, btMatrix3x3& h)
|
||||
{
|
||||
static btPolarDecomposition polar;
|
||||
return polar.decompose(a, u, h);
|
||||
}
|
||||
|
||||
73
opencl/parallel_primitives/host/btPolarDecomposition.h
Normal file
73
opencl/parallel_primitives/host/btPolarDecomposition.h
Normal file
@@ -0,0 +1,73 @@
|
||||
#ifndef POLARDECOMPOSITION_H
|
||||
#define POLARDECOMPOSITION_H
|
||||
|
||||
#include "btMatrix3x3.h"
|
||||
|
||||
/**
|
||||
* This class is used to compute the polar decomposition of a matrix. In
|
||||
* general, the polar decomposition factorizes a matrix, A, into two parts: a
|
||||
* unitary matrix (U) and a positive, semi-definite Hermitian matrix (H).
|
||||
* However, in this particular implementation the original matrix, A, is
|
||||
* required to be a square 3x3 matrix with real elements. This means that U will
|
||||
* be an orthogonal matrix and H with be a positive-definite, symmetric matrix.
|
||||
*/
|
||||
class btPolarDecomposition
|
||||
{
|
||||
public:
|
||||
static const btScalar DEFAULT_TOLERANCE;
|
||||
static const unsigned int DEFAULT_MAX_ITERATIONS;
|
||||
|
||||
/**
|
||||
* Creates an instance with optional parameters.
|
||||
*
|
||||
* @param tolerance - the tolerance used to determine convergence of the
|
||||
* algorithm
|
||||
* @param maxIterations - the maximum number of iterations used to achieve
|
||||
* convergence
|
||||
*/
|
||||
btPolarDecomposition(btScalar tolerance = DEFAULT_TOLERANCE,
|
||||
unsigned int maxIterations = DEFAULT_MAX_ITERATIONS);
|
||||
|
||||
/**
|
||||
* Decomposes a matrix into orthogonal and symmetric, positive-definite
|
||||
* parts. If the number of iterations returned by this function is equal to
|
||||
* the maximum number of iterations, the algorithm has failed to converge.
|
||||
*
|
||||
* @param a - the original matrix
|
||||
* @param u - the resulting orthogonal matrix
|
||||
* @param h - the resulting symmetric matrix
|
||||
*
|
||||
* @return the number of iterations performed by the algorithm.
|
||||
*/
|
||||
unsigned int decompose(const btMatrix3x3& a, btMatrix3x3& u, btMatrix3x3& h) const;
|
||||
|
||||
/**
|
||||
* Returns the maximum number of iterations that this algorithm will perform
|
||||
* to achieve convergence.
|
||||
*
|
||||
* @return maximum number of iterations
|
||||
*/
|
||||
unsigned int maxIterations() const;
|
||||
|
||||
private:
|
||||
btScalar m_tolerance;
|
||||
unsigned int m_maxIterations;
|
||||
};
|
||||
|
||||
/**
|
||||
* This functions decomposes the matrix 'a' into two parts: an orthogonal matrix
|
||||
* 'u' and a symmetric, positive-definite matrix 'h'. If the number of
|
||||
* iterations returned by this function is equal to
|
||||
* btPolarDecomposition::DEFAULT_MAX_ITERATIONS, the algorithm has failed to
|
||||
* converge.
|
||||
*
|
||||
* @param a - the original matrix
|
||||
* @param u - the resulting orthogonal matrix
|
||||
* @param h - the resulting symmetric matrix
|
||||
*
|
||||
* @return the number of iterations performed by the algorithm.
|
||||
*/
|
||||
unsigned int polarDecompose(const btMatrix3x3& a, btMatrix3x3& u, btMatrix3x3& h);
|
||||
|
||||
#endif // POLARDECOMPOSITION_H
|
||||
|
||||
121
opencl/parallel_primitives/host/btPoolAllocator.h
Normal file
121
opencl/parallel_primitives/host/btPoolAllocator.h
Normal file
@@ -0,0 +1,121 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef _BT_POOL_ALLOCATOR_H
|
||||
#define _BT_POOL_ALLOCATOR_H
|
||||
|
||||
#include "btScalar.h"
|
||||
#include "btAlignedAllocator.h"
|
||||
|
||||
///The btPoolAllocator class allows to efficiently allocate a large pool of objects, instead of dynamically allocating them separately.
|
||||
class btPoolAllocator
|
||||
{
|
||||
int m_elemSize;
|
||||
int m_maxElements;
|
||||
int m_freeCount;
|
||||
void* m_firstFree;
|
||||
unsigned char* m_pool;
|
||||
|
||||
public:
|
||||
|
||||
btPoolAllocator(int elemSize, int maxElements)
|
||||
:m_elemSize(elemSize),
|
||||
m_maxElements(maxElements)
|
||||
{
|
||||
m_pool = (unsigned char*) btAlignedAlloc( static_cast<unsigned int>(m_elemSize*m_maxElements),16);
|
||||
|
||||
unsigned char* p = m_pool;
|
||||
m_firstFree = p;
|
||||
m_freeCount = m_maxElements;
|
||||
int count = m_maxElements;
|
||||
while (--count) {
|
||||
*(void**)p = (p + m_elemSize);
|
||||
p += m_elemSize;
|
||||
}
|
||||
*(void**)p = 0;
|
||||
}
|
||||
|
||||
~btPoolAllocator()
|
||||
{
|
||||
btAlignedFree( m_pool);
|
||||
}
|
||||
|
||||
int getFreeCount() const
|
||||
{
|
||||
return m_freeCount;
|
||||
}
|
||||
|
||||
int getUsedCount() const
|
||||
{
|
||||
return m_maxElements - m_freeCount;
|
||||
}
|
||||
|
||||
int getMaxCount() const
|
||||
{
|
||||
return m_maxElements;
|
||||
}
|
||||
|
||||
void* allocate(int size)
|
||||
{
|
||||
// release mode fix
|
||||
(void)size;
|
||||
btAssert(!size || size<=m_elemSize);
|
||||
btAssert(m_freeCount>0);
|
||||
void* result = m_firstFree;
|
||||
m_firstFree = *(void**)m_firstFree;
|
||||
--m_freeCount;
|
||||
return result;
|
||||
}
|
||||
|
||||
bool validPtr(void* ptr)
|
||||
{
|
||||
if (ptr) {
|
||||
if (((unsigned char*)ptr >= m_pool && (unsigned char*)ptr < m_pool + m_maxElements * m_elemSize))
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void freeMemory(void* ptr)
|
||||
{
|
||||
if (ptr) {
|
||||
btAssert((unsigned char*)ptr >= m_pool && (unsigned char*)ptr < m_pool + m_maxElements * m_elemSize);
|
||||
|
||||
*(void**)ptr = m_firstFree;
|
||||
m_firstFree = ptr;
|
||||
++m_freeCount;
|
||||
}
|
||||
}
|
||||
|
||||
int getElementSize() const
|
||||
{
|
||||
return m_elemSize;
|
||||
}
|
||||
|
||||
unsigned char* getPoolAddress()
|
||||
{
|
||||
return m_pool;
|
||||
}
|
||||
|
||||
const unsigned char* getPoolAddress() const
|
||||
{
|
||||
return m_pool;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
#endif //_BT_POOL_ALLOCATOR_H
|
||||
244
opencl/parallel_primitives/host/btQuadWord.h
Normal file
244
opencl/parallel_primitives/host/btQuadWord.h
Normal file
@@ -0,0 +1,244 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef BT_SIMD_QUADWORD_H
|
||||
#define BT_SIMD_QUADWORD_H
|
||||
|
||||
#include "btScalar.h"
|
||||
#include "btMinMax.h"
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#if defined (__CELLOS_LV2) && defined (__SPU__)
|
||||
#include <altivec.h>
|
||||
#endif
|
||||
|
||||
/**@brief The btQuadWord class is base class for btVector3 and btQuaternion.
|
||||
* Some issues under PS3 Linux with IBM 2.1 SDK, gcc compiler prevent from using aligned quadword.
|
||||
*/
|
||||
#ifndef USE_LIBSPE2
|
||||
ATTRIBUTE_ALIGNED16(class) btQuadWord
|
||||
#else
|
||||
class btQuadWord
|
||||
#endif
|
||||
{
|
||||
protected:
|
||||
|
||||
#if defined (__SPU__) && defined (__CELLOS_LV2__)
|
||||
union {
|
||||
vec_float4 mVec128;
|
||||
btScalar m_floats[4];
|
||||
};
|
||||
public:
|
||||
vec_float4 get128() const
|
||||
{
|
||||
return mVec128;
|
||||
}
|
||||
protected:
|
||||
#else //__CELLOS_LV2__ __SPU__
|
||||
|
||||
#if defined(BT_USE_SSE) || defined(BT_USE_NEON)
|
||||
union {
|
||||
btSimdFloat4 mVec128;
|
||||
btScalar m_floats[4];
|
||||
};
|
||||
public:
|
||||
SIMD_FORCE_INLINE btSimdFloat4 get128() const
|
||||
{
|
||||
return mVec128;
|
||||
}
|
||||
SIMD_FORCE_INLINE void set128(btSimdFloat4 v128)
|
||||
{
|
||||
mVec128 = v128;
|
||||
}
|
||||
#else
|
||||
btScalar m_floats[4];
|
||||
#endif // BT_USE_SSE
|
||||
|
||||
#endif //__CELLOS_LV2__ __SPU__
|
||||
|
||||
public:
|
||||
|
||||
#if defined(BT_USE_SSE) || defined(BT_USE_NEON)
|
||||
|
||||
// Set Vector
|
||||
SIMD_FORCE_INLINE btQuadWord(const btSimdFloat4 vec)
|
||||
{
|
||||
mVec128 = vec;
|
||||
}
|
||||
|
||||
// Copy constructor
|
||||
SIMD_FORCE_INLINE btQuadWord(const btQuadWord& rhs)
|
||||
{
|
||||
mVec128 = rhs.mVec128;
|
||||
}
|
||||
|
||||
// Assignment Operator
|
||||
SIMD_FORCE_INLINE btQuadWord&
|
||||
operator=(const btQuadWord& v)
|
||||
{
|
||||
mVec128 = v.mVec128;
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/**@brief Return the x value */
|
||||
SIMD_FORCE_INLINE const btScalar& getX() const { return m_floats[0]; }
|
||||
/**@brief Return the y value */
|
||||
SIMD_FORCE_INLINE const btScalar& getY() const { return m_floats[1]; }
|
||||
/**@brief Return the z value */
|
||||
SIMD_FORCE_INLINE const btScalar& getZ() const { return m_floats[2]; }
|
||||
/**@brief Set the x value */
|
||||
SIMD_FORCE_INLINE void setX(btScalar _x) { m_floats[0] = _x;};
|
||||
/**@brief Set the y value */
|
||||
SIMD_FORCE_INLINE void setY(btScalar _y) { m_floats[1] = _y;};
|
||||
/**@brief Set the z value */
|
||||
SIMD_FORCE_INLINE void setZ(btScalar _z) { m_floats[2] = _z;};
|
||||
/**@brief Set the w value */
|
||||
SIMD_FORCE_INLINE void setW(btScalar _w) { m_floats[3] = _w;};
|
||||
/**@brief Return the x value */
|
||||
SIMD_FORCE_INLINE const btScalar& x() const { return m_floats[0]; }
|
||||
/**@brief Return the y value */
|
||||
SIMD_FORCE_INLINE const btScalar& y() const { return m_floats[1]; }
|
||||
/**@brief Return the z value */
|
||||
SIMD_FORCE_INLINE const btScalar& z() const { return m_floats[2]; }
|
||||
/**@brief Return the w value */
|
||||
SIMD_FORCE_INLINE const btScalar& w() const { return m_floats[3]; }
|
||||
|
||||
//SIMD_FORCE_INLINE btScalar& operator[](int i) { return (&m_floats[0])[i]; }
|
||||
//SIMD_FORCE_INLINE const btScalar& operator[](int i) const { return (&m_floats[0])[i]; }
|
||||
///operator btScalar*() replaces operator[], using implicit conversion. We added operator != and operator == to avoid pointer comparisons.
|
||||
SIMD_FORCE_INLINE operator btScalar *() { return &m_floats[0]; }
|
||||
SIMD_FORCE_INLINE operator const btScalar *() const { return &m_floats[0]; }
|
||||
|
||||
SIMD_FORCE_INLINE bool operator==(const btQuadWord& other) const
|
||||
{
|
||||
#ifdef BT_USE_SSE
|
||||
return (0xf == _mm_movemask_ps((__m128)_mm_cmpeq_ps(mVec128, other.mVec128)));
|
||||
#else
|
||||
return ((m_floats[3]==other.m_floats[3]) &&
|
||||
(m_floats[2]==other.m_floats[2]) &&
|
||||
(m_floats[1]==other.m_floats[1]) &&
|
||||
(m_floats[0]==other.m_floats[0]));
|
||||
#endif
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE bool operator!=(const btQuadWord& other) const
|
||||
{
|
||||
return !(*this == other);
|
||||
}
|
||||
|
||||
/**@brief Set x,y,z and zero w
|
||||
* @param x Value of x
|
||||
* @param y Value of y
|
||||
* @param z Value of z
|
||||
*/
|
||||
SIMD_FORCE_INLINE void setValue(const btScalar& _x, const btScalar& _y, const btScalar& _z)
|
||||
{
|
||||
m_floats[0]=_x;
|
||||
m_floats[1]=_y;
|
||||
m_floats[2]=_z;
|
||||
m_floats[3] = 0.f;
|
||||
}
|
||||
|
||||
/* void getValue(btScalar *m) const
|
||||
{
|
||||
m[0] = m_floats[0];
|
||||
m[1] = m_floats[1];
|
||||
m[2] = m_floats[2];
|
||||
}
|
||||
*/
|
||||
/**@brief Set the values
|
||||
* @param x Value of x
|
||||
* @param y Value of y
|
||||
* @param z Value of z
|
||||
* @param w Value of w
|
||||
*/
|
||||
SIMD_FORCE_INLINE void setValue(const btScalar& _x, const btScalar& _y, const btScalar& _z,const btScalar& _w)
|
||||
{
|
||||
m_floats[0]=_x;
|
||||
m_floats[1]=_y;
|
||||
m_floats[2]=_z;
|
||||
m_floats[3]=_w;
|
||||
}
|
||||
/**@brief No initialization constructor */
|
||||
SIMD_FORCE_INLINE btQuadWord()
|
||||
// :m_floats[0](btScalar(0.)),m_floats[1](btScalar(0.)),m_floats[2](btScalar(0.)),m_floats[3](btScalar(0.))
|
||||
{
|
||||
}
|
||||
|
||||
/**@brief Three argument constructor (zeros w)
|
||||
* @param x Value of x
|
||||
* @param y Value of y
|
||||
* @param z Value of z
|
||||
*/
|
||||
SIMD_FORCE_INLINE btQuadWord(const btScalar& _x, const btScalar& _y, const btScalar& _z)
|
||||
{
|
||||
m_floats[0] = _x, m_floats[1] = _y, m_floats[2] = _z, m_floats[3] = 0.0f;
|
||||
}
|
||||
|
||||
/**@brief Initializing constructor
|
||||
* @param x Value of x
|
||||
* @param y Value of y
|
||||
* @param z Value of z
|
||||
* @param w Value of w
|
||||
*/
|
||||
SIMD_FORCE_INLINE btQuadWord(const btScalar& _x, const btScalar& _y, const btScalar& _z,const btScalar& _w)
|
||||
{
|
||||
m_floats[0] = _x, m_floats[1] = _y, m_floats[2] = _z, m_floats[3] = _w;
|
||||
}
|
||||
|
||||
/**@brief Set each element to the max of the current values and the values of another btQuadWord
|
||||
* @param other The other btQuadWord to compare with
|
||||
*/
|
||||
SIMD_FORCE_INLINE void setMax(const btQuadWord& other)
|
||||
{
|
||||
#ifdef BT_USE_SSE
|
||||
mVec128 = _mm_max_ps(mVec128, other.mVec128);
|
||||
#elif defined(BT_USE_NEON)
|
||||
mVec128 = vmaxq_f32(mVec128, other.mVec128);
|
||||
#else
|
||||
btSetMax(m_floats[0], other.m_floats[0]);
|
||||
btSetMax(m_floats[1], other.m_floats[1]);
|
||||
btSetMax(m_floats[2], other.m_floats[2]);
|
||||
btSetMax(m_floats[3], other.m_floats[3]);
|
||||
#endif
|
||||
}
|
||||
/**@brief Set each element to the min of the current values and the values of another btQuadWord
|
||||
* @param other The other btQuadWord to compare with
|
||||
*/
|
||||
SIMD_FORCE_INLINE void setMin(const btQuadWord& other)
|
||||
{
|
||||
#ifdef BT_USE_SSE
|
||||
mVec128 = _mm_min_ps(mVec128, other.mVec128);
|
||||
#elif defined(BT_USE_NEON)
|
||||
mVec128 = vminq_f32(mVec128, other.mVec128);
|
||||
#else
|
||||
btSetMin(m_floats[0], other.m_floats[0]);
|
||||
btSetMin(m_floats[1], other.m_floats[1]);
|
||||
btSetMin(m_floats[2], other.m_floats[2]);
|
||||
btSetMin(m_floats[3], other.m_floats[3]);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
||||
};
|
||||
|
||||
#endif //BT_SIMD_QUADWORD_H
|
||||
877
opencl/parallel_primitives/host/btQuaternion.h
Normal file
877
opencl/parallel_primitives/host/btQuaternion.h
Normal file
@@ -0,0 +1,877 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#ifndef BT_SIMD__QUATERNION_H_
|
||||
#define BT_SIMD__QUATERNION_H_
|
||||
|
||||
|
||||
#include "btVector3.h"
|
||||
#include "btQuadWord.h"
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef BT_USE_SSE
|
||||
|
||||
const __m128 ATTRIBUTE_ALIGNED16(vOnes) = {1.0f, 1.0f, 1.0f, 1.0f};
|
||||
|
||||
#endif
|
||||
|
||||
#if defined(BT_USE_SSE) || defined(BT_USE_NEON)
|
||||
|
||||
const btSimdFloat4 ATTRIBUTE_ALIGNED16(vQInv) = {-0.0f, -0.0f, -0.0f, +0.0f};
|
||||
const btSimdFloat4 ATTRIBUTE_ALIGNED16(vPPPM) = {+0.0f, +0.0f, +0.0f, -0.0f};
|
||||
|
||||
#endif
|
||||
|
||||
/**@brief The btQuaternion implements quaternion to perform linear algebra rotations in combination with btMatrix3x3, btVector3 and btTransform. */
|
||||
class btQuaternion : public btQuadWord {
|
||||
public:
|
||||
/**@brief No initialization constructor */
|
||||
btQuaternion() {}
|
||||
|
||||
#if (defined(BT_USE_SSE_IN_API) && defined(BT_USE_SSE))|| defined(BT_USE_NEON)
|
||||
// Set Vector
|
||||
SIMD_FORCE_INLINE btQuaternion(const btSimdFloat4 vec)
|
||||
{
|
||||
mVec128 = vec;
|
||||
}
|
||||
|
||||
// Copy constructor
|
||||
SIMD_FORCE_INLINE btQuaternion(const btQuaternion& rhs)
|
||||
{
|
||||
mVec128 = rhs.mVec128;
|
||||
}
|
||||
|
||||
// Assignment Operator
|
||||
SIMD_FORCE_INLINE btQuaternion&
|
||||
operator=(const btQuaternion& v)
|
||||
{
|
||||
mVec128 = v.mVec128;
|
||||
|
||||
return *this;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
// template <typename btScalar>
|
||||
// explicit Quaternion(const btScalar *v) : Tuple4<btScalar>(v) {}
|
||||
/**@brief Constructor from scalars */
|
||||
btQuaternion(const btScalar& _x, const btScalar& _y, const btScalar& _z, const btScalar& _w)
|
||||
: btQuadWord(_x, _y, _z, _w)
|
||||
{}
|
||||
/**@brief Axis angle Constructor
|
||||
* @param axis The axis which the rotation is around
|
||||
* @param angle The magnitude of the rotation around the angle (Radians) */
|
||||
btQuaternion(const btVector3& _axis, const btScalar& _angle)
|
||||
{
|
||||
setRotation(_axis, _angle);
|
||||
}
|
||||
/**@brief Constructor from Euler angles
|
||||
* @param yaw Angle around Y unless BT_EULER_DEFAULT_ZYX defined then Z
|
||||
* @param pitch Angle around X unless BT_EULER_DEFAULT_ZYX defined then Y
|
||||
* @param roll Angle around Z unless BT_EULER_DEFAULT_ZYX defined then X */
|
||||
btQuaternion(const btScalar& yaw, const btScalar& pitch, const btScalar& roll)
|
||||
{
|
||||
#ifndef BT_EULER_DEFAULT_ZYX
|
||||
setEuler(yaw, pitch, roll);
|
||||
#else
|
||||
setEulerZYX(yaw, pitch, roll);
|
||||
#endif
|
||||
}
|
||||
/**@brief Set the rotation using axis angle notation
|
||||
* @param axis The axis around which to rotate
|
||||
* @param angle The magnitude of the rotation in Radians */
|
||||
void setRotation(const btVector3& axis, const btScalar& _angle)
|
||||
{
|
||||
btScalar d = axis.length();
|
||||
btAssert(d != btScalar(0.0));
|
||||
btScalar s = btSin(_angle * btScalar(0.5)) / d;
|
||||
setValue(axis.x() * s, axis.y() * s, axis.z() * s,
|
||||
btCos(_angle * btScalar(0.5)));
|
||||
}
|
||||
/**@brief Set the quaternion using Euler angles
|
||||
* @param yaw Angle around Y
|
||||
* @param pitch Angle around X
|
||||
* @param roll Angle around Z */
|
||||
void setEuler(const btScalar& yaw, const btScalar& pitch, const btScalar& roll)
|
||||
{
|
||||
btScalar halfYaw = btScalar(yaw) * btScalar(0.5);
|
||||
btScalar halfPitch = btScalar(pitch) * btScalar(0.5);
|
||||
btScalar halfRoll = btScalar(roll) * btScalar(0.5);
|
||||
btScalar cosYaw = btCos(halfYaw);
|
||||
btScalar sinYaw = btSin(halfYaw);
|
||||
btScalar cosPitch = btCos(halfPitch);
|
||||
btScalar sinPitch = btSin(halfPitch);
|
||||
btScalar cosRoll = btCos(halfRoll);
|
||||
btScalar sinRoll = btSin(halfRoll);
|
||||
setValue(cosRoll * sinPitch * cosYaw + sinRoll * cosPitch * sinYaw,
|
||||
cosRoll * cosPitch * sinYaw - sinRoll * sinPitch * cosYaw,
|
||||
sinRoll * cosPitch * cosYaw - cosRoll * sinPitch * sinYaw,
|
||||
cosRoll * cosPitch * cosYaw + sinRoll * sinPitch * sinYaw);
|
||||
}
|
||||
/**@brief Set the quaternion using euler angles
|
||||
* @param yaw Angle around Z
|
||||
* @param pitch Angle around Y
|
||||
* @param roll Angle around X */
|
||||
void setEulerZYX(const btScalar& yaw, const btScalar& pitch, const btScalar& roll)
|
||||
{
|
||||
btScalar halfYaw = btScalar(yaw) * btScalar(0.5);
|
||||
btScalar halfPitch = btScalar(pitch) * btScalar(0.5);
|
||||
btScalar halfRoll = btScalar(roll) * btScalar(0.5);
|
||||
btScalar cosYaw = btCos(halfYaw);
|
||||
btScalar sinYaw = btSin(halfYaw);
|
||||
btScalar cosPitch = btCos(halfPitch);
|
||||
btScalar sinPitch = btSin(halfPitch);
|
||||
btScalar cosRoll = btCos(halfRoll);
|
||||
btScalar sinRoll = btSin(halfRoll);
|
||||
setValue(sinRoll * cosPitch * cosYaw - cosRoll * sinPitch * sinYaw, //x
|
||||
cosRoll * sinPitch * cosYaw + sinRoll * cosPitch * sinYaw, //y
|
||||
cosRoll * cosPitch * sinYaw - sinRoll * sinPitch * cosYaw, //z
|
||||
cosRoll * cosPitch * cosYaw + sinRoll * sinPitch * sinYaw); //formerly yzx
|
||||
}
|
||||
/**@brief Add two quaternions
|
||||
* @param q The quaternion to add to this one */
|
||||
SIMD_FORCE_INLINE btQuaternion& operator+=(const btQuaternion& q)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
mVec128 = _mm_add_ps(mVec128, q.mVec128);
|
||||
#elif defined(BT_USE_NEON)
|
||||
mVec128 = vaddq_f32(mVec128, q.mVec128);
|
||||
#else
|
||||
m_floats[0] += q.x();
|
||||
m_floats[1] += q.y();
|
||||
m_floats[2] += q.z();
|
||||
m_floats[3] += q.m_floats[3];
|
||||
#endif
|
||||
return *this;
|
||||
}
|
||||
|
||||
/**@brief Subtract out a quaternion
|
||||
* @param q The quaternion to subtract from this one */
|
||||
btQuaternion& operator-=(const btQuaternion& q)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
mVec128 = _mm_sub_ps(mVec128, q.mVec128);
|
||||
#elif defined(BT_USE_NEON)
|
||||
mVec128 = vsubq_f32(mVec128, q.mVec128);
|
||||
#else
|
||||
m_floats[0] -= q.x();
|
||||
m_floats[1] -= q.y();
|
||||
m_floats[2] -= q.z();
|
||||
m_floats[3] -= q.m_floats[3];
|
||||
#endif
|
||||
return *this;
|
||||
}
|
||||
|
||||
/**@brief Scale this quaternion
|
||||
* @param s The scalar to scale by */
|
||||
btQuaternion& operator*=(const btScalar& s)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vs = _mm_load_ss(&s); // (S 0 0 0)
|
||||
vs = bt_pshufd_ps(vs, 0); // (S S S S)
|
||||
mVec128 = _mm_mul_ps(mVec128, vs);
|
||||
#elif defined(BT_USE_NEON)
|
||||
mVec128 = vmulq_n_f32(mVec128, s);
|
||||
#else
|
||||
m_floats[0] *= s;
|
||||
m_floats[1] *= s;
|
||||
m_floats[2] *= s;
|
||||
m_floats[3] *= s;
|
||||
#endif
|
||||
return *this;
|
||||
}
|
||||
|
||||
/**@brief Multiply this quaternion by q on the right
|
||||
* @param q The other quaternion
|
||||
* Equivilant to this = this * q */
|
||||
btQuaternion& operator*=(const btQuaternion& q)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vQ2 = q.get128();
|
||||
|
||||
__m128 A1 = bt_pshufd_ps(mVec128, BT_SHUFFLE(0,1,2,0));
|
||||
__m128 B1 = bt_pshufd_ps(vQ2, BT_SHUFFLE(3,3,3,0));
|
||||
|
||||
A1 = A1 * B1;
|
||||
|
||||
__m128 A2 = bt_pshufd_ps(mVec128, BT_SHUFFLE(1,2,0,1));
|
||||
__m128 B2 = bt_pshufd_ps(vQ2, BT_SHUFFLE(2,0,1,1));
|
||||
|
||||
A2 = A2 * B2;
|
||||
|
||||
B1 = bt_pshufd_ps(mVec128, BT_SHUFFLE(2,0,1,2));
|
||||
B2 = bt_pshufd_ps(vQ2, BT_SHUFFLE(1,2,0,2));
|
||||
|
||||
B1 = B1 * B2; // A3 *= B3
|
||||
|
||||
mVec128 = bt_splat_ps(mVec128, 3); // A0
|
||||
mVec128 = mVec128 * vQ2; // A0 * B0
|
||||
|
||||
A1 = A1 + A2; // AB12
|
||||
mVec128 = mVec128 - B1; // AB03 = AB0 - AB3
|
||||
A1 = _mm_xor_ps(A1, vPPPM); // change sign of the last element
|
||||
mVec128 = mVec128+ A1; // AB03 + AB12
|
||||
|
||||
#elif defined(BT_USE_NEON)
|
||||
|
||||
float32x4_t vQ1 = mVec128;
|
||||
float32x4_t vQ2 = q.get128();
|
||||
float32x4_t A0, A1, B1, A2, B2, A3, B3;
|
||||
float32x2_t vQ1zx, vQ2wx, vQ1yz, vQ2zx, vQ2yz, vQ2xz;
|
||||
|
||||
{
|
||||
float32x2x2_t tmp;
|
||||
tmp = vtrn_f32( vget_high_f32(vQ1), vget_low_f32(vQ1) ); // {z x}, {w y}
|
||||
vQ1zx = tmp.val[0];
|
||||
|
||||
tmp = vtrn_f32( vget_high_f32(vQ2), vget_low_f32(vQ2) ); // {z x}, {w y}
|
||||
vQ2zx = tmp.val[0];
|
||||
}
|
||||
vQ2wx = vext_f32(vget_high_f32(vQ2), vget_low_f32(vQ2), 1);
|
||||
|
||||
vQ1yz = vext_f32(vget_low_f32(vQ1), vget_high_f32(vQ1), 1);
|
||||
|
||||
vQ2yz = vext_f32(vget_low_f32(vQ2), vget_high_f32(vQ2), 1);
|
||||
vQ2xz = vext_f32(vQ2zx, vQ2zx, 1);
|
||||
|
||||
A1 = vcombine_f32(vget_low_f32(vQ1), vQ1zx); // X Y z x
|
||||
B1 = vcombine_f32(vdup_lane_f32(vget_high_f32(vQ2), 1), vQ2wx); // W W W X
|
||||
|
||||
A2 = vcombine_f32(vQ1yz, vget_low_f32(vQ1));
|
||||
B2 = vcombine_f32(vQ2zx, vdup_lane_f32(vget_low_f32(vQ2), 1));
|
||||
|
||||
A3 = vcombine_f32(vQ1zx, vQ1yz); // Z X Y Z
|
||||
B3 = vcombine_f32(vQ2yz, vQ2xz); // Y Z x z
|
||||
|
||||
A1 = vmulq_f32(A1, B1);
|
||||
A2 = vmulq_f32(A2, B2);
|
||||
A3 = vmulq_f32(A3, B3); // A3 *= B3
|
||||
A0 = vmulq_lane_f32(vQ2, vget_high_f32(vQ1), 1); // A0 * B0
|
||||
|
||||
A1 = vaddq_f32(A1, A2); // AB12 = AB1 + AB2
|
||||
A0 = vsubq_f32(A0, A3); // AB03 = AB0 - AB3
|
||||
|
||||
// change the sign of the last element
|
||||
A1 = (btSimdFloat4)veorq_s32((int32x4_t)A1, (int32x4_t)vPPPM);
|
||||
A0 = vaddq_f32(A0, A1); // AB03 + AB12
|
||||
|
||||
mVec128 = A0;
|
||||
#else
|
||||
setValue(
|
||||
m_floats[3] * q.x() + m_floats[0] * q.m_floats[3] + m_floats[1] * q.z() - m_floats[2] * q.y(),
|
||||
m_floats[3] * q.y() + m_floats[1] * q.m_floats[3] + m_floats[2] * q.x() - m_floats[0] * q.z(),
|
||||
m_floats[3] * q.z() + m_floats[2] * q.m_floats[3] + m_floats[0] * q.y() - m_floats[1] * q.x(),
|
||||
m_floats[3] * q.m_floats[3] - m_floats[0] * q.x() - m_floats[1] * q.y() - m_floats[2] * q.z());
|
||||
#endif
|
||||
return *this;
|
||||
}
|
||||
/**@brief Return the dot product between this quaternion and another
|
||||
* @param q The other quaternion */
|
||||
btScalar dot(const btQuaternion& q) const
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vd;
|
||||
|
||||
vd = _mm_mul_ps(mVec128, q.mVec128);
|
||||
|
||||
__m128 t = _mm_movehl_ps(vd, vd);
|
||||
vd = _mm_add_ps(vd, t);
|
||||
t = _mm_shuffle_ps(vd, vd, 0x55);
|
||||
vd = _mm_add_ss(vd, t);
|
||||
|
||||
return _mm_cvtss_f32(vd);
|
||||
#elif defined(BT_USE_NEON)
|
||||
float32x4_t vd = vmulq_f32(mVec128, q.mVec128);
|
||||
float32x2_t x = vpadd_f32(vget_low_f32(vd), vget_high_f32(vd));
|
||||
x = vpadd_f32(x, x);
|
||||
return vget_lane_f32(x, 0);
|
||||
#else
|
||||
return m_floats[0] * q.x() +
|
||||
m_floats[1] * q.y() +
|
||||
m_floats[2] * q.z() +
|
||||
m_floats[3] * q.m_floats[3];
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Return the length squared of the quaternion */
|
||||
btScalar length2() const
|
||||
{
|
||||
return dot(*this);
|
||||
}
|
||||
|
||||
/**@brief Return the length of the quaternion */
|
||||
btScalar length() const
|
||||
{
|
||||
return btSqrt(length2());
|
||||
}
|
||||
|
||||
/**@brief Normalize the quaternion
|
||||
* Such that x^2 + y^2 + z^2 +w^2 = 1 */
|
||||
btQuaternion& normalize()
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vd;
|
||||
|
||||
vd = _mm_mul_ps(mVec128, mVec128);
|
||||
|
||||
__m128 t = _mm_movehl_ps(vd, vd);
|
||||
vd = _mm_add_ps(vd, t);
|
||||
t = _mm_shuffle_ps(vd, vd, 0x55);
|
||||
vd = _mm_add_ss(vd, t);
|
||||
|
||||
vd = _mm_sqrt_ss(vd);
|
||||
vd = _mm_div_ss(vOnes, vd);
|
||||
vd = bt_pshufd_ps(vd, 0); // splat
|
||||
mVec128 = _mm_mul_ps(mVec128, vd);
|
||||
|
||||
return *this;
|
||||
#else
|
||||
return *this /= length();
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Return a scaled version of this quaternion
|
||||
* @param s The scale factor */
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
operator*(const btScalar& s) const
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vs = _mm_load_ss(&s); // (S 0 0 0)
|
||||
vs = bt_pshufd_ps(vs, 0x00); // (S S S S)
|
||||
|
||||
return btQuaternion(_mm_mul_ps(mVec128, vs));
|
||||
#elif defined(BT_USE_NEON)
|
||||
return btQuaternion(vmulq_n_f32(mVec128, s));
|
||||
#else
|
||||
return btQuaternion(x() * s, y() * s, z() * s, m_floats[3] * s);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Return an inversely scaled versionof this quaternion
|
||||
* @param s The inverse scale factor */
|
||||
btQuaternion operator/(const btScalar& s) const
|
||||
{
|
||||
btAssert(s != btScalar(0.0));
|
||||
return *this * (btScalar(1.0) / s);
|
||||
}
|
||||
|
||||
/**@brief Inversely scale this quaternion
|
||||
* @param s The scale factor */
|
||||
btQuaternion& operator/=(const btScalar& s)
|
||||
{
|
||||
btAssert(s != btScalar(0.0));
|
||||
return *this *= btScalar(1.0) / s;
|
||||
}
|
||||
|
||||
/**@brief Return a normalized version of this quaternion */
|
||||
btQuaternion normalized() const
|
||||
{
|
||||
return *this / length();
|
||||
}
|
||||
/**@brief Return the angle between this quaternion and the other
|
||||
* @param q The other quaternion */
|
||||
btScalar angle(const btQuaternion& q) const
|
||||
{
|
||||
btScalar s = btSqrt(length2() * q.length2());
|
||||
btAssert(s != btScalar(0.0));
|
||||
return btAcos(dot(q) / s);
|
||||
}
|
||||
/**@brief Return the angle of rotation represented by this quaternion */
|
||||
btScalar getAngle() const
|
||||
{
|
||||
btScalar s = btScalar(2.) * btAcos(m_floats[3]);
|
||||
return s;
|
||||
}
|
||||
|
||||
/**@brief Return the axis of the rotation represented by this quaternion */
|
||||
btVector3 getAxis() const
|
||||
{
|
||||
btScalar s_squared = 1.f-m_floats[3]*m_floats[3];
|
||||
|
||||
if (s_squared < btScalar(10.) * SIMD_EPSILON) //Check for divide by zero
|
||||
return btVector3(1.0, 0.0, 0.0); // Arbitrary
|
||||
btScalar s = 1.f/btSqrt(s_squared);
|
||||
return btVector3(m_floats[0] * s, m_floats[1] * s, m_floats[2] * s);
|
||||
}
|
||||
|
||||
/**@brief Return the inverse of this quaternion */
|
||||
btQuaternion inverse() const
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
return btQuaternion(_mm_xor_ps(mVec128, vQInv));
|
||||
#elif defined(BT_USE_NEON)
|
||||
return btQuaternion((btSimdFloat4)veorq_s32((int32x4_t)mVec128, (int32x4_t)vQInv));
|
||||
#else
|
||||
return btQuaternion(-m_floats[0], -m_floats[1], -m_floats[2], m_floats[3]);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Return the sum of this quaternion and the other
|
||||
* @param q2 The other quaternion */
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
operator+(const btQuaternion& q2) const
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
return btQuaternion(_mm_add_ps(mVec128, q2.mVec128));
|
||||
#elif defined(BT_USE_NEON)
|
||||
return btQuaternion(vaddq_f32(mVec128, q2.mVec128));
|
||||
#else
|
||||
const btQuaternion& q1 = *this;
|
||||
return btQuaternion(q1.x() + q2.x(), q1.y() + q2.y(), q1.z() + q2.z(), q1.m_floats[3] + q2.m_floats[3]);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Return the difference between this quaternion and the other
|
||||
* @param q2 The other quaternion */
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
operator-(const btQuaternion& q2) const
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
return btQuaternion(_mm_sub_ps(mVec128, q2.mVec128));
|
||||
#elif defined(BT_USE_NEON)
|
||||
return btQuaternion(vsubq_f32(mVec128, q2.mVec128));
|
||||
#else
|
||||
const btQuaternion& q1 = *this;
|
||||
return btQuaternion(q1.x() - q2.x(), q1.y() - q2.y(), q1.z() - q2.z(), q1.m_floats[3] - q2.m_floats[3]);
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Return the negative of this quaternion
|
||||
* This simply negates each element */
|
||||
SIMD_FORCE_INLINE btQuaternion operator-() const
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
return btQuaternion(_mm_xor_ps(mVec128, btvMzeroMask));
|
||||
#elif defined(BT_USE_NEON)
|
||||
return btQuaternion((btSimdFloat4)veorq_s32((int32x4_t)mVec128, (int32x4_t)btvMzeroMask) );
|
||||
#else
|
||||
const btQuaternion& q2 = *this;
|
||||
return btQuaternion( - q2.x(), - q2.y(), - q2.z(), - q2.m_floats[3]);
|
||||
#endif
|
||||
}
|
||||
/**@todo document this and it's use */
|
||||
SIMD_FORCE_INLINE btQuaternion farthest( const btQuaternion& qd) const
|
||||
{
|
||||
btQuaternion diff,sum;
|
||||
diff = *this - qd;
|
||||
sum = *this + qd;
|
||||
if( diff.dot(diff) > sum.dot(sum) )
|
||||
return qd;
|
||||
return (-qd);
|
||||
}
|
||||
|
||||
/**@todo document this and it's use */
|
||||
SIMD_FORCE_INLINE btQuaternion nearest( const btQuaternion& qd) const
|
||||
{
|
||||
btQuaternion diff,sum;
|
||||
diff = *this - qd;
|
||||
sum = *this + qd;
|
||||
if( diff.dot(diff) < sum.dot(sum) )
|
||||
return qd;
|
||||
return (-qd);
|
||||
}
|
||||
|
||||
|
||||
/**@brief Return the quaternion which is the result of Spherical Linear Interpolation between this and the other quaternion
|
||||
* @param q The other quaternion to interpolate with
|
||||
* @param t The ratio between this and q to interpolate. If t = 0 the result is this, if t=1 the result is q.
|
||||
* Slerp interpolates assuming constant velocity. */
|
||||
btQuaternion slerp(const btQuaternion& q, const btScalar& t) const
|
||||
{
|
||||
btScalar magnitude = btSqrt(length2() * q.length2());
|
||||
btAssert(magnitude > btScalar(0));
|
||||
|
||||
btScalar product = dot(q) / magnitude;
|
||||
if (btFabs(product) < btScalar(1))
|
||||
{
|
||||
// Take care of long angle case see http://en.wikipedia.org/wiki/Slerp
|
||||
const btScalar sign = (product < 0) ? btScalar(-1) : btScalar(1);
|
||||
|
||||
const btScalar theta = btAcos(sign * product);
|
||||
const btScalar s1 = btSin(sign * t * theta);
|
||||
const btScalar d = btScalar(1.0) / btSin(theta);
|
||||
const btScalar s0 = btSin((btScalar(1.0) - t) * theta);
|
||||
|
||||
return btQuaternion(
|
||||
(m_floats[0] * s0 + q.x() * s1) * d,
|
||||
(m_floats[1] * s0 + q.y() * s1) * d,
|
||||
(m_floats[2] * s0 + q.z() * s1) * d,
|
||||
(m_floats[3] * s0 + q.m_floats[3] * s1) * d);
|
||||
}
|
||||
else
|
||||
{
|
||||
return *this;
|
||||
}
|
||||
}
|
||||
|
||||
static const btQuaternion& getIdentity()
|
||||
{
|
||||
static const btQuaternion identityQuat(btScalar(0.),btScalar(0.),btScalar(0.),btScalar(1.));
|
||||
return identityQuat;
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE const btScalar& getW() const { return m_floats[3]; }
|
||||
|
||||
|
||||
};
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/**@brief Return the product of two quaternions */
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
operator*(const btQuaternion& q1, const btQuaternion& q2)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vQ1 = q1.get128();
|
||||
__m128 vQ2 = q2.get128();
|
||||
__m128 A0, A1, B1, A2, B2;
|
||||
|
||||
A1 = bt_pshufd_ps(vQ1, BT_SHUFFLE(0,1,2,0)); // X Y z x // vtrn
|
||||
B1 = bt_pshufd_ps(vQ2, BT_SHUFFLE(3,3,3,0)); // W W W X // vdup vext
|
||||
|
||||
A1 = A1 * B1;
|
||||
|
||||
A2 = bt_pshufd_ps(vQ1, BT_SHUFFLE(1,2,0,1)); // Y Z X Y // vext
|
||||
B2 = bt_pshufd_ps(vQ2, BT_SHUFFLE(2,0,1,1)); // z x Y Y // vtrn vdup
|
||||
|
||||
A2 = A2 * B2;
|
||||
|
||||
B1 = bt_pshufd_ps(vQ1, BT_SHUFFLE(2,0,1,2)); // z x Y Z // vtrn vext
|
||||
B2 = bt_pshufd_ps(vQ2, BT_SHUFFLE(1,2,0,2)); // Y Z x z // vext vtrn
|
||||
|
||||
B1 = B1 * B2; // A3 *= B3
|
||||
|
||||
A0 = bt_splat_ps(vQ1, 3); // A0
|
||||
A0 = A0 * vQ2; // A0 * B0
|
||||
|
||||
A1 = A1 + A2; // AB12
|
||||
A0 = A0 - B1; // AB03 = AB0 - AB3
|
||||
|
||||
A1 = _mm_xor_ps(A1, vPPPM); // change sign of the last element
|
||||
A0 = A0 + A1; // AB03 + AB12
|
||||
|
||||
return btQuaternion(A0);
|
||||
|
||||
#elif defined(BT_USE_NEON)
|
||||
|
||||
float32x4_t vQ1 = q1.get128();
|
||||
float32x4_t vQ2 = q2.get128();
|
||||
float32x4_t A0, A1, B1, A2, B2, A3, B3;
|
||||
float32x2_t vQ1zx, vQ2wx, vQ1yz, vQ2zx, vQ2yz, vQ2xz;
|
||||
|
||||
{
|
||||
float32x2x2_t tmp;
|
||||
tmp = vtrn_f32( vget_high_f32(vQ1), vget_low_f32(vQ1) ); // {z x}, {w y}
|
||||
vQ1zx = tmp.val[0];
|
||||
|
||||
tmp = vtrn_f32( vget_high_f32(vQ2), vget_low_f32(vQ2) ); // {z x}, {w y}
|
||||
vQ2zx = tmp.val[0];
|
||||
}
|
||||
vQ2wx = vext_f32(vget_high_f32(vQ2), vget_low_f32(vQ2), 1);
|
||||
|
||||
vQ1yz = vext_f32(vget_low_f32(vQ1), vget_high_f32(vQ1), 1);
|
||||
|
||||
vQ2yz = vext_f32(vget_low_f32(vQ2), vget_high_f32(vQ2), 1);
|
||||
vQ2xz = vext_f32(vQ2zx, vQ2zx, 1);
|
||||
|
||||
A1 = vcombine_f32(vget_low_f32(vQ1), vQ1zx); // X Y z x
|
||||
B1 = vcombine_f32(vdup_lane_f32(vget_high_f32(vQ2), 1), vQ2wx); // W W W X
|
||||
|
||||
A2 = vcombine_f32(vQ1yz, vget_low_f32(vQ1));
|
||||
B2 = vcombine_f32(vQ2zx, vdup_lane_f32(vget_low_f32(vQ2), 1));
|
||||
|
||||
A3 = vcombine_f32(vQ1zx, vQ1yz); // Z X Y Z
|
||||
B3 = vcombine_f32(vQ2yz, vQ2xz); // Y Z x z
|
||||
|
||||
A1 = vmulq_f32(A1, B1);
|
||||
A2 = vmulq_f32(A2, B2);
|
||||
A3 = vmulq_f32(A3, B3); // A3 *= B3
|
||||
A0 = vmulq_lane_f32(vQ2, vget_high_f32(vQ1), 1); // A0 * B0
|
||||
|
||||
A1 = vaddq_f32(A1, A2); // AB12 = AB1 + AB2
|
||||
A0 = vsubq_f32(A0, A3); // AB03 = AB0 - AB3
|
||||
|
||||
// change the sign of the last element
|
||||
A1 = (btSimdFloat4)veorq_s32((int32x4_t)A1, (int32x4_t)vPPPM);
|
||||
A0 = vaddq_f32(A0, A1); // AB03 + AB12
|
||||
|
||||
return btQuaternion(A0);
|
||||
|
||||
#else
|
||||
return btQuaternion(
|
||||
q1.w() * q2.x() + q1.x() * q2.w() + q1.y() * q2.z() - q1.z() * q2.y(),
|
||||
q1.w() * q2.y() + q1.y() * q2.w() + q1.z() * q2.x() - q1.x() * q2.z(),
|
||||
q1.w() * q2.z() + q1.z() * q2.w() + q1.x() * q2.y() - q1.y() * q2.x(),
|
||||
q1.w() * q2.w() - q1.x() * q2.x() - q1.y() * q2.y() - q1.z() * q2.z());
|
||||
#endif
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
operator*(const btQuaternion& q, const btVector3& w)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vQ1 = q.get128();
|
||||
__m128 vQ2 = w.get128();
|
||||
__m128 A1, B1, A2, B2, A3, B3;
|
||||
|
||||
A1 = bt_pshufd_ps(vQ1, BT_SHUFFLE(3,3,3,0));
|
||||
B1 = bt_pshufd_ps(vQ2, BT_SHUFFLE(0,1,2,0));
|
||||
|
||||
A1 = A1 * B1;
|
||||
|
||||
A2 = bt_pshufd_ps(vQ1, BT_SHUFFLE(1,2,0,1));
|
||||
B2 = bt_pshufd_ps(vQ2, BT_SHUFFLE(2,0,1,1));
|
||||
|
||||
A2 = A2 * B2;
|
||||
|
||||
A3 = bt_pshufd_ps(vQ1, BT_SHUFFLE(2,0,1,2));
|
||||
B3 = bt_pshufd_ps(vQ2, BT_SHUFFLE(1,2,0,2));
|
||||
|
||||
A3 = A3 * B3; // A3 *= B3
|
||||
|
||||
A1 = A1 + A2; // AB12
|
||||
A1 = _mm_xor_ps(A1, vPPPM); // change sign of the last element
|
||||
A1 = A1 - A3; // AB123 = AB12 - AB3
|
||||
|
||||
return btQuaternion(A1);
|
||||
|
||||
#elif defined(BT_USE_NEON)
|
||||
|
||||
float32x4_t vQ1 = q.get128();
|
||||
float32x4_t vQ2 = w.get128();
|
||||
float32x4_t A1, B1, A2, B2, A3, B3;
|
||||
float32x2_t vQ1wx, vQ2zx, vQ1yz, vQ2yz, vQ1zx, vQ2xz;
|
||||
|
||||
vQ1wx = vext_f32(vget_high_f32(vQ1), vget_low_f32(vQ1), 1);
|
||||
{
|
||||
float32x2x2_t tmp;
|
||||
|
||||
tmp = vtrn_f32( vget_high_f32(vQ2), vget_low_f32(vQ2) ); // {z x}, {w y}
|
||||
vQ2zx = tmp.val[0];
|
||||
|
||||
tmp = vtrn_f32( vget_high_f32(vQ1), vget_low_f32(vQ1) ); // {z x}, {w y}
|
||||
vQ1zx = tmp.val[0];
|
||||
}
|
||||
|
||||
vQ1yz = vext_f32(vget_low_f32(vQ1), vget_high_f32(vQ1), 1);
|
||||
|
||||
vQ2yz = vext_f32(vget_low_f32(vQ2), vget_high_f32(vQ2), 1);
|
||||
vQ2xz = vext_f32(vQ2zx, vQ2zx, 1);
|
||||
|
||||
A1 = vcombine_f32(vdup_lane_f32(vget_high_f32(vQ1), 1), vQ1wx); // W W W X
|
||||
B1 = vcombine_f32(vget_low_f32(vQ2), vQ2zx); // X Y z x
|
||||
|
||||
A2 = vcombine_f32(vQ1yz, vget_low_f32(vQ1));
|
||||
B2 = vcombine_f32(vQ2zx, vdup_lane_f32(vget_low_f32(vQ2), 1));
|
||||
|
||||
A3 = vcombine_f32(vQ1zx, vQ1yz); // Z X Y Z
|
||||
B3 = vcombine_f32(vQ2yz, vQ2xz); // Y Z x z
|
||||
|
||||
A1 = vmulq_f32(A1, B1);
|
||||
A2 = vmulq_f32(A2, B2);
|
||||
A3 = vmulq_f32(A3, B3); // A3 *= B3
|
||||
|
||||
A1 = vaddq_f32(A1, A2); // AB12 = AB1 + AB2
|
||||
|
||||
// change the sign of the last element
|
||||
A1 = (btSimdFloat4)veorq_s32((int32x4_t)A1, (int32x4_t)vPPPM);
|
||||
|
||||
A1 = vsubq_f32(A1, A3); // AB123 = AB12 - AB3
|
||||
|
||||
return btQuaternion(A1);
|
||||
|
||||
#else
|
||||
return btQuaternion(
|
||||
q.w() * w.x() + q.y() * w.z() - q.z() * w.y(),
|
||||
q.w() * w.y() + q.z() * w.x() - q.x() * w.z(),
|
||||
q.w() * w.z() + q.x() * w.y() - q.y() * w.x(),
|
||||
-q.x() * w.x() - q.y() * w.y() - q.z() * w.z());
|
||||
#endif
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
operator*(const btVector3& w, const btQuaternion& q)
|
||||
{
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
__m128 vQ1 = w.get128();
|
||||
__m128 vQ2 = q.get128();
|
||||
__m128 A1, B1, A2, B2, A3, B3;
|
||||
|
||||
A1 = bt_pshufd_ps(vQ1, BT_SHUFFLE(0,1,2,0)); // X Y z x
|
||||
B1 = bt_pshufd_ps(vQ2, BT_SHUFFLE(3,3,3,0)); // W W W X
|
||||
|
||||
A1 = A1 * B1;
|
||||
|
||||
A2 = bt_pshufd_ps(vQ1, BT_SHUFFLE(1,2,0,1));
|
||||
B2 = bt_pshufd_ps(vQ2, BT_SHUFFLE(2,0,1,1));
|
||||
|
||||
A2 = A2 *B2;
|
||||
|
||||
A3 = bt_pshufd_ps(vQ1, BT_SHUFFLE(2,0,1,2));
|
||||
B3 = bt_pshufd_ps(vQ2, BT_SHUFFLE(1,2,0,2));
|
||||
|
||||
A3 = A3 * B3; // A3 *= B3
|
||||
|
||||
A1 = A1 + A2; // AB12
|
||||
A1 = _mm_xor_ps(A1, vPPPM); // change sign of the last element
|
||||
A1 = A1 - A3; // AB123 = AB12 - AB3
|
||||
|
||||
return btQuaternion(A1);
|
||||
|
||||
#elif defined(BT_USE_NEON)
|
||||
|
||||
float32x4_t vQ1 = w.get128();
|
||||
float32x4_t vQ2 = q.get128();
|
||||
float32x4_t A1, B1, A2, B2, A3, B3;
|
||||
float32x2_t vQ1zx, vQ2wx, vQ1yz, vQ2zx, vQ2yz, vQ2xz;
|
||||
|
||||
{
|
||||
float32x2x2_t tmp;
|
||||
|
||||
tmp = vtrn_f32( vget_high_f32(vQ1), vget_low_f32(vQ1) ); // {z x}, {w y}
|
||||
vQ1zx = tmp.val[0];
|
||||
|
||||
tmp = vtrn_f32( vget_high_f32(vQ2), vget_low_f32(vQ2) ); // {z x}, {w y}
|
||||
vQ2zx = tmp.val[0];
|
||||
}
|
||||
vQ2wx = vext_f32(vget_high_f32(vQ2), vget_low_f32(vQ2), 1);
|
||||
|
||||
vQ1yz = vext_f32(vget_low_f32(vQ1), vget_high_f32(vQ1), 1);
|
||||
|
||||
vQ2yz = vext_f32(vget_low_f32(vQ2), vget_high_f32(vQ2), 1);
|
||||
vQ2xz = vext_f32(vQ2zx, vQ2zx, 1);
|
||||
|
||||
A1 = vcombine_f32(vget_low_f32(vQ1), vQ1zx); // X Y z x
|
||||
B1 = vcombine_f32(vdup_lane_f32(vget_high_f32(vQ2), 1), vQ2wx); // W W W X
|
||||
|
||||
A2 = vcombine_f32(vQ1yz, vget_low_f32(vQ1));
|
||||
B2 = vcombine_f32(vQ2zx, vdup_lane_f32(vget_low_f32(vQ2), 1));
|
||||
|
||||
A3 = vcombine_f32(vQ1zx, vQ1yz); // Z X Y Z
|
||||
B3 = vcombine_f32(vQ2yz, vQ2xz); // Y Z x z
|
||||
|
||||
A1 = vmulq_f32(A1, B1);
|
||||
A2 = vmulq_f32(A2, B2);
|
||||
A3 = vmulq_f32(A3, B3); // A3 *= B3
|
||||
|
||||
A1 = vaddq_f32(A1, A2); // AB12 = AB1 + AB2
|
||||
|
||||
// change the sign of the last element
|
||||
A1 = (btSimdFloat4)veorq_s32((int32x4_t)A1, (int32x4_t)vPPPM);
|
||||
|
||||
A1 = vsubq_f32(A1, A3); // AB123 = AB12 - AB3
|
||||
|
||||
return btQuaternion(A1);
|
||||
|
||||
#else
|
||||
return btQuaternion(
|
||||
+w.x() * q.w() + w.y() * q.z() - w.z() * q.y(),
|
||||
+w.y() * q.w() + w.z() * q.x() - w.x() * q.z(),
|
||||
+w.z() * q.w() + w.x() * q.y() - w.y() * q.x(),
|
||||
-w.x() * q.x() - w.y() * q.y() - w.z() * q.z());
|
||||
#endif
|
||||
}
|
||||
|
||||
/**@brief Calculate the dot product between two quaternions */
|
||||
SIMD_FORCE_INLINE btScalar
|
||||
dot(const btQuaternion& q1, const btQuaternion& q2)
|
||||
{
|
||||
return q1.dot(q2);
|
||||
}
|
||||
|
||||
|
||||
/**@brief Return the length of a quaternion */
|
||||
SIMD_FORCE_INLINE btScalar
|
||||
length(const btQuaternion& q)
|
||||
{
|
||||
return q.length();
|
||||
}
|
||||
|
||||
/**@brief Return the angle between two quaternions*/
|
||||
SIMD_FORCE_INLINE btScalar
|
||||
btAngle(const btQuaternion& q1, const btQuaternion& q2)
|
||||
{
|
||||
return q1.angle(q2);
|
||||
}
|
||||
|
||||
/**@brief Return the inverse of a quaternion*/
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
inverse(const btQuaternion& q)
|
||||
{
|
||||
return q.inverse();
|
||||
}
|
||||
|
||||
/**@brief Return the result of spherical linear interpolation betwen two quaternions
|
||||
* @param q1 The first quaternion
|
||||
* @param q2 The second quaternion
|
||||
* @param t The ration between q1 and q2. t = 0 return q1, t=1 returns q2
|
||||
* Slerp assumes constant velocity between positions. */
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
slerp(const btQuaternion& q1, const btQuaternion& q2, const btScalar& t)
|
||||
{
|
||||
return q1.slerp(q2, t);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btVector3
|
||||
quatRotate(const btQuaternion& rotation, const btVector3& v)
|
||||
{
|
||||
btQuaternion q = rotation * v;
|
||||
q *= rotation.inverse();
|
||||
#if defined (BT_USE_SSE_IN_API) && defined (BT_USE_SSE)
|
||||
return btVector3(_mm_and_ps(q.get128(), btvFFF0fMask));
|
||||
#elif defined(BT_USE_NEON)
|
||||
return btVector3((float32x4_t)vandq_s32((int32x4_t)q.get128(), btvFFF0Mask));
|
||||
#else
|
||||
return btVector3(q.getX(),q.getY(),q.getZ());
|
||||
#endif
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
shortestArcQuat(const btVector3& v0, const btVector3& v1) // Game Programming Gems 2.10. make sure v0,v1 are normalized
|
||||
{
|
||||
btVector3 c = v0.cross(v1);
|
||||
btScalar d = v0.dot(v1);
|
||||
|
||||
if (d < -1.0 + SIMD_EPSILON)
|
||||
{
|
||||
btVector3 n,unused;
|
||||
btPlaneSpace1(v0,n,unused);
|
||||
return btQuaternion(n.x(),n.y(),n.z(),0.0f); // just pick any vector that is orthogonal to v0
|
||||
}
|
||||
|
||||
btScalar s = btSqrt((1.0f + d) * 2.0f);
|
||||
btScalar rs = 1.0f / s;
|
||||
|
||||
return btQuaternion(c.getX()*rs,c.getY()*rs,c.getZ()*rs,s * 0.5f);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btQuaternion
|
||||
shortestArcQuatNormalize2(btVector3& v0,btVector3& v1)
|
||||
{
|
||||
v0.normalize();
|
||||
v1.normalize();
|
||||
return shortestArcQuat(v0,v1);
|
||||
}
|
||||
|
||||
#endif //BT_SIMD__QUATERNION_H_
|
||||
|
||||
|
||||
|
||||
42
opencl/parallel_primitives/host/btRandom.h
Normal file
42
opencl/parallel_primitives/host/btRandom.h
Normal file
@@ -0,0 +1,42 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#ifndef BT_GEN_RANDOM_H
|
||||
#define BT_GEN_RANDOM_H
|
||||
|
||||
#ifdef MT19937
|
||||
|
||||
#include <limits.h>
|
||||
#include <mt19937.h>
|
||||
|
||||
#define GEN_RAND_MAX UINT_MAX
|
||||
|
||||
SIMD_FORCE_INLINE void GEN_srand(unsigned int seed) { init_genrand(seed); }
|
||||
SIMD_FORCE_INLINE unsigned int GEN_rand() { return genrand_int32(); }
|
||||
|
||||
#else
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
#define GEN_RAND_MAX RAND_MAX
|
||||
|
||||
SIMD_FORCE_INLINE void GEN_srand(unsigned int seed) { srand(seed); }
|
||||
SIMD_FORCE_INLINE unsigned int GEN_rand() { return rand(); }
|
||||
|
||||
#endif
|
||||
|
||||
#endif //BT_GEN_RANDOM_H
|
||||
|
||||
116
opencl/parallel_primitives/host/btStackAlloc.h
Normal file
116
opencl/parallel_primitives/host/btStackAlloc.h
Normal file
@@ -0,0 +1,116 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
/*
|
||||
StackAlloc extracted from GJK-EPA collision solver by Nathanael Presson
|
||||
Nov.2006
|
||||
*/
|
||||
|
||||
#ifndef BT_STACK_ALLOC
|
||||
#define BT_STACK_ALLOC
|
||||
|
||||
#include "btScalar.h" //for btAssert
|
||||
#include "btAlignedAllocator.h"
|
||||
|
||||
///The btBlock class is an internal structure for the btStackAlloc memory allocator.
|
||||
struct btBlock
|
||||
{
|
||||
btBlock* previous;
|
||||
unsigned char* address;
|
||||
};
|
||||
|
||||
///The StackAlloc class provides some fast stack-based memory allocator (LIFO last-in first-out)
|
||||
class btStackAlloc
|
||||
{
|
||||
public:
|
||||
|
||||
btStackAlloc(unsigned int size) { ctor();create(size); }
|
||||
~btStackAlloc() { destroy(); }
|
||||
|
||||
inline void create(unsigned int size)
|
||||
{
|
||||
destroy();
|
||||
data = (unsigned char*) btAlignedAlloc(size,16);
|
||||
totalsize = size;
|
||||
}
|
||||
inline void destroy()
|
||||
{
|
||||
btAssert(usedsize==0);
|
||||
//Raise(L"StackAlloc is still in use");
|
||||
|
||||
if(usedsize==0)
|
||||
{
|
||||
if(!ischild && data)
|
||||
btAlignedFree(data);
|
||||
|
||||
data = 0;
|
||||
usedsize = 0;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
int getAvailableMemory() const
|
||||
{
|
||||
return static_cast<int>(totalsize - usedsize);
|
||||
}
|
||||
|
||||
unsigned char* allocate(unsigned int size)
|
||||
{
|
||||
const unsigned int nus(usedsize+size);
|
||||
if(nus<totalsize)
|
||||
{
|
||||
usedsize=nus;
|
||||
return(data+(usedsize-size));
|
||||
}
|
||||
btAssert(0);
|
||||
//&& (L"Not enough memory"));
|
||||
|
||||
return(0);
|
||||
}
|
||||
SIMD_FORCE_INLINE btBlock* beginBlock()
|
||||
{
|
||||
btBlock* pb = (btBlock*)allocate(sizeof(btBlock));
|
||||
pb->previous = current;
|
||||
pb->address = data+usedsize;
|
||||
current = pb;
|
||||
return(pb);
|
||||
}
|
||||
SIMD_FORCE_INLINE void endBlock(btBlock* block)
|
||||
{
|
||||
btAssert(block==current);
|
||||
//Raise(L"Unmatched blocks");
|
||||
if(block==current)
|
||||
{
|
||||
current = block->previous;
|
||||
usedsize = (unsigned int)((block->address-data)-sizeof(btBlock));
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
void ctor()
|
||||
{
|
||||
data = 0;
|
||||
totalsize = 0;
|
||||
usedsize = 0;
|
||||
current = 0;
|
||||
ischild = false;
|
||||
}
|
||||
unsigned char* data;
|
||||
unsigned int totalsize;
|
||||
unsigned int usedsize;
|
||||
btBlock* current;
|
||||
bool ischild;
|
||||
};
|
||||
|
||||
#endif //BT_STACK_ALLOC
|
||||
305
opencl/parallel_primitives/host/btTransform.h
Normal file
305
opencl/parallel_primitives/host/btTransform.h
Normal file
@@ -0,0 +1,305 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
|
||||
#ifndef BT_TRANSFORM_H
|
||||
#define BT_TRANSFORM_H
|
||||
|
||||
|
||||
#include "btMatrix3x3.h"
|
||||
|
||||
#ifdef BT_USE_DOUBLE_PRECISION
|
||||
#define btTransformData btTransformDoubleData
|
||||
#else
|
||||
#define btTransformData btTransformFloatData
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
/**@brief The btTransform class supports rigid transforms with only translation and rotation and no scaling/shear.
|
||||
*It can be used in combination with btVector3, btQuaternion and btMatrix3x3 linear algebra classes. */
|
||||
ATTRIBUTE_ALIGNED16(class) btTransform {
|
||||
|
||||
///Storage for the rotation
|
||||
btMatrix3x3 m_basis;
|
||||
///Storage for the translation
|
||||
btVector3 m_origin;
|
||||
|
||||
public:
|
||||
|
||||
/**@brief No initialization constructor */
|
||||
btTransform() {}
|
||||
/**@brief Constructor from btQuaternion (optional btVector3 )
|
||||
* @param q Rotation from quaternion
|
||||
* @param c Translation from Vector (default 0,0,0) */
|
||||
explicit SIMD_FORCE_INLINE btTransform(const btQuaternion& q,
|
||||
const btVector3& c = btVector3(btScalar(0), btScalar(0), btScalar(0)))
|
||||
: m_basis(q),
|
||||
m_origin(c)
|
||||
{}
|
||||
|
||||
/**@brief Constructor from btMatrix3x3 (optional btVector3)
|
||||
* @param b Rotation from Matrix
|
||||
* @param c Translation from Vector default (0,0,0)*/
|
||||
explicit SIMD_FORCE_INLINE btTransform(const btMatrix3x3& b,
|
||||
const btVector3& c = btVector3(btScalar(0), btScalar(0), btScalar(0)))
|
||||
: m_basis(b),
|
||||
m_origin(c)
|
||||
{}
|
||||
/**@brief Copy constructor */
|
||||
SIMD_FORCE_INLINE btTransform (const btTransform& other)
|
||||
: m_basis(other.m_basis),
|
||||
m_origin(other.m_origin)
|
||||
{
|
||||
}
|
||||
/**@brief Assignment Operator */
|
||||
SIMD_FORCE_INLINE btTransform& operator=(const btTransform& other)
|
||||
{
|
||||
m_basis = other.m_basis;
|
||||
m_origin = other.m_origin;
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
||||
/**@brief Set the current transform as the value of the product of two transforms
|
||||
* @param t1 Transform 1
|
||||
* @param t2 Transform 2
|
||||
* This = Transform1 * Transform2 */
|
||||
SIMD_FORCE_INLINE void mult(const btTransform& t1, const btTransform& t2) {
|
||||
m_basis = t1.m_basis * t2.m_basis;
|
||||
m_origin = t1(t2.m_origin);
|
||||
}
|
||||
|
||||
/* void multInverseLeft(const btTransform& t1, const btTransform& t2) {
|
||||
btVector3 v = t2.m_origin - t1.m_origin;
|
||||
m_basis = btMultTransposeLeft(t1.m_basis, t2.m_basis);
|
||||
m_origin = v * t1.m_basis;
|
||||
}
|
||||
*/
|
||||
|
||||
/**@brief Return the transform of the vector */
|
||||
SIMD_FORCE_INLINE btVector3 operator()(const btVector3& x) const
|
||||
{
|
||||
return x.dot3(m_basis[0], m_basis[1], m_basis[2]) + m_origin;
|
||||
}
|
||||
|
||||
/**@brief Return the transform of the vector */
|
||||
SIMD_FORCE_INLINE btVector3 operator*(const btVector3& x) const
|
||||
{
|
||||
return (*this)(x);
|
||||
}
|
||||
|
||||
/**@brief Return the transform of the btQuaternion */
|
||||
SIMD_FORCE_INLINE btQuaternion operator*(const btQuaternion& q) const
|
||||
{
|
||||
return getRotation() * q;
|
||||
}
|
||||
|
||||
/**@brief Return the basis matrix for the rotation */
|
||||
SIMD_FORCE_INLINE btMatrix3x3& getBasis() { return m_basis; }
|
||||
/**@brief Return the basis matrix for the rotation */
|
||||
SIMD_FORCE_INLINE const btMatrix3x3& getBasis() const { return m_basis; }
|
||||
|
||||
/**@brief Return the origin vector translation */
|
||||
SIMD_FORCE_INLINE btVector3& getOrigin() { return m_origin; }
|
||||
/**@brief Return the origin vector translation */
|
||||
SIMD_FORCE_INLINE const btVector3& getOrigin() const { return m_origin; }
|
||||
|
||||
/**@brief Return a quaternion representing the rotation */
|
||||
btQuaternion getRotation() const {
|
||||
btQuaternion q;
|
||||
m_basis.getRotation(q);
|
||||
return q;
|
||||
}
|
||||
|
||||
|
||||
/**@brief Set from an array
|
||||
* @param m A pointer to a 15 element array (12 rotation(row major padded on the right by 1), and 3 translation */
|
||||
void setFromOpenGLMatrix(const btScalar *m)
|
||||
{
|
||||
m_basis.setFromOpenGLSubMatrix(m);
|
||||
m_origin.setValue(m[12],m[13],m[14]);
|
||||
}
|
||||
|
||||
/**@brief Fill an array representation
|
||||
* @param m A pointer to a 15 element array (12 rotation(row major padded on the right by 1), and 3 translation */
|
||||
void getOpenGLMatrix(btScalar *m) const
|
||||
{
|
||||
m_basis.getOpenGLSubMatrix(m);
|
||||
m[12] = m_origin.x();
|
||||
m[13] = m_origin.y();
|
||||
m[14] = m_origin.z();
|
||||
m[15] = btScalar(1.0);
|
||||
}
|
||||
|
||||
/**@brief Set the translational element
|
||||
* @param origin The vector to set the translation to */
|
||||
SIMD_FORCE_INLINE void setOrigin(const btVector3& origin)
|
||||
{
|
||||
m_origin = origin;
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btVector3 invXform(const btVector3& inVec) const;
|
||||
|
||||
|
||||
/**@brief Set the rotational element by btMatrix3x3 */
|
||||
SIMD_FORCE_INLINE void setBasis(const btMatrix3x3& basis)
|
||||
{
|
||||
m_basis = basis;
|
||||
}
|
||||
|
||||
/**@brief Set the rotational element by btQuaternion */
|
||||
SIMD_FORCE_INLINE void setRotation(const btQuaternion& q)
|
||||
{
|
||||
m_basis.setRotation(q);
|
||||
}
|
||||
|
||||
|
||||
/**@brief Set this transformation to the identity */
|
||||
void setIdentity()
|
||||
{
|
||||
m_basis.setIdentity();
|
||||
m_origin.setValue(btScalar(0.0), btScalar(0.0), btScalar(0.0));
|
||||
}
|
||||
|
||||
/**@brief Multiply this Transform by another(this = this * another)
|
||||
* @param t The other transform */
|
||||
btTransform& operator*=(const btTransform& t)
|
||||
{
|
||||
m_origin += m_basis * t.m_origin;
|
||||
m_basis *= t.m_basis;
|
||||
return *this;
|
||||
}
|
||||
|
||||
/**@brief Return the inverse of this transform */
|
||||
btTransform inverse() const
|
||||
{
|
||||
btMatrix3x3 inv = m_basis.transpose();
|
||||
return btTransform(inv, inv * -m_origin);
|
||||
}
|
||||
|
||||
/**@brief Return the inverse of this transform times the other transform
|
||||
* @param t The other transform
|
||||
* return this.inverse() * the other */
|
||||
btTransform inverseTimes(const btTransform& t) const;
|
||||
|
||||
/**@brief Return the product of this transform and the other */
|
||||
btTransform operator*(const btTransform& t) const;
|
||||
|
||||
/**@brief Return an identity transform */
|
||||
static const btTransform& getIdentity()
|
||||
{
|
||||
static const btTransform identityTransform(btMatrix3x3::getIdentity());
|
||||
return identityTransform;
|
||||
}
|
||||
|
||||
void serialize(struct btTransformData& dataOut) const;
|
||||
|
||||
void serializeFloat(struct btTransformFloatData& dataOut) const;
|
||||
|
||||
void deSerialize(const struct btTransformData& dataIn);
|
||||
|
||||
void deSerializeDouble(const struct btTransformDoubleData& dataIn);
|
||||
|
||||
void deSerializeFloat(const struct btTransformFloatData& dataIn);
|
||||
|
||||
};
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE btVector3
|
||||
btTransform::invXform(const btVector3& inVec) const
|
||||
{
|
||||
btVector3 v = inVec - m_origin;
|
||||
return (m_basis.transpose() * v);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btTransform
|
||||
btTransform::inverseTimes(const btTransform& t) const
|
||||
{
|
||||
btVector3 v = t.getOrigin() - m_origin;
|
||||
return btTransform(m_basis.transposeTimes(t.m_basis),
|
||||
v * m_basis);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE btTransform
|
||||
btTransform::operator*(const btTransform& t) const
|
||||
{
|
||||
return btTransform(m_basis * t.m_basis,
|
||||
(*this)(t.m_origin));
|
||||
}
|
||||
|
||||
/**@brief Test if two transforms have all elements equal */
|
||||
SIMD_FORCE_INLINE bool operator==(const btTransform& t1, const btTransform& t2)
|
||||
{
|
||||
return ( t1.getBasis() == t2.getBasis() &&
|
||||
t1.getOrigin() == t2.getOrigin() );
|
||||
}
|
||||
|
||||
|
||||
///for serialization
|
||||
struct btTransformFloatData
|
||||
{
|
||||
btMatrix3x3FloatData m_basis;
|
||||
btVector3FloatData m_origin;
|
||||
};
|
||||
|
||||
struct btTransformDoubleData
|
||||
{
|
||||
btMatrix3x3DoubleData m_basis;
|
||||
btVector3DoubleData m_origin;
|
||||
};
|
||||
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE void btTransform::serialize(btTransformData& dataOut) const
|
||||
{
|
||||
m_basis.serialize(dataOut.m_basis);
|
||||
m_origin.serialize(dataOut.m_origin);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE void btTransform::serializeFloat(btTransformFloatData& dataOut) const
|
||||
{
|
||||
m_basis.serializeFloat(dataOut.m_basis);
|
||||
m_origin.serializeFloat(dataOut.m_origin);
|
||||
}
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE void btTransform::deSerialize(const btTransformData& dataIn)
|
||||
{
|
||||
m_basis.deSerialize(dataIn.m_basis);
|
||||
m_origin.deSerialize(dataIn.m_origin);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE void btTransform::deSerializeFloat(const btTransformFloatData& dataIn)
|
||||
{
|
||||
m_basis.deSerializeFloat(dataIn.m_basis);
|
||||
m_origin.deSerializeFloat(dataIn.m_origin);
|
||||
}
|
||||
|
||||
SIMD_FORCE_INLINE void btTransform::deSerializeDouble(const btTransformDoubleData& dataIn)
|
||||
{
|
||||
m_basis.deSerializeDouble(dataIn.m_basis);
|
||||
m_origin.deSerializeDouble(dataIn.m_origin);
|
||||
}
|
||||
|
||||
|
||||
#endif //BT_TRANSFORM_H
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
228
opencl/parallel_primitives/host/btTransformUtil.h
Normal file
228
opencl/parallel_primitives/host/btTransformUtil.h
Normal file
@@ -0,0 +1,228 @@
|
||||
/*
|
||||
Copyright (c) 2003-2006 Gino van den Bergen / Erwin Coumans http://continuousphysics.com/Bullet/
|
||||
|
||||
This software is provided 'as-is', without any express or implied warranty.
|
||||
In no event will the authors be held liable for any damages arising from the use of this software.
|
||||
Permission is granted to anyone to use this software for any purpose,
|
||||
including commercial applications, and to alter it and redistribute it freely,
|
||||
subject to the following restrictions:
|
||||
|
||||
1. The origin of this software must not be misrepresented; you must not claim that you wrote the original software. If you use this software in a product, an acknowledgment in the product documentation would be appreciated but is not required.
|
||||
2. Altered source versions must be plainly marked as such, and must not be misrepresented as being the original software.
|
||||
3. This notice may not be removed or altered from any source distribution.
|
||||
*/
|
||||
|
||||
|
||||
#ifndef BT_TRANSFORM_UTIL_H
|
||||
#define BT_TRANSFORM_UTIL_H
|
||||
|
||||
#include "btTransform.h"
|
||||
#define ANGULAR_MOTION_THRESHOLD btScalar(0.5)*SIMD_HALF_PI
|
||||
|
||||
|
||||
|
||||
|
||||
SIMD_FORCE_INLINE btVector3 btAabbSupport(const btVector3& halfExtents,const btVector3& supportDir)
|
||||
{
|
||||
return btVector3(supportDir.x() < btScalar(0.0) ? -halfExtents.x() : halfExtents.x(),
|
||||
supportDir.y() < btScalar(0.0) ? -halfExtents.y() : halfExtents.y(),
|
||||
supportDir.z() < btScalar(0.0) ? -halfExtents.z() : halfExtents.z());
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/// Utils related to temporal transforms
|
||||
class btTransformUtil
|
||||
{
|
||||
|
||||
public:
|
||||
|
||||
static void integrateTransform(const btTransform& curTrans,const btVector3& linvel,const btVector3& angvel,btScalar timeStep,btTransform& predictedTransform)
|
||||
{
|
||||
predictedTransform.setOrigin(curTrans.getOrigin() + linvel * timeStep);
|
||||
// #define QUATERNION_DERIVATIVE
|
||||
#ifdef QUATERNION_DERIVATIVE
|
||||
btQuaternion predictedOrn = curTrans.getRotation();
|
||||
predictedOrn += (angvel * predictedOrn) * (timeStep * btScalar(0.5));
|
||||
predictedOrn.normalize();
|
||||
#else
|
||||
//Exponential map
|
||||
//google for "Practical Parameterization of Rotations Using the Exponential Map", F. Sebastian Grassia
|
||||
|
||||
btVector3 axis;
|
||||
btScalar fAngle = angvel.length();
|
||||
//limit the angular motion
|
||||
if (fAngle*timeStep > ANGULAR_MOTION_THRESHOLD)
|
||||
{
|
||||
fAngle = ANGULAR_MOTION_THRESHOLD / timeStep;
|
||||
}
|
||||
|
||||
if ( fAngle < btScalar(0.001) )
|
||||
{
|
||||
// use Taylor's expansions of sync function
|
||||
axis = angvel*( btScalar(0.5)*timeStep-(timeStep*timeStep*timeStep)*(btScalar(0.020833333333))*fAngle*fAngle );
|
||||
}
|
||||
else
|
||||
{
|
||||
// sync(fAngle) = sin(c*fAngle)/t
|
||||
axis = angvel*( btSin(btScalar(0.5)*fAngle*timeStep)/fAngle );
|
||||
}
|
||||
btQuaternion dorn (axis.x(),axis.y(),axis.z(),btCos( fAngle*timeStep*btScalar(0.5) ));
|
||||
btQuaternion orn0 = curTrans.getRotation();
|
||||
|
||||
btQuaternion predictedOrn = dorn * orn0;
|
||||
predictedOrn.normalize();
|
||||
#endif
|
||||
predictedTransform.setRotation(predictedOrn);
|
||||
}
|
||||
|
||||
static void calculateVelocityQuaternion(const btVector3& pos0,const btVector3& pos1,const btQuaternion& orn0,const btQuaternion& orn1,btScalar timeStep,btVector3& linVel,btVector3& angVel)
|
||||
{
|
||||
linVel = (pos1 - pos0) / timeStep;
|
||||
btVector3 axis;
|
||||
btScalar angle;
|
||||
if (orn0 != orn1)
|
||||
{
|
||||
calculateDiffAxisAngleQuaternion(orn0,orn1,axis,angle);
|
||||
angVel = axis * angle / timeStep;
|
||||
} else
|
||||
{
|
||||
angVel.setValue(0,0,0);
|
||||
}
|
||||
}
|
||||
|
||||
static void calculateDiffAxisAngleQuaternion(const btQuaternion& orn0,const btQuaternion& orn1a,btVector3& axis,btScalar& angle)
|
||||
{
|
||||
btQuaternion orn1 = orn0.nearest(orn1a);
|
||||
btQuaternion dorn = orn1 * orn0.inverse();
|
||||
angle = dorn.getAngle();
|
||||
axis = btVector3(dorn.x(),dorn.y(),dorn.z());
|
||||
axis[3] = btScalar(0.);
|
||||
//check for axis length
|
||||
btScalar len = axis.length2();
|
||||
if (len < SIMD_EPSILON*SIMD_EPSILON)
|
||||
axis = btVector3(btScalar(1.),btScalar(0.),btScalar(0.));
|
||||
else
|
||||
axis /= btSqrt(len);
|
||||
}
|
||||
|
||||
static void calculateVelocity(const btTransform& transform0,const btTransform& transform1,btScalar timeStep,btVector3& linVel,btVector3& angVel)
|
||||
{
|
||||
linVel = (transform1.getOrigin() - transform0.getOrigin()) / timeStep;
|
||||
btVector3 axis;
|
||||
btScalar angle;
|
||||
calculateDiffAxisAngle(transform0,transform1,axis,angle);
|
||||
angVel = axis * angle / timeStep;
|
||||
}
|
||||
|
||||
static void calculateDiffAxisAngle(const btTransform& transform0,const btTransform& transform1,btVector3& axis,btScalar& angle)
|
||||
{
|
||||
btMatrix3x3 dmat = transform1.getBasis() * transform0.getBasis().inverse();
|
||||
btQuaternion dorn;
|
||||
dmat.getRotation(dorn);
|
||||
|
||||
///floating point inaccuracy can lead to w component > 1..., which breaks
|
||||
dorn.normalize();
|
||||
|
||||
angle = dorn.getAngle();
|
||||
axis = btVector3(dorn.x(),dorn.y(),dorn.z());
|
||||
axis[3] = btScalar(0.);
|
||||
//check for axis length
|
||||
btScalar len = axis.length2();
|
||||
if (len < SIMD_EPSILON*SIMD_EPSILON)
|
||||
axis = btVector3(btScalar(1.),btScalar(0.),btScalar(0.));
|
||||
else
|
||||
axis /= btSqrt(len);
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
///The btConvexSeparatingDistanceUtil can help speed up convex collision detection
|
||||
///by conservatively updating a cached separating distance/vector instead of re-calculating the closest distance
|
||||
class btConvexSeparatingDistanceUtil
|
||||
{
|
||||
btQuaternion m_ornA;
|
||||
btQuaternion m_ornB;
|
||||
btVector3 m_posA;
|
||||
btVector3 m_posB;
|
||||
|
||||
btVector3 m_separatingNormal;
|
||||
|
||||
btScalar m_boundingRadiusA;
|
||||
btScalar m_boundingRadiusB;
|
||||
btScalar m_separatingDistance;
|
||||
|
||||
public:
|
||||
|
||||
btConvexSeparatingDistanceUtil(btScalar boundingRadiusA,btScalar boundingRadiusB)
|
||||
:m_boundingRadiusA(boundingRadiusA),
|
||||
m_boundingRadiusB(boundingRadiusB),
|
||||
m_separatingDistance(0.f)
|
||||
{
|
||||
}
|
||||
|
||||
btScalar getConservativeSeparatingDistance()
|
||||
{
|
||||
return m_separatingDistance;
|
||||
}
|
||||
|
||||
void updateSeparatingDistance(const btTransform& transA,const btTransform& transB)
|
||||
{
|
||||
const btVector3& toPosA = transA.getOrigin();
|
||||
const btVector3& toPosB = transB.getOrigin();
|
||||
btQuaternion toOrnA = transA.getRotation();
|
||||
btQuaternion toOrnB = transB.getRotation();
|
||||
|
||||
if (m_separatingDistance>0.f)
|
||||
{
|
||||
|
||||
|
||||
btVector3 linVelA,angVelA,linVelB,angVelB;
|
||||
btTransformUtil::calculateVelocityQuaternion(m_posA,toPosA,m_ornA,toOrnA,btScalar(1.),linVelA,angVelA);
|
||||
btTransformUtil::calculateVelocityQuaternion(m_posB,toPosB,m_ornB,toOrnB,btScalar(1.),linVelB,angVelB);
|
||||
btScalar maxAngularProjectedVelocity = angVelA.length() * m_boundingRadiusA + angVelB.length() * m_boundingRadiusB;
|
||||
btVector3 relLinVel = (linVelB-linVelA);
|
||||
btScalar relLinVelocLength = relLinVel.dot(m_separatingNormal);
|
||||
if (relLinVelocLength<0.f)
|
||||
{
|
||||
relLinVelocLength = 0.f;
|
||||
}
|
||||
|
||||
btScalar projectedMotion = maxAngularProjectedVelocity +relLinVelocLength;
|
||||
m_separatingDistance -= projectedMotion;
|
||||
}
|
||||
|
||||
m_posA = toPosA;
|
||||
m_posB = toPosB;
|
||||
m_ornA = toOrnA;
|
||||
m_ornB = toOrnB;
|
||||
}
|
||||
|
||||
void initSeparatingDistance(const btVector3& separatingVector,btScalar separatingDistance,const btTransform& transA,const btTransform& transB)
|
||||
{
|
||||
m_separatingDistance = separatingDistance;
|
||||
|
||||
if (m_separatingDistance>0.f)
|
||||
{
|
||||
m_separatingNormal = separatingVector;
|
||||
|
||||
const btVector3& toPosA = transA.getOrigin();
|
||||
const btVector3& toPosB = transB.getOrigin();
|
||||
btQuaternion toOrnA = transA.getRotation();
|
||||
btQuaternion toOrnB = transB.getRotation();
|
||||
m_posA = toPosA;
|
||||
m_posB = toPosB;
|
||||
m_ornA = toOrnA;
|
||||
m_ornB = toOrnB;
|
||||
}
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
|
||||
#endif //BT_TRANSFORM_UTIL_H
|
||||
|
||||
1631
opencl/parallel_primitives/host/btVector3.cpp
Normal file
1631
opencl/parallel_primitives/host/btVector3.cpp
Normal file
File diff suppressed because it is too large
Load Diff
1343
opencl/parallel_primitives/host/btVector3.h
Normal file
1343
opencl/parallel_primitives/host/btVector3.h
Normal file
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user