From f9b06f8d895f1b59d30e037a708a4046a11ed620 Mon Sep 17 00:00:00 2001 From: aramis_acg Date: Thu, 20 May 2010 12:07:04 +0000 Subject: [PATCH] 3ds loader now sets aiMesh::mName according to the original mesh groups found in the file. git-svn-id: https://assimp.svn.sourceforge.net/svnroot/assimp/trunk@727 67173fc5-114c-0410-ac8e-9d2fd5bffc1f --- code/3DSConverter.cpp | 98 +++++++++++++++++++++-------------------- code/StringComparison.h | 11 ++--- 2 files changed, 56 insertions(+), 53 deletions(-) diff --git a/code/3DSConverter.cpp b/code/3DSConverter.cpp index dafb06909..6fb6e8efa 100644 --- a/code/3DSConverter.cpp +++ b/code/3DSConverter.cpp @@ -348,14 +348,14 @@ void Discreet3DSImporter::ConvertMeshes(aiScene* pcOut) std::vector avOutMeshes; avOutMeshes.reserve(mScene->mMeshes.size() * 2); - unsigned int iFaceCnt = 0; + unsigned int iFaceCnt = 0,num = 0; + aiString name; // we need to split all meshes by their materials - for (std::vector::iterator i = mScene->mMeshes.begin(); - i != mScene->mMeshes.end();++i) - { - std::vector* aiSplit = new std::vector[ - mScene->mMaterials.size()]; + for (std::vector::iterator i = mScene->mMeshes.begin(); i != mScene->mMeshes.end();++i) { + boost::scoped_array< std::vector > aiSplit(new std::vector[mScene->mMaterials.size()]); + + name.length = ASSIMP_itoa10(name.data,num++); unsigned int iNum = 0; for (std::vector::const_iterator a = (*i).mFaceMaterials.begin(); @@ -366,66 +366,68 @@ void Discreet3DSImporter::ConvertMeshes(aiScene* pcOut) // now generate submeshes for (unsigned int p = 0; p < mScene->mMaterials.size();++p) { - if (aiSplit[p].size()) + if (aiSplit[p].empty()) { + continue; + } + aiMesh* meshOut = new aiMesh(); + meshOut->mName = name; + meshOut->mPrimitiveTypes = aiPrimitiveType_TRIANGLE; + + // be sure to setup the correct material index + meshOut->mMaterialIndex = p; + + // use the color data as temporary storage + meshOut->mColors[0] = (aiColor4D*)(&*i); + avOutMeshes.push_back(meshOut); + + // convert vertices + meshOut->mNumFaces = (unsigned int)aiSplit[p].size(); + meshOut->mNumVertices = meshOut->mNumFaces*3; + + // allocate enough storage for faces + meshOut->mFaces = new aiFace[meshOut->mNumFaces]; + iFaceCnt += meshOut->mNumFaces; + + meshOut->mVertices = new aiVector3D[meshOut->mNumVertices]; + meshOut->mNormals = new aiVector3D[meshOut->mNumVertices]; + if ((*i).mTexCoords.size()) { - aiMesh* meshOut = new aiMesh(); - meshOut->mPrimitiveTypes = aiPrimitiveType_TRIANGLE; + meshOut->mTextureCoords[0] = new aiVector3D[meshOut->mNumVertices]; + } + for (unsigned int q = 0, base = 0; q < aiSplit[p].size();++q) + { + register unsigned int index = aiSplit[p][q]; + aiFace& face = meshOut->mFaces[q]; - // be sure to setup the correct material index - meshOut->mMaterialIndex = p; + face.mIndices = new unsigned int[3]; + face.mNumIndices = 3; - // use the color data as temporary storage - meshOut->mColors[0] = (aiColor4D*)(&*i); - avOutMeshes.push_back(meshOut); - - // convert vertices - meshOut->mNumFaces = (unsigned int)aiSplit[p].size(); - meshOut->mNumVertices = meshOut->mNumFaces*3; - - // allocate enough storage for faces - meshOut->mFaces = new aiFace[meshOut->mNumFaces]; - iFaceCnt += meshOut->mNumFaces; - - meshOut->mVertices = new aiVector3D[meshOut->mNumVertices]; - meshOut->mNormals = new aiVector3D[meshOut->mNumVertices]; - if ((*i).mTexCoords.size()) + for (unsigned int a = 0; a < 3;++a,++base) { - meshOut->mTextureCoords[0] = new aiVector3D[meshOut->mNumVertices]; - } - for (unsigned int q = 0, base = 0; q < aiSplit[p].size();++q) - { - register unsigned int index = aiSplit[p][q]; - aiFace& face = meshOut->mFaces[q]; + unsigned int idx = (*i).mFaces[index].mIndices[a]; + meshOut->mVertices[base] = (*i).mPositions[idx]; + meshOut->mNormals [base] = (*i).mNormals[idx]; - face.mIndices = new unsigned int[3]; - face.mNumIndices = 3; + if ((*i).mTexCoords.size()) + meshOut->mTextureCoords[0][base] = (*i).mTexCoords[idx]; - for (unsigned int a = 0; a < 3;++a,++base) - { - unsigned int idx = (*i).mFaces[index].mIndices[a]; - meshOut->mVertices[base] = (*i).mPositions[idx]; - meshOut->mNormals [base] = (*i).mNormals[idx]; - - if ((*i).mTexCoords.size()) - meshOut->mTextureCoords[0][base] = (*i).mTexCoords[idx]; - - face.mIndices[a] = base; - } + face.mIndices[a] = base; } } } - delete[] aiSplit; } // Copy them to the output array pcOut->mNumMeshes = (unsigned int)avOutMeshes.size(); pcOut->mMeshes = new aiMesh*[pcOut->mNumMeshes](); - for (unsigned int a = 0; a < pcOut->mNumMeshes;++a) + for (unsigned int a = 0; a < pcOut->mNumMeshes;++a) { pcOut->mMeshes[a] = avOutMeshes[a]; + } // We should have at least one face here - if (!iFaceCnt) + if (!iFaceCnt) { throw DeadlyImportError("No faces loaded. The mesh is empty"); + } } // ------------------------------------------------------------------------------------------------ diff --git a/code/StringComparison.h b/code/StringComparison.h index 0d33e1d51..8b7a1c621 100644 --- a/code/StringComparison.h +++ b/code/StringComparison.h @@ -58,9 +58,10 @@ namespace Assimp { * to have a small replacement function here. No need to use a full sprintf() * if we just want to print a number ... * @param out Output buffer - * @param max Maximum number of characters to be written, including '\0' + * @param max Maximum number of characters to be written, including '\0'. + * This parameter may not be 0. * @param number Number to be written - * @return Number of bytes written. + * @return Length of the output string, excluding the '\0' */ inline unsigned int ASSIMP_itoa10( char* out, unsigned int max, int32_t number) { @@ -97,15 +98,15 @@ inline unsigned int ASSIMP_itoa10( char* out, unsigned int max, int32_t number) // append a terminal zero *out++ = '\0'; - return written; + return written-1; } // ------------------------------------------------------------------------------- /** @brief itoa with a fixed base 10 (Secure template overload) - * The compiler should choose this function if he is able to determine the + * The compiler should choose this function if he or she is able to determine the * size of the array automatically. */ -template +template inline unsigned int ASSIMP_itoa10( char(& out)[length], int32_t number) { return ASSIMP_itoa10(out,length,number);