fix: some file didn't have the svn:eol-style native yet
This commit is contained in:
@@ -1,112 +1,112 @@
|
||||
#ifndef CONVEX_BUILDER_H
|
||||
#define CONVEX_BUILDER_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
#include "ConvexDecomposition.h"
|
||||
#include "vlookup.h"
|
||||
#include "LinearMath/btAlignedObjectArray.h"
|
||||
|
||||
using namespace ConvexDecomposition;
|
||||
|
||||
|
||||
class CHull
|
||||
{
|
||||
public:
|
||||
CHull(const ConvexResult &result);
|
||||
|
||||
~CHull(void);
|
||||
|
||||
bool overlap(const CHull &h) const;
|
||||
|
||||
float mMin[3];
|
||||
float mMax[3];
|
||||
float mVolume;
|
||||
float mDiagonal; // long edge..
|
||||
ConvexResult *mResult;
|
||||
};
|
||||
|
||||
// Usage: std::sort( list.begin(), list.end(), StringSortRef() );
|
||||
class CHullSort
|
||||
{
|
||||
public:
|
||||
|
||||
inline bool operator()(const CHull *a,const CHull *b) const
|
||||
{
|
||||
return a->mVolume < b->mVolume;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
typedef btAlignedObjectArray< CHull * > CHullVector;
|
||||
|
||||
|
||||
|
||||
class ConvexBuilder : public ConvexDecompInterface
|
||||
{
|
||||
public:
|
||||
ConvexBuilder(ConvexDecompInterface *callback);
|
||||
|
||||
virtual ~ConvexBuilder(void);
|
||||
|
||||
bool isDuplicate(unsigned int i1,unsigned int i2,unsigned int i3,
|
||||
unsigned int ci1,unsigned int ci2,unsigned int ci3);
|
||||
|
||||
void getMesh(const ConvexResult &cr,VertexLookup vc,UintVector &indices);
|
||||
|
||||
CHull * canMerge(CHull *a,CHull *b);
|
||||
|
||||
bool combineHulls(void);
|
||||
|
||||
unsigned int process(const DecompDesc &desc);
|
||||
|
||||
virtual void ConvexDebugTri(const float *p1,const float *p2,const float *p3,unsigned int color);
|
||||
|
||||
virtual void ConvexDebugOBB(const float *sides, const float *matrix,unsigned int color);
|
||||
virtual void ConvexDebugPoint(const float *p,float dist,unsigned int color);
|
||||
|
||||
virtual void ConvexDebugBound(const float *bmin,const float *bmax,unsigned int color);
|
||||
|
||||
virtual void ConvexDecompResult(ConvexResult &result);
|
||||
|
||||
void sortChulls(CHullVector &hulls);
|
||||
|
||||
CHullVector mChulls;
|
||||
ConvexDecompInterface *mCallback;
|
||||
};
|
||||
|
||||
#endif //CONVEX_BUILDER_H
|
||||
|
||||
#ifndef CONVEX_BUILDER_H
|
||||
#define CONVEX_BUILDER_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
#include "ConvexDecomposition.h"
|
||||
#include "vlookup.h"
|
||||
#include "LinearMath/btAlignedObjectArray.h"
|
||||
|
||||
using namespace ConvexDecomposition;
|
||||
|
||||
|
||||
class CHull
|
||||
{
|
||||
public:
|
||||
CHull(const ConvexResult &result);
|
||||
|
||||
~CHull(void);
|
||||
|
||||
bool overlap(const CHull &h) const;
|
||||
|
||||
float mMin[3];
|
||||
float mMax[3];
|
||||
float mVolume;
|
||||
float mDiagonal; // long edge..
|
||||
ConvexResult *mResult;
|
||||
};
|
||||
|
||||
// Usage: std::sort( list.begin(), list.end(), StringSortRef() );
|
||||
class CHullSort
|
||||
{
|
||||
public:
|
||||
|
||||
inline bool operator()(const CHull *a,const CHull *b) const
|
||||
{
|
||||
return a->mVolume < b->mVolume;
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
typedef btAlignedObjectArray< CHull * > CHullVector;
|
||||
|
||||
|
||||
|
||||
class ConvexBuilder : public ConvexDecompInterface
|
||||
{
|
||||
public:
|
||||
ConvexBuilder(ConvexDecompInterface *callback);
|
||||
|
||||
virtual ~ConvexBuilder(void);
|
||||
|
||||
bool isDuplicate(unsigned int i1,unsigned int i2,unsigned int i3,
|
||||
unsigned int ci1,unsigned int ci2,unsigned int ci3);
|
||||
|
||||
void getMesh(const ConvexResult &cr,VertexLookup vc,UintVector &indices);
|
||||
|
||||
CHull * canMerge(CHull *a,CHull *b);
|
||||
|
||||
bool combineHulls(void);
|
||||
|
||||
unsigned int process(const DecompDesc &desc);
|
||||
|
||||
virtual void ConvexDebugTri(const float *p1,const float *p2,const float *p3,unsigned int color);
|
||||
|
||||
virtual void ConvexDebugOBB(const float *sides, const float *matrix,unsigned int color);
|
||||
virtual void ConvexDebugPoint(const float *p,float dist,unsigned int color);
|
||||
|
||||
virtual void ConvexDebugBound(const float *bmin,const float *bmax,unsigned int color);
|
||||
|
||||
virtual void ConvexDecompResult(ConvexResult &result);
|
||||
|
||||
void sortChulls(CHullVector &hulls);
|
||||
|
||||
CHullVector mChulls;
|
||||
ConvexDecompInterface *mCallback;
|
||||
};
|
||||
|
||||
#endif //CONVEX_BUILDER_H
|
||||
|
||||
|
||||
@@ -1,375 +1,375 @@
|
||||
#include "float_math.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
#include "ConvexDecomposition.h"
|
||||
#include "cd_vector.h"
|
||||
#include "cd_hull.h"
|
||||
#include "bestfit.h"
|
||||
#include "planetri.h"
|
||||
#include "vlookup.h"
|
||||
#include "splitplane.h"
|
||||
#include "meshvolume.h"
|
||||
#include "concavity.h"
|
||||
#include "bestfitobb.h"
|
||||
#include "float_math.h"
|
||||
#include "fitsphere.h"
|
||||
|
||||
#define SHOW_MESH 0
|
||||
#define MAKE_MESH 1
|
||||
|
||||
|
||||
using namespace ConvexDecomposition;
|
||||
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class FaceTri
|
||||
{
|
||||
public:
|
||||
FaceTri(void) { };
|
||||
FaceTri(const float *vertices,unsigned int i1,unsigned int i2,unsigned int i3)
|
||||
{
|
||||
mP1.Set( &vertices[i1*3] );
|
||||
mP2.Set( &vertices[i2*3] );
|
||||
mP3.Set( &vertices[i3*3] );
|
||||
}
|
||||
|
||||
Vector3d mP1;
|
||||
Vector3d mP2;
|
||||
Vector3d mP3;
|
||||
Vector3d mNormal;
|
||||
|
||||
};
|
||||
|
||||
|
||||
void addTri(VertexLookup vl,UintVector &list,const Vector3d &p1,const Vector3d &p2,const Vector3d &p3)
|
||||
{
|
||||
unsigned int i1 = Vl_getIndex(vl, p1.Ptr() );
|
||||
unsigned int i2 = Vl_getIndex(vl, p2.Ptr() );
|
||||
unsigned int i3 = Vl_getIndex(vl, p3.Ptr() );
|
||||
|
||||
// do *not* process degenerate triangles!
|
||||
|
||||
if ( i1 != i2 && i1 != i3 && i2 != i3 )
|
||||
{
|
||||
list.push_back(i1);
|
||||
list.push_back(i2);
|
||||
list.push_back(i3);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void calcConvexDecomposition(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float masterVolume,
|
||||
unsigned int depth)
|
||||
|
||||
{
|
||||
|
||||
float plane[4];
|
||||
|
||||
bool split = false;
|
||||
|
||||
|
||||
if ( depth < MAXDEPTH )
|
||||
{
|
||||
|
||||
float volume;
|
||||
float c = computeConcavity( vcount, vertices, tcount, indices, callback, plane, volume );
|
||||
|
||||
if ( depth == 0 )
|
||||
{
|
||||
masterVolume = volume;
|
||||
}
|
||||
|
||||
float percent = (c*100.0f)/masterVolume;
|
||||
|
||||
if ( percent > CONCAVE_PERCENT ) // if great than 5% of the total volume is concave, go ahead and keep splitting.
|
||||
{
|
||||
split = true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if ( depth >= MAXDEPTH || !split )
|
||||
{
|
||||
|
||||
#if 1
|
||||
|
||||
HullResult result;
|
||||
HullLibrary hl;
|
||||
HullDesc desc;
|
||||
|
||||
desc.SetHullFlag(QF_TRIANGLES);
|
||||
|
||||
desc.mVcount = vcount;
|
||||
desc.mVertices = vertices;
|
||||
desc.mVertexStride = sizeof(float)*3;
|
||||
|
||||
HullError ret = hl.CreateConvexHull(desc,result);
|
||||
|
||||
if ( ret == QE_OK )
|
||||
{
|
||||
|
||||
ConvexResult r(result.mNumOutputVertices, result.mOutputVertices, result.mNumFaces, result.mIndices);
|
||||
|
||||
|
||||
callback->ConvexDecompResult(r);
|
||||
}
|
||||
|
||||
|
||||
#else
|
||||
|
||||
static unsigned int colors[8] =
|
||||
{
|
||||
0xFF0000,
|
||||
0x00FF00,
|
||||
0x0000FF,
|
||||
0xFFFF00,
|
||||
0x00FFFF,
|
||||
0xFF00FF,
|
||||
0xFFFFFF,
|
||||
0xFF8040
|
||||
};
|
||||
|
||||
static int count = 0;
|
||||
|
||||
count++;
|
||||
|
||||
if ( count == 8 ) count = 0;
|
||||
|
||||
assert( count >= 0 && count < 8 );
|
||||
|
||||
unsigned int color = colors[count];
|
||||
|
||||
const unsigned int *source = indices;
|
||||
|
||||
for (unsigned int i=0; i<tcount; i++)
|
||||
{
|
||||
|
||||
unsigned int i1 = *source++;
|
||||
unsigned int i2 = *source++;
|
||||
unsigned int i3 = *source++;
|
||||
|
||||
FaceTri t(vertices, i1, i2, i3 );
|
||||
|
||||
callback->ConvexDebugTri( t.mP1.Ptr(), t.mP2.Ptr(), t.mP3.Ptr(), color );
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
hl.ReleaseResult (result);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
UintVector ifront;
|
||||
UintVector iback;
|
||||
|
||||
VertexLookup vfront = Vl_createVertexLookup();
|
||||
VertexLookup vback = Vl_createVertexLookup();
|
||||
|
||||
|
||||
bool showmesh = false;
|
||||
#if SHOW_MESH
|
||||
showmesh = true;
|
||||
#endif
|
||||
|
||||
if ( 0 )
|
||||
{
|
||||
showmesh = true;
|
||||
for (float x=-1; x<1; x+=0.10f)
|
||||
{
|
||||
for (float y=0; y<1; y+=0.10f)
|
||||
{
|
||||
for (float z=-1; z<1; z+=0.04f)
|
||||
{
|
||||
float d = x*plane[0] + y*plane[1] + z*plane[2] + plane[3];
|
||||
Vector3d p(x,y,z);
|
||||
if ( d >= 0 )
|
||||
callback->ConvexDebugPoint(p.Ptr(), 0.02f, 0x00FF00);
|
||||
else
|
||||
callback->ConvexDebugPoint(p.Ptr(), 0.02f, 0xFF0000);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
// ok..now we are going to 'split' all of the input triangles against this plane!
|
||||
const unsigned int *source = indices;
|
||||
for (unsigned int i=0; i<tcount; i++)
|
||||
{
|
||||
unsigned int i1 = *source++;
|
||||
unsigned int i2 = *source++;
|
||||
unsigned int i3 = *source++;
|
||||
|
||||
FaceTri t(vertices, i1, i2, i3 );
|
||||
|
||||
Vector3d front[4];
|
||||
Vector3d back[4];
|
||||
|
||||
unsigned int fcount=0;
|
||||
unsigned int bcount=0;
|
||||
|
||||
PlaneTriResult result;
|
||||
|
||||
result = planeTriIntersection(plane,t.mP1.Ptr(),sizeof(Vector3d),0.00001f,front[0].Ptr(),fcount,back[0].Ptr(),bcount );
|
||||
|
||||
if( fcount > 4 || bcount > 4 )
|
||||
{
|
||||
result = planeTriIntersection(plane,t.mP1.Ptr(),sizeof(Vector3d),0.00001f,front[0].Ptr(),fcount,back[0].Ptr(),bcount );
|
||||
}
|
||||
|
||||
switch ( result )
|
||||
{
|
||||
case PTR_FRONT:
|
||||
|
||||
assert( fcount == 3 );
|
||||
|
||||
if ( showmesh )
|
||||
callback->ConvexDebugTri( front[0].Ptr(), front[1].Ptr(), front[2].Ptr(), 0x00FF00 );
|
||||
|
||||
#if MAKE_MESH
|
||||
|
||||
addTri( vfront, ifront, front[0], front[1], front[2] );
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
break;
|
||||
case PTR_BACK:
|
||||
assert( bcount == 3 );
|
||||
|
||||
if ( showmesh )
|
||||
callback->ConvexDebugTri( back[0].Ptr(), back[1].Ptr(), back[2].Ptr(), 0xFFFF00 );
|
||||
|
||||
#if MAKE_MESH
|
||||
|
||||
addTri( vback, iback, back[0], back[1], back[2] );
|
||||
|
||||
#endif
|
||||
|
||||
break;
|
||||
case PTR_SPLIT:
|
||||
|
||||
assert( fcount >= 3 && fcount <= 4);
|
||||
assert( bcount >= 3 && bcount <= 4);
|
||||
|
||||
#if MAKE_MESH
|
||||
|
||||
addTri( vfront, ifront, front[0], front[1], front[2] );
|
||||
addTri( vback, iback, back[0], back[1], back[2] );
|
||||
|
||||
|
||||
if ( fcount == 4 )
|
||||
{
|
||||
addTri( vfront, ifront, front[0], front[2], front[3] );
|
||||
}
|
||||
|
||||
if ( bcount == 4 )
|
||||
{
|
||||
addTri( vback, iback, back[0], back[2], back[3] );
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
if ( showmesh )
|
||||
{
|
||||
callback->ConvexDebugTri( front[0].Ptr(), front[1].Ptr(), front[2].Ptr(), 0x00D000 );
|
||||
callback->ConvexDebugTri( back[0].Ptr(), back[1].Ptr(), back[2].Ptr(), 0xD0D000 );
|
||||
|
||||
if ( fcount == 4 )
|
||||
{
|
||||
callback->ConvexDebugTri( front[0].Ptr(), front[2].Ptr(), front[3].Ptr(), 0x00D000 );
|
||||
}
|
||||
if ( bcount == 4 )
|
||||
{
|
||||
callback->ConvexDebugTri( back[0].Ptr(), back[2].Ptr(), back[3].Ptr(), 0xD0D000 );
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// ok... here we recursively call
|
||||
if ( ifront.size() )
|
||||
{
|
||||
unsigned int vcount = Vl_getVcount(vfront);
|
||||
const float *vertices = Vl_getVertices(vfront);
|
||||
unsigned int tcount = ifront.size()/3;
|
||||
|
||||
calcConvexDecomposition(vcount, vertices, tcount, &ifront[0], callback, masterVolume, depth+1);
|
||||
|
||||
}
|
||||
|
||||
ifront.clear();
|
||||
|
||||
Vl_releaseVertexLookup(vfront);
|
||||
|
||||
if ( iback.size() )
|
||||
{
|
||||
unsigned int vcount = Vl_getVcount(vback);
|
||||
const float *vertices = Vl_getVertices(vback);
|
||||
unsigned int tcount = iback.size()/3;
|
||||
|
||||
calcConvexDecomposition(vcount, vertices, tcount, &iback[0], callback, masterVolume, depth+1);
|
||||
|
||||
}
|
||||
|
||||
iback.clear();
|
||||
Vl_releaseVertexLookup(vback);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
#include "float_math.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
#include "ConvexDecomposition.h"
|
||||
#include "cd_vector.h"
|
||||
#include "cd_hull.h"
|
||||
#include "bestfit.h"
|
||||
#include "planetri.h"
|
||||
#include "vlookup.h"
|
||||
#include "splitplane.h"
|
||||
#include "meshvolume.h"
|
||||
#include "concavity.h"
|
||||
#include "bestfitobb.h"
|
||||
#include "float_math.h"
|
||||
#include "fitsphere.h"
|
||||
|
||||
#define SHOW_MESH 0
|
||||
#define MAKE_MESH 1
|
||||
|
||||
|
||||
using namespace ConvexDecomposition;
|
||||
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class FaceTri
|
||||
{
|
||||
public:
|
||||
FaceTri(void) { };
|
||||
FaceTri(const float *vertices,unsigned int i1,unsigned int i2,unsigned int i3)
|
||||
{
|
||||
mP1.Set( &vertices[i1*3] );
|
||||
mP2.Set( &vertices[i2*3] );
|
||||
mP3.Set( &vertices[i3*3] );
|
||||
}
|
||||
|
||||
Vector3d mP1;
|
||||
Vector3d mP2;
|
||||
Vector3d mP3;
|
||||
Vector3d mNormal;
|
||||
|
||||
};
|
||||
|
||||
|
||||
void addTri(VertexLookup vl,UintVector &list,const Vector3d &p1,const Vector3d &p2,const Vector3d &p3)
|
||||
{
|
||||
unsigned int i1 = Vl_getIndex(vl, p1.Ptr() );
|
||||
unsigned int i2 = Vl_getIndex(vl, p2.Ptr() );
|
||||
unsigned int i3 = Vl_getIndex(vl, p3.Ptr() );
|
||||
|
||||
// do *not* process degenerate triangles!
|
||||
|
||||
if ( i1 != i2 && i1 != i3 && i2 != i3 )
|
||||
{
|
||||
list.push_back(i1);
|
||||
list.push_back(i2);
|
||||
list.push_back(i3);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void calcConvexDecomposition(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float masterVolume,
|
||||
unsigned int depth)
|
||||
|
||||
{
|
||||
|
||||
float plane[4];
|
||||
|
||||
bool split = false;
|
||||
|
||||
|
||||
if ( depth < MAXDEPTH )
|
||||
{
|
||||
|
||||
float volume;
|
||||
float c = computeConcavity( vcount, vertices, tcount, indices, callback, plane, volume );
|
||||
|
||||
if ( depth == 0 )
|
||||
{
|
||||
masterVolume = volume;
|
||||
}
|
||||
|
||||
float percent = (c*100.0f)/masterVolume;
|
||||
|
||||
if ( percent > CONCAVE_PERCENT ) // if great than 5% of the total volume is concave, go ahead and keep splitting.
|
||||
{
|
||||
split = true;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
if ( depth >= MAXDEPTH || !split )
|
||||
{
|
||||
|
||||
#if 1
|
||||
|
||||
HullResult result;
|
||||
HullLibrary hl;
|
||||
HullDesc desc;
|
||||
|
||||
desc.SetHullFlag(QF_TRIANGLES);
|
||||
|
||||
desc.mVcount = vcount;
|
||||
desc.mVertices = vertices;
|
||||
desc.mVertexStride = sizeof(float)*3;
|
||||
|
||||
HullError ret = hl.CreateConvexHull(desc,result);
|
||||
|
||||
if ( ret == QE_OK )
|
||||
{
|
||||
|
||||
ConvexResult r(result.mNumOutputVertices, result.mOutputVertices, result.mNumFaces, result.mIndices);
|
||||
|
||||
|
||||
callback->ConvexDecompResult(r);
|
||||
}
|
||||
|
||||
|
||||
#else
|
||||
|
||||
static unsigned int colors[8] =
|
||||
{
|
||||
0xFF0000,
|
||||
0x00FF00,
|
||||
0x0000FF,
|
||||
0xFFFF00,
|
||||
0x00FFFF,
|
||||
0xFF00FF,
|
||||
0xFFFFFF,
|
||||
0xFF8040
|
||||
};
|
||||
|
||||
static int count = 0;
|
||||
|
||||
count++;
|
||||
|
||||
if ( count == 8 ) count = 0;
|
||||
|
||||
assert( count >= 0 && count < 8 );
|
||||
|
||||
unsigned int color = colors[count];
|
||||
|
||||
const unsigned int *source = indices;
|
||||
|
||||
for (unsigned int i=0; i<tcount; i++)
|
||||
{
|
||||
|
||||
unsigned int i1 = *source++;
|
||||
unsigned int i2 = *source++;
|
||||
unsigned int i3 = *source++;
|
||||
|
||||
FaceTri t(vertices, i1, i2, i3 );
|
||||
|
||||
callback->ConvexDebugTri( t.mP1.Ptr(), t.mP2.Ptr(), t.mP3.Ptr(), color );
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
hl.ReleaseResult (result);
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
UintVector ifront;
|
||||
UintVector iback;
|
||||
|
||||
VertexLookup vfront = Vl_createVertexLookup();
|
||||
VertexLookup vback = Vl_createVertexLookup();
|
||||
|
||||
|
||||
bool showmesh = false;
|
||||
#if SHOW_MESH
|
||||
showmesh = true;
|
||||
#endif
|
||||
|
||||
if ( 0 )
|
||||
{
|
||||
showmesh = true;
|
||||
for (float x=-1; x<1; x+=0.10f)
|
||||
{
|
||||
for (float y=0; y<1; y+=0.10f)
|
||||
{
|
||||
for (float z=-1; z<1; z+=0.04f)
|
||||
{
|
||||
float d = x*plane[0] + y*plane[1] + z*plane[2] + plane[3];
|
||||
Vector3d p(x,y,z);
|
||||
if ( d >= 0 )
|
||||
callback->ConvexDebugPoint(p.Ptr(), 0.02f, 0x00FF00);
|
||||
else
|
||||
callback->ConvexDebugPoint(p.Ptr(), 0.02f, 0xFF0000);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
// ok..now we are going to 'split' all of the input triangles against this plane!
|
||||
const unsigned int *source = indices;
|
||||
for (unsigned int i=0; i<tcount; i++)
|
||||
{
|
||||
unsigned int i1 = *source++;
|
||||
unsigned int i2 = *source++;
|
||||
unsigned int i3 = *source++;
|
||||
|
||||
FaceTri t(vertices, i1, i2, i3 );
|
||||
|
||||
Vector3d front[4];
|
||||
Vector3d back[4];
|
||||
|
||||
unsigned int fcount=0;
|
||||
unsigned int bcount=0;
|
||||
|
||||
PlaneTriResult result;
|
||||
|
||||
result = planeTriIntersection(plane,t.mP1.Ptr(),sizeof(Vector3d),0.00001f,front[0].Ptr(),fcount,back[0].Ptr(),bcount );
|
||||
|
||||
if( fcount > 4 || bcount > 4 )
|
||||
{
|
||||
result = planeTriIntersection(plane,t.mP1.Ptr(),sizeof(Vector3d),0.00001f,front[0].Ptr(),fcount,back[0].Ptr(),bcount );
|
||||
}
|
||||
|
||||
switch ( result )
|
||||
{
|
||||
case PTR_FRONT:
|
||||
|
||||
assert( fcount == 3 );
|
||||
|
||||
if ( showmesh )
|
||||
callback->ConvexDebugTri( front[0].Ptr(), front[1].Ptr(), front[2].Ptr(), 0x00FF00 );
|
||||
|
||||
#if MAKE_MESH
|
||||
|
||||
addTri( vfront, ifront, front[0], front[1], front[2] );
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
break;
|
||||
case PTR_BACK:
|
||||
assert( bcount == 3 );
|
||||
|
||||
if ( showmesh )
|
||||
callback->ConvexDebugTri( back[0].Ptr(), back[1].Ptr(), back[2].Ptr(), 0xFFFF00 );
|
||||
|
||||
#if MAKE_MESH
|
||||
|
||||
addTri( vback, iback, back[0], back[1], back[2] );
|
||||
|
||||
#endif
|
||||
|
||||
break;
|
||||
case PTR_SPLIT:
|
||||
|
||||
assert( fcount >= 3 && fcount <= 4);
|
||||
assert( bcount >= 3 && bcount <= 4);
|
||||
|
||||
#if MAKE_MESH
|
||||
|
||||
addTri( vfront, ifront, front[0], front[1], front[2] );
|
||||
addTri( vback, iback, back[0], back[1], back[2] );
|
||||
|
||||
|
||||
if ( fcount == 4 )
|
||||
{
|
||||
addTri( vfront, ifront, front[0], front[2], front[3] );
|
||||
}
|
||||
|
||||
if ( bcount == 4 )
|
||||
{
|
||||
addTri( vback, iback, back[0], back[2], back[3] );
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
if ( showmesh )
|
||||
{
|
||||
callback->ConvexDebugTri( front[0].Ptr(), front[1].Ptr(), front[2].Ptr(), 0x00D000 );
|
||||
callback->ConvexDebugTri( back[0].Ptr(), back[1].Ptr(), back[2].Ptr(), 0xD0D000 );
|
||||
|
||||
if ( fcount == 4 )
|
||||
{
|
||||
callback->ConvexDebugTri( front[0].Ptr(), front[2].Ptr(), front[3].Ptr(), 0x00D000 );
|
||||
}
|
||||
if ( bcount == 4 )
|
||||
{
|
||||
callback->ConvexDebugTri( back[0].Ptr(), back[2].Ptr(), back[3].Ptr(), 0xD0D000 );
|
||||
}
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// ok... here we recursively call
|
||||
if ( ifront.size() )
|
||||
{
|
||||
unsigned int vcount = Vl_getVcount(vfront);
|
||||
const float *vertices = Vl_getVertices(vfront);
|
||||
unsigned int tcount = ifront.size()/3;
|
||||
|
||||
calcConvexDecomposition(vcount, vertices, tcount, &ifront[0], callback, masterVolume, depth+1);
|
||||
|
||||
}
|
||||
|
||||
ifront.clear();
|
||||
|
||||
Vl_releaseVertexLookup(vfront);
|
||||
|
||||
if ( iback.size() )
|
||||
{
|
||||
unsigned int vcount = Vl_getVcount(vback);
|
||||
const float *vertices = Vl_getVertices(vback);
|
||||
unsigned int tcount = iback.size()/3;
|
||||
|
||||
calcConvexDecomposition(vcount, vertices, tcount, &iback[0], callback, masterVolume, depth+1);
|
||||
|
||||
}
|
||||
|
||||
iback.clear();
|
||||
Vl_releaseVertexLookup(vback);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -1,466 +1,466 @@
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
// Geometric Tools, Inc.
|
||||
// http://www.geometrictools.com
|
||||
// Copyright (c) 1998-2006. All Rights Reserved
|
||||
//
|
||||
// The Wild Magic Library (WM3) source code is supplied under the terms of
|
||||
// the license agreement
|
||||
// http://www.geometrictools.com/License/WildMagic3License.pdf
|
||||
// and may not be copied or disclosed except in accordance with the terms
|
||||
// of that agreement.
|
||||
|
||||
#include "bestfit.h"
|
||||
|
||||
namespace BestFit
|
||||
{
|
||||
|
||||
class Vec3
|
||||
{
|
||||
public:
|
||||
Vec3(void) { };
|
||||
Vec3(float _x,float _y,float _z) { x = _x; y = _y; z = _z; };
|
||||
|
||||
|
||||
float dot(const Vec3 &v)
|
||||
{
|
||||
return x*v.x + y*v.y + z*v.z; // the dot product
|
||||
}
|
||||
|
||||
float x;
|
||||
float y;
|
||||
float z;
|
||||
};
|
||||
|
||||
|
||||
class Eigen
|
||||
{
|
||||
public:
|
||||
|
||||
|
||||
void DecrSortEigenStuff(void)
|
||||
{
|
||||
Tridiagonal(); //diagonalize the matrix.
|
||||
QLAlgorithm(); //
|
||||
DecreasingSort();
|
||||
GuaranteeRotation();
|
||||
}
|
||||
|
||||
void Tridiagonal(void)
|
||||
{
|
||||
float fM00 = mElement[0][0];
|
||||
float fM01 = mElement[0][1];
|
||||
float fM02 = mElement[0][2];
|
||||
float fM11 = mElement[1][1];
|
||||
float fM12 = mElement[1][2];
|
||||
float fM22 = mElement[2][2];
|
||||
|
||||
m_afDiag[0] = fM00;
|
||||
m_afSubd[2] = 0;
|
||||
if (fM02 != (float)0.0)
|
||||
{
|
||||
float fLength = sqrtf(fM01*fM01+fM02*fM02);
|
||||
float fInvLength = ((float)1.0)/fLength;
|
||||
fM01 *= fInvLength;
|
||||
fM02 *= fInvLength;
|
||||
float fQ = ((float)2.0)*fM01*fM12+fM02*(fM22-fM11);
|
||||
m_afDiag[1] = fM11+fM02*fQ;
|
||||
m_afDiag[2] = fM22-fM02*fQ;
|
||||
m_afSubd[0] = fLength;
|
||||
m_afSubd[1] = fM12-fM01*fQ;
|
||||
mElement[0][0] = (float)1.0;
|
||||
mElement[0][1] = (float)0.0;
|
||||
mElement[0][2] = (float)0.0;
|
||||
mElement[1][0] = (float)0.0;
|
||||
mElement[1][1] = fM01;
|
||||
mElement[1][2] = fM02;
|
||||
mElement[2][0] = (float)0.0;
|
||||
mElement[2][1] = fM02;
|
||||
mElement[2][2] = -fM01;
|
||||
m_bIsRotation = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_afDiag[1] = fM11;
|
||||
m_afDiag[2] = fM22;
|
||||
m_afSubd[0] = fM01;
|
||||
m_afSubd[1] = fM12;
|
||||
mElement[0][0] = (float)1.0;
|
||||
mElement[0][1] = (float)0.0;
|
||||
mElement[0][2] = (float)0.0;
|
||||
mElement[1][0] = (float)0.0;
|
||||
mElement[1][1] = (float)1.0;
|
||||
mElement[1][2] = (float)0.0;
|
||||
mElement[2][0] = (float)0.0;
|
||||
mElement[2][1] = (float)0.0;
|
||||
mElement[2][2] = (float)1.0;
|
||||
m_bIsRotation = true;
|
||||
}
|
||||
}
|
||||
|
||||
bool QLAlgorithm(void)
|
||||
{
|
||||
const int iMaxIter = 32;
|
||||
|
||||
for (int i0 = 0; i0 <3; i0++)
|
||||
{
|
||||
int i1;
|
||||
for (i1 = 0; i1 < iMaxIter; i1++)
|
||||
{
|
||||
int i2;
|
||||
for (i2 = i0; i2 <= (3-2); i2++)
|
||||
{
|
||||
float fTmp = fabsf(m_afDiag[i2]) + fabsf(m_afDiag[i2+1]);
|
||||
if ( fabsf(m_afSubd[i2]) + fTmp == fTmp )
|
||||
break;
|
||||
}
|
||||
if (i2 == i0)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
float fG = (m_afDiag[i0+1] - m_afDiag[i0])/(((float)2.0) * m_afSubd[i0]);
|
||||
float fR = sqrtf(fG*fG+(float)1.0);
|
||||
if (fG < (float)0.0)
|
||||
{
|
||||
fG = m_afDiag[i2]-m_afDiag[i0]+m_afSubd[i0]/(fG-fR);
|
||||
}
|
||||
else
|
||||
{
|
||||
fG = m_afDiag[i2]-m_afDiag[i0]+m_afSubd[i0]/(fG+fR);
|
||||
}
|
||||
float fSin = (float)1.0, fCos = (float)1.0, fP = (float)0.0;
|
||||
for (int i3 = i2-1; i3 >= i0; i3--)
|
||||
{
|
||||
float fF = fSin*m_afSubd[i3];
|
||||
float fB = fCos*m_afSubd[i3];
|
||||
if (fabsf(fF) >= fabsf(fG))
|
||||
{
|
||||
fCos = fG/fF;
|
||||
fR = sqrtf(fCos*fCos+(float)1.0);
|
||||
m_afSubd[i3+1] = fF*fR;
|
||||
fSin = ((float)1.0)/fR;
|
||||
fCos *= fSin;
|
||||
}
|
||||
else
|
||||
{
|
||||
fSin = fF/fG;
|
||||
fR = sqrtf(fSin*fSin+(float)1.0);
|
||||
m_afSubd[i3+1] = fG*fR;
|
||||
fCos = ((float)1.0)/fR;
|
||||
fSin *= fCos;
|
||||
}
|
||||
fG = m_afDiag[i3+1]-fP;
|
||||
fR = (m_afDiag[i3]-fG)*fSin+((float)2.0)*fB*fCos;
|
||||
fP = fSin*fR;
|
||||
m_afDiag[i3+1] = fG+fP;
|
||||
fG = fCos*fR-fB;
|
||||
for (int i4 = 0; i4 < 3; i4++)
|
||||
{
|
||||
fF = mElement[i4][i3+1];
|
||||
mElement[i4][i3+1] = fSin*mElement[i4][i3]+fCos*fF;
|
||||
mElement[i4][i3] = fCos*mElement[i4][i3]-fSin*fF;
|
||||
}
|
||||
}
|
||||
m_afDiag[i0] -= fP;
|
||||
m_afSubd[i0] = fG;
|
||||
m_afSubd[i2] = (float)0.0;
|
||||
}
|
||||
if (i1 == iMaxIter)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void DecreasingSort(void)
|
||||
{
|
||||
//sort eigenvalues in decreasing order, e[0] >= ... >= e[iSize-1]
|
||||
for (int i0 = 0, i1; i0 <= 3-2; i0++)
|
||||
{
|
||||
// locate maximum eigenvalue
|
||||
i1 = i0;
|
||||
float fMax = m_afDiag[i1];
|
||||
int i2;
|
||||
for (i2 = i0+1; i2 < 3; i2++)
|
||||
{
|
||||
if (m_afDiag[i2] > fMax)
|
||||
{
|
||||
i1 = i2;
|
||||
fMax = m_afDiag[i1];
|
||||
}
|
||||
}
|
||||
|
||||
if (i1 != i0)
|
||||
{
|
||||
// swap eigenvalues
|
||||
m_afDiag[i1] = m_afDiag[i0];
|
||||
m_afDiag[i0] = fMax;
|
||||
// swap eigenvectors
|
||||
for (i2 = 0; i2 < 3; i2++)
|
||||
{
|
||||
float fTmp = mElement[i2][i0];
|
||||
mElement[i2][i0] = mElement[i2][i1];
|
||||
mElement[i2][i1] = fTmp;
|
||||
m_bIsRotation = !m_bIsRotation;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void GuaranteeRotation(void)
|
||||
{
|
||||
if (!m_bIsRotation)
|
||||
{
|
||||
// change sign on the first column
|
||||
for (int iRow = 0; iRow <3; iRow++)
|
||||
{
|
||||
mElement[iRow][0] = -mElement[iRow][0];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
float mElement[3][3];
|
||||
float m_afDiag[3];
|
||||
float m_afSubd[3];
|
||||
bool m_bIsRotation;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
|
||||
using namespace BestFit;
|
||||
|
||||
|
||||
bool getBestFitPlane(unsigned int vcount,
|
||||
const float *points,
|
||||
unsigned int vstride,
|
||||
const float *weights,
|
||||
unsigned int wstride,
|
||||
float *plane)
|
||||
{
|
||||
bool ret = false;
|
||||
|
||||
Vec3 kOrigin(0,0,0);
|
||||
|
||||
float wtotal = 0;
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
const char *source = (const char *) points;
|
||||
const char *wsource = (const char *) weights;
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
|
||||
const float *p = (const float *) source;
|
||||
|
||||
float w = 1;
|
||||
|
||||
if ( wsource )
|
||||
{
|
||||
const float *ws = (const float *) wsource;
|
||||
w = *ws; //
|
||||
wsource+=wstride;
|
||||
}
|
||||
|
||||
kOrigin.x+=p[0]*w;
|
||||
kOrigin.y+=p[1]*w;
|
||||
kOrigin.z+=p[2]*w;
|
||||
|
||||
wtotal+=w;
|
||||
|
||||
source+=vstride;
|
||||
}
|
||||
}
|
||||
|
||||
float recip = 1.0f / wtotal; // reciprocol of total weighting
|
||||
|
||||
kOrigin.x*=recip;
|
||||
kOrigin.y*=recip;
|
||||
kOrigin.z*=recip;
|
||||
|
||||
|
||||
float fSumXX=0;
|
||||
float fSumXY=0;
|
||||
float fSumXZ=0;
|
||||
|
||||
float fSumYY=0;
|
||||
float fSumYZ=0;
|
||||
float fSumZZ=0;
|
||||
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
const char *source = (const char *) points;
|
||||
const char *wsource = (const char *) weights;
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
|
||||
const float *p = (const float *) source;
|
||||
|
||||
float w = 1;
|
||||
|
||||
if ( wsource )
|
||||
{
|
||||
const float *ws = (const float *) wsource;
|
||||
w = *ws; //
|
||||
wsource+=wstride;
|
||||
}
|
||||
|
||||
Vec3 kDiff;
|
||||
|
||||
kDiff.x = w*(p[0] - kOrigin.x); // apply vertex weighting!
|
||||
kDiff.y = w*(p[1] - kOrigin.y);
|
||||
kDiff.z = w*(p[2] - kOrigin.z);
|
||||
|
||||
fSumXX+= kDiff.x * kDiff.x; // sume of the squares of the differences.
|
||||
fSumXY+= kDiff.x * kDiff.y; // sume of the squares of the differences.
|
||||
fSumXZ+= kDiff.x * kDiff.z; // sume of the squares of the differences.
|
||||
|
||||
fSumYY+= kDiff.y * kDiff.y;
|
||||
fSumYZ+= kDiff.y * kDiff.z;
|
||||
fSumZZ+= kDiff.z * kDiff.z;
|
||||
|
||||
|
||||
source+=vstride;
|
||||
}
|
||||
}
|
||||
|
||||
fSumXX *= recip;
|
||||
fSumXY *= recip;
|
||||
fSumXZ *= recip;
|
||||
fSumYY *= recip;
|
||||
fSumYZ *= recip;
|
||||
fSumZZ *= recip;
|
||||
|
||||
// setup the eigensolver
|
||||
Eigen kES;
|
||||
|
||||
kES.mElement[0][0] = fSumXX;
|
||||
kES.mElement[0][1] = fSumXY;
|
||||
kES.mElement[0][2] = fSumXZ;
|
||||
|
||||
kES.mElement[1][0] = fSumXY;
|
||||
kES.mElement[1][1] = fSumYY;
|
||||
kES.mElement[1][2] = fSumYZ;
|
||||
|
||||
kES.mElement[2][0] = fSumXZ;
|
||||
kES.mElement[2][1] = fSumYZ;
|
||||
kES.mElement[2][2] = fSumZZ;
|
||||
|
||||
// compute eigenstuff, smallest eigenvalue is in last position
|
||||
kES.DecrSortEigenStuff();
|
||||
|
||||
Vec3 kNormal;
|
||||
|
||||
kNormal.x = kES.mElement[0][2];
|
||||
kNormal.y = kES.mElement[1][2];
|
||||
kNormal.z = kES.mElement[2][2];
|
||||
|
||||
// the minimum energy
|
||||
plane[0] = kNormal.x;
|
||||
plane[1] = kNormal.y;
|
||||
plane[2] = kNormal.z;
|
||||
|
||||
plane[3] = 0 - kNormal.dot(kOrigin);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
float getBoundingRegion(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax) // returns the diagonal distance
|
||||
{
|
||||
|
||||
const unsigned char *source = (const unsigned char *) points;
|
||||
|
||||
bmin[0] = points[0];
|
||||
bmin[1] = points[1];
|
||||
bmin[2] = points[2];
|
||||
|
||||
bmax[0] = points[0];
|
||||
bmax[1] = points[1];
|
||||
bmax[2] = points[2];
|
||||
|
||||
|
||||
for (unsigned int i=1; i<vcount; i++)
|
||||
{
|
||||
source+=pstride;
|
||||
const float *p = (const float *) source;
|
||||
|
||||
if ( p[0] < bmin[0] ) bmin[0] = p[0];
|
||||
if ( p[1] < bmin[1] ) bmin[1] = p[1];
|
||||
if ( p[2] < bmin[2] ) bmin[2] = p[2];
|
||||
|
||||
if ( p[0] > bmax[0] ) bmax[0] = p[0];
|
||||
if ( p[1] > bmax[1] ) bmax[1] = p[1];
|
||||
if ( p[2] > bmax[2] ) bmax[2] = p[2];
|
||||
|
||||
}
|
||||
|
||||
float dx = bmax[0] - bmin[0];
|
||||
float dy = bmax[1] - bmin[1];
|
||||
float dz = bmax[2] - bmin[2];
|
||||
|
||||
return sqrtf( dx*dx + dy*dy + dz*dz );
|
||||
|
||||
}
|
||||
|
||||
|
||||
bool overlapAABB(const float *bmin1,const float *bmax1,const float *bmin2,const float *bmax2) // return true if the two AABB's overlap.
|
||||
{
|
||||
if ( bmax2[0] < bmin1[0] ) return false; // if the maximum is less than our minimum on any axis
|
||||
if ( bmax2[1] < bmin1[1] ) return false;
|
||||
if ( bmax2[2] < bmin1[2] ) return false;
|
||||
|
||||
if ( bmin2[0] > bmax1[0] ) return false; // if the minimum is greater than our maximum on any axis
|
||||
if ( bmin2[1] > bmax1[1] ) return false; // if the minimum is greater than our maximum on any axis
|
||||
if ( bmin2[2] > bmax1[2] ) return false; // if the minimum is greater than our maximum on any axis
|
||||
|
||||
|
||||
return true; // the extents overlap
|
||||
}
|
||||
|
||||
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
// Geometric Tools, Inc.
|
||||
// http://www.geometrictools.com
|
||||
// Copyright (c) 1998-2006. All Rights Reserved
|
||||
//
|
||||
// The Wild Magic Library (WM3) source code is supplied under the terms of
|
||||
// the license agreement
|
||||
// http://www.geometrictools.com/License/WildMagic3License.pdf
|
||||
// and may not be copied or disclosed except in accordance with the terms
|
||||
// of that agreement.
|
||||
|
||||
#include "bestfit.h"
|
||||
|
||||
namespace BestFit
|
||||
{
|
||||
|
||||
class Vec3
|
||||
{
|
||||
public:
|
||||
Vec3(void) { };
|
||||
Vec3(float _x,float _y,float _z) { x = _x; y = _y; z = _z; };
|
||||
|
||||
|
||||
float dot(const Vec3 &v)
|
||||
{
|
||||
return x*v.x + y*v.y + z*v.z; // the dot product
|
||||
}
|
||||
|
||||
float x;
|
||||
float y;
|
||||
float z;
|
||||
};
|
||||
|
||||
|
||||
class Eigen
|
||||
{
|
||||
public:
|
||||
|
||||
|
||||
void DecrSortEigenStuff(void)
|
||||
{
|
||||
Tridiagonal(); //diagonalize the matrix.
|
||||
QLAlgorithm(); //
|
||||
DecreasingSort();
|
||||
GuaranteeRotation();
|
||||
}
|
||||
|
||||
void Tridiagonal(void)
|
||||
{
|
||||
float fM00 = mElement[0][0];
|
||||
float fM01 = mElement[0][1];
|
||||
float fM02 = mElement[0][2];
|
||||
float fM11 = mElement[1][1];
|
||||
float fM12 = mElement[1][2];
|
||||
float fM22 = mElement[2][2];
|
||||
|
||||
m_afDiag[0] = fM00;
|
||||
m_afSubd[2] = 0;
|
||||
if (fM02 != (float)0.0)
|
||||
{
|
||||
float fLength = sqrtf(fM01*fM01+fM02*fM02);
|
||||
float fInvLength = ((float)1.0)/fLength;
|
||||
fM01 *= fInvLength;
|
||||
fM02 *= fInvLength;
|
||||
float fQ = ((float)2.0)*fM01*fM12+fM02*(fM22-fM11);
|
||||
m_afDiag[1] = fM11+fM02*fQ;
|
||||
m_afDiag[2] = fM22-fM02*fQ;
|
||||
m_afSubd[0] = fLength;
|
||||
m_afSubd[1] = fM12-fM01*fQ;
|
||||
mElement[0][0] = (float)1.0;
|
||||
mElement[0][1] = (float)0.0;
|
||||
mElement[0][2] = (float)0.0;
|
||||
mElement[1][0] = (float)0.0;
|
||||
mElement[1][1] = fM01;
|
||||
mElement[1][2] = fM02;
|
||||
mElement[2][0] = (float)0.0;
|
||||
mElement[2][1] = fM02;
|
||||
mElement[2][2] = -fM01;
|
||||
m_bIsRotation = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
m_afDiag[1] = fM11;
|
||||
m_afDiag[2] = fM22;
|
||||
m_afSubd[0] = fM01;
|
||||
m_afSubd[1] = fM12;
|
||||
mElement[0][0] = (float)1.0;
|
||||
mElement[0][1] = (float)0.0;
|
||||
mElement[0][2] = (float)0.0;
|
||||
mElement[1][0] = (float)0.0;
|
||||
mElement[1][1] = (float)1.0;
|
||||
mElement[1][2] = (float)0.0;
|
||||
mElement[2][0] = (float)0.0;
|
||||
mElement[2][1] = (float)0.0;
|
||||
mElement[2][2] = (float)1.0;
|
||||
m_bIsRotation = true;
|
||||
}
|
||||
}
|
||||
|
||||
bool QLAlgorithm(void)
|
||||
{
|
||||
const int iMaxIter = 32;
|
||||
|
||||
for (int i0 = 0; i0 <3; i0++)
|
||||
{
|
||||
int i1;
|
||||
for (i1 = 0; i1 < iMaxIter; i1++)
|
||||
{
|
||||
int i2;
|
||||
for (i2 = i0; i2 <= (3-2); i2++)
|
||||
{
|
||||
float fTmp = fabsf(m_afDiag[i2]) + fabsf(m_afDiag[i2+1]);
|
||||
if ( fabsf(m_afSubd[i2]) + fTmp == fTmp )
|
||||
break;
|
||||
}
|
||||
if (i2 == i0)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
float fG = (m_afDiag[i0+1] - m_afDiag[i0])/(((float)2.0) * m_afSubd[i0]);
|
||||
float fR = sqrtf(fG*fG+(float)1.0);
|
||||
if (fG < (float)0.0)
|
||||
{
|
||||
fG = m_afDiag[i2]-m_afDiag[i0]+m_afSubd[i0]/(fG-fR);
|
||||
}
|
||||
else
|
||||
{
|
||||
fG = m_afDiag[i2]-m_afDiag[i0]+m_afSubd[i0]/(fG+fR);
|
||||
}
|
||||
float fSin = (float)1.0, fCos = (float)1.0, fP = (float)0.0;
|
||||
for (int i3 = i2-1; i3 >= i0; i3--)
|
||||
{
|
||||
float fF = fSin*m_afSubd[i3];
|
||||
float fB = fCos*m_afSubd[i3];
|
||||
if (fabsf(fF) >= fabsf(fG))
|
||||
{
|
||||
fCos = fG/fF;
|
||||
fR = sqrtf(fCos*fCos+(float)1.0);
|
||||
m_afSubd[i3+1] = fF*fR;
|
||||
fSin = ((float)1.0)/fR;
|
||||
fCos *= fSin;
|
||||
}
|
||||
else
|
||||
{
|
||||
fSin = fF/fG;
|
||||
fR = sqrtf(fSin*fSin+(float)1.0);
|
||||
m_afSubd[i3+1] = fG*fR;
|
||||
fCos = ((float)1.0)/fR;
|
||||
fSin *= fCos;
|
||||
}
|
||||
fG = m_afDiag[i3+1]-fP;
|
||||
fR = (m_afDiag[i3]-fG)*fSin+((float)2.0)*fB*fCos;
|
||||
fP = fSin*fR;
|
||||
m_afDiag[i3+1] = fG+fP;
|
||||
fG = fCos*fR-fB;
|
||||
for (int i4 = 0; i4 < 3; i4++)
|
||||
{
|
||||
fF = mElement[i4][i3+1];
|
||||
mElement[i4][i3+1] = fSin*mElement[i4][i3]+fCos*fF;
|
||||
mElement[i4][i3] = fCos*mElement[i4][i3]-fSin*fF;
|
||||
}
|
||||
}
|
||||
m_afDiag[i0] -= fP;
|
||||
m_afSubd[i0] = fG;
|
||||
m_afSubd[i2] = (float)0.0;
|
||||
}
|
||||
if (i1 == iMaxIter)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void DecreasingSort(void)
|
||||
{
|
||||
//sort eigenvalues in decreasing order, e[0] >= ... >= e[iSize-1]
|
||||
for (int i0 = 0, i1; i0 <= 3-2; i0++)
|
||||
{
|
||||
// locate maximum eigenvalue
|
||||
i1 = i0;
|
||||
float fMax = m_afDiag[i1];
|
||||
int i2;
|
||||
for (i2 = i0+1; i2 < 3; i2++)
|
||||
{
|
||||
if (m_afDiag[i2] > fMax)
|
||||
{
|
||||
i1 = i2;
|
||||
fMax = m_afDiag[i1];
|
||||
}
|
||||
}
|
||||
|
||||
if (i1 != i0)
|
||||
{
|
||||
// swap eigenvalues
|
||||
m_afDiag[i1] = m_afDiag[i0];
|
||||
m_afDiag[i0] = fMax;
|
||||
// swap eigenvectors
|
||||
for (i2 = 0; i2 < 3; i2++)
|
||||
{
|
||||
float fTmp = mElement[i2][i0];
|
||||
mElement[i2][i0] = mElement[i2][i1];
|
||||
mElement[i2][i1] = fTmp;
|
||||
m_bIsRotation = !m_bIsRotation;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void GuaranteeRotation(void)
|
||||
{
|
||||
if (!m_bIsRotation)
|
||||
{
|
||||
// change sign on the first column
|
||||
for (int iRow = 0; iRow <3; iRow++)
|
||||
{
|
||||
mElement[iRow][0] = -mElement[iRow][0];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
float mElement[3][3];
|
||||
float m_afDiag[3];
|
||||
float m_afSubd[3];
|
||||
bool m_bIsRotation;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
|
||||
using namespace BestFit;
|
||||
|
||||
|
||||
bool getBestFitPlane(unsigned int vcount,
|
||||
const float *points,
|
||||
unsigned int vstride,
|
||||
const float *weights,
|
||||
unsigned int wstride,
|
||||
float *plane)
|
||||
{
|
||||
bool ret = false;
|
||||
|
||||
Vec3 kOrigin(0,0,0);
|
||||
|
||||
float wtotal = 0;
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
const char *source = (const char *) points;
|
||||
const char *wsource = (const char *) weights;
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
|
||||
const float *p = (const float *) source;
|
||||
|
||||
float w = 1;
|
||||
|
||||
if ( wsource )
|
||||
{
|
||||
const float *ws = (const float *) wsource;
|
||||
w = *ws; //
|
||||
wsource+=wstride;
|
||||
}
|
||||
|
||||
kOrigin.x+=p[0]*w;
|
||||
kOrigin.y+=p[1]*w;
|
||||
kOrigin.z+=p[2]*w;
|
||||
|
||||
wtotal+=w;
|
||||
|
||||
source+=vstride;
|
||||
}
|
||||
}
|
||||
|
||||
float recip = 1.0f / wtotal; // reciprocol of total weighting
|
||||
|
||||
kOrigin.x*=recip;
|
||||
kOrigin.y*=recip;
|
||||
kOrigin.z*=recip;
|
||||
|
||||
|
||||
float fSumXX=0;
|
||||
float fSumXY=0;
|
||||
float fSumXZ=0;
|
||||
|
||||
float fSumYY=0;
|
||||
float fSumYZ=0;
|
||||
float fSumZZ=0;
|
||||
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
const char *source = (const char *) points;
|
||||
const char *wsource = (const char *) weights;
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
|
||||
const float *p = (const float *) source;
|
||||
|
||||
float w = 1;
|
||||
|
||||
if ( wsource )
|
||||
{
|
||||
const float *ws = (const float *) wsource;
|
||||
w = *ws; //
|
||||
wsource+=wstride;
|
||||
}
|
||||
|
||||
Vec3 kDiff;
|
||||
|
||||
kDiff.x = w*(p[0] - kOrigin.x); // apply vertex weighting!
|
||||
kDiff.y = w*(p[1] - kOrigin.y);
|
||||
kDiff.z = w*(p[2] - kOrigin.z);
|
||||
|
||||
fSumXX+= kDiff.x * kDiff.x; // sume of the squares of the differences.
|
||||
fSumXY+= kDiff.x * kDiff.y; // sume of the squares of the differences.
|
||||
fSumXZ+= kDiff.x * kDiff.z; // sume of the squares of the differences.
|
||||
|
||||
fSumYY+= kDiff.y * kDiff.y;
|
||||
fSumYZ+= kDiff.y * kDiff.z;
|
||||
fSumZZ+= kDiff.z * kDiff.z;
|
||||
|
||||
|
||||
source+=vstride;
|
||||
}
|
||||
}
|
||||
|
||||
fSumXX *= recip;
|
||||
fSumXY *= recip;
|
||||
fSumXZ *= recip;
|
||||
fSumYY *= recip;
|
||||
fSumYZ *= recip;
|
||||
fSumZZ *= recip;
|
||||
|
||||
// setup the eigensolver
|
||||
Eigen kES;
|
||||
|
||||
kES.mElement[0][0] = fSumXX;
|
||||
kES.mElement[0][1] = fSumXY;
|
||||
kES.mElement[0][2] = fSumXZ;
|
||||
|
||||
kES.mElement[1][0] = fSumXY;
|
||||
kES.mElement[1][1] = fSumYY;
|
||||
kES.mElement[1][2] = fSumYZ;
|
||||
|
||||
kES.mElement[2][0] = fSumXZ;
|
||||
kES.mElement[2][1] = fSumYZ;
|
||||
kES.mElement[2][2] = fSumZZ;
|
||||
|
||||
// compute eigenstuff, smallest eigenvalue is in last position
|
||||
kES.DecrSortEigenStuff();
|
||||
|
||||
Vec3 kNormal;
|
||||
|
||||
kNormal.x = kES.mElement[0][2];
|
||||
kNormal.y = kES.mElement[1][2];
|
||||
kNormal.z = kES.mElement[2][2];
|
||||
|
||||
// the minimum energy
|
||||
plane[0] = kNormal.x;
|
||||
plane[1] = kNormal.y;
|
||||
plane[2] = kNormal.z;
|
||||
|
||||
plane[3] = 0 - kNormal.dot(kOrigin);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
float getBoundingRegion(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax) // returns the diagonal distance
|
||||
{
|
||||
|
||||
const unsigned char *source = (const unsigned char *) points;
|
||||
|
||||
bmin[0] = points[0];
|
||||
bmin[1] = points[1];
|
||||
bmin[2] = points[2];
|
||||
|
||||
bmax[0] = points[0];
|
||||
bmax[1] = points[1];
|
||||
bmax[2] = points[2];
|
||||
|
||||
|
||||
for (unsigned int i=1; i<vcount; i++)
|
||||
{
|
||||
source+=pstride;
|
||||
const float *p = (const float *) source;
|
||||
|
||||
if ( p[0] < bmin[0] ) bmin[0] = p[0];
|
||||
if ( p[1] < bmin[1] ) bmin[1] = p[1];
|
||||
if ( p[2] < bmin[2] ) bmin[2] = p[2];
|
||||
|
||||
if ( p[0] > bmax[0] ) bmax[0] = p[0];
|
||||
if ( p[1] > bmax[1] ) bmax[1] = p[1];
|
||||
if ( p[2] > bmax[2] ) bmax[2] = p[2];
|
||||
|
||||
}
|
||||
|
||||
float dx = bmax[0] - bmin[0];
|
||||
float dy = bmax[1] - bmin[1];
|
||||
float dz = bmax[2] - bmin[2];
|
||||
|
||||
return sqrtf( dx*dx + dy*dy + dz*dz );
|
||||
|
||||
}
|
||||
|
||||
|
||||
bool overlapAABB(const float *bmin1,const float *bmax1,const float *bmin2,const float *bmax2) // return true if the two AABB's overlap.
|
||||
{
|
||||
if ( bmax2[0] < bmin1[0] ) return false; // if the maximum is less than our minimum on any axis
|
||||
if ( bmax2[1] < bmin1[1] ) return false;
|
||||
if ( bmax2[2] < bmin1[2] ) return false;
|
||||
|
||||
if ( bmin2[0] > bmax1[0] ) return false; // if the minimum is greater than our maximum on any axis
|
||||
if ( bmin2[1] > bmax1[1] ) return false; // if the minimum is greater than our maximum on any axis
|
||||
if ( bmin2[2] > bmax1[2] ) return false; // if the minimum is greater than our maximum on any axis
|
||||
|
||||
|
||||
return true; // the extents overlap
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -1,65 +1,65 @@
|
||||
#ifndef BEST_FIT_H
|
||||
|
||||
#define BEST_FIT_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
// This routine was released in 'snippet' form
|
||||
// by John W. Ratcliff mailto:jratcliff@infiniplex.net
|
||||
// on March 22, 2006.
|
||||
//
|
||||
// This routine computes the 'best fit' plane equation to
|
||||
// a set of input data points with an optional per vertex
|
||||
// weighting component.
|
||||
//
|
||||
// The implementation for this was lifted directly from
|
||||
// David Eberly's Magic Software implementation.
|
||||
|
||||
// computes the best fit plane to a collection of data points.
|
||||
// returns the plane equation as A,B,C,D format. (Ax+By+Cz+D)
|
||||
|
||||
bool getBestFitPlane(unsigned int vcount, // number of input data points
|
||||
const float *points, // starting address of points array.
|
||||
unsigned int vstride, // stride between input points.
|
||||
const float *weights, // *optional point weighting values.
|
||||
unsigned int wstride, // weight stride for each vertex.
|
||||
float *plane);
|
||||
|
||||
|
||||
float getBoundingRegion(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax); // returns the diagonal distance
|
||||
bool overlapAABB(const float *bmin1,const float *bmax1,const float *bmin2,const float *bmax2); // return true if the two AABB's overlap.
|
||||
|
||||
#endif
|
||||
#ifndef BEST_FIT_H
|
||||
|
||||
#define BEST_FIT_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
// This routine was released in 'snippet' form
|
||||
// by John W. Ratcliff mailto:jratcliff@infiniplex.net
|
||||
// on March 22, 2006.
|
||||
//
|
||||
// This routine computes the 'best fit' plane equation to
|
||||
// a set of input data points with an optional per vertex
|
||||
// weighting component.
|
||||
//
|
||||
// The implementation for this was lifted directly from
|
||||
// David Eberly's Magic Software implementation.
|
||||
|
||||
// computes the best fit plane to a collection of data points.
|
||||
// returns the plane equation as A,B,C,D format. (Ax+By+Cz+D)
|
||||
|
||||
bool getBestFitPlane(unsigned int vcount, // number of input data points
|
||||
const float *points, // starting address of points array.
|
||||
unsigned int vstride, // stride between input points.
|
||||
const float *weights, // *optional point weighting values.
|
||||
unsigned int wstride, // weight stride for each vertex.
|
||||
float *plane);
|
||||
|
||||
|
||||
float getBoundingRegion(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax); // returns the diagonal distance
|
||||
bool overlapAABB(const float *bmin1,const float *bmax1,const float *bmin2,const float *bmax2); // return true if the two AABB's overlap.
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,173 +1,173 @@
|
||||
#include "float_math.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
#include <assert.h>
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
#include "bestfitobb.h"
|
||||
#include "float_math.h"
|
||||
|
||||
// computes the OBB for this set of points relative to this transform matrix.
|
||||
void computeOBB(unsigned int vcount,const float *points,unsigned int pstride,float *sides,const float *matrix)
|
||||
{
|
||||
const char *src = (const char *) points;
|
||||
|
||||
float bmin[3] = { 1e9, 1e9, 1e9 };
|
||||
float bmax[3] = { -1e9, -1e9, -1e9 };
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
const float *p = (const float *) src;
|
||||
float t[3];
|
||||
|
||||
fm_inverseRT(matrix, p, t ); // inverse rotate translate
|
||||
|
||||
if ( t[0] < bmin[0] ) bmin[0] = t[0];
|
||||
if ( t[1] < bmin[1] ) bmin[1] = t[1];
|
||||
if ( t[2] < bmin[2] ) bmin[2] = t[2];
|
||||
|
||||
if ( t[0] > bmax[0] ) bmax[0] = t[0];
|
||||
if ( t[1] > bmax[1] ) bmax[1] = t[1];
|
||||
if ( t[2] > bmax[2] ) bmax[2] = t[2];
|
||||
|
||||
src+=pstride;
|
||||
}
|
||||
|
||||
|
||||
sides[0] = bmax[0];
|
||||
sides[1] = bmax[1];
|
||||
sides[2] = bmax[2];
|
||||
|
||||
if ( fabsf(bmin[0]) > sides[0] ) sides[0] = fabsf(bmin[0]);
|
||||
if ( fabsf(bmin[1]) > sides[1] ) sides[1] = fabsf(bmin[1]);
|
||||
if ( fabsf(bmin[2]) > sides[2] ) sides[2] = fabsf(bmin[2]);
|
||||
|
||||
sides[0]*=2.0f;
|
||||
sides[1]*=2.0f;
|
||||
sides[2]*=2.0f;
|
||||
|
||||
}
|
||||
|
||||
void computeBestFitOBB(unsigned int vcount,const float *points,unsigned int pstride,float *sides,float *matrix)
|
||||
{
|
||||
|
||||
float bmin[3];
|
||||
float bmax[3];
|
||||
|
||||
fm_getAABB(vcount,points,pstride,bmin,bmax);
|
||||
|
||||
float center[3];
|
||||
|
||||
center[0] = (bmax[0]-bmin[0])*0.5f + bmin[0];
|
||||
center[1] = (bmax[1]-bmin[1])*0.5f + bmin[1];
|
||||
center[2] = (bmax[2]-bmin[2])*0.5f + bmin[2];
|
||||
|
||||
float ax = 0;
|
||||
float ay = 0;
|
||||
float az = 0;
|
||||
|
||||
float sweep = 45.0f; // 180 degree sweep on all three axes.
|
||||
float steps = 8.0f; // 16 steps on each axis.
|
||||
|
||||
float bestVolume = 1e9;
|
||||
float angle[3]={0.f,0.f,0.f};
|
||||
|
||||
while ( sweep >= 1 )
|
||||
{
|
||||
|
||||
bool found = false;
|
||||
|
||||
float stepsize = sweep / steps;
|
||||
|
||||
for (float x=ax-sweep; x<=ax+sweep; x+=stepsize)
|
||||
{
|
||||
for (float y=ay-sweep; y<=ay+sweep; y+=stepsize)
|
||||
{
|
||||
for (float z=az-sweep; z<=az+sweep; z+=stepsize)
|
||||
{
|
||||
float pmatrix[16];
|
||||
|
||||
fm_eulerMatrix( x*FM_DEG_TO_RAD, y*FM_DEG_TO_RAD, z*FM_DEG_TO_RAD, pmatrix );
|
||||
|
||||
pmatrix[3*4+0] = center[0];
|
||||
pmatrix[3*4+1] = center[1];
|
||||
pmatrix[3*4+2] = center[2];
|
||||
|
||||
float psides[3];
|
||||
|
||||
computeOBB( vcount, points, pstride, psides, pmatrix );
|
||||
|
||||
float volume = psides[0]*psides[1]*psides[2]; // the volume of the cube
|
||||
|
||||
if ( volume <= bestVolume )
|
||||
{
|
||||
bestVolume = volume;
|
||||
|
||||
sides[0] = psides[0];
|
||||
sides[1] = psides[1];
|
||||
sides[2] = psides[2];
|
||||
|
||||
angle[0] = ax;
|
||||
angle[1] = ay;
|
||||
angle[2] = az;
|
||||
|
||||
memcpy(matrix,pmatrix,sizeof(float)*16);
|
||||
found = true; // yes, we found an improvement.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( found )
|
||||
{
|
||||
|
||||
ax = angle[0];
|
||||
ay = angle[1];
|
||||
az = angle[2];
|
||||
|
||||
sweep*=0.5f; // sweep 1/2 the distance as the last time.
|
||||
}
|
||||
else
|
||||
{
|
||||
break; // no improvement, so just
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
#include "float_math.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
#include <assert.h>
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
#include "bestfitobb.h"
|
||||
#include "float_math.h"
|
||||
|
||||
// computes the OBB for this set of points relative to this transform matrix.
|
||||
void computeOBB(unsigned int vcount,const float *points,unsigned int pstride,float *sides,const float *matrix)
|
||||
{
|
||||
const char *src = (const char *) points;
|
||||
|
||||
float bmin[3] = { 1e9, 1e9, 1e9 };
|
||||
float bmax[3] = { -1e9, -1e9, -1e9 };
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
const float *p = (const float *) src;
|
||||
float t[3];
|
||||
|
||||
fm_inverseRT(matrix, p, t ); // inverse rotate translate
|
||||
|
||||
if ( t[0] < bmin[0] ) bmin[0] = t[0];
|
||||
if ( t[1] < bmin[1] ) bmin[1] = t[1];
|
||||
if ( t[2] < bmin[2] ) bmin[2] = t[2];
|
||||
|
||||
if ( t[0] > bmax[0] ) bmax[0] = t[0];
|
||||
if ( t[1] > bmax[1] ) bmax[1] = t[1];
|
||||
if ( t[2] > bmax[2] ) bmax[2] = t[2];
|
||||
|
||||
src+=pstride;
|
||||
}
|
||||
|
||||
|
||||
sides[0] = bmax[0];
|
||||
sides[1] = bmax[1];
|
||||
sides[2] = bmax[2];
|
||||
|
||||
if ( fabsf(bmin[0]) > sides[0] ) sides[0] = fabsf(bmin[0]);
|
||||
if ( fabsf(bmin[1]) > sides[1] ) sides[1] = fabsf(bmin[1]);
|
||||
if ( fabsf(bmin[2]) > sides[2] ) sides[2] = fabsf(bmin[2]);
|
||||
|
||||
sides[0]*=2.0f;
|
||||
sides[1]*=2.0f;
|
||||
sides[2]*=2.0f;
|
||||
|
||||
}
|
||||
|
||||
void computeBestFitOBB(unsigned int vcount,const float *points,unsigned int pstride,float *sides,float *matrix)
|
||||
{
|
||||
|
||||
float bmin[3];
|
||||
float bmax[3];
|
||||
|
||||
fm_getAABB(vcount,points,pstride,bmin,bmax);
|
||||
|
||||
float center[3];
|
||||
|
||||
center[0] = (bmax[0]-bmin[0])*0.5f + bmin[0];
|
||||
center[1] = (bmax[1]-bmin[1])*0.5f + bmin[1];
|
||||
center[2] = (bmax[2]-bmin[2])*0.5f + bmin[2];
|
||||
|
||||
float ax = 0;
|
||||
float ay = 0;
|
||||
float az = 0;
|
||||
|
||||
float sweep = 45.0f; // 180 degree sweep on all three axes.
|
||||
float steps = 8.0f; // 16 steps on each axis.
|
||||
|
||||
float bestVolume = 1e9;
|
||||
float angle[3]={0.f,0.f,0.f};
|
||||
|
||||
while ( sweep >= 1 )
|
||||
{
|
||||
|
||||
bool found = false;
|
||||
|
||||
float stepsize = sweep / steps;
|
||||
|
||||
for (float x=ax-sweep; x<=ax+sweep; x+=stepsize)
|
||||
{
|
||||
for (float y=ay-sweep; y<=ay+sweep; y+=stepsize)
|
||||
{
|
||||
for (float z=az-sweep; z<=az+sweep; z+=stepsize)
|
||||
{
|
||||
float pmatrix[16];
|
||||
|
||||
fm_eulerMatrix( x*FM_DEG_TO_RAD, y*FM_DEG_TO_RAD, z*FM_DEG_TO_RAD, pmatrix );
|
||||
|
||||
pmatrix[3*4+0] = center[0];
|
||||
pmatrix[3*4+1] = center[1];
|
||||
pmatrix[3*4+2] = center[2];
|
||||
|
||||
float psides[3];
|
||||
|
||||
computeOBB( vcount, points, pstride, psides, pmatrix );
|
||||
|
||||
float volume = psides[0]*psides[1]*psides[2]; // the volume of the cube
|
||||
|
||||
if ( volume <= bestVolume )
|
||||
{
|
||||
bestVolume = volume;
|
||||
|
||||
sides[0] = psides[0];
|
||||
sides[1] = psides[1];
|
||||
sides[2] = psides[2];
|
||||
|
||||
angle[0] = ax;
|
||||
angle[1] = ay;
|
||||
angle[2] = az;
|
||||
|
||||
memcpy(matrix,pmatrix,sizeof(float)*16);
|
||||
found = true; // yes, we found an improvement.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( found )
|
||||
{
|
||||
|
||||
ax = angle[0];
|
||||
ay = angle[1];
|
||||
az = angle[2];
|
||||
|
||||
sweep*=0.5f; // sweep 1/2 the distance as the last time.
|
||||
}
|
||||
else
|
||||
{
|
||||
break; // no improvement, so just
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
@@ -1,43 +1,43 @@
|
||||
#ifndef BEST_FIT_OBB_H
|
||||
|
||||
#define BEST_FIT_OBB_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
void computeBestFitOBB(unsigned int vcount,const float *points,unsigned int pstride,float *sides,float *matrix);
|
||||
|
||||
#endif
|
||||
#ifndef BEST_FIT_OBB_H
|
||||
|
||||
#define BEST_FIT_OBB_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
void computeBestFitOBB(unsigned int vcount,const float *points,unsigned int pstride,float *sides,float *matrix);
|
||||
|
||||
#endif
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,153 +1,153 @@
|
||||
#ifndef CD_HULL_H
|
||||
|
||||
#define CD_HULL_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class HullResult
|
||||
{
|
||||
public:
|
||||
HullResult(void)
|
||||
{
|
||||
mPolygons = true;
|
||||
mNumOutputVertices = 0;
|
||||
mOutputVertices = 0;
|
||||
mNumFaces = 0;
|
||||
mNumIndices = 0;
|
||||
mIndices = 0;
|
||||
}
|
||||
bool mPolygons; // true if indices represents polygons, false indices are triangles
|
||||
unsigned int mNumOutputVertices; // number of vertices in the output hull
|
||||
float *mOutputVertices; // array of vertices, 3 floats each x,y,z
|
||||
unsigned int mNumFaces; // the number of faces produced
|
||||
unsigned int mNumIndices; // the total number of indices
|
||||
unsigned int *mIndices; // 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_SKIN_WIDTH = (1<<2), // extrude hull based on this skin width
|
||||
QF_DEFAULT = 0
|
||||
};
|
||||
|
||||
|
||||
class HullDesc
|
||||
{
|
||||
public:
|
||||
HullDesc(void)
|
||||
{
|
||||
mFlags = QF_DEFAULT;
|
||||
mVcount = 0;
|
||||
mVertices = 0;
|
||||
mVertexStride = sizeof(float)*3;
|
||||
mNormalEpsilon = 0.001f;
|
||||
mMaxVertices = 4096; // maximum number of points to be considered for a convex hull.
|
||||
mMaxFaces = 4096;
|
||||
mSkinWidth = 0.01f; // default is one centimeter
|
||||
};
|
||||
|
||||
HullDesc(HullFlag flag,
|
||||
unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int stride)
|
||||
{
|
||||
mFlags = flag;
|
||||
mVcount = vcount;
|
||||
mVertices = vertices;
|
||||
mVertexStride = stride;
|
||||
mNormalEpsilon = 0.001f;
|
||||
mMaxVertices = 4096;
|
||||
mSkinWidth = 0.01f; // default is one centimeter
|
||||
}
|
||||
|
||||
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 float *mVertices; // the array of vertices.
|
||||
unsigned int mVertexStride; // the stride of each vertex, in bytes.
|
||||
float mNormalEpsilon; // the epsilon for removing duplicates. This is a normalized value, if normalized bit is on.
|
||||
float mSkinWidth;
|
||||
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 HullLibrary
|
||||
{
|
||||
public:
|
||||
|
||||
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:
|
||||
|
||||
void BringOutYourDead(const float *verts,unsigned int vcount, float *overts,unsigned int &ocount,unsigned int *indices,unsigned indexcount);
|
||||
|
||||
bool CleanupVertices(unsigned int svcount,
|
||||
const float *svertices,
|
||||
unsigned int stride,
|
||||
unsigned int &vcount, // output number of vertices
|
||||
float *vertices, // location to store the results.
|
||||
float normalepsilon,
|
||||
float *scale);
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef CD_HULL_H
|
||||
|
||||
#define CD_HULL_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class HullResult
|
||||
{
|
||||
public:
|
||||
HullResult(void)
|
||||
{
|
||||
mPolygons = true;
|
||||
mNumOutputVertices = 0;
|
||||
mOutputVertices = 0;
|
||||
mNumFaces = 0;
|
||||
mNumIndices = 0;
|
||||
mIndices = 0;
|
||||
}
|
||||
bool mPolygons; // true if indices represents polygons, false indices are triangles
|
||||
unsigned int mNumOutputVertices; // number of vertices in the output hull
|
||||
float *mOutputVertices; // array of vertices, 3 floats each x,y,z
|
||||
unsigned int mNumFaces; // the number of faces produced
|
||||
unsigned int mNumIndices; // the total number of indices
|
||||
unsigned int *mIndices; // 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_SKIN_WIDTH = (1<<2), // extrude hull based on this skin width
|
||||
QF_DEFAULT = 0
|
||||
};
|
||||
|
||||
|
||||
class HullDesc
|
||||
{
|
||||
public:
|
||||
HullDesc(void)
|
||||
{
|
||||
mFlags = QF_DEFAULT;
|
||||
mVcount = 0;
|
||||
mVertices = 0;
|
||||
mVertexStride = sizeof(float)*3;
|
||||
mNormalEpsilon = 0.001f;
|
||||
mMaxVertices = 4096; // maximum number of points to be considered for a convex hull.
|
||||
mMaxFaces = 4096;
|
||||
mSkinWidth = 0.01f; // default is one centimeter
|
||||
};
|
||||
|
||||
HullDesc(HullFlag flag,
|
||||
unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int stride)
|
||||
{
|
||||
mFlags = flag;
|
||||
mVcount = vcount;
|
||||
mVertices = vertices;
|
||||
mVertexStride = stride;
|
||||
mNormalEpsilon = 0.001f;
|
||||
mMaxVertices = 4096;
|
||||
mSkinWidth = 0.01f; // default is one centimeter
|
||||
}
|
||||
|
||||
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 float *mVertices; // the array of vertices.
|
||||
unsigned int mVertexStride; // the stride of each vertex, in bytes.
|
||||
float mNormalEpsilon; // the epsilon for removing duplicates. This is a normalized value, if normalized bit is on.
|
||||
float mSkinWidth;
|
||||
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 HullLibrary
|
||||
{
|
||||
public:
|
||||
|
||||
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:
|
||||
|
||||
void BringOutYourDead(const float *verts,unsigned int vcount, float *overts,unsigned int &ocount,unsigned int *indices,unsigned indexcount);
|
||||
|
||||
bool CleanupVertices(unsigned int svcount,
|
||||
const float *svertices,
|
||||
unsigned int stride,
|
||||
unsigned int &vcount, // output number of vertices
|
||||
float *vertices, // location to store the results.
|
||||
float normalepsilon,
|
||||
float *scale);
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,62 +1,62 @@
|
||||
#ifndef CD_WAVEFRONT_OBJ_H
|
||||
|
||||
|
||||
#define CD_WAVEFRONT_OBJ_H
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class WavefrontObj
|
||||
{
|
||||
public:
|
||||
|
||||
WavefrontObj(void);
|
||||
~WavefrontObj(void);
|
||||
|
||||
unsigned int loadObj(const char *fname); // load a wavefront obj returns number of triangles that were loaded. Data is persists until the class is destructed.
|
||||
|
||||
int mVertexCount;
|
||||
int mTriCount;
|
||||
int *mIndices;
|
||||
float *mVertices;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
#ifndef CD_WAVEFRONT_OBJ_H
|
||||
|
||||
|
||||
#define CD_WAVEFRONT_OBJ_H
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class WavefrontObj
|
||||
{
|
||||
public:
|
||||
|
||||
WavefrontObj(void);
|
||||
~WavefrontObj(void);
|
||||
|
||||
unsigned int loadObj(const char *fname); // load a wavefront obj returns number of triangles that were loaded. Data is persists until the class is destructed.
|
||||
|
||||
int mVertexCount;
|
||||
int mTriCount;
|
||||
int *mIndices;
|
||||
float *mVertices;
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,60 +1,60 @@
|
||||
#ifndef COMPUTE_CONCAVITY_H
|
||||
|
||||
#define COMPUTE_CONCAVITY_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class ConvexDecompInterface;
|
||||
|
||||
// compute's how 'concave' this object is and returns the total volume of the
|
||||
// convex hull as well as the volume of the 'concavity' which was found.
|
||||
float computeConcavity(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float *plane,
|
||||
float &volume);
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
#endif
|
||||
#ifndef COMPUTE_CONCAVITY_H
|
||||
|
||||
#define COMPUTE_CONCAVITY_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class ConvexDecompInterface;
|
||||
|
||||
// compute's how 'concave' this object is and returns the total volume of the
|
||||
// convex hull as well as the volume of the 'concavity' which was found.
|
||||
float computeConcavity(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float *plane,
|
||||
float &volume);
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,202 +1,202 @@
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
#include "fitsphere.h"
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
/*
|
||||
An Efficient Bounding Sphere
|
||||
by Jack Ritter
|
||||
from "Graphics Gems", Academic Press, 1990
|
||||
*/
|
||||
|
||||
/* Routine to calculate tight bounding sphere over */
|
||||
/* a set of points in 3D */
|
||||
/* This contains the routine find_bounding_sphere(), */
|
||||
/* the struct definition, and the globals used for parameters. */
|
||||
/* The abs() of all coordinates must be < BIGNUMBER */
|
||||
/* Code written by Jack Ritter and Lyle Rains. */
|
||||
|
||||
#define BIGNUMBER 100000000.0 /* hundred million */
|
||||
|
||||
static inline void Set(float *n,float x,float y,float z)
|
||||
{
|
||||
n[0] = x;
|
||||
n[1] = y;
|
||||
n[2] = z;
|
||||
}
|
||||
|
||||
static inline void Copy(float *dest,const float *source)
|
||||
{
|
||||
dest[0] = source[0];
|
||||
dest[1] = source[1];
|
||||
dest[2] = source[2];
|
||||
}
|
||||
|
||||
float computeBoundingSphere(unsigned int vcount,const float *points,float *center)
|
||||
{
|
||||
|
||||
float mRadius;
|
||||
float mRadius2;
|
||||
|
||||
float xmin[3];
|
||||
float xmax[3];
|
||||
float ymin[3];
|
||||
float ymax[3];
|
||||
float zmin[3];
|
||||
float zmax[3];
|
||||
float dia1[3];
|
||||
float dia2[3];
|
||||
|
||||
/* FIRST PASS: find 6 minima/maxima points */
|
||||
Set(xmin,BIGNUMBER,BIGNUMBER,BIGNUMBER);
|
||||
Set(xmax,-BIGNUMBER,-BIGNUMBER,-BIGNUMBER);
|
||||
Set(ymin,BIGNUMBER,BIGNUMBER,BIGNUMBER);
|
||||
Set(ymax,-BIGNUMBER,-BIGNUMBER,-BIGNUMBER);
|
||||
Set(zmin,BIGNUMBER,BIGNUMBER,BIGNUMBER);
|
||||
Set(zmax,-BIGNUMBER,-BIGNUMBER,-BIGNUMBER);
|
||||
|
||||
for (unsigned i=0; i<vcount; i++)
|
||||
{
|
||||
const float *caller_p = &points[i*3];
|
||||
|
||||
if (caller_p[0]<xmin[0])
|
||||
Copy(xmin,caller_p); /* New xminimum point */
|
||||
if (caller_p[0]>xmax[0])
|
||||
Copy(xmax,caller_p);
|
||||
if (caller_p[1]<ymin[1])
|
||||
Copy(ymin,caller_p);
|
||||
if (caller_p[1]>ymax[1])
|
||||
Copy(ymax,caller_p);
|
||||
if (caller_p[2]<zmin[2])
|
||||
Copy(zmin,caller_p);
|
||||
if (caller_p[2]>zmax[2])
|
||||
Copy(zmax,caller_p);
|
||||
}
|
||||
|
||||
/* Set xspan = distance between the 2 points xmin & xmax (squared) */
|
||||
float dx = xmax[0] - xmin[0];
|
||||
float dy = xmax[1] - xmin[1];
|
||||
float dz = xmax[2] - xmin[2];
|
||||
float xspan = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
/* Same for y & z spans */
|
||||
dx = ymax[0] - ymin[0];
|
||||
dy = ymax[1] - ymin[1];
|
||||
dz = ymax[2] - ymin[2];
|
||||
float yspan = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
dx = zmax[0] - zmin[0];
|
||||
dy = zmax[1] - zmin[1];
|
||||
dz = zmax[2] - zmin[2];
|
||||
float zspan = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
/* Set points dia1 & dia2 to the maximally separated pair */
|
||||
Copy(dia1,xmin);
|
||||
Copy(dia2,xmax); /* assume xspan biggest */
|
||||
float maxspan = xspan;
|
||||
|
||||
if (yspan>maxspan)
|
||||
{
|
||||
maxspan = yspan;
|
||||
Copy(dia1,ymin);
|
||||
Copy(dia2,ymax);
|
||||
}
|
||||
|
||||
if (zspan>maxspan)
|
||||
{
|
||||
Copy(dia1,zmin);
|
||||
Copy(dia2,zmax);
|
||||
}
|
||||
|
||||
|
||||
/* dia1,dia2 is a diameter of initial sphere */
|
||||
/* calc initial center */
|
||||
center[0] = (dia1[0]+dia2[0])*0.5f;
|
||||
center[1] = (dia1[1]+dia2[1])*0.5f;
|
||||
center[2] = (dia1[2]+dia2[2])*0.5f;
|
||||
|
||||
/* calculate initial radius**2 and radius */
|
||||
|
||||
dx = dia2[0]-center[0]; /* x component of radius vector */
|
||||
dy = dia2[1]-center[1]; /* y component of radius vector */
|
||||
dz = dia2[2]-center[2]; /* z component of radius vector */
|
||||
|
||||
mRadius2 = dx*dx + dy*dy + dz*dz;
|
||||
mRadius = float(sqrt(mRadius2));
|
||||
|
||||
/* SECOND PASS: increment current sphere */
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
for (unsigned i=0; i<vcount; i++)
|
||||
{
|
||||
const float *caller_p = &points[i*3];
|
||||
|
||||
dx = caller_p[0]-center[0];
|
||||
dy = caller_p[1]-center[1];
|
||||
dz = caller_p[2]-center[2];
|
||||
|
||||
float old_to_p_sq = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
if (old_to_p_sq > mRadius2) /* do r**2 test first */
|
||||
{ /* this point is outside of current sphere */
|
||||
float old_to_p = float(sqrt(old_to_p_sq));
|
||||
/* calc radius of new sphere */
|
||||
mRadius = (mRadius + old_to_p) * 0.5f;
|
||||
mRadius2 = mRadius*mRadius; /* for next r**2 compare */
|
||||
float old_to_new = old_to_p - mRadius;
|
||||
|
||||
/* calc center of new sphere */
|
||||
|
||||
float recip = 1.0f /old_to_p;
|
||||
|
||||
float cx = (mRadius*center[0] + old_to_new*caller_p[0]) * recip;
|
||||
float cy = (mRadius*center[1] + old_to_new*caller_p[1]) * recip;
|
||||
float cz = (mRadius*center[2] + old_to_new*caller_p[2]) * recip;
|
||||
|
||||
Set(center,cx,cy,cz);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return mRadius;
|
||||
}
|
||||
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
#include "fitsphere.h"
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
/*
|
||||
An Efficient Bounding Sphere
|
||||
by Jack Ritter
|
||||
from "Graphics Gems", Academic Press, 1990
|
||||
*/
|
||||
|
||||
/* Routine to calculate tight bounding sphere over */
|
||||
/* a set of points in 3D */
|
||||
/* This contains the routine find_bounding_sphere(), */
|
||||
/* the struct definition, and the globals used for parameters. */
|
||||
/* The abs() of all coordinates must be < BIGNUMBER */
|
||||
/* Code written by Jack Ritter and Lyle Rains. */
|
||||
|
||||
#define BIGNUMBER 100000000.0 /* hundred million */
|
||||
|
||||
static inline void Set(float *n,float x,float y,float z)
|
||||
{
|
||||
n[0] = x;
|
||||
n[1] = y;
|
||||
n[2] = z;
|
||||
}
|
||||
|
||||
static inline void Copy(float *dest,const float *source)
|
||||
{
|
||||
dest[0] = source[0];
|
||||
dest[1] = source[1];
|
||||
dest[2] = source[2];
|
||||
}
|
||||
|
||||
float computeBoundingSphere(unsigned int vcount,const float *points,float *center)
|
||||
{
|
||||
|
||||
float mRadius;
|
||||
float mRadius2;
|
||||
|
||||
float xmin[3];
|
||||
float xmax[3];
|
||||
float ymin[3];
|
||||
float ymax[3];
|
||||
float zmin[3];
|
||||
float zmax[3];
|
||||
float dia1[3];
|
||||
float dia2[3];
|
||||
|
||||
/* FIRST PASS: find 6 minima/maxima points */
|
||||
Set(xmin,BIGNUMBER,BIGNUMBER,BIGNUMBER);
|
||||
Set(xmax,-BIGNUMBER,-BIGNUMBER,-BIGNUMBER);
|
||||
Set(ymin,BIGNUMBER,BIGNUMBER,BIGNUMBER);
|
||||
Set(ymax,-BIGNUMBER,-BIGNUMBER,-BIGNUMBER);
|
||||
Set(zmin,BIGNUMBER,BIGNUMBER,BIGNUMBER);
|
||||
Set(zmax,-BIGNUMBER,-BIGNUMBER,-BIGNUMBER);
|
||||
|
||||
for (unsigned i=0; i<vcount; i++)
|
||||
{
|
||||
const float *caller_p = &points[i*3];
|
||||
|
||||
if (caller_p[0]<xmin[0])
|
||||
Copy(xmin,caller_p); /* New xminimum point */
|
||||
if (caller_p[0]>xmax[0])
|
||||
Copy(xmax,caller_p);
|
||||
if (caller_p[1]<ymin[1])
|
||||
Copy(ymin,caller_p);
|
||||
if (caller_p[1]>ymax[1])
|
||||
Copy(ymax,caller_p);
|
||||
if (caller_p[2]<zmin[2])
|
||||
Copy(zmin,caller_p);
|
||||
if (caller_p[2]>zmax[2])
|
||||
Copy(zmax,caller_p);
|
||||
}
|
||||
|
||||
/* Set xspan = distance between the 2 points xmin & xmax (squared) */
|
||||
float dx = xmax[0] - xmin[0];
|
||||
float dy = xmax[1] - xmin[1];
|
||||
float dz = xmax[2] - xmin[2];
|
||||
float xspan = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
/* Same for y & z spans */
|
||||
dx = ymax[0] - ymin[0];
|
||||
dy = ymax[1] - ymin[1];
|
||||
dz = ymax[2] - ymin[2];
|
||||
float yspan = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
dx = zmax[0] - zmin[0];
|
||||
dy = zmax[1] - zmin[1];
|
||||
dz = zmax[2] - zmin[2];
|
||||
float zspan = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
/* Set points dia1 & dia2 to the maximally separated pair */
|
||||
Copy(dia1,xmin);
|
||||
Copy(dia2,xmax); /* assume xspan biggest */
|
||||
float maxspan = xspan;
|
||||
|
||||
if (yspan>maxspan)
|
||||
{
|
||||
maxspan = yspan;
|
||||
Copy(dia1,ymin);
|
||||
Copy(dia2,ymax);
|
||||
}
|
||||
|
||||
if (zspan>maxspan)
|
||||
{
|
||||
Copy(dia1,zmin);
|
||||
Copy(dia2,zmax);
|
||||
}
|
||||
|
||||
|
||||
/* dia1,dia2 is a diameter of initial sphere */
|
||||
/* calc initial center */
|
||||
center[0] = (dia1[0]+dia2[0])*0.5f;
|
||||
center[1] = (dia1[1]+dia2[1])*0.5f;
|
||||
center[2] = (dia1[2]+dia2[2])*0.5f;
|
||||
|
||||
/* calculate initial radius**2 and radius */
|
||||
|
||||
dx = dia2[0]-center[0]; /* x component of radius vector */
|
||||
dy = dia2[1]-center[1]; /* y component of radius vector */
|
||||
dz = dia2[2]-center[2]; /* z component of radius vector */
|
||||
|
||||
mRadius2 = dx*dx + dy*dy + dz*dz;
|
||||
mRadius = float(sqrt(mRadius2));
|
||||
|
||||
/* SECOND PASS: increment current sphere */
|
||||
|
||||
if ( 1 )
|
||||
{
|
||||
for (unsigned i=0; i<vcount; i++)
|
||||
{
|
||||
const float *caller_p = &points[i*3];
|
||||
|
||||
dx = caller_p[0]-center[0];
|
||||
dy = caller_p[1]-center[1];
|
||||
dz = caller_p[2]-center[2];
|
||||
|
||||
float old_to_p_sq = dx*dx + dy*dy + dz*dz;
|
||||
|
||||
if (old_to_p_sq > mRadius2) /* do r**2 test first */
|
||||
{ /* this point is outside of current sphere */
|
||||
float old_to_p = float(sqrt(old_to_p_sq));
|
||||
/* calc radius of new sphere */
|
||||
mRadius = (mRadius + old_to_p) * 0.5f;
|
||||
mRadius2 = mRadius*mRadius; /* for next r**2 compare */
|
||||
float old_to_new = old_to_p - mRadius;
|
||||
|
||||
/* calc center of new sphere */
|
||||
|
||||
float recip = 1.0f /old_to_p;
|
||||
|
||||
float cx = (mRadius*center[0] + old_to_new*caller_p[0]) * recip;
|
||||
float cy = (mRadius*center[1] + old_to_new*caller_p[1]) * recip;
|
||||
float cz = (mRadius*center[2] + old_to_new*caller_p[2]) * recip;
|
||||
|
||||
Set(center,cx,cy,cz);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return mRadius;
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -1,43 +1,43 @@
|
||||
#ifndef FIT_SPHERE_H
|
||||
|
||||
#define FIT_SPHERE_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
float computeBoundingSphere(unsigned int vcount,const float *points,float *center);
|
||||
|
||||
#endif
|
||||
#ifndef FIT_SPHERE_H
|
||||
|
||||
#define FIT_SPHERE_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
float computeBoundingSphere(unsigned int vcount,const float *points,float *center);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,257 +1,257 @@
|
||||
#include "float_math.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
void fm_inverseRT(const float *matrix,const float *pos,float *t) // inverse rotate translate the point.
|
||||
{
|
||||
|
||||
float _x = pos[0] - matrix[3*4+0];
|
||||
float _y = pos[1] - matrix[3*4+1];
|
||||
float _z = pos[2] - matrix[3*4+2];
|
||||
|
||||
// Multiply inverse-translated source vector by inverted rotation transform
|
||||
|
||||
t[0] = (matrix[0*4+0] * _x) + (matrix[0*4+1] * _y) + (matrix[0*4+2] * _z);
|
||||
t[1] = (matrix[1*4+0] * _x) + (matrix[1*4+1] * _y) + (matrix[1*4+2] * _z);
|
||||
t[2] = (matrix[2*4+0] * _x) + (matrix[2*4+1] * _y) + (matrix[2*4+2] * _z);
|
||||
|
||||
}
|
||||
|
||||
|
||||
void fm_identity(float *matrix) // set 4x4 matrix to identity.
|
||||
{
|
||||
matrix[0*4+0] = 1;
|
||||
matrix[1*4+1] = 1;
|
||||
matrix[2*4+2] = 1;
|
||||
matrix[3*4+3] = 1;
|
||||
|
||||
matrix[1*4+0] = 0;
|
||||
matrix[2*4+0] = 0;
|
||||
matrix[3*4+0] = 0;
|
||||
|
||||
matrix[0*4+1] = 0;
|
||||
matrix[2*4+1] = 0;
|
||||
matrix[3*4+1] = 0;
|
||||
|
||||
matrix[0*4+2] = 0;
|
||||
matrix[1*4+2] = 0;
|
||||
matrix[3*4+2] = 0;
|
||||
|
||||
matrix[0*4+3] = 0;
|
||||
matrix[1*4+3] = 0;
|
||||
matrix[2*4+3] = 0;
|
||||
|
||||
}
|
||||
|
||||
void fm_eulerMatrix(float ax,float ay,float az,float *matrix) // convert euler (in radians) to a dest 4x4 matrix (translation set to zero)
|
||||
{
|
||||
float quat[4];
|
||||
fm_eulerToQuat(ax,ay,az,quat);
|
||||
fm_quatToMatrix(quat,matrix);
|
||||
}
|
||||
|
||||
void fm_getAABB(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax)
|
||||
{
|
||||
|
||||
const unsigned char *source = (const unsigned char *) points;
|
||||
|
||||
bmin[0] = points[0];
|
||||
bmin[1] = points[1];
|
||||
bmin[2] = points[2];
|
||||
|
||||
bmax[0] = points[0];
|
||||
bmax[1] = points[1];
|
||||
bmax[2] = points[2];
|
||||
|
||||
|
||||
for (unsigned int i=1; i<vcount; i++)
|
||||
{
|
||||
source+=pstride;
|
||||
const float *p = (const float *) source;
|
||||
|
||||
if ( p[0] < bmin[0] ) bmin[0] = p[0];
|
||||
if ( p[1] < bmin[1] ) bmin[1] = p[1];
|
||||
if ( p[2] < bmin[2] ) bmin[2] = p[2];
|
||||
|
||||
if ( p[0] > bmax[0] ) bmax[0] = p[0];
|
||||
if ( p[1] > bmax[1] ) bmax[1] = p[1];
|
||||
if ( p[2] > bmax[2] ) bmax[2] = p[2];
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void fm_eulerToQuat(float roll,float pitch,float yaw,float *quat) // convert euler angles to quaternion.
|
||||
{
|
||||
roll *= 0.5f;
|
||||
pitch *= 0.5f;
|
||||
yaw *= 0.5f;
|
||||
|
||||
float cr = cosf(roll);
|
||||
float cp = cosf(pitch);
|
||||
float cy = cosf(yaw);
|
||||
|
||||
float sr = sinf(roll);
|
||||
float sp = sinf(pitch);
|
||||
float sy = sinf(yaw);
|
||||
|
||||
float cpcy = cp * cy;
|
||||
float spsy = sp * sy;
|
||||
float spcy = sp * cy;
|
||||
float cpsy = cp * sy;
|
||||
|
||||
quat[0] = ( sr * cpcy - cr * spsy);
|
||||
quat[1] = ( cr * spcy + sr * cpsy);
|
||||
quat[2] = ( cr * cpsy - sr * spcy);
|
||||
quat[3] = cr * cpcy + sr * spsy;
|
||||
}
|
||||
|
||||
void fm_quatToMatrix(const float *quat,float *matrix) // convert quaterinion rotation to matrix, zeros out the translation component.
|
||||
{
|
||||
|
||||
float xx = quat[0]*quat[0];
|
||||
float yy = quat[1]*quat[1];
|
||||
float zz = quat[2]*quat[2];
|
||||
float xy = quat[0]*quat[1];
|
||||
float xz = quat[0]*quat[2];
|
||||
float yz = quat[1]*quat[2];
|
||||
float wx = quat[3]*quat[0];
|
||||
float wy = quat[3]*quat[1];
|
||||
float wz = quat[3]*quat[2];
|
||||
|
||||
matrix[0*4+0] = 1 - 2 * ( yy + zz );
|
||||
matrix[1*4+0] = 2 * ( xy - wz );
|
||||
matrix[2*4+0] = 2 * ( xz + wy );
|
||||
|
||||
matrix[0*4+1] = 2 * ( xy + wz );
|
||||
matrix[1*4+1] = 1 - 2 * ( xx + zz );
|
||||
matrix[2*4+1] = 2 * ( yz - wx );
|
||||
|
||||
matrix[0*4+2] = 2 * ( xz - wy );
|
||||
matrix[1*4+2] = 2 * ( yz + wx );
|
||||
matrix[2*4+2] = 1 - 2 * ( xx + yy );
|
||||
|
||||
matrix[3*4+0] = matrix[3*4+1] = matrix[3*4+2] = 0.0f;
|
||||
matrix[0*4+3] = matrix[1*4+3] = matrix[2*4+3] = 0.0f;
|
||||
matrix[3*4+3] = 1.0f;
|
||||
|
||||
}
|
||||
|
||||
|
||||
void fm_quatRotate(const float *quat,const float *v,float *r) // rotate a vector directly by a quaternion.
|
||||
{
|
||||
float left[4];
|
||||
|
||||
left[0] = quat[3]*v[0] + quat[1]*v[2] - v[1]*quat[2];
|
||||
left[1] = quat[3]*v[1] + quat[2]*v[0] - v[2]*quat[0];
|
||||
left[2] = quat[3]*v[2] + quat[0]*v[1] - v[0]*quat[1];
|
||||
left[3] = - quat[0]*v[0] - quat[1]*v[1] - quat[2]*v[2];
|
||||
|
||||
r[0] = (left[3]*-quat[0]) + (quat[3]*left[0]) + (left[1]*-quat[2]) - (-quat[1]*left[2]);
|
||||
r[1] = (left[3]*-quat[1]) + (quat[3]*left[1]) + (left[2]*-quat[0]) - (-quat[2]*left[0]);
|
||||
r[2] = (left[3]*-quat[2]) + (quat[3]*left[2]) + (left[0]*-quat[1]) - (-quat[0]*left[1]);
|
||||
|
||||
}
|
||||
|
||||
|
||||
void fm_getTranslation(const float *matrix,float *t)
|
||||
{
|
||||
t[0] = matrix[3*4+0];
|
||||
t[1] = matrix[3*4+1];
|
||||
t[2] = matrix[3*4+2];
|
||||
}
|
||||
|
||||
void fm_matrixToQuat(const float *matrix,float *quat) // convert the 3x3 portion of a 4x4 matrix into a quaterion as x,y,z,w
|
||||
{
|
||||
|
||||
float tr = matrix[0*4+0] + matrix[1*4+1] + matrix[2*4+2];
|
||||
|
||||
// check the diagonal
|
||||
|
||||
if (tr > 0.0f )
|
||||
{
|
||||
float s = (float) sqrt ( (double) (tr + 1.0f) );
|
||||
quat[3] = s * 0.5f;
|
||||
s = 0.5f / s;
|
||||
quat[0] = (matrix[1*4+2] - matrix[2*4+1]) * s;
|
||||
quat[1] = (matrix[2*4+0] - matrix[0*4+2]) * s;
|
||||
quat[2] = (matrix[0*4+1] - matrix[1*4+0]) * s;
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
// diagonal is negative
|
||||
int nxt[3] = {1, 2, 0};
|
||||
float qa[4];
|
||||
|
||||
int i = 0;
|
||||
|
||||
if (matrix[1*4+1] > matrix[0*4+0]) i = 1;
|
||||
if (matrix[2*4+2] > matrix[i*4+i]) i = 2;
|
||||
|
||||
int j = nxt[i];
|
||||
int k = nxt[j];
|
||||
|
||||
float s = sqrtf ( ((matrix[i*4+i] - (matrix[j*4+j] + matrix[k*4+k])) + 1.0f) );
|
||||
|
||||
qa[i] = s * 0.5f;
|
||||
|
||||
if (s != 0.0f ) s = 0.5f / s;
|
||||
|
||||
qa[3] = (matrix[j*4+k] - matrix[k*4+j]) * s;
|
||||
qa[j] = (matrix[i*4+j] + matrix[j*4+i]) * s;
|
||||
qa[k] = (matrix[i*4+k] + matrix[k*4+i]) * s;
|
||||
|
||||
quat[0] = qa[0];
|
||||
quat[1] = qa[1];
|
||||
quat[2] = qa[2];
|
||||
quat[3] = qa[3];
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
float fm_sphereVolume(float radius) // return's the volume of a sphere of this radius (4/3 PI * R cubed )
|
||||
{
|
||||
return (4.0f / 3.0f ) * FM_PI * radius * radius * radius;
|
||||
}
|
||||
#include "float_math.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
void fm_inverseRT(const float *matrix,const float *pos,float *t) // inverse rotate translate the point.
|
||||
{
|
||||
|
||||
float _x = pos[0] - matrix[3*4+0];
|
||||
float _y = pos[1] - matrix[3*4+1];
|
||||
float _z = pos[2] - matrix[3*4+2];
|
||||
|
||||
// Multiply inverse-translated source vector by inverted rotation transform
|
||||
|
||||
t[0] = (matrix[0*4+0] * _x) + (matrix[0*4+1] * _y) + (matrix[0*4+2] * _z);
|
||||
t[1] = (matrix[1*4+0] * _x) + (matrix[1*4+1] * _y) + (matrix[1*4+2] * _z);
|
||||
t[2] = (matrix[2*4+0] * _x) + (matrix[2*4+1] * _y) + (matrix[2*4+2] * _z);
|
||||
|
||||
}
|
||||
|
||||
|
||||
void fm_identity(float *matrix) // set 4x4 matrix to identity.
|
||||
{
|
||||
matrix[0*4+0] = 1;
|
||||
matrix[1*4+1] = 1;
|
||||
matrix[2*4+2] = 1;
|
||||
matrix[3*4+3] = 1;
|
||||
|
||||
matrix[1*4+0] = 0;
|
||||
matrix[2*4+0] = 0;
|
||||
matrix[3*4+0] = 0;
|
||||
|
||||
matrix[0*4+1] = 0;
|
||||
matrix[2*4+1] = 0;
|
||||
matrix[3*4+1] = 0;
|
||||
|
||||
matrix[0*4+2] = 0;
|
||||
matrix[1*4+2] = 0;
|
||||
matrix[3*4+2] = 0;
|
||||
|
||||
matrix[0*4+3] = 0;
|
||||
matrix[1*4+3] = 0;
|
||||
matrix[2*4+3] = 0;
|
||||
|
||||
}
|
||||
|
||||
void fm_eulerMatrix(float ax,float ay,float az,float *matrix) // convert euler (in radians) to a dest 4x4 matrix (translation set to zero)
|
||||
{
|
||||
float quat[4];
|
||||
fm_eulerToQuat(ax,ay,az,quat);
|
||||
fm_quatToMatrix(quat,matrix);
|
||||
}
|
||||
|
||||
void fm_getAABB(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax)
|
||||
{
|
||||
|
||||
const unsigned char *source = (const unsigned char *) points;
|
||||
|
||||
bmin[0] = points[0];
|
||||
bmin[1] = points[1];
|
||||
bmin[2] = points[2];
|
||||
|
||||
bmax[0] = points[0];
|
||||
bmax[1] = points[1];
|
||||
bmax[2] = points[2];
|
||||
|
||||
|
||||
for (unsigned int i=1; i<vcount; i++)
|
||||
{
|
||||
source+=pstride;
|
||||
const float *p = (const float *) source;
|
||||
|
||||
if ( p[0] < bmin[0] ) bmin[0] = p[0];
|
||||
if ( p[1] < bmin[1] ) bmin[1] = p[1];
|
||||
if ( p[2] < bmin[2] ) bmin[2] = p[2];
|
||||
|
||||
if ( p[0] > bmax[0] ) bmax[0] = p[0];
|
||||
if ( p[1] > bmax[1] ) bmax[1] = p[1];
|
||||
if ( p[2] > bmax[2] ) bmax[2] = p[2];
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void fm_eulerToQuat(float roll,float pitch,float yaw,float *quat) // convert euler angles to quaternion.
|
||||
{
|
||||
roll *= 0.5f;
|
||||
pitch *= 0.5f;
|
||||
yaw *= 0.5f;
|
||||
|
||||
float cr = cosf(roll);
|
||||
float cp = cosf(pitch);
|
||||
float cy = cosf(yaw);
|
||||
|
||||
float sr = sinf(roll);
|
||||
float sp = sinf(pitch);
|
||||
float sy = sinf(yaw);
|
||||
|
||||
float cpcy = cp * cy;
|
||||
float spsy = sp * sy;
|
||||
float spcy = sp * cy;
|
||||
float cpsy = cp * sy;
|
||||
|
||||
quat[0] = ( sr * cpcy - cr * spsy);
|
||||
quat[1] = ( cr * spcy + sr * cpsy);
|
||||
quat[2] = ( cr * cpsy - sr * spcy);
|
||||
quat[3] = cr * cpcy + sr * spsy;
|
||||
}
|
||||
|
||||
void fm_quatToMatrix(const float *quat,float *matrix) // convert quaterinion rotation to matrix, zeros out the translation component.
|
||||
{
|
||||
|
||||
float xx = quat[0]*quat[0];
|
||||
float yy = quat[1]*quat[1];
|
||||
float zz = quat[2]*quat[2];
|
||||
float xy = quat[0]*quat[1];
|
||||
float xz = quat[0]*quat[2];
|
||||
float yz = quat[1]*quat[2];
|
||||
float wx = quat[3]*quat[0];
|
||||
float wy = quat[3]*quat[1];
|
||||
float wz = quat[3]*quat[2];
|
||||
|
||||
matrix[0*4+0] = 1 - 2 * ( yy + zz );
|
||||
matrix[1*4+0] = 2 * ( xy - wz );
|
||||
matrix[2*4+0] = 2 * ( xz + wy );
|
||||
|
||||
matrix[0*4+1] = 2 * ( xy + wz );
|
||||
matrix[1*4+1] = 1 - 2 * ( xx + zz );
|
||||
matrix[2*4+1] = 2 * ( yz - wx );
|
||||
|
||||
matrix[0*4+2] = 2 * ( xz - wy );
|
||||
matrix[1*4+2] = 2 * ( yz + wx );
|
||||
matrix[2*4+2] = 1 - 2 * ( xx + yy );
|
||||
|
||||
matrix[3*4+0] = matrix[3*4+1] = matrix[3*4+2] = 0.0f;
|
||||
matrix[0*4+3] = matrix[1*4+3] = matrix[2*4+3] = 0.0f;
|
||||
matrix[3*4+3] = 1.0f;
|
||||
|
||||
}
|
||||
|
||||
|
||||
void fm_quatRotate(const float *quat,const float *v,float *r) // rotate a vector directly by a quaternion.
|
||||
{
|
||||
float left[4];
|
||||
|
||||
left[0] = quat[3]*v[0] + quat[1]*v[2] - v[1]*quat[2];
|
||||
left[1] = quat[3]*v[1] + quat[2]*v[0] - v[2]*quat[0];
|
||||
left[2] = quat[3]*v[2] + quat[0]*v[1] - v[0]*quat[1];
|
||||
left[3] = - quat[0]*v[0] - quat[1]*v[1] - quat[2]*v[2];
|
||||
|
||||
r[0] = (left[3]*-quat[0]) + (quat[3]*left[0]) + (left[1]*-quat[2]) - (-quat[1]*left[2]);
|
||||
r[1] = (left[3]*-quat[1]) + (quat[3]*left[1]) + (left[2]*-quat[0]) - (-quat[2]*left[0]);
|
||||
r[2] = (left[3]*-quat[2]) + (quat[3]*left[2]) + (left[0]*-quat[1]) - (-quat[0]*left[1]);
|
||||
|
||||
}
|
||||
|
||||
|
||||
void fm_getTranslation(const float *matrix,float *t)
|
||||
{
|
||||
t[0] = matrix[3*4+0];
|
||||
t[1] = matrix[3*4+1];
|
||||
t[2] = matrix[3*4+2];
|
||||
}
|
||||
|
||||
void fm_matrixToQuat(const float *matrix,float *quat) // convert the 3x3 portion of a 4x4 matrix into a quaterion as x,y,z,w
|
||||
{
|
||||
|
||||
float tr = matrix[0*4+0] + matrix[1*4+1] + matrix[2*4+2];
|
||||
|
||||
// check the diagonal
|
||||
|
||||
if (tr > 0.0f )
|
||||
{
|
||||
float s = (float) sqrt ( (double) (tr + 1.0f) );
|
||||
quat[3] = s * 0.5f;
|
||||
s = 0.5f / s;
|
||||
quat[0] = (matrix[1*4+2] - matrix[2*4+1]) * s;
|
||||
quat[1] = (matrix[2*4+0] - matrix[0*4+2]) * s;
|
||||
quat[2] = (matrix[0*4+1] - matrix[1*4+0]) * s;
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
// diagonal is negative
|
||||
int nxt[3] = {1, 2, 0};
|
||||
float qa[4];
|
||||
|
||||
int i = 0;
|
||||
|
||||
if (matrix[1*4+1] > matrix[0*4+0]) i = 1;
|
||||
if (matrix[2*4+2] > matrix[i*4+i]) i = 2;
|
||||
|
||||
int j = nxt[i];
|
||||
int k = nxt[j];
|
||||
|
||||
float s = sqrtf ( ((matrix[i*4+i] - (matrix[j*4+j] + matrix[k*4+k])) + 1.0f) );
|
||||
|
||||
qa[i] = s * 0.5f;
|
||||
|
||||
if (s != 0.0f ) s = 0.5f / s;
|
||||
|
||||
qa[3] = (matrix[j*4+k] - matrix[k*4+j]) * s;
|
||||
qa[j] = (matrix[i*4+j] + matrix[j*4+i]) * s;
|
||||
qa[k] = (matrix[i*4+k] + matrix[k*4+i]) * s;
|
||||
|
||||
quat[0] = qa[0];
|
||||
quat[1] = qa[1];
|
||||
quat[2] = qa[2];
|
||||
quat[3] = qa[3];
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
float fm_sphereVolume(float radius) // return's the volume of a sphere of this radius (4/3 PI * R cubed )
|
||||
{
|
||||
return (4.0f / 3.0f ) * FM_PI * radius * radius * radius;
|
||||
}
|
||||
|
||||
@@ -1,72 +1,72 @@
|
||||
#ifndef FLOAT_MATH_H
|
||||
|
||||
#define FLOAT_MATH_H
|
||||
|
||||
#ifdef _WIN32
|
||||
#pragma warning(disable : 4324) // disable padding warning
|
||||
#pragma warning(disable : 4244) // disable padding warning
|
||||
#pragma warning(disable : 4267) // possible loss of data
|
||||
#pragma warning(disable:4530) // Disable the exception disable but used in MSCV Stl warning.
|
||||
#pragma warning(disable:4996) //Turn off warnings about deprecated C routines
|
||||
#pragma warning(disable:4786) // Disable the "debug name too long" warning
|
||||
#endif
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
// a set of routines that last you do common 3d math
|
||||
// operations without any vector, matrix, or quaternion
|
||||
// classes or templates.
|
||||
//
|
||||
// a vector (or point) is a 'float *' to 3 floating point numbers.
|
||||
// a matrix is a 'float *' to an array of 16 floating point numbers representing a 4x4 transformation matrix compatible with D3D or OGL
|
||||
// a quaternion is a 'float *' to 4 floats representing a quaternion x,y,z,w
|
||||
|
||||
const float FM_PI = 3.141592654f;
|
||||
const float FM_DEG_TO_RAD = ((2.0f * FM_PI) / 360.0f);
|
||||
const float FM_RAD_TO_DEG = (360.0f / (2.0f * FM_PI));
|
||||
|
||||
void fm_identity(float *matrix); // set 4x4 matrix to identity.
|
||||
void fm_inverseRT(const float *matrix,const float *pos,float *t); // inverse rotate translate the point.
|
||||
void fm_eulerMatrix(float ax,float ay,float az,float *matrix); // convert euler (in radians) to a dest 4x4 matrix (translation set to zero)
|
||||
void fm_getAABB(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax);
|
||||
void fm_eulerToQuat(float roll,float pitch,float yaw,float *quat); // convert euler angles to quaternion.
|
||||
void fm_quatToMatrix(const float *quat,float *matrix); // convert quaterinion rotation to matrix, translation set to zero.
|
||||
void fm_quatRotate(const float *quat,const float *v,float *r); // rotate a vector directly by a quaternion.
|
||||
void fm_getTranslation(const float *matrix,float *t);
|
||||
void fm_matrixToQuat(const float *matrix,float *quat); // convert the 3x3 portion of a 4x4 matrix into a quaterion as x,y,z,w
|
||||
float fm_sphereVolume(float radius); // return's the volume of a sphere of this radius (4/3 PI * R cubed )
|
||||
|
||||
#endif
|
||||
#ifndef FLOAT_MATH_H
|
||||
|
||||
#define FLOAT_MATH_H
|
||||
|
||||
#ifdef _WIN32
|
||||
#pragma warning(disable : 4324) // disable padding warning
|
||||
#pragma warning(disable : 4244) // disable padding warning
|
||||
#pragma warning(disable : 4267) // possible loss of data
|
||||
#pragma warning(disable:4530) // Disable the exception disable but used in MSCV Stl warning.
|
||||
#pragma warning(disable:4996) //Turn off warnings about deprecated C routines
|
||||
#pragma warning(disable:4786) // Disable the "debug name too long" warning
|
||||
#endif
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
// a set of routines that last you do common 3d math
|
||||
// operations without any vector, matrix, or quaternion
|
||||
// classes or templates.
|
||||
//
|
||||
// a vector (or point) is a 'float *' to 3 floating point numbers.
|
||||
// a matrix is a 'float *' to an array of 16 floating point numbers representing a 4x4 transformation matrix compatible with D3D or OGL
|
||||
// a quaternion is a 'float *' to 4 floats representing a quaternion x,y,z,w
|
||||
|
||||
const float FM_PI = 3.141592654f;
|
||||
const float FM_DEG_TO_RAD = ((2.0f * FM_PI) / 360.0f);
|
||||
const float FM_RAD_TO_DEG = (360.0f / (2.0f * FM_PI));
|
||||
|
||||
void fm_identity(float *matrix); // set 4x4 matrix to identity.
|
||||
void fm_inverseRT(const float *matrix,const float *pos,float *t); // inverse rotate translate the point.
|
||||
void fm_eulerMatrix(float ax,float ay,float az,float *matrix); // convert euler (in radians) to a dest 4x4 matrix (translation set to zero)
|
||||
void fm_getAABB(unsigned int vcount,const float *points,unsigned int pstride,float *bmin,float *bmax);
|
||||
void fm_eulerToQuat(float roll,float pitch,float yaw,float *quat); // convert euler angles to quaternion.
|
||||
void fm_quatToMatrix(const float *quat,float *matrix); // convert quaterinion rotation to matrix, translation set to zero.
|
||||
void fm_quatRotate(const float *quat,const float *v,float *r); // rotate a vector directly by a quaternion.
|
||||
void fm_getTranslation(const float *matrix,float *t);
|
||||
void fm_matrixToQuat(const float *matrix,float *quat); // convert the 3x3 portion of a 4x4 matrix into a quaterion as x,y,z,w
|
||||
float fm_sphereVolume(float radius); // return's the volume of a sphere of this radius (4/3 PI * R cubed )
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,128 +1,128 @@
|
||||
#include "float_math.h"
|
||||
#include "meshvolume.h"
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
inline float det(const float *p1,const float *p2,const float *p3)
|
||||
{
|
||||
return p1[0]*p2[1]*p3[2] + p2[0]*p3[1]*p1[2] + p3[0]*p1[1]*p2[2] -p1[0]*p3[1]*p2[2] - p2[0]*p1[1]*p3[2] - p3[0]*p2[1]*p1[2];
|
||||
}
|
||||
|
||||
float computeMeshVolume(const float *vertices,unsigned int tcount,const unsigned int *indices)
|
||||
{
|
||||
float volume = 0;
|
||||
|
||||
for (unsigned int i=0; i<tcount; i++,indices+=3)
|
||||
{
|
||||
|
||||
const float *p1 = &vertices[ indices[0]*3 ];
|
||||
const float *p2 = &vertices[ indices[1]*3 ];
|
||||
const float *p3 = &vertices[ indices[2]*3 ];
|
||||
|
||||
volume+=det(p1,p2,p3); // compute the volume of the tetrahedran relative to the origin.
|
||||
}
|
||||
|
||||
volume*=(1.0f/6.0f);
|
||||
if ( volume < 0 )
|
||||
volume*=-1;
|
||||
return volume;
|
||||
}
|
||||
|
||||
|
||||
inline void CrossProduct(const float *a,const float *b,float *cross)
|
||||
{
|
||||
cross[0] = a[1]*b[2] - a[2]*b[1];
|
||||
cross[1] = a[2]*b[0] - a[0]*b[2];
|
||||
cross[2] = a[0]*b[1] - a[1]*b[0];
|
||||
}
|
||||
|
||||
inline float DotProduct(const float *a,const float *b)
|
||||
{
|
||||
return a[0] * b[0] + a[1] * b[1] + a[2] * b[2];
|
||||
}
|
||||
|
||||
inline float tetVolume(const float *p0,const float *p1,const float *p2,const float *p3)
|
||||
{
|
||||
float a[3];
|
||||
float b[3];
|
||||
float c[3];
|
||||
|
||||
a[0] = p1[0] - p0[0];
|
||||
a[1] = p1[1] - p0[1];
|
||||
a[2] = p1[2] - p0[2];
|
||||
|
||||
b[0] = p2[0] - p0[0];
|
||||
b[1] = p2[1] - p0[1];
|
||||
b[2] = p2[2] - p0[2];
|
||||
|
||||
c[0] = p3[0] - p0[0];
|
||||
c[1] = p3[1] - p0[1];
|
||||
c[2] = p3[2] - p0[2];
|
||||
|
||||
float cross[3];
|
||||
|
||||
CrossProduct( b, c, cross );
|
||||
|
||||
float volume = DotProduct( a, cross );
|
||||
|
||||
if ( volume < 0 )
|
||||
return -volume;
|
||||
|
||||
return volume;
|
||||
}
|
||||
|
||||
inline float det(const float *p0,const float *p1,const float *p2,const float *p3)
|
||||
{
|
||||
return p1[0]*p2[1]*p3[2] + p2[0]*p3[1]*p1[2] + p3[0]*p1[1]*p2[2] -p1[0]*p3[1]*p2[2] - p2[0]*p1[1]*p3[2] - p3[0]*p2[1]*p1[2];
|
||||
}
|
||||
|
||||
float computeMeshVolume2(const float *vertices,unsigned int tcount,const unsigned int *indices)
|
||||
{
|
||||
float volume = 0;
|
||||
|
||||
const float *p0 = vertices;
|
||||
for (unsigned int i=0; i<tcount; i++,indices+=3)
|
||||
{
|
||||
|
||||
const float *p1 = &vertices[ indices[0]*3 ];
|
||||
const float *p2 = &vertices[ indices[1]*3 ];
|
||||
const float *p3 = &vertices[ indices[2]*3 ];
|
||||
|
||||
volume+=tetVolume(p0,p1,p2,p3); // compute the volume of the tetrahdren relative to the root vertice
|
||||
}
|
||||
|
||||
return volume * (1.0f / 6.0f );
|
||||
}
|
||||
|
||||
#include "float_math.h"
|
||||
#include "meshvolume.h"
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
inline float det(const float *p1,const float *p2,const float *p3)
|
||||
{
|
||||
return p1[0]*p2[1]*p3[2] + p2[0]*p3[1]*p1[2] + p3[0]*p1[1]*p2[2] -p1[0]*p3[1]*p2[2] - p2[0]*p1[1]*p3[2] - p3[0]*p2[1]*p1[2];
|
||||
}
|
||||
|
||||
float computeMeshVolume(const float *vertices,unsigned int tcount,const unsigned int *indices)
|
||||
{
|
||||
float volume = 0;
|
||||
|
||||
for (unsigned int i=0; i<tcount; i++,indices+=3)
|
||||
{
|
||||
|
||||
const float *p1 = &vertices[ indices[0]*3 ];
|
||||
const float *p2 = &vertices[ indices[1]*3 ];
|
||||
const float *p3 = &vertices[ indices[2]*3 ];
|
||||
|
||||
volume+=det(p1,p2,p3); // compute the volume of the tetrahedran relative to the origin.
|
||||
}
|
||||
|
||||
volume*=(1.0f/6.0f);
|
||||
if ( volume < 0 )
|
||||
volume*=-1;
|
||||
return volume;
|
||||
}
|
||||
|
||||
|
||||
inline void CrossProduct(const float *a,const float *b,float *cross)
|
||||
{
|
||||
cross[0] = a[1]*b[2] - a[2]*b[1];
|
||||
cross[1] = a[2]*b[0] - a[0]*b[2];
|
||||
cross[2] = a[0]*b[1] - a[1]*b[0];
|
||||
}
|
||||
|
||||
inline float DotProduct(const float *a,const float *b)
|
||||
{
|
||||
return a[0] * b[0] + a[1] * b[1] + a[2] * b[2];
|
||||
}
|
||||
|
||||
inline float tetVolume(const float *p0,const float *p1,const float *p2,const float *p3)
|
||||
{
|
||||
float a[3];
|
||||
float b[3];
|
||||
float c[3];
|
||||
|
||||
a[0] = p1[0] - p0[0];
|
||||
a[1] = p1[1] - p0[1];
|
||||
a[2] = p1[2] - p0[2];
|
||||
|
||||
b[0] = p2[0] - p0[0];
|
||||
b[1] = p2[1] - p0[1];
|
||||
b[2] = p2[2] - p0[2];
|
||||
|
||||
c[0] = p3[0] - p0[0];
|
||||
c[1] = p3[1] - p0[1];
|
||||
c[2] = p3[2] - p0[2];
|
||||
|
||||
float cross[3];
|
||||
|
||||
CrossProduct( b, c, cross );
|
||||
|
||||
float volume = DotProduct( a, cross );
|
||||
|
||||
if ( volume < 0 )
|
||||
return -volume;
|
||||
|
||||
return volume;
|
||||
}
|
||||
|
||||
inline float det(const float *p0,const float *p1,const float *p2,const float *p3)
|
||||
{
|
||||
return p1[0]*p2[1]*p3[2] + p2[0]*p3[1]*p1[2] + p3[0]*p1[1]*p2[2] -p1[0]*p3[1]*p2[2] - p2[0]*p1[1]*p3[2] - p3[0]*p2[1]*p1[2];
|
||||
}
|
||||
|
||||
float computeMeshVolume2(const float *vertices,unsigned int tcount,const unsigned int *indices)
|
||||
{
|
||||
float volume = 0;
|
||||
|
||||
const float *p0 = vertices;
|
||||
for (unsigned int i=0; i<tcount; i++,indices+=3)
|
||||
{
|
||||
|
||||
const float *p1 = &vertices[ indices[0]*3 ];
|
||||
const float *p2 = &vertices[ indices[1]*3 ];
|
||||
const float *p3 = &vertices[ indices[2]*3 ];
|
||||
|
||||
volume+=tetVolume(p0,p1,p2,p3); // compute the volume of the tetrahdren relative to the root vertice
|
||||
}
|
||||
|
||||
return volume * (1.0f / 6.0f );
|
||||
}
|
||||
|
||||
|
||||
@@ -1,45 +1,45 @@
|
||||
#ifndef MESH_VOLUME_H
|
||||
|
||||
#define MESH_VOLUME_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
float computeMeshVolume(const float *vertices,unsigned int tcount,const unsigned int *indices);
|
||||
float computeMeshVolume2(const float *vertices,unsigned int tcount,const unsigned int *indices);
|
||||
|
||||
|
||||
#endif
|
||||
#ifndef MESH_VOLUME_H
|
||||
|
||||
#define MESH_VOLUME_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
float computeMeshVolume(const float *vertices,unsigned int tcount,const unsigned int *indices);
|
||||
float computeMeshVolume2(const float *vertices,unsigned int tcount,const unsigned int *indices);
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,238 +1,238 @@
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
#include "planetri.h"
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
static inline float DistToPt(const float *p,const float *plane)
|
||||
{
|
||||
float x = p[0];
|
||||
float y = p[1];
|
||||
float z = p[2];
|
||||
float d = x*plane[0] + y*plane[1] + z*plane[2] + plane[3];
|
||||
return d;
|
||||
}
|
||||
|
||||
|
||||
static PlaneTriResult getSidePlane(const float *p,const float *plane,float epsilon)
|
||||
{
|
||||
|
||||
float d = DistToPt(p,plane);
|
||||
|
||||
if ( (d+epsilon) > 0 )
|
||||
return PTR_FRONT; // it is 'in front' within the provided epsilon value.
|
||||
|
||||
return PTR_BACK;
|
||||
}
|
||||
|
||||
static void add(const float *p,float *dest,unsigned int tstride,unsigned int &pcount)
|
||||
{
|
||||
char *d = (char *) dest;
|
||||
d = d + pcount*tstride;
|
||||
dest = (float *) d;
|
||||
dest[0] = p[0];
|
||||
dest[1] = p[1];
|
||||
dest[2] = p[2];
|
||||
pcount++;
|
||||
assert( pcount <= 4 );
|
||||
}
|
||||
|
||||
|
||||
// assumes that the points are on opposite sides of the plane!
|
||||
static void intersect(const float *p1,const float *p2,float *split,const float *plane)
|
||||
{
|
||||
|
||||
float dp1 = DistToPt(p1,plane);
|
||||
|
||||
float dir[3];
|
||||
|
||||
dir[0] = p2[0] - p1[0];
|
||||
dir[1] = p2[1] - p1[1];
|
||||
dir[2] = p2[2] - p1[2];
|
||||
|
||||
float dot1 = dir[0]*plane[0] + dir[1]*plane[1] + dir[2]*plane[2];
|
||||
float dot2 = dp1 - plane[3];
|
||||
|
||||
float t = -(plane[3] + dot2 ) / dot1;
|
||||
|
||||
split[0] = (dir[0]*t)+p1[0];
|
||||
split[1] = (dir[1]*t)+p1[1];
|
||||
split[2] = (dir[2]*t)+p1[2];
|
||||
|
||||
}
|
||||
|
||||
PlaneTriResult planeTriIntersection(const float *plane, // the plane equation in Ax+By+Cz+D format
|
||||
const float *triangle, // the source triangle.
|
||||
unsigned int tstride, // stride in bytes of the input and output triangles
|
||||
float epsilon, // the co-planer epsilon value.
|
||||
float *front, // the triangle in front of the
|
||||
unsigned int &fcount, // number of vertices in the 'front' triangle
|
||||
float *back, // the triangle in back of the plane
|
||||
unsigned int &bcount) // the number of vertices in the 'back' triangle.
|
||||
{
|
||||
fcount = 0;
|
||||
bcount = 0;
|
||||
|
||||
const char *tsource = (const char *) triangle;
|
||||
|
||||
// get the three vertices of the triangle.
|
||||
const float *p1 = (const float *) (tsource);
|
||||
const float *p2 = (const float *) (tsource+tstride);
|
||||
const float *p3 = (const float *) (tsource+tstride*2);
|
||||
|
||||
|
||||
PlaneTriResult r1 = getSidePlane(p1,plane,epsilon); // compute the side of the plane each vertex is on
|
||||
PlaneTriResult r2 = getSidePlane(p2,plane,epsilon);
|
||||
PlaneTriResult r3 = getSidePlane(p3,plane,epsilon);
|
||||
|
||||
if ( r1 == r2 && r1 == r3 ) // if all three vertices are on the same side of the plane.
|
||||
{
|
||||
if ( r1 == PTR_FRONT ) // if all three are in front of the plane, then copy to the 'front' output triangle.
|
||||
{
|
||||
add(p1,front,tstride,fcount);
|
||||
add(p2,front,tstride,fcount);
|
||||
add(p3,front,tstride,fcount);
|
||||
}
|
||||
else
|
||||
{
|
||||
add(p1,back,tstride,bcount); // if all three are in 'abck' then copy to the 'back' output triangle.
|
||||
add(p2,back,tstride,bcount);
|
||||
add(p3,back,tstride,bcount);
|
||||
}
|
||||
return r1; // if all three points are on the same side of the plane return result
|
||||
}
|
||||
|
||||
// ok.. we need to split the triangle at the plane.
|
||||
|
||||
// First test ray segment P1 to P2
|
||||
if ( r1 == r2 ) // if these are both on the same side...
|
||||
{
|
||||
if ( r1 == PTR_FRONT )
|
||||
{
|
||||
add( p1, front, tstride, fcount );
|
||||
add( p2, front, tstride, fcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add( p1, back, tstride, bcount );
|
||||
add( p2, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float split[3]; // split the point
|
||||
intersect(p1,p2,split,plane);
|
||||
|
||||
if ( r1 == PTR_FRONT )
|
||||
{
|
||||
|
||||
add(p1, front, tstride, fcount );
|
||||
add(split, front, tstride, fcount );
|
||||
|
||||
add(split, back, tstride, bcount );
|
||||
add(p2, back, tstride, bcount );
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
add(p1, back, tstride, bcount );
|
||||
add(split, back, tstride, bcount );
|
||||
|
||||
add(split, front, tstride, fcount );
|
||||
add(p2, front, tstride, fcount );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Next test ray segment P2 to P3
|
||||
if ( r2 == r3 ) // if these are both on the same side...
|
||||
{
|
||||
if ( r3 == PTR_FRONT )
|
||||
{
|
||||
add( p3, front, tstride, fcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add( p3, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float split[3]; // split the point
|
||||
intersect(p2,p3,split,plane);
|
||||
|
||||
if ( r3 == PTR_FRONT )
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
|
||||
add(p3, front, tstride, fcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
|
||||
add(p3, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
|
||||
// Next test ray segment P3 to P1
|
||||
if ( r3 != r1 ) // if these are both on the same side...
|
||||
{
|
||||
float split[3]; // split the point
|
||||
|
||||
intersect(p3,p1,split,plane);
|
||||
|
||||
if ( r1 == PTR_FRONT )
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
return PTR_SPLIT;
|
||||
}
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
#include "planetri.h"
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
static inline float DistToPt(const float *p,const float *plane)
|
||||
{
|
||||
float x = p[0];
|
||||
float y = p[1];
|
||||
float z = p[2];
|
||||
float d = x*plane[0] + y*plane[1] + z*plane[2] + plane[3];
|
||||
return d;
|
||||
}
|
||||
|
||||
|
||||
static PlaneTriResult getSidePlane(const float *p,const float *plane,float epsilon)
|
||||
{
|
||||
|
||||
float d = DistToPt(p,plane);
|
||||
|
||||
if ( (d+epsilon) > 0 )
|
||||
return PTR_FRONT; // it is 'in front' within the provided epsilon value.
|
||||
|
||||
return PTR_BACK;
|
||||
}
|
||||
|
||||
static void add(const float *p,float *dest,unsigned int tstride,unsigned int &pcount)
|
||||
{
|
||||
char *d = (char *) dest;
|
||||
d = d + pcount*tstride;
|
||||
dest = (float *) d;
|
||||
dest[0] = p[0];
|
||||
dest[1] = p[1];
|
||||
dest[2] = p[2];
|
||||
pcount++;
|
||||
assert( pcount <= 4 );
|
||||
}
|
||||
|
||||
|
||||
// assumes that the points are on opposite sides of the plane!
|
||||
static void intersect(const float *p1,const float *p2,float *split,const float *plane)
|
||||
{
|
||||
|
||||
float dp1 = DistToPt(p1,plane);
|
||||
|
||||
float dir[3];
|
||||
|
||||
dir[0] = p2[0] - p1[0];
|
||||
dir[1] = p2[1] - p1[1];
|
||||
dir[2] = p2[2] - p1[2];
|
||||
|
||||
float dot1 = dir[0]*plane[0] + dir[1]*plane[1] + dir[2]*plane[2];
|
||||
float dot2 = dp1 - plane[3];
|
||||
|
||||
float t = -(plane[3] + dot2 ) / dot1;
|
||||
|
||||
split[0] = (dir[0]*t)+p1[0];
|
||||
split[1] = (dir[1]*t)+p1[1];
|
||||
split[2] = (dir[2]*t)+p1[2];
|
||||
|
||||
}
|
||||
|
||||
PlaneTriResult planeTriIntersection(const float *plane, // the plane equation in Ax+By+Cz+D format
|
||||
const float *triangle, // the source triangle.
|
||||
unsigned int tstride, // stride in bytes of the input and output triangles
|
||||
float epsilon, // the co-planer epsilon value.
|
||||
float *front, // the triangle in front of the
|
||||
unsigned int &fcount, // number of vertices in the 'front' triangle
|
||||
float *back, // the triangle in back of the plane
|
||||
unsigned int &bcount) // the number of vertices in the 'back' triangle.
|
||||
{
|
||||
fcount = 0;
|
||||
bcount = 0;
|
||||
|
||||
const char *tsource = (const char *) triangle;
|
||||
|
||||
// get the three vertices of the triangle.
|
||||
const float *p1 = (const float *) (tsource);
|
||||
const float *p2 = (const float *) (tsource+tstride);
|
||||
const float *p3 = (const float *) (tsource+tstride*2);
|
||||
|
||||
|
||||
PlaneTriResult r1 = getSidePlane(p1,plane,epsilon); // compute the side of the plane each vertex is on
|
||||
PlaneTriResult r2 = getSidePlane(p2,plane,epsilon);
|
||||
PlaneTriResult r3 = getSidePlane(p3,plane,epsilon);
|
||||
|
||||
if ( r1 == r2 && r1 == r3 ) // if all three vertices are on the same side of the plane.
|
||||
{
|
||||
if ( r1 == PTR_FRONT ) // if all three are in front of the plane, then copy to the 'front' output triangle.
|
||||
{
|
||||
add(p1,front,tstride,fcount);
|
||||
add(p2,front,tstride,fcount);
|
||||
add(p3,front,tstride,fcount);
|
||||
}
|
||||
else
|
||||
{
|
||||
add(p1,back,tstride,bcount); // if all three are in 'abck' then copy to the 'back' output triangle.
|
||||
add(p2,back,tstride,bcount);
|
||||
add(p3,back,tstride,bcount);
|
||||
}
|
||||
return r1; // if all three points are on the same side of the plane return result
|
||||
}
|
||||
|
||||
// ok.. we need to split the triangle at the plane.
|
||||
|
||||
// First test ray segment P1 to P2
|
||||
if ( r1 == r2 ) // if these are both on the same side...
|
||||
{
|
||||
if ( r1 == PTR_FRONT )
|
||||
{
|
||||
add( p1, front, tstride, fcount );
|
||||
add( p2, front, tstride, fcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add( p1, back, tstride, bcount );
|
||||
add( p2, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float split[3]; // split the point
|
||||
intersect(p1,p2,split,plane);
|
||||
|
||||
if ( r1 == PTR_FRONT )
|
||||
{
|
||||
|
||||
add(p1, front, tstride, fcount );
|
||||
add(split, front, tstride, fcount );
|
||||
|
||||
add(split, back, tstride, bcount );
|
||||
add(p2, back, tstride, bcount );
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
add(p1, back, tstride, bcount );
|
||||
add(split, back, tstride, bcount );
|
||||
|
||||
add(split, front, tstride, fcount );
|
||||
add(p2, front, tstride, fcount );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// Next test ray segment P2 to P3
|
||||
if ( r2 == r3 ) // if these are both on the same side...
|
||||
{
|
||||
if ( r3 == PTR_FRONT )
|
||||
{
|
||||
add( p3, front, tstride, fcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add( p3, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
float split[3]; // split the point
|
||||
intersect(p2,p3,split,plane);
|
||||
|
||||
if ( r3 == PTR_FRONT )
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
|
||||
add(p3, front, tstride, fcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
|
||||
add(p3, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
|
||||
// Next test ray segment P3 to P1
|
||||
if ( r3 != r1 ) // if these are both on the same side...
|
||||
{
|
||||
float split[3]; // split the point
|
||||
|
||||
intersect(p3,p1,split,plane);
|
||||
|
||||
if ( r1 == PTR_FRONT )
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
}
|
||||
else
|
||||
{
|
||||
add(split, front, tstride, fcount );
|
||||
add(split, back, tstride, bcount );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
return PTR_SPLIT;
|
||||
}
|
||||
|
||||
@@ -1,58 +1,58 @@
|
||||
#ifndef PLANE_TRI_H
|
||||
|
||||
#define PLANE_TRI_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
enum PlaneTriResult
|
||||
{
|
||||
PTR_FRONT,
|
||||
PTR_BACK,
|
||||
PTR_SPLIT
|
||||
};
|
||||
|
||||
PlaneTriResult planeTriIntersection(const float *plane, // the plane equation in Ax+By+Cz+D format
|
||||
const float *triangle, // the source position triangle.
|
||||
unsigned int tstride, // stride in bytes between vertices of the triangle.
|
||||
float epsilon, // the co-planer epsilon value.
|
||||
float *front, // the triangle in front of the
|
||||
unsigned int &fcount, // number of vertices in the 'front' triangle.
|
||||
float *back, // the triangle in back of the plane
|
||||
unsigned int &bcount); // the number of vertices in the 'back' triangle.
|
||||
|
||||
|
||||
#endif
|
||||
#ifndef PLANE_TRI_H
|
||||
|
||||
#define PLANE_TRI_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
enum PlaneTriResult
|
||||
{
|
||||
PTR_FRONT,
|
||||
PTR_BACK,
|
||||
PTR_SPLIT
|
||||
};
|
||||
|
||||
PlaneTriResult planeTriIntersection(const float *plane, // the plane equation in Ax+By+Cz+D format
|
||||
const float *triangle, // the source position triangle.
|
||||
unsigned int tstride, // stride in bytes between vertices of the triangle.
|
||||
float epsilon, // the co-planer epsilon value.
|
||||
float *front, // the triangle in front of the
|
||||
unsigned int &fcount, // number of vertices in the 'front' triangle.
|
||||
float *back, // the triangle in back of the plane
|
||||
unsigned int &bcount); // the number of vertices in the 'back' triangle.
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,134 +1,134 @@
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
#include "raytri.h"
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
/* a = b - c */
|
||||
#define vector(a,b,c) \
|
||||
(a)[0] = (b)[0] - (c)[0]; \
|
||||
(a)[1] = (b)[1] - (c)[1]; \
|
||||
(a)[2] = (b)[2] - (c)[2];
|
||||
|
||||
|
||||
|
||||
#define innerProduct(v,q) \
|
||||
((v)[0] * (q)[0] + \
|
||||
(v)[1] * (q)[1] + \
|
||||
(v)[2] * (q)[2])
|
||||
|
||||
#define crossProduct(a,b,c) \
|
||||
(a)[0] = (b)[1] * (c)[2] - (c)[1] * (b)[2]; \
|
||||
(a)[1] = (b)[2] * (c)[0] - (c)[2] * (b)[0]; \
|
||||
(a)[2] = (b)[0] * (c)[1] - (c)[0] * (b)[1];
|
||||
|
||||
bool rayIntersectsTriangle(const float *p,const float *d,const float *v0,const float *v1,const float *v2,float &t)
|
||||
{
|
||||
|
||||
float e1[3],e2[3],h[3],s[3],q[3];
|
||||
float a,f,u,v;
|
||||
|
||||
vector(e1,v1,v0);
|
||||
vector(e2,v2,v0);
|
||||
crossProduct(h,d,e2);
|
||||
a = innerProduct(e1,h);
|
||||
|
||||
if (a > -0.00001 && a < 0.00001)
|
||||
return(false);
|
||||
|
||||
f = 1/a;
|
||||
vector(s,p,v0);
|
||||
u = f * (innerProduct(s,h));
|
||||
|
||||
if (u < 0.0 || u > 1.0)
|
||||
return(false);
|
||||
|
||||
crossProduct(q,s,e1);
|
||||
v = f * innerProduct(d,q);
|
||||
if (v < 0.0 || u + v > 1.0)
|
||||
return(false);
|
||||
// at this stage we can compute t to find out where
|
||||
// the intersection point is on the line
|
||||
t = f * innerProduct(e2,q);
|
||||
if (t > 0) // ray intersection
|
||||
return(true);
|
||||
else // this means that there is a line intersection
|
||||
// but not a ray intersection
|
||||
return (false);
|
||||
}
|
||||
|
||||
|
||||
bool lineIntersectsTriangle(const float *rayStart,const float *rayEnd,const float *p1,const float *p2,const float *p3,float *sect)
|
||||
{
|
||||
float dir[3];
|
||||
|
||||
dir[0] = rayEnd[0] - rayStart[0];
|
||||
dir[1] = rayEnd[1] - rayStart[1];
|
||||
dir[2] = rayEnd[2] - rayStart[2];
|
||||
|
||||
float d = sqrtf(dir[0]*dir[0] + dir[1]*dir[1] + dir[2]*dir[2]);
|
||||
float r = 1.0f / d;
|
||||
|
||||
dir[0]*=r;
|
||||
dir[1]*=r;
|
||||
dir[2]*=r;
|
||||
|
||||
|
||||
float t;
|
||||
|
||||
bool ret = rayIntersectsTriangle(rayStart, dir, p1, p2, p3, t );
|
||||
|
||||
if ( ret )
|
||||
{
|
||||
if ( t > d )
|
||||
{
|
||||
sect[0] = rayStart[0] + dir[0]*t;
|
||||
sect[1] = rayStart[1] + dir[1]*t;
|
||||
sect[2] = rayStart[2] + dir[2]*t;
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = false;
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <math.h>
|
||||
|
||||
#include "raytri.h"
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
/* a = b - c */
|
||||
#define vector(a,b,c) \
|
||||
(a)[0] = (b)[0] - (c)[0]; \
|
||||
(a)[1] = (b)[1] - (c)[1]; \
|
||||
(a)[2] = (b)[2] - (c)[2];
|
||||
|
||||
|
||||
|
||||
#define innerProduct(v,q) \
|
||||
((v)[0] * (q)[0] + \
|
||||
(v)[1] * (q)[1] + \
|
||||
(v)[2] * (q)[2])
|
||||
|
||||
#define crossProduct(a,b,c) \
|
||||
(a)[0] = (b)[1] * (c)[2] - (c)[1] * (b)[2]; \
|
||||
(a)[1] = (b)[2] * (c)[0] - (c)[2] * (b)[0]; \
|
||||
(a)[2] = (b)[0] * (c)[1] - (c)[0] * (b)[1];
|
||||
|
||||
bool rayIntersectsTriangle(const float *p,const float *d,const float *v0,const float *v1,const float *v2,float &t)
|
||||
{
|
||||
|
||||
float e1[3],e2[3],h[3],s[3],q[3];
|
||||
float a,f,u,v;
|
||||
|
||||
vector(e1,v1,v0);
|
||||
vector(e2,v2,v0);
|
||||
crossProduct(h,d,e2);
|
||||
a = innerProduct(e1,h);
|
||||
|
||||
if (a > -0.00001 && a < 0.00001)
|
||||
return(false);
|
||||
|
||||
f = 1/a;
|
||||
vector(s,p,v0);
|
||||
u = f * (innerProduct(s,h));
|
||||
|
||||
if (u < 0.0 || u > 1.0)
|
||||
return(false);
|
||||
|
||||
crossProduct(q,s,e1);
|
||||
v = f * innerProduct(d,q);
|
||||
if (v < 0.0 || u + v > 1.0)
|
||||
return(false);
|
||||
// at this stage we can compute t to find out where
|
||||
// the intersection point is on the line
|
||||
t = f * innerProduct(e2,q);
|
||||
if (t > 0) // ray intersection
|
||||
return(true);
|
||||
else // this means that there is a line intersection
|
||||
// but not a ray intersection
|
||||
return (false);
|
||||
}
|
||||
|
||||
|
||||
bool lineIntersectsTriangle(const float *rayStart,const float *rayEnd,const float *p1,const float *p2,const float *p3,float *sect)
|
||||
{
|
||||
float dir[3];
|
||||
|
||||
dir[0] = rayEnd[0] - rayStart[0];
|
||||
dir[1] = rayEnd[1] - rayStart[1];
|
||||
dir[2] = rayEnd[2] - rayStart[2];
|
||||
|
||||
float d = sqrtf(dir[0]*dir[0] + dir[1]*dir[1] + dir[2]*dir[2]);
|
||||
float r = 1.0f / d;
|
||||
|
||||
dir[0]*=r;
|
||||
dir[1]*=r;
|
||||
dir[2]*=r;
|
||||
|
||||
|
||||
float t;
|
||||
|
||||
bool ret = rayIntersectsTriangle(rayStart, dir, p1, p2, p3, t );
|
||||
|
||||
if ( ret )
|
||||
{
|
||||
if ( t > d )
|
||||
{
|
||||
sect[0] = rayStart[0] + dir[0]*t;
|
||||
sect[1] = rayStart[1] + dir[1]*t;
|
||||
sect[2] = rayStart[2] + dir[2]*t;
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = false;
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1,45 +1,45 @@
|
||||
#ifndef RAY_TRI_H
|
||||
|
||||
#define RAY_TRI_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
// returns true if the ray intersects the triangle.
|
||||
bool lineIntersectsTriangle(const float *rayStart,const float *rayEnd,const float *p1,const float *p2,const float *p3,float *sect);
|
||||
bool rayIntersectsTriangle(const float *p,const float *d,const float *v0,const float *v1,const float *v2,float &t);
|
||||
|
||||
#endif
|
||||
#ifndef RAY_TRI_H
|
||||
|
||||
#define RAY_TRI_H
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
// returns true if the ray intersects the triangle.
|
||||
bool lineIntersectsTriangle(const float *rayStart,const float *rayEnd,const float *p1,const float *p2,const float *p3,float *sect);
|
||||
bool rayIntersectsTriangle(const float *p,const float *d,const float *v0,const float *v1,const float *v2,float &t);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,306 +1,306 @@
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <float.h>
|
||||
#include <math.h>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
#include "splitplane.h"
|
||||
#include "ConvexDecomposition.h"
|
||||
#include "cd_vector.h"
|
||||
#include "cd_hull.h"
|
||||
#include "cd_wavefront.h"
|
||||
#include "bestfit.h"
|
||||
#include "planetri.h"
|
||||
#include "vlookup.h"
|
||||
#include "meshvolume.h"
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
static void computePlane(const float *A,const float *B,const float *C,float *plane)
|
||||
{
|
||||
|
||||
float vx = (B[0] - C[0]);
|
||||
float vy = (B[1] - C[1]);
|
||||
float vz = (B[2] - C[2]);
|
||||
|
||||
float wx = (A[0] - B[0]);
|
||||
float wy = (A[1] - B[1]);
|
||||
float wz = (A[2] - B[2]);
|
||||
|
||||
float vw_x = vy * wz - vz * wy;
|
||||
float vw_y = vz * wx - vx * wz;
|
||||
float vw_z = vx * wy - vy * wx;
|
||||
|
||||
float mag = sqrtf((vw_x * vw_x) + (vw_y * vw_y) + (vw_z * vw_z));
|
||||
|
||||
if ( mag < 0.000001f )
|
||||
{
|
||||
mag = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
mag = 1.0f/mag;
|
||||
}
|
||||
|
||||
float x = vw_x * mag;
|
||||
float y = vw_y * mag;
|
||||
float z = vw_z * mag;
|
||||
|
||||
|
||||
float D = 0.0f - ((x*A[0])+(y*A[1])+(z*A[2]));
|
||||
|
||||
plane[0] = x;
|
||||
plane[1] = y;
|
||||
plane[2] = z;
|
||||
plane[3] = D;
|
||||
|
||||
}
|
||||
|
||||
class Rect3d
|
||||
{
|
||||
public:
|
||||
Rect3d(void) { };
|
||||
|
||||
Rect3d(const float *bmin,const float *bmax)
|
||||
{
|
||||
|
||||
mMin[0] = bmin[0];
|
||||
mMin[1] = bmin[1];
|
||||
mMin[2] = bmin[2];
|
||||
|
||||
mMax[0] = bmax[0];
|
||||
mMax[1] = bmax[1];
|
||||
mMax[2] = bmax[2];
|
||||
|
||||
}
|
||||
|
||||
void SetMin(const float *bmin)
|
||||
{
|
||||
mMin[0] = bmin[0];
|
||||
mMin[1] = bmin[1];
|
||||
mMin[2] = bmin[2];
|
||||
}
|
||||
|
||||
void SetMax(const float *bmax)
|
||||
{
|
||||
mMax[0] = bmax[0];
|
||||
mMax[1] = bmax[1];
|
||||
mMax[2] = bmax[2];
|
||||
}
|
||||
|
||||
void SetMin(float x,float y,float z)
|
||||
{
|
||||
mMin[0] = x;
|
||||
mMin[1] = y;
|
||||
mMin[2] = z;
|
||||
}
|
||||
|
||||
void SetMax(float x,float y,float z)
|
||||
{
|
||||
mMax[0] = x;
|
||||
mMax[1] = y;
|
||||
mMax[2] = z;
|
||||
}
|
||||
|
||||
float mMin[3];
|
||||
float mMax[3];
|
||||
};
|
||||
|
||||
void splitRect(unsigned int axis,
|
||||
const Rect3d &source,
|
||||
Rect3d &b1,
|
||||
Rect3d &b2,
|
||||
const float *midpoint)
|
||||
{
|
||||
switch ( axis )
|
||||
{
|
||||
case 0:
|
||||
b1.SetMin(source.mMin);
|
||||
b1.SetMax( midpoint[0], source.mMax[1], source.mMax[2] );
|
||||
|
||||
b2.SetMin( midpoint[0], source.mMin[1], source.mMin[2] );
|
||||
b2.SetMax(source.mMax);
|
||||
|
||||
break;
|
||||
case 1:
|
||||
b1.SetMin(source.mMin);
|
||||
b1.SetMax( source.mMax[0], midpoint[1], source.mMax[2] );
|
||||
|
||||
b2.SetMin( source.mMin[0], midpoint[1], source.mMin[2] );
|
||||
b2.SetMax(source.mMax);
|
||||
|
||||
break;
|
||||
case 2:
|
||||
b1.SetMin(source.mMin);
|
||||
b1.SetMax( source.mMax[0], source.mMax[1], midpoint[2] );
|
||||
|
||||
b2.SetMin( source.mMin[0], source.mMin[1], midpoint[2] );
|
||||
b2.SetMax(source.mMax);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
bool computeSplitPlane(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float *plane)
|
||||
{
|
||||
float bmin[3] = { 1e9, 1e9, 1e9 };
|
||||
float bmax[3] = { -1e9, -1e9, -1e9 };
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
const float *p = &vertices[i*3];
|
||||
|
||||
if ( p[0] < bmin[0] ) bmin[0] = p[0];
|
||||
if ( p[1] < bmin[1] ) bmin[1] = p[1];
|
||||
if ( p[2] < bmin[2] ) bmin[2] = p[2];
|
||||
|
||||
if ( p[0] > bmax[0] ) bmax[0] = p[0];
|
||||
if ( p[1] > bmax[1] ) bmax[1] = p[1];
|
||||
if ( p[2] > bmax[2] ) bmax[2] = p[2];
|
||||
|
||||
}
|
||||
|
||||
float dx = bmax[0] - bmin[0];
|
||||
float dy = bmax[1] - bmin[1];
|
||||
float dz = bmax[2] - bmin[2];
|
||||
|
||||
|
||||
float laxis = dx;
|
||||
|
||||
unsigned int axis = 0;
|
||||
|
||||
if ( dy > dx )
|
||||
{
|
||||
axis = 1;
|
||||
laxis = dy;
|
||||
}
|
||||
|
||||
if ( dz > dx && dz > dy )
|
||||
{
|
||||
axis = 2;
|
||||
laxis = dz;
|
||||
}
|
||||
|
||||
float p1[3];
|
||||
float p2[3];
|
||||
float p3[3];
|
||||
|
||||
p3[0] = p2[0] = p1[0] = bmin[0] + dx*0.5f;
|
||||
p3[1] = p2[1] = p1[1] = bmin[1] + dy*0.5f;
|
||||
p3[2] = p2[2] = p1[2] = bmin[2] + dz*0.5f;
|
||||
|
||||
Rect3d b(bmin,bmax);
|
||||
|
||||
Rect3d b1,b2;
|
||||
|
||||
splitRect(axis,b,b1,b2,p1);
|
||||
|
||||
|
||||
// callback->ConvexDebugBound(b1.mMin,b1.mMax,0x00FF00);
|
||||
// callback->ConvexDebugBound(b2.mMin,b2.mMax,0xFFFF00);
|
||||
|
||||
switch ( axis )
|
||||
{
|
||||
case 0:
|
||||
p2[1] = bmin[1];
|
||||
p2[2] = bmin[2];
|
||||
|
||||
if ( dz > dy )
|
||||
{
|
||||
p3[1] = bmax[1];
|
||||
p3[2] = bmin[2];
|
||||
}
|
||||
else
|
||||
{
|
||||
p3[1] = bmin[1];
|
||||
p3[2] = bmax[2];
|
||||
}
|
||||
|
||||
break;
|
||||
case 1:
|
||||
p2[0] = bmin[0];
|
||||
p2[2] = bmin[2];
|
||||
|
||||
if ( dx > dz )
|
||||
{
|
||||
p3[0] = bmax[0];
|
||||
p3[2] = bmin[2];
|
||||
}
|
||||
else
|
||||
{
|
||||
p3[0] = bmin[0];
|
||||
p3[2] = bmax[2];
|
||||
}
|
||||
|
||||
break;
|
||||
case 2:
|
||||
p2[0] = bmin[0];
|
||||
p2[1] = bmin[1];
|
||||
|
||||
if ( dx > dy )
|
||||
{
|
||||
p3[0] = bmax[0];
|
||||
p3[1] = bmin[1];
|
||||
}
|
||||
else
|
||||
{
|
||||
p3[0] = bmin[0];
|
||||
p3[1] = bmax[1];
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
// callback->ConvexDebugTri(p1,p2,p3,0xFF0000);
|
||||
|
||||
computePlane(p1,p2,p3,plane);
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
#include <float.h>
|
||||
#include <math.h>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
#include "splitplane.h"
|
||||
#include "ConvexDecomposition.h"
|
||||
#include "cd_vector.h"
|
||||
#include "cd_hull.h"
|
||||
#include "cd_wavefront.h"
|
||||
#include "bestfit.h"
|
||||
#include "planetri.h"
|
||||
#include "vlookup.h"
|
||||
#include "meshvolume.h"
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
static void computePlane(const float *A,const float *B,const float *C,float *plane)
|
||||
{
|
||||
|
||||
float vx = (B[0] - C[0]);
|
||||
float vy = (B[1] - C[1]);
|
||||
float vz = (B[2] - C[2]);
|
||||
|
||||
float wx = (A[0] - B[0]);
|
||||
float wy = (A[1] - B[1]);
|
||||
float wz = (A[2] - B[2]);
|
||||
|
||||
float vw_x = vy * wz - vz * wy;
|
||||
float vw_y = vz * wx - vx * wz;
|
||||
float vw_z = vx * wy - vy * wx;
|
||||
|
||||
float mag = sqrtf((vw_x * vw_x) + (vw_y * vw_y) + (vw_z * vw_z));
|
||||
|
||||
if ( mag < 0.000001f )
|
||||
{
|
||||
mag = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
mag = 1.0f/mag;
|
||||
}
|
||||
|
||||
float x = vw_x * mag;
|
||||
float y = vw_y * mag;
|
||||
float z = vw_z * mag;
|
||||
|
||||
|
||||
float D = 0.0f - ((x*A[0])+(y*A[1])+(z*A[2]));
|
||||
|
||||
plane[0] = x;
|
||||
plane[1] = y;
|
||||
plane[2] = z;
|
||||
plane[3] = D;
|
||||
|
||||
}
|
||||
|
||||
class Rect3d
|
||||
{
|
||||
public:
|
||||
Rect3d(void) { };
|
||||
|
||||
Rect3d(const float *bmin,const float *bmax)
|
||||
{
|
||||
|
||||
mMin[0] = bmin[0];
|
||||
mMin[1] = bmin[1];
|
||||
mMin[2] = bmin[2];
|
||||
|
||||
mMax[0] = bmax[0];
|
||||
mMax[1] = bmax[1];
|
||||
mMax[2] = bmax[2];
|
||||
|
||||
}
|
||||
|
||||
void SetMin(const float *bmin)
|
||||
{
|
||||
mMin[0] = bmin[0];
|
||||
mMin[1] = bmin[1];
|
||||
mMin[2] = bmin[2];
|
||||
}
|
||||
|
||||
void SetMax(const float *bmax)
|
||||
{
|
||||
mMax[0] = bmax[0];
|
||||
mMax[1] = bmax[1];
|
||||
mMax[2] = bmax[2];
|
||||
}
|
||||
|
||||
void SetMin(float x,float y,float z)
|
||||
{
|
||||
mMin[0] = x;
|
||||
mMin[1] = y;
|
||||
mMin[2] = z;
|
||||
}
|
||||
|
||||
void SetMax(float x,float y,float z)
|
||||
{
|
||||
mMax[0] = x;
|
||||
mMax[1] = y;
|
||||
mMax[2] = z;
|
||||
}
|
||||
|
||||
float mMin[3];
|
||||
float mMax[3];
|
||||
};
|
||||
|
||||
void splitRect(unsigned int axis,
|
||||
const Rect3d &source,
|
||||
Rect3d &b1,
|
||||
Rect3d &b2,
|
||||
const float *midpoint)
|
||||
{
|
||||
switch ( axis )
|
||||
{
|
||||
case 0:
|
||||
b1.SetMin(source.mMin);
|
||||
b1.SetMax( midpoint[0], source.mMax[1], source.mMax[2] );
|
||||
|
||||
b2.SetMin( midpoint[0], source.mMin[1], source.mMin[2] );
|
||||
b2.SetMax(source.mMax);
|
||||
|
||||
break;
|
||||
case 1:
|
||||
b1.SetMin(source.mMin);
|
||||
b1.SetMax( source.mMax[0], midpoint[1], source.mMax[2] );
|
||||
|
||||
b2.SetMin( source.mMin[0], midpoint[1], source.mMin[2] );
|
||||
b2.SetMax(source.mMax);
|
||||
|
||||
break;
|
||||
case 2:
|
||||
b1.SetMin(source.mMin);
|
||||
b1.SetMax( source.mMax[0], source.mMax[1], midpoint[2] );
|
||||
|
||||
b2.SetMin( source.mMin[0], source.mMin[1], midpoint[2] );
|
||||
b2.SetMax(source.mMax);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
bool computeSplitPlane(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float *plane)
|
||||
{
|
||||
float bmin[3] = { 1e9, 1e9, 1e9 };
|
||||
float bmax[3] = { -1e9, -1e9, -1e9 };
|
||||
|
||||
for (unsigned int i=0; i<vcount; i++)
|
||||
{
|
||||
const float *p = &vertices[i*3];
|
||||
|
||||
if ( p[0] < bmin[0] ) bmin[0] = p[0];
|
||||
if ( p[1] < bmin[1] ) bmin[1] = p[1];
|
||||
if ( p[2] < bmin[2] ) bmin[2] = p[2];
|
||||
|
||||
if ( p[0] > bmax[0] ) bmax[0] = p[0];
|
||||
if ( p[1] > bmax[1] ) bmax[1] = p[1];
|
||||
if ( p[2] > bmax[2] ) bmax[2] = p[2];
|
||||
|
||||
}
|
||||
|
||||
float dx = bmax[0] - bmin[0];
|
||||
float dy = bmax[1] - bmin[1];
|
||||
float dz = bmax[2] - bmin[2];
|
||||
|
||||
|
||||
float laxis = dx;
|
||||
|
||||
unsigned int axis = 0;
|
||||
|
||||
if ( dy > dx )
|
||||
{
|
||||
axis = 1;
|
||||
laxis = dy;
|
||||
}
|
||||
|
||||
if ( dz > dx && dz > dy )
|
||||
{
|
||||
axis = 2;
|
||||
laxis = dz;
|
||||
}
|
||||
|
||||
float p1[3];
|
||||
float p2[3];
|
||||
float p3[3];
|
||||
|
||||
p3[0] = p2[0] = p1[0] = bmin[0] + dx*0.5f;
|
||||
p3[1] = p2[1] = p1[1] = bmin[1] + dy*0.5f;
|
||||
p3[2] = p2[2] = p1[2] = bmin[2] + dz*0.5f;
|
||||
|
||||
Rect3d b(bmin,bmax);
|
||||
|
||||
Rect3d b1,b2;
|
||||
|
||||
splitRect(axis,b,b1,b2,p1);
|
||||
|
||||
|
||||
// callback->ConvexDebugBound(b1.mMin,b1.mMax,0x00FF00);
|
||||
// callback->ConvexDebugBound(b2.mMin,b2.mMax,0xFFFF00);
|
||||
|
||||
switch ( axis )
|
||||
{
|
||||
case 0:
|
||||
p2[1] = bmin[1];
|
||||
p2[2] = bmin[2];
|
||||
|
||||
if ( dz > dy )
|
||||
{
|
||||
p3[1] = bmax[1];
|
||||
p3[2] = bmin[2];
|
||||
}
|
||||
else
|
||||
{
|
||||
p3[1] = bmin[1];
|
||||
p3[2] = bmax[2];
|
||||
}
|
||||
|
||||
break;
|
||||
case 1:
|
||||
p2[0] = bmin[0];
|
||||
p2[2] = bmin[2];
|
||||
|
||||
if ( dx > dz )
|
||||
{
|
||||
p3[0] = bmax[0];
|
||||
p3[2] = bmin[2];
|
||||
}
|
||||
else
|
||||
{
|
||||
p3[0] = bmin[0];
|
||||
p3[2] = bmax[2];
|
||||
}
|
||||
|
||||
break;
|
||||
case 2:
|
||||
p2[0] = bmin[0];
|
||||
p2[1] = bmin[1];
|
||||
|
||||
if ( dx > dy )
|
||||
{
|
||||
p3[0] = bmax[0];
|
||||
p3[1] = bmin[1];
|
||||
}
|
||||
else
|
||||
{
|
||||
p3[0] = bmin[0];
|
||||
p3[1] = bmax[1];
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
// callback->ConvexDebugTri(p1,p2,p3,0xFF0000);
|
||||
|
||||
computePlane(p1,p2,p3,plane);
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -1,59 +1,59 @@
|
||||
#ifndef SPLIT_PLANE_H
|
||||
|
||||
#define SPLIT_PLANE_H
|
||||
|
||||
//** Computes an 'optimal' split plane for the supplied mesh.
|
||||
//** needs much improvement since it currently just splits along
|
||||
//** the longest side of the AABB.
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class ConvexDecompInterface;
|
||||
|
||||
bool computeSplitPlane(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float *plane);
|
||||
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
#ifndef SPLIT_PLANE_H
|
||||
|
||||
#define SPLIT_PLANE_H
|
||||
|
||||
//** Computes an 'optimal' split plane for the supplied mesh.
|
||||
//** needs much improvement since it currently just splits along
|
||||
//** the longest side of the AABB.
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
|
||||
namespace ConvexDecomposition
|
||||
{
|
||||
|
||||
class ConvexDecompInterface;
|
||||
|
||||
bool computeSplitPlane(unsigned int vcount,
|
||||
const float *vertices,
|
||||
unsigned int tcount,
|
||||
const unsigned int *indices,
|
||||
ConvexDecompInterface *callback,
|
||||
float *plane);
|
||||
|
||||
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
@@ -1,307 +1,307 @@
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
#pragma warning(disable:4786)
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <set>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
// CodeSnippet provided by John W. Ratcliff
|
||||
// on March 23, 2006.
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// Personal website: http://jratcliffscarab.blogspot.com
|
||||
// Coding Website: http://codesuppository.blogspot.com
|
||||
// FundRaising Blog: http://amillionpixels.blogspot.com
|
||||
// Fundraising site: http://www.amillionpixels.us
|
||||
// New Temple Site: http://newtemple.blogspot.com
|
||||
//
|
||||
// This snippet shows how to 'hide' the complexity of
|
||||
// the STL by wrapping some useful piece of functionality
|
||||
// around a handful of discrete API calls.
|
||||
//
|
||||
// This API allows you to create an indexed triangle list
|
||||
// from a collection of raw input triangles. Internally
|
||||
// it uses an STL set to build the lookup table very rapidly.
|
||||
//
|
||||
// Here is how you would use it to build an indexed triangle
|
||||
// list from a raw list of triangles.
|
||||
//
|
||||
// (1) create a 'VertexLookup' interface by calling
|
||||
//
|
||||
// VertexLook vl = Vl_createVertexLookup();
|
||||
//
|
||||
// (2) For each vertice in each triangle call:
|
||||
//
|
||||
// unsigned int i1 = Vl_getIndex(vl,p1);
|
||||
// unsigned int i2 = Vl_getIndex(vl,p2);
|
||||
// unsigned int i3 = Vl_getIndex(vl,p3);
|
||||
//
|
||||
// save the 3 indices into your triangle list array.
|
||||
//
|
||||
// (3) Get the vertex array by calling:
|
||||
//
|
||||
// const float *vertices = Vl_getVertices(vl);
|
||||
//
|
||||
// (4) Get the number of vertices so you can copy them into
|
||||
// your own buffer.
|
||||
// unsigned int vcount = Vl_getVcount(vl);
|
||||
//
|
||||
// (5) Release the VertexLookup interface when you are done with it.
|
||||
// Vl_releaseVertexLookup(vl);
|
||||
//
|
||||
// Teaches the following lessons:
|
||||
//
|
||||
// How to wrap the complexity of STL and C++ classes around a
|
||||
// simple API interface.
|
||||
//
|
||||
// How to use an STL set and custom comparator operator for
|
||||
// a complex data type.
|
||||
//
|
||||
// How to create a template class.
|
||||
//
|
||||
// How to achieve significant performance improvements by
|
||||
// taking advantage of built in STL containers in just
|
||||
// a few lines of code.
|
||||
//
|
||||
// You could easily modify this code to support other vertex
|
||||
// formats with any number of interpolants.
|
||||
|
||||
|
||||
|
||||
|
||||
#include "vlookup.h"
|
||||
|
||||
namespace Vlookup
|
||||
{
|
||||
|
||||
class VertexPosition
|
||||
{
|
||||
public:
|
||||
VertexPosition(void) { };
|
||||
VertexPosition(const float *p)
|
||||
{
|
||||
mPos[0] = p[0];
|
||||
mPos[1] = p[1];
|
||||
mPos[2] = p[2];
|
||||
};
|
||||
|
||||
void Set(int index,const float *pos)
|
||||
{
|
||||
const float * p = &pos[index*3];
|
||||
|
||||
mPos[0] = p[0];
|
||||
mPos[1] = p[1];
|
||||
mPos[2] = p[2];
|
||||
|
||||
};
|
||||
|
||||
float GetX(void) const { return mPos[0]; };
|
||||
float GetY(void) const { return mPos[1]; };
|
||||
float GetZ(void) const { return mPos[2]; };
|
||||
|
||||
float mPos[3];
|
||||
};
|
||||
|
||||
|
||||
class VertexLess
|
||||
{
|
||||
public:
|
||||
typedef std::vector< VertexPosition > VertexVector;
|
||||
|
||||
bool operator()(int v1,int v2) const;
|
||||
|
||||
static void SetSearch(const VertexPosition& match,VertexVector *list)
|
||||
{
|
||||
mFind = match;
|
||||
mList = list;
|
||||
};
|
||||
|
||||
private:
|
||||
const VertexPosition& Get(int index) const
|
||||
{
|
||||
if ( index == -1 ) return mFind;
|
||||
VertexVector &vlist = *mList;
|
||||
return vlist[index];
|
||||
}
|
||||
static VertexPosition mFind; // vertice to locate.
|
||||
static VertexVector *mList;
|
||||
};
|
||||
|
||||
template <class Type> class VertexPool
|
||||
{
|
||||
public:
|
||||
typedef std::set<int, VertexLess > VertexSet;
|
||||
typedef std::vector< Type > VertexVector;
|
||||
|
||||
int getVertex(const Type& vtx)
|
||||
{
|
||||
VertexLess::SetSearch(vtx,&mVtxs);
|
||||
VertexSet::iterator found;
|
||||
found = mVertSet.find( -1 );
|
||||
if ( found != mVertSet.end() )
|
||||
{
|
||||
return *found;
|
||||
}
|
||||
int idx = (int)mVtxs.size();
|
||||
mVtxs.push_back( vtx );
|
||||
mVertSet.insert( idx );
|
||||
return idx;
|
||||
};
|
||||
|
||||
|
||||
const float * GetPos(int idx) const
|
||||
{
|
||||
return mVtxs[idx].mPos;
|
||||
}
|
||||
|
||||
const Type& Get(int idx) const
|
||||
{
|
||||
return mVtxs[idx];
|
||||
};
|
||||
|
||||
unsigned int GetSize(void) const
|
||||
{
|
||||
return mVtxs.size();
|
||||
};
|
||||
|
||||
void Clear(int reservesize) // clear the vertice pool.
|
||||
{
|
||||
mVertSet.clear();
|
||||
mVtxs.clear();
|
||||
mVtxs.reserve(reservesize);
|
||||
};
|
||||
|
||||
const VertexVector& GetVertexList(void) const { return mVtxs; };
|
||||
|
||||
void Set(const Type& vtx)
|
||||
{
|
||||
mVtxs.push_back(vtx);
|
||||
}
|
||||
|
||||
unsigned int GetVertexCount(void) const
|
||||
{
|
||||
return mVtxs.size();
|
||||
};
|
||||
|
||||
|
||||
Type * getBuffer(void)
|
||||
{
|
||||
return &mVtxs[0];
|
||||
};
|
||||
|
||||
private:
|
||||
VertexSet mVertSet; // ordered list.
|
||||
VertexVector mVtxs; // set of vertices.
|
||||
};
|
||||
|
||||
|
||||
VertexPosition VertexLess::mFind;
|
||||
std::vector<VertexPosition > *VertexLess::mList=0;
|
||||
|
||||
bool VertexLess::operator()(int v1,int v2) const
|
||||
{
|
||||
|
||||
const VertexPosition& a = Get(v1);
|
||||
const VertexPosition& b = Get(v2);
|
||||
|
||||
int ixA = (int) (a.GetX()*10000.0f);
|
||||
int ixB = (int) (b.GetX()*10000.0f);
|
||||
|
||||
if ( ixA < ixB ) return true;
|
||||
if ( ixA > ixB ) return false;
|
||||
|
||||
int iyA = (int) (a.GetY()*10000.0f);
|
||||
int iyB = (int) (b.GetY()*10000.0f);
|
||||
|
||||
if ( iyA < iyB ) return true;
|
||||
if ( iyA > iyB ) return false;
|
||||
|
||||
int izA = (int) (a.GetZ()*10000.0f);
|
||||
int izB = (int) (b.GetZ()*10000.0f);
|
||||
|
||||
if ( izA < izB ) return true;
|
||||
if ( izA > izB ) return false;
|
||||
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
using namespace Vlookup;
|
||||
|
||||
VertexLookup Vl_createVertexLookup(void)
|
||||
{
|
||||
VertexLookup ret = new VertexPool< VertexPosition >;
|
||||
return ret;
|
||||
}
|
||||
|
||||
void Vl_releaseVertexLookup(VertexLookup vlook)
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
delete vp;
|
||||
}
|
||||
|
||||
unsigned int Vl_getIndex(VertexLookup vlook,const float *pos) // get index.
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
VertexPosition p(pos);
|
||||
return vp->getVertex(p);
|
||||
}
|
||||
|
||||
const float * Vl_getVertices(VertexLookup vlook)
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
return vp->GetPos(0);
|
||||
}
|
||||
|
||||
|
||||
unsigned int Vl_getVcount(VertexLookup vlook)
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
return vp->GetVertexCount();
|
||||
}
|
||||
#include "float_math.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
#pragma warning(disable:4786)
|
||||
|
||||
#include <vector>
|
||||
#include <map>
|
||||
#include <set>
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
// CodeSnippet provided by John W. Ratcliff
|
||||
// on March 23, 2006.
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// Personal website: http://jratcliffscarab.blogspot.com
|
||||
// Coding Website: http://codesuppository.blogspot.com
|
||||
// FundRaising Blog: http://amillionpixels.blogspot.com
|
||||
// Fundraising site: http://www.amillionpixels.us
|
||||
// New Temple Site: http://newtemple.blogspot.com
|
||||
//
|
||||
// This snippet shows how to 'hide' the complexity of
|
||||
// the STL by wrapping some useful piece of functionality
|
||||
// around a handful of discrete API calls.
|
||||
//
|
||||
// This API allows you to create an indexed triangle list
|
||||
// from a collection of raw input triangles. Internally
|
||||
// it uses an STL set to build the lookup table very rapidly.
|
||||
//
|
||||
// Here is how you would use it to build an indexed triangle
|
||||
// list from a raw list of triangles.
|
||||
//
|
||||
// (1) create a 'VertexLookup' interface by calling
|
||||
//
|
||||
// VertexLook vl = Vl_createVertexLookup();
|
||||
//
|
||||
// (2) For each vertice in each triangle call:
|
||||
//
|
||||
// unsigned int i1 = Vl_getIndex(vl,p1);
|
||||
// unsigned int i2 = Vl_getIndex(vl,p2);
|
||||
// unsigned int i3 = Vl_getIndex(vl,p3);
|
||||
//
|
||||
// save the 3 indices into your triangle list array.
|
||||
//
|
||||
// (3) Get the vertex array by calling:
|
||||
//
|
||||
// const float *vertices = Vl_getVertices(vl);
|
||||
//
|
||||
// (4) Get the number of vertices so you can copy them into
|
||||
// your own buffer.
|
||||
// unsigned int vcount = Vl_getVcount(vl);
|
||||
//
|
||||
// (5) Release the VertexLookup interface when you are done with it.
|
||||
// Vl_releaseVertexLookup(vl);
|
||||
//
|
||||
// Teaches the following lessons:
|
||||
//
|
||||
// How to wrap the complexity of STL and C++ classes around a
|
||||
// simple API interface.
|
||||
//
|
||||
// How to use an STL set and custom comparator operator for
|
||||
// a complex data type.
|
||||
//
|
||||
// How to create a template class.
|
||||
//
|
||||
// How to achieve significant performance improvements by
|
||||
// taking advantage of built in STL containers in just
|
||||
// a few lines of code.
|
||||
//
|
||||
// You could easily modify this code to support other vertex
|
||||
// formats with any number of interpolants.
|
||||
|
||||
|
||||
|
||||
|
||||
#include "vlookup.h"
|
||||
|
||||
namespace Vlookup
|
||||
{
|
||||
|
||||
class VertexPosition
|
||||
{
|
||||
public:
|
||||
VertexPosition(void) { };
|
||||
VertexPosition(const float *p)
|
||||
{
|
||||
mPos[0] = p[0];
|
||||
mPos[1] = p[1];
|
||||
mPos[2] = p[2];
|
||||
};
|
||||
|
||||
void Set(int index,const float *pos)
|
||||
{
|
||||
const float * p = &pos[index*3];
|
||||
|
||||
mPos[0] = p[0];
|
||||
mPos[1] = p[1];
|
||||
mPos[2] = p[2];
|
||||
|
||||
};
|
||||
|
||||
float GetX(void) const { return mPos[0]; };
|
||||
float GetY(void) const { return mPos[1]; };
|
||||
float GetZ(void) const { return mPos[2]; };
|
||||
|
||||
float mPos[3];
|
||||
};
|
||||
|
||||
|
||||
class VertexLess
|
||||
{
|
||||
public:
|
||||
typedef std::vector< VertexPosition > VertexVector;
|
||||
|
||||
bool operator()(int v1,int v2) const;
|
||||
|
||||
static void SetSearch(const VertexPosition& match,VertexVector *list)
|
||||
{
|
||||
mFind = match;
|
||||
mList = list;
|
||||
};
|
||||
|
||||
private:
|
||||
const VertexPosition& Get(int index) const
|
||||
{
|
||||
if ( index == -1 ) return mFind;
|
||||
VertexVector &vlist = *mList;
|
||||
return vlist[index];
|
||||
}
|
||||
static VertexPosition mFind; // vertice to locate.
|
||||
static VertexVector *mList;
|
||||
};
|
||||
|
||||
template <class Type> class VertexPool
|
||||
{
|
||||
public:
|
||||
typedef std::set<int, VertexLess > VertexSet;
|
||||
typedef std::vector< Type > VertexVector;
|
||||
|
||||
int getVertex(const Type& vtx)
|
||||
{
|
||||
VertexLess::SetSearch(vtx,&mVtxs);
|
||||
VertexSet::iterator found;
|
||||
found = mVertSet.find( -1 );
|
||||
if ( found != mVertSet.end() )
|
||||
{
|
||||
return *found;
|
||||
}
|
||||
int idx = (int)mVtxs.size();
|
||||
mVtxs.push_back( vtx );
|
||||
mVertSet.insert( idx );
|
||||
return idx;
|
||||
};
|
||||
|
||||
|
||||
const float * GetPos(int idx) const
|
||||
{
|
||||
return mVtxs[idx].mPos;
|
||||
}
|
||||
|
||||
const Type& Get(int idx) const
|
||||
{
|
||||
return mVtxs[idx];
|
||||
};
|
||||
|
||||
unsigned int GetSize(void) const
|
||||
{
|
||||
return mVtxs.size();
|
||||
};
|
||||
|
||||
void Clear(int reservesize) // clear the vertice pool.
|
||||
{
|
||||
mVertSet.clear();
|
||||
mVtxs.clear();
|
||||
mVtxs.reserve(reservesize);
|
||||
};
|
||||
|
||||
const VertexVector& GetVertexList(void) const { return mVtxs; };
|
||||
|
||||
void Set(const Type& vtx)
|
||||
{
|
||||
mVtxs.push_back(vtx);
|
||||
}
|
||||
|
||||
unsigned int GetVertexCount(void) const
|
||||
{
|
||||
return mVtxs.size();
|
||||
};
|
||||
|
||||
|
||||
Type * getBuffer(void)
|
||||
{
|
||||
return &mVtxs[0];
|
||||
};
|
||||
|
||||
private:
|
||||
VertexSet mVertSet; // ordered list.
|
||||
VertexVector mVtxs; // set of vertices.
|
||||
};
|
||||
|
||||
|
||||
VertexPosition VertexLess::mFind;
|
||||
std::vector<VertexPosition > *VertexLess::mList=0;
|
||||
|
||||
bool VertexLess::operator()(int v1,int v2) const
|
||||
{
|
||||
|
||||
const VertexPosition& a = Get(v1);
|
||||
const VertexPosition& b = Get(v2);
|
||||
|
||||
int ixA = (int) (a.GetX()*10000.0f);
|
||||
int ixB = (int) (b.GetX()*10000.0f);
|
||||
|
||||
if ( ixA < ixB ) return true;
|
||||
if ( ixA > ixB ) return false;
|
||||
|
||||
int iyA = (int) (a.GetY()*10000.0f);
|
||||
int iyB = (int) (b.GetY()*10000.0f);
|
||||
|
||||
if ( iyA < iyB ) return true;
|
||||
if ( iyA > iyB ) return false;
|
||||
|
||||
int izA = (int) (a.GetZ()*10000.0f);
|
||||
int izB = (int) (b.GetZ()*10000.0f);
|
||||
|
||||
if ( izA < izB ) return true;
|
||||
if ( izA > izB ) return false;
|
||||
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
using namespace Vlookup;
|
||||
|
||||
VertexLookup Vl_createVertexLookup(void)
|
||||
{
|
||||
VertexLookup ret = new VertexPool< VertexPosition >;
|
||||
return ret;
|
||||
}
|
||||
|
||||
void Vl_releaseVertexLookup(VertexLookup vlook)
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
delete vp;
|
||||
}
|
||||
|
||||
unsigned int Vl_getIndex(VertexLookup vlook,const float *pos) // get index.
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
VertexPosition p(pos);
|
||||
return vp->getVertex(p);
|
||||
}
|
||||
|
||||
const float * Vl_getVertices(VertexLookup vlook)
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
return vp->GetPos(0);
|
||||
}
|
||||
|
||||
|
||||
unsigned int Vl_getVcount(VertexLookup vlook)
|
||||
{
|
||||
VertexPool< VertexPosition > *vp = (VertexPool< VertexPosition > *) vlook;
|
||||
return vp->GetVertexCount();
|
||||
}
|
||||
|
||||
@@ -1,119 +1,119 @@
|
||||
#ifndef VLOOKUP_H
|
||||
|
||||
#define VLOOKUP_H
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
// CodeSnippet provided by John W. Ratcliff
|
||||
// on March 23, 2006.
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// Personal website: http://jratcliffscarab.blogspot.com
|
||||
// Coding Website: http://codesuppository.blogspot.com
|
||||
// FundRaising Blog: http://amillionpixels.blogspot.com
|
||||
// Fundraising site: http://www.amillionpixels.us
|
||||
// New Temple Site: http://newtemple.blogspot.com
|
||||
//
|
||||
// This snippet shows how to 'hide' the complexity of
|
||||
// the STL by wrapping some useful piece of functionality
|
||||
// around a handful of discrete API calls.
|
||||
//
|
||||
// This API allows you to create an indexed triangle list
|
||||
// from a collection of raw input triangles. Internally
|
||||
// it uses an STL set to build the lookup table very rapidly.
|
||||
//
|
||||
// Here is how you would use it to build an indexed triangle
|
||||
// list from a raw list of triangles.
|
||||
//
|
||||
// (1) create a 'VertexLookup' interface by calling
|
||||
//
|
||||
// VertexLook vl = Vl_createVertexLookup();
|
||||
//
|
||||
// (2) For each vertice in each triangle call:
|
||||
//
|
||||
// unsigned int i1 = Vl_getIndex(vl,p1);
|
||||
// unsigned int i2 = Vl_getIndex(vl,p2);
|
||||
// unsigned int i3 = Vl_getIndex(vl,p3);
|
||||
//
|
||||
// save the 3 indices into your triangle list array.
|
||||
//
|
||||
// (3) Get the vertex array by calling:
|
||||
//
|
||||
// const float *vertices = Vl_getVertices(vl);
|
||||
//
|
||||
// (4) Get the number of vertices so you can copy them into
|
||||
// your own buffer.
|
||||
// unsigned int vcount = Vl_getVcount(vl);
|
||||
//
|
||||
// (5) Release the VertexLookup interface when you are done with it.
|
||||
// Vl_releaseVertexLookup(vl);
|
||||
//
|
||||
// Teaches the following lessons:
|
||||
//
|
||||
// How to wrap the complexity of STL and C++ classes around a
|
||||
// simple API interface.
|
||||
//
|
||||
// How to use an STL set and custom comparator operator for
|
||||
// a complex data type.
|
||||
//
|
||||
// How to create a template class.
|
||||
//
|
||||
// How to achieve significant performance improvements by
|
||||
// taking advantage of built in STL containers in just
|
||||
// a few lines of code.
|
||||
//
|
||||
// You could easily modify this code to support other vertex
|
||||
// formats with any number of interpolants.
|
||||
//
|
||||
// Hide C++ classes from the rest of your application by
|
||||
// keeping them in the CPP and wrapping them in a namespace
|
||||
// Uses an STL set to create an index table for a bunch of vertex positions
|
||||
// used typically to re-index a collection of raw triangle data.
|
||||
|
||||
|
||||
typedef void * VertexLookup;
|
||||
|
||||
VertexLookup Vl_createVertexLookup(void);
|
||||
void Vl_releaseVertexLookup(VertexLookup vlook);
|
||||
|
||||
unsigned int Vl_getIndex(VertexLookup vlook,const float *pos); // get index.
|
||||
const float * Vl_getVertices(VertexLookup vlook);
|
||||
unsigned int Vl_getVcount(VertexLookup vlook);
|
||||
|
||||
|
||||
#endif
|
||||
#ifndef VLOOKUP_H
|
||||
|
||||
#define VLOOKUP_H
|
||||
|
||||
|
||||
/*----------------------------------------------------------------------
|
||||
Copyright (c) 2004 Open Dynamics Framework Group
|
||||
www.physicstools.org
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without modification, are permitted provided
|
||||
that the following conditions are met:
|
||||
|
||||
Redistributions of source code must retain the above copyright notice, this list of conditions
|
||||
and the following disclaimer.
|
||||
|
||||
Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the documentation
|
||||
and/or other materials provided with the distribution.
|
||||
|
||||
Neither the name of the Open Dynamics Framework Group nor the names of its contributors may
|
||||
be used to endorse or promote products derived from this software without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 'AS IS' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||
DISCLAIMED. IN NO EVENT SHALL THE INTEL OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER
|
||||
IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||
THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
// http://codesuppository.blogspot.com
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// http://www.amillionpixels.us
|
||||
//
|
||||
|
||||
|
||||
// CodeSnippet provided by John W. Ratcliff
|
||||
// on March 23, 2006.
|
||||
//
|
||||
// mailto: jratcliff@infiniplex.net
|
||||
//
|
||||
// Personal website: http://jratcliffscarab.blogspot.com
|
||||
// Coding Website: http://codesuppository.blogspot.com
|
||||
// FundRaising Blog: http://amillionpixels.blogspot.com
|
||||
// Fundraising site: http://www.amillionpixels.us
|
||||
// New Temple Site: http://newtemple.blogspot.com
|
||||
//
|
||||
// This snippet shows how to 'hide' the complexity of
|
||||
// the STL by wrapping some useful piece of functionality
|
||||
// around a handful of discrete API calls.
|
||||
//
|
||||
// This API allows you to create an indexed triangle list
|
||||
// from a collection of raw input triangles. Internally
|
||||
// it uses an STL set to build the lookup table very rapidly.
|
||||
//
|
||||
// Here is how you would use it to build an indexed triangle
|
||||
// list from a raw list of triangles.
|
||||
//
|
||||
// (1) create a 'VertexLookup' interface by calling
|
||||
//
|
||||
// VertexLook vl = Vl_createVertexLookup();
|
||||
//
|
||||
// (2) For each vertice in each triangle call:
|
||||
//
|
||||
// unsigned int i1 = Vl_getIndex(vl,p1);
|
||||
// unsigned int i2 = Vl_getIndex(vl,p2);
|
||||
// unsigned int i3 = Vl_getIndex(vl,p3);
|
||||
//
|
||||
// save the 3 indices into your triangle list array.
|
||||
//
|
||||
// (3) Get the vertex array by calling:
|
||||
//
|
||||
// const float *vertices = Vl_getVertices(vl);
|
||||
//
|
||||
// (4) Get the number of vertices so you can copy them into
|
||||
// your own buffer.
|
||||
// unsigned int vcount = Vl_getVcount(vl);
|
||||
//
|
||||
// (5) Release the VertexLookup interface when you are done with it.
|
||||
// Vl_releaseVertexLookup(vl);
|
||||
//
|
||||
// Teaches the following lessons:
|
||||
//
|
||||
// How to wrap the complexity of STL and C++ classes around a
|
||||
// simple API interface.
|
||||
//
|
||||
// How to use an STL set and custom comparator operator for
|
||||
// a complex data type.
|
||||
//
|
||||
// How to create a template class.
|
||||
//
|
||||
// How to achieve significant performance improvements by
|
||||
// taking advantage of built in STL containers in just
|
||||
// a few lines of code.
|
||||
//
|
||||
// You could easily modify this code to support other vertex
|
||||
// formats with any number of interpolants.
|
||||
//
|
||||
// Hide C++ classes from the rest of your application by
|
||||
// keeping them in the CPP and wrapping them in a namespace
|
||||
// Uses an STL set to create an index table for a bunch of vertex positions
|
||||
// used typically to re-index a collection of raw triangle data.
|
||||
|
||||
|
||||
typedef void * VertexLookup;
|
||||
|
||||
VertexLookup Vl_createVertexLookup(void);
|
||||
void Vl_releaseVertexLookup(VertexLookup vlook);
|
||||
|
||||
unsigned int Vl_getIndex(VertexLookup vlook,const float *pos); // get index.
|
||||
const float * Vl_getVertices(VertexLookup vlook);
|
||||
unsigned int Vl_getVcount(VertexLookup vlook);
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
Reference in New Issue
Block a user