diff --git a/code/LWOFileData.h b/code/LWOFileData.h index e39eeaab5..30cde324c 100644 --- a/code/LWOFileData.h +++ b/code/LWOFileData.h @@ -52,6 +52,7 @@ Original copyright notice: "Ernie Wright 17 Sep 00" #include "IFF.h" #include +#include #include "../include/aiMesh.h" namespace Assimp { @@ -334,6 +335,39 @@ struct Surface break; \ } \ + +typedef std::vector PointList; +typedef std::vector FaceList; +typedef std::vector SurfaceList; +typedef std::vector TagList; +typedef std::vector TagMappingTable; + + +// --------------------------------------------------------------------------- +/** \brief Represents a layer in the file + */ +struct Layer +{ + Layer() + : mParent (0xffff) + {} + + /** Temporary point list from the file */ + PointList mTempPoints; + + /** Temporary face list from the file*/ + FaceList mFaces; + + /** Parent index */ + uint16_t mParent; + + /** Name of the layer */ + std::string mName; +}; + +typedef std::list LayerList; + + }} diff --git a/code/LWOLoader.cpp b/code/LWOLoader.cpp index 4716ed75d..51c7ca459 100644 --- a/code/LWOLoader.cpp +++ b/code/LWOLoader.cpp @@ -126,13 +126,11 @@ void LWOImporter::InternReadFile( const std::string& pFile, mFileBuffer = &mBuffer[0] + 12; fileSize -= 12; - // create temporary storage on the stack but store points to - // it in the class instance. Therefoe everything will be destructed - // properly if an exception is thrown. - PointList _mTempPoints; - mTempPoints = &_mTempPoints; - FaceList _mFaces; - mFaces = &_mFaces; + // create temporary storage on the stack but store pointers to it in the class + // instance. Therefore everything will be destructed properly if an exception + // is thrown and we needn't take care of that. + LayerList _mLayers; + mLayers = &_mLayers; TagList _mTags; mTags = &_mTags; TagMappingTable _mMapping; @@ -140,6 +138,11 @@ void LWOImporter::InternReadFile( const std::string& pFile, SurfaceList _mSurfaces; mSurfaces = &_mSurfaces; + // allocate a default layer + mLayers->push_back(Layer()); + mCurLayer = &mLayers->back(); + mCurLayer->mName = ""; + // old lightwave file format (prior to v6) if (AI_LWO_FOURCC_LWOB == fileType) { @@ -150,6 +153,7 @@ void LWOImporter::InternReadFile( const std::string& pFile, // new lightwave format else if (AI_LWO_FOURCC_LWO2 == fileType) { + throw new ImportErrorException("LWO2 is under development and currently disabled."); mIsLWO2 = true; this->LoadLWO2File(); } @@ -166,100 +170,210 @@ void LWOImporter::InternReadFile( const std::string& pFile, } ResolveTags(); - // now sort all faces by the surfaces assigned to them - typedef std::vector SortedRep; - std::vector pSorted(mSurfaces->size()+1); + // now process all layers and build meshes and nodes + std::vector apcMeshes; + std::vector apcNodes; + apcNodes.reserve(mLayers->size()); + apcMeshes.reserve(mLayers->size()*std::min((mSurfaces->size()/2u), 1u)); - unsigned int i = 0; - unsigned int iDefaultSurface = 0xffffffff; - for (FaceList::iterator it = mFaces->begin(), end = mFaces->end(); - it != end;++it,++i) + // the RemoveRedundantMaterials step will clean this up later + pScene->mMaterials = new aiMaterial*[pScene->mNumMaterials = mSurfaces->size()]; + for (unsigned int mat = 0; mat < pScene->mNumMaterials;++mat) { - unsigned int idx = (*it).surfaceIndex; - if (idx >= mTags->size()) - { - DefaultLogger::get()->warn("LWO: Invalid face surface index"); - idx = mTags->size()-1; - } - if(0xffffffff == (idx = _mMapping[idx])) - { - if (0xffffffff == iDefaultSurface) - { - iDefaultSurface = mSurfaces->size(); - mSurfaces->push_back(LWO::Surface()); - LWO::Surface& surf = mSurfaces->back(); - surf.mColor.r = surf.mColor.g = surf.mColor.b = 0.6f; - } - idx = iDefaultSurface; - } - pSorted[idx].push_back(i); - } - if (0xffffffff == iDefaultSurface)pSorted.erase(pSorted.end()-1); - - // now generate output meshes - for (unsigned int p = 0; p < mSurfaces->size();++p) - if (!pSorted[p].empty())pScene->mNumMeshes++; - - if (!(pScene->mNumMaterials = pScene->mNumMeshes)) - throw new ImportErrorException("LWO: There are no meshes"); - - pScene->mMeshes = new aiMesh*[pScene->mNumMeshes]; - pScene->mMaterials = new aiMaterial*[pScene->mNumMaterials]; - for (unsigned int p = 0,i = 0;i < mSurfaces->size();++i) - { - SortedRep& sorted = pSorted[i]; - if (sorted.empty())continue; - - // generate the mesh - aiMesh* mesh = pScene->mMeshes[p] = new aiMesh(); - mesh->mNumFaces = sorted.size(); - if ((*mSurfaces)[i].mMaximumSmoothAngle) - mesh->mMaxSmoothingAngle = AI_DEG_TO_RAD((*mSurfaces)[i].mMaximumSmoothAngle); - - for (SortedRep::const_iterator it = sorted.begin(), end = sorted.end(); - it != end;++it) - { - mesh->mNumVertices += _mFaces[*it].mNumIndices; - } - - aiVector3D* pv = mesh->mVertices = new aiVector3D[mesh->mNumVertices]; - aiFace* pf = mesh->mFaces = new aiFace[mesh->mNumFaces]; - mesh->mMaterialIndex = p; - - // now convert all faces - unsigned int vert = 0; - for (SortedRep::const_iterator it = sorted.begin(), end = sorted.end(); - it != end;++it) - { - LWO::Face& face = _mFaces[*it]; - - // copy all vertices - for (unsigned int q = 0; q < face.mNumIndices;++q) - { - *pv++ = _mTempPoints[face.mIndices[q]]; - face.mIndices[q] = vert++; - } - - pf->mIndices = face.mIndices; - pf->mNumIndices = face.mNumIndices; - face.mIndices = NULL; // make sure it won't be deleted - pf++; - } - - // generate the corresponding material MaterialHelper* pcMat = new MaterialHelper(); - pScene->mMaterials[p] = pcMat; - ConvertMaterial((*mSurfaces)[i],pcMat); - ++p; + pScene->mMaterials[mat] = pcMat; + ConvertMaterial((*mSurfaces)[mat],pcMat); } - // create a dummy nodegraph - the root node renders everything - aiNode* p = pScene->mRootNode = new aiNode(); - p->mNumMeshes = pScene->mNumMeshes; - p->mMeshes = new unsigned int[pScene->mNumMeshes]; - p->mName.Set(""); - for (unsigned int i = 0; i < pScene->mNumMeshes;++i) - p->mMeshes[i] = i; + unsigned int iDefaultSurface = 0xffffffff; // index of the default surface + for (LayerList::const_iterator lit = mLayers->begin(), lend = mLayers->end(); + lit != lend;++lit) + { + const LWO::Layer& layer = *lit; + + // I don't know whether there could be dummy layers, but it would be possible + const unsigned int meshStart = apcMeshes.size(); + if (!layer.mFaces.empty() && !layer.mTempPoints.empty()) + { + // now sort all faces by the surfaces assigned to them + typedef std::vector SortedRep; + std::vector pSorted(mSurfaces->size()+1); + + unsigned int i = 0; + for (FaceList::const_iterator it = layer.mFaces.begin(), end = layer.mFaces.end(); + it != end;++it,++i) + { + unsigned int idx = (*it).surfaceIndex; + if (idx >= mTags->size()) + { + DefaultLogger::get()->warn("LWO: Invalid face surface index"); + idx = mTags->size()-1; + } + if(0xffffffff == (idx = _mMapping[idx])) + { + if (0xffffffff == iDefaultSurface) + { + iDefaultSurface = mSurfaces->size(); + mSurfaces->push_back(LWO::Surface()); + LWO::Surface& surf = mSurfaces->back(); + surf.mColor.r = surf.mColor.g = surf.mColor.b = 0.6f; + } + idx = iDefaultSurface; + } + pSorted[idx].push_back(i); + } + if (0xffffffff == iDefaultSurface)pSorted.erase(pSorted.end()-1); + + // now generate output meshes + for (unsigned int p = 0; p < mSurfaces->size();++p) + if (!pSorted[p].empty())pScene->mNumMeshes++; + + if (!pScene->mNumMeshes) + throw new ImportErrorException("LWO: There are no meshes"); + + pScene->mMeshes = new aiMesh*[pScene->mNumMeshes]; + for (unsigned int p = 0,i = 0;i < mSurfaces->size();++i) + { + SortedRep& sorted = pSorted[i]; + if (sorted.empty())continue; + + // generate the mesh + aiMesh* mesh = new aiMesh(); + apcMeshes.push_back(mesh); + mesh->mNumFaces = sorted.size(); + + for (SortedRep::const_iterator it = sorted.begin(), end = sorted.end(); + it != end;++it) + { + mesh->mNumVertices += layer.mFaces[*it].mNumIndices; + } + + aiVector3D* pv = mesh->mVertices = new aiVector3D[mesh->mNumVertices]; + aiFace* pf = mesh->mFaces = new aiFace[mesh->mNumFaces]; + mesh->mMaterialIndex = i; + + // now convert all faces + unsigned int vert = 0; + for (SortedRep::const_iterator it = sorted.begin(), end = sorted.end(); + it != end;++it) + { + const LWO::Face& face = layer.mFaces[*it]; + + // copy all vertices + for (unsigned int q = 0; q < face.mNumIndices;++q) + { + *pv++ = layer.mTempPoints[face.mIndices[q]]; + face.mIndices[q] = vert++; + } + + pf->mIndices = face.mIndices; + pf->mNumIndices = face.mNumIndices; + const_cast(face.mIndices) = NULL; // make sure it won't be deleted + pf++; + } + ++p; + } + } + + // generate nodes to render the mesh. Store the parent index + // in the mParent member of the nodes + aiNode* pcNode = new aiNode(); + apcNodes.push_back(pcNode); + pcNode->mName.Set(layer.mName); + pcNode->mParent = reinterpret_cast(layer.mParent); + pcNode->mNumMeshes = apcMeshes.size() - meshStart; + pcNode->mMeshes = new unsigned int[pcNode->mNumMeshes]; + for (unsigned int p = 0; p < pcNode->mNumMeshes;++p) + pcNode->mMeshes[p] = p + meshStart; + } + // generate the final node graph + GenerateNodeGraph(apcNodes); + + // copy the meshes to the output structure + if (apcMeshes.size()) // shouldn't occur, just to be sure we don't crash + { + pScene->mMeshes = new aiMesh*[ pScene->mNumMeshes = apcMeshes.size() ]; + ::memcpy(pScene->mMeshes,&apcMeshes[0],pScene->mNumMeshes*sizeof(void*)); + } +} + +// ------------------------------------------------------------------------------------------------ +void LWOImporter::GenerateNodeGraph(std::vector& apcNodes) +{ + // now generate the final nodegraph + uint16_t curIndex = 0; + while (curIndex < (uint16_t)apcNodes.size()) + { + aiNode* node; + uint16_t iCurParent = curIndex-1; + node = curIndex ? apcNodes[iCurParent] : new aiNode(""); + + unsigned int numChilds = 0; + for (unsigned int i = 0; i < apcNodes.size();++i) + { + if (i == iCurParent)continue; + if ( reinterpret_cast(apcNodes[i]->mParent) == iCurParent)++numChilds; + } + if (numChilds) + { + if (!pScene->mRootNode) + { + pScene->mRootNode = node; + } + node->mChildren = new aiNode* [ node->mNumChildren = numChilds ]; + for (unsigned int i = 0, p = 0; i < apcNodes.size();++i) + { + if (i == iCurParent)continue; + uint16_t parent = reinterpret_cast(apcNodes[i]->mParent); + if (parent == iCurParent) + { + node->mChildren[p++] = apcNodes[i]; + apcNodes[i]->mParent = node; + apcNodes[i] = NULL; + } + } + } + else if (!curIndex)delete node; + ++curIndex; + } + // remove a single root node + // TODO: implement directly in the above loop, no need to deallocate here + if (1 == pScene->mRootNode->mNumChildren) + { + aiNode* pc = pScene->mRootNode->mChildren[0]; + pc->mParent = pScene->mRootNode->mChildren[0] = NULL; + delete pScene->mRootNode; + pScene->mRootNode = pc; + } + + // add unreferenced nodes to a dummy root + unsigned int m = 0; + for (std::vector::iterator it = apcNodes.begin(), end = apcNodes.end(); + it != end;++it) + { + aiNode* p = *it; + if (p)++m; + } + if (m) + { + aiNode* pc = new aiNode(); + pc->mName.Set(""); + aiNode** cc = pc->mChildren = new aiNode*[ pc->mNumChildren = m+1 ]; + for (std::vector::iterator it = apcNodes.begin(), end = apcNodes.end(); + it != end;++it) + { + aiNode* p = *it; + if (p)*cc++ = p; + } + if (pScene->mRootNode) + { + *cc = pScene->mRootNode; + pScene->mRootNode->mParent = pc; + } + else --pc->mNumChildren; + pScene->mRootNode = pc; + } + if (!pScene->mRootNode)throw new ImportErrorException("LWO: Unable to build a valid node graph"); } // ------------------------------------------------------------------------------------------------ @@ -282,7 +396,7 @@ void LWOImporter::CountVertsAndFaces(unsigned int& verts, unsigned int& faces, } // ------------------------------------------------------------------------------------------------ -void LWOImporter::CopyFaceIndices(LWOImporter::FaceList::iterator& it, +void LWOImporter::CopyFaceIndices(FaceList::iterator& it, LE_NCONST uint16_t*& cursor, const uint16_t* const end, unsigned int max) @@ -296,11 +410,11 @@ void LWOImporter::CopyFaceIndices(LWOImporter::FaceList::iterator& it, face.mIndices = new unsigned int[face.mNumIndices]; for (unsigned int i = 0; i < face.mNumIndices;++i) { - face.mIndices[i] = *cursor++; - if (face.mIndices[i] >= mTempPoints->size()) + unsigned int & mi = face.mIndices[i] = *cursor++; + if (mi > mCurLayer->mTempPoints.size()) { - face.mIndices[i] = mTempPoints->size()-1; - DefaultLogger::get()->warn("LWO: Face index is out of range"); + DefaultLogger::get()->warn("LWO: face index is out of range"); + mi = mCurLayer->mTempPoints.size()-1; } } } @@ -384,14 +498,53 @@ void LWOImporter::LoadLWOTags(unsigned int size) } } +// ------------------------------------------------------------------------------------------------ +void LWOImporter::LoadLWOPoints(unsigned int length) +{ + mCurLayer->mTempPoints.resize( length / 12 ); + + // perform endianess conversions +#ifndef AI_BUILD_BIG_ENDIAN + for (unsigned int i = 0; i < length>>2;++i) + ByteSwap::Swap4( mFileBuffer + (i << 2)); +#endif + ::memcpy(&mCurLayer->mTempPoints[0],mFileBuffer,length); +} + +// ------------------------------------------------------------------------------------------------ +void LWOImporter::LoadLWOPolygons(unsigned int length) +{ + // first find out how many faces and vertices we'll finally need + LE_NCONST uint16_t* const end = (LE_NCONST uint16_t*)(mFileBuffer+length); + LE_NCONST uint16_t* cursor = (LE_NCONST uint16_t*)mFileBuffer; + + // perform endianess conversions +#ifndef AI_BUILD_BIG_ENDIAN + while (cursor < end)ByteSwap::Swap2(cursor++); + cursor = (LE_NCONST uint16_t*)mFileBuffer; +#endif + + unsigned int iNumFaces = 0,iNumVertices = 0; + CountVertsAndFaces(iNumVertices,iNumFaces,cursor,end); + + // allocate the output array and copy face indices + if (iNumFaces) + { + cursor = (LE_NCONST uint16_t*)mFileBuffer; + // this->mTempPoints->resize(iNumVertices); + mCurLayer->mFaces.resize(iNumFaces); + FaceList::iterator it = mCurLayer->mFaces.begin(); + CopyFaceIndices(it,cursor,end); + } +} + // ------------------------------------------------------------------------------------------------ void LWOImporter::LoadLWOBFile() { LE_NCONST uint8_t* const end = mFileBuffer + fileSize; while (true) { - if (mFileBuffer + sizeof(IFF::ChunkHeader) > end) - break; + if (mFileBuffer + sizeof(IFF::ChunkHeader) > end)break; LE_NCONST IFF::ChunkHeader* const head = (LE_NCONST IFF::ChunkHeader*)mFileBuffer; AI_LSWAP4(head->length); AI_LSWAP4(head->type); @@ -408,51 +561,34 @@ void LWOImporter::LoadLWOBFile() // vertex list case AI_LWO_PNTS: { - mTempPoints->resize( head->length / 12 ); -#ifndef AI_BUILD_BIG_ENDIAN - for (unsigned int i = 0; i < head->length>>2;++i) - ByteSwap::Swap4( mFileBuffer + (i << 2)); -#endif - ::memcpy(&(*mTempPoints)[0],mFileBuffer,head->length); + if (!mCurLayer->mTempPoints.empty()) + DefaultLogger::get()->warn("LWO: PNTS chunk encountered twice"); + else LoadLWOPoints(head->length); break; } // face list case AI_LWO_POLS: { - // first find out how many faces and vertices we'll finally need - LE_NCONST uint16_t* const end = (LE_NCONST uint16_t*)next; - LE_NCONST uint16_t* cursor = (LE_NCONST uint16_t*)mFileBuffer; - -#ifndef AI_BUILD_BIG_ENDIAN - while (cursor < end)ByteSwap::Swap2(cursor++); - cursor = (LE_NCONST uint16_t*)mFileBuffer; -#endif - - unsigned int iNumFaces = 0,iNumVertices = 0; - CountVertsAndFaces(iNumVertices,iNumFaces,cursor,end); - - // allocate the output array and copy face indices - if (iNumFaces) - { - cursor = (LE_NCONST uint16_t*)mFileBuffer; - this->mTempPoints->resize(iNumVertices); - this->mFaces->resize(iNumFaces); - FaceList::iterator it = this->mFaces->begin(); - CopyFaceIndices(it,cursor,end); - } + if (!mCurLayer->mFaces.empty()) + DefaultLogger::get()->warn("LWO: POLS chunk encountered twice"); + else LoadLWOPolygons(head->length); break; } // list of tags case AI_LWO_SRFS: { - LoadLWOTags(head->length); + if (!mTags->empty()) + DefaultLogger::get()->warn("LWO: SRFS chunk encountered twice"); + else LoadLWOTags(head->length); break; } // surface chunk case AI_LWO_SURF: { - LoadLWOBSurface(head->length); + if (!mSurfaces->empty()) + DefaultLogger::get()->warn("LWO: SURF chunk encountered twice"); + else LoadLWOBSurface(head->length); break; } } @@ -462,4 +598,86 @@ void LWOImporter::LoadLWOBFile() // ------------------------------------------------------------------------------------------------ void LWOImporter::LoadLWO2File() { + LE_NCONST uint8_t* const end = mFileBuffer + fileSize; + while (true) + { + if (mFileBuffer + sizeof(IFF::ChunkHeader) > end)break; + LE_NCONST IFF::ChunkHeader* const head = (LE_NCONST IFF::ChunkHeader*)mFileBuffer; + AI_LSWAP4(head->length); + AI_LSWAP4(head->type); + mFileBuffer += sizeof(IFF::ChunkHeader); + if (mFileBuffer + head->length > end) + { + throw new ImportErrorException("LWOB: Invalid file, the size attribute of " + "a chunk points behind the end of the file"); + break; + } + LE_NCONST uint8_t* const next = mFileBuffer+head->length; + unsigned int iUnnamed = 0; + switch (head->type) + { + // new layer + case AI_LWO_LAYR: + { + // add a new layer to the list .... + mLayers->push_back ( LWO::Layer() ); + LWO::Layer& layer = mLayers->back(); + mCurLayer = &layer; + + AI_LWO_VALIDATE_CHUNK_LENGTH(head->length,LAYR,16); + + // and parse its properties + mFileBuffer += 16; + ParseString(layer.mName,head->length-16); + + // if the name is empty, generate a default name + if (layer.mName.empty()) + { + char buffer[128]; // should be sufficiently large + ::sprintf(buffer,"Layer_%i", iUnnamed++); + layer.mName = buffer; + } + + if (mFileBuffer + 2 <= next) + layer.mParent = *((uint16_t*)mFileBuffer); + + break; + } + + // vertex list + case AI_LWO_PNTS: + { + if (!mCurLayer->mTempPoints.empty()) + DefaultLogger::get()->warn("LWO: PNTS chunk encountered twice"); + else LoadLWOPoints(head->length); + break; + } + // face list + case AI_LWO_POLS: + { + if (!mCurLayer->mFaces.empty()) + DefaultLogger::get()->warn("LWO: POLS chunk encountered twice"); + else LoadLWOPolygons(head->length); + break; + } + // list of tags + case AI_LWO_SRFS: + { + if (!mTags->empty()) + DefaultLogger::get()->warn("LWO: SRFS chunk encountered twice"); + else LoadLWOTags(head->length); + break; + } + + // surface chunk + case AI_LWO_SURF: + { + if (!mSurfaces->empty()) + DefaultLogger::get()->warn("LWO: SURF chunk encountered twice"); + else LoadLWOBSurface(head->length); + break; + } + } + mFileBuffer = next; + } } \ No newline at end of file diff --git a/code/LWOLoader.h b/code/LWOLoader.h index 621f54b27..84f752813 100644 --- a/code/LWOLoader.h +++ b/code/LWOLoader.h @@ -48,8 +48,8 @@ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. #include "LWOFileData.h" #include "MaterialSystem.h" -#include struct aiTexture; +struct aiNode; namespace Assimp { using namespace LWO; @@ -61,6 +61,7 @@ class LWOImporter : public BaseImporter { friend class Importer; + protected: /** Constructor to be privately used by Importer */ LWOImporter(); @@ -101,6 +102,7 @@ protected: void InternReadFile( const std::string& pFile, aiScene* pScene, IOSystem* pIOHandler); +private: // ------------------------------------------------------------------- /** Loads a LWO file in the older LWOB format (LW < 6) @@ -149,6 +151,36 @@ protected: */ void LoadLWOTags(unsigned int size); + // ------------------------------------------------------------------- + /** Load polygons from a POLS chunk + * @param length Size of the chunk + */ + void LoadLWOPolygons(unsigned int length); + + // ------------------------------------------------------------------- + /** Load polygons from a PNTS chunk + * @param length Size of the chunk + */ + void LoadLWOPoints(unsigned int length); + + + // ------------------------------------------------------------------- + /** Count vertices and faces in a LWOB/LWO2 file + */ + void CountVertsAndFaces(unsigned int& verts, + unsigned int& faces, + LE_NCONST uint16_t*& cursor, + const uint16_t* const end, + unsigned int max = 0xffffffff); + + // ------------------------------------------------------------------- + /** Read vertices and faces in a LWOB/LWO2 file + */ + void CopyFaceIndices(LWO::FaceList::iterator& it, + LE_NCONST uint16_t*& cursor, + const uint16_t* const end, + unsigned int max = 0xffffffff); + // ------------------------------------------------------------------- /** Resolve the tag and surface lists that have been loaded. * Generates the mMapping table. @@ -166,32 +198,6 @@ protected: bool ComputeGradientTexture(LWO::GradientInfo& grad, std::vector& out); - - typedef std::vector PointList; - typedef std::vector FaceList; - typedef std::vector SurfaceList; - typedef std::vector TagList; - typedef std::vector TagMappingTable; - -private: - - // ------------------------------------------------------------------- - /** Count vertices and faces in a LWOB file - */ - void CountVertsAndFaces(unsigned int& verts, - unsigned int& faces, - LE_NCONST uint16_t*& cursor, - const uint16_t* const end, - unsigned int max = 0xffffffff); - - // ------------------------------------------------------------------- - /** Read vertices and faces in a LWOB file - */ - void CopyFaceIndices(FaceList::iterator& it, - LE_NCONST uint16_t*& cursor, - const uint16_t* const end, - unsigned int max = 0xffffffff); - // ------------------------------------------------------------------- /** Parse a string from the current file position */ @@ -207,16 +213,23 @@ private: */ void ConvertMaterial(const LWO::Surface& surf,MaterialHelper* pcMat); + // ------------------------------------------------------------------- + /** Generate the final node graph + * Unused nodes are deleted. + * @param apcNodes Flat list of nodes + */ + void GenerateNodeGraph(std::vector& apcNodes); + protected: /** true if the file is a LWO2 file*/ bool mIsLWO2; - /** Temporary point list from the file */ - PointList* mTempPoints; + /** Temporary list of layers from the file */ + LayerList* mLayers; - /** Temporary face list from the file*/ - FaceList* mFaces; + /** Pointer to the current layer */ + LWO::Layer* mCurLayer; /** Temporary tag list from the file */ TagList* mTags; diff --git a/code/STLLoader.cpp b/code/STLLoader.cpp index 92fa6270c..17a0f9917 100644 --- a/code/STLLoader.cpp +++ b/code/STLLoader.cpp @@ -166,8 +166,6 @@ void STLImporter::InternReadFile( pScene->mNumMaterials = 1; pScene->mMaterials = new aiMaterial*[1]; pScene->mMaterials[0] = pcMat; - - delete[] this->mBuffer;AI_DEBUG_INVALIDATE_PTR(this->mBuffer); } // ------------------------------------------------------------------------------------------------ // Read an ASCII STL file diff --git a/include/aiScene.h b/include/aiScene.h index ae670c20f..307d65497 100644 --- a/include/aiScene.h +++ b/include/aiScene.h @@ -100,6 +100,16 @@ struct aiNode mNumMeshes = 0; mMeshes = NULL; } + /** Construction from a specific name */ + aiNode(const std::string& name) + { + // set all members to zero by default + mParent = NULL; + mNumChildren = 0; mChildren = NULL; + mNumMeshes = 0; mMeshes = NULL; + mName = name; + } + /** Destructor */ ~aiNode() { diff --git a/workspaces/vc8/assimp.vcproj b/workspaces/vc8/assimp.vcproj index 8f4c9581d..139cc9424 100644 --- a/workspaces/vc8/assimp.vcproj +++ b/workspaces/vc8/assimp.vcproj @@ -818,74 +818,6 @@ RelativePath="..\..\code\VertexTriangleAdjacency.h" > - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -898,78 +830,6 @@ > - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -995,68 +855,212 @@ - - - + + + + + + + - - - - + + + + + - - - - + + + + + - - - - + + + + + - - + + + + + + + - - - - + + + + + - - + + + + + - - + + + + + + + - - - - + + + + + + + + + - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - @@ -1283,60 +1187,164 @@ - - - - - + + + + + + + + + - - - - + + + + + - - + + + - - - - + + + + + - - - - + + + - - + + + - - - - + + + + + - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +