ADD Vertex utility class to simplify conversion from and to interleaved vertices.

Refactor JoinVerticesProcess to utilize the new utility.
ADD basic operators for aiColor4D, move to dedicated header and implementation file.
ADD some utility functions to SpatialSort.
ADD my existing Catmull-Clark implementation to Assimp for all model formats with support for subdivision surfaces. Slightly WIP, likely to produce errors on non-closed meshes. Currently only implemented in the AC3D loader.
Switch to byteswap intrinsics instead of inline assembly (bswap). Currently MSVC only.
FIX phong shading in assimp_view.
VertexTriangleAdjacency class now also works on arbitrary polygons - UNTESTED, tbd.

git-svn-id: https://assimp.svn.sourceforge.net/svnroot/assimp/trunk@532 67173fc5-114c-0410-ac8e-9d2fd5bffc1f
This commit is contained in:
aramis_acg
2010-01-28 21:17:25 +00:00
parent ce29aca94e
commit 2e3fee99f0
29 changed files with 1947 additions and 316 deletions

View File

@@ -39,93 +39,103 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
---------------------------------------------------------------------------
*/
/** @file Implementation of the VertexTriangleAdjacency helper class
*/
/** @file Implementation of the VertexTriangleAdjacency helper class */
#include "AssimpPCH.h"
// internal headers
#include "VertexTriangleAdjacency.h"
using namespace Assimp;
// ------------------------------------------------------------------------------------------------
// Compute a vertex-to-faces adjacency table. To save small memory allocations, the information
// is encoded in three continous buffers - the offset table maps a single vertex index to an
// entry in the adjacency table, which in turn contains n entries, which are the faces adjacent
// to the vertex. n is taken from the third buffer, which stores face counts per vertex.
// ------------------------------------------------------------------------------------------------
VertexTriangleAdjacency::VertexTriangleAdjacency(aiFace *pcFaces,
unsigned int iNumFaces,
unsigned int iNumVertices /*= 0*/,
bool bComputeNumTriangles /*= false*/)
{
// compute the number of referenced vertices if it wasn't specified by the caller
// ---------------------------------------------------------------------
// 0: compute the number of referenced vertices if not
// specified by the caller.
// ---------------------------------------------------------------------
const aiFace* const pcFaceEnd = pcFaces + iNumFaces;
if (!iNumVertices) {
for (aiFace* pcFace = pcFaces; pcFace != pcFaceEnd; ++pcFace) {
ai_assert(3 == pcFace->mNumIndices);
iNumVertices = std::max(iNumVertices,pcFace->mIndices[0]);
iNumVertices = std::max(iNumVertices,pcFace->mIndices[1]);
iNumVertices = std::max(iNumVertices,pcFace->mIndices[2]);
for (unsigned int i = 0; i < pcFace->mNumIndices; ++i) {
iNumVertices = std::max(iNumVertices,pcFace->mIndices[i]);
}
}
}
unsigned int* pi;
// allocate storage
// ---------------------------------------------------------------------
// 1. Allocate output storage
// ---------------------------------------------------------------------
if (bComputeNumTriangles) {
pi = mLiveTriangles = new unsigned int[iNumVertices+1];
memset(mLiveTriangles,0,sizeof(unsigned int)*(iNumVertices+1));
mOffsetTable = new unsigned int[iNumVertices+2]+1;
}
else {
pi = mOffsetTable = new unsigned int[iNumVertices+2]+1;
memset(mOffsetTable,0,sizeof(unsigned int)*(iNumVertices+1));
mLiveTriangles = NULL; // important, otherwise the d'tor would crash
// important, otherwise the d'tor would crash
mLiveTriangles = NULL;
}
// get a pointer to the end of the buffer
unsigned int* piEnd = pi+iNumVertices;
*piEnd++ = 0u;
// first pass: compute the number of faces referencing each vertex
for (aiFace* pcFace = pcFaces; pcFace != pcFaceEnd; ++pcFace)
{
pi[pcFace->mIndices[0]]++;
pi[pcFace->mIndices[1]]++;
pi[pcFace->mIndices[2]]++;
// ---------------------------------------------------------------------
// 2. Compute the number of faces referencing each vertex
// ---------------------------------------------------------------------
for (aiFace* pcFace = pcFaces; pcFace != pcFaceEnd; ++pcFace) {
for (unsigned int i = 0; i < pcFace->mNumIndices; ++i) {
pi[pcFace->mIndices[i]]++;
}
}
// second pass: compute the final offset table
// ---------------------------------------------------------------------
// 3. Compute the offset table to map each face to a
// start position in the adjacency table.
// ---------------------------------------------------------------------
unsigned int iSum = 0;
unsigned int* piCurOut = this->mOffsetTable;
unsigned int* piCurOut = mOffsetTable;
for (unsigned int* piCur = pi; piCur != piEnd;++piCur,++piCurOut) {
unsigned int iLastSum = iSum;
iSum += *piCur;
*piCurOut = iLastSum;
}
pi = this->mOffsetTable;
pi = mOffsetTable;
// third pass: compute the final table
this->mAdjacencyTable = new unsigned int[iSum];
// ---------------------------------------------------------------------
// 4. Compute the final adjacency table
// ---------------------------------------------------------------------
mAdjacencyTable = new unsigned int[iSum];
iSum = 0;
for (aiFace* pcFace = pcFaces; pcFace != pcFaceEnd; ++pcFace,++iSum) {
unsigned int idx = pcFace->mIndices[0];
mAdjacencyTable[pi[idx]++] = iSum;
idx = pcFace->mIndices[1];
mAdjacencyTable[pi[idx]++] = iSum;
idx = pcFace->mIndices[2];
mAdjacencyTable[pi[idx]++] = iSum;
for (unsigned int i = 0; i < pcFace->mNumIndices; ++i) {
mAdjacencyTable[pi[pcFace->mIndices[i]]++] = iSum;
}
}
// fourth pass: undo the offset computations made during the third pass
// We could do this in a separate buffer, but this would be TIMES slower.
// ---------------------------------------------------------------------
// 5. Undo the offset computations made during step 4
// ---------------------------------------------------------------------
--mOffsetTable;
*mOffsetTable = 0u;
}
// ------------------------------------------------------------------------------------------------
VertexTriangleAdjacency::~VertexTriangleAdjacency()
{
// delete allocated storage
delete[] mOffsetTable;
delete[] mAdjacencyTable;
delete[] mLiveTriangles;