From 31965fe59903d95dd71342e0f95c099a8da146ca Mon Sep 17 00:00:00 2001 From: cutealien Date: Wed, 24 Aug 2022 22:14:50 +0000 Subject: [PATCH] CMeshManipulator::createMeshWelded now cloning buffers it can't weld. Not optimal, but making this real 32-bit is sadly a bit more work. This way at lest meshes with mixed 16/32 bit buffers can weld the 16-bit ones. And hopefully a bit of step in the right direction to fully support 32-bit another day. git-svn-id: svn://svn.code.sf.net/p/irrlicht/code/trunk@6417 dfc29bdd-3216-0410-991c-e03cc46cb475 --- include/IMeshManipulator.h | 15 ++++--- source/Irrlicht/CMeshManipulator.cpp | 58 ++++++++++++++-------------- 2 files changed, 39 insertions(+), 34 deletions(-) diff --git a/include/IMeshManipulator.h b/include/IMeshManipulator.h index 1b307301..0f4d0414 100644 --- a/include/IMeshManipulator.h +++ b/include/IMeshManipulator.h @@ -239,6 +239,7 @@ namespace scene /** This is useful if you want to draw tangent space normal mapped geometry because it calculates the tangent and binormal data which is needed there. + Note: Only 16-bit meshbuffers supported so far \param mesh Input mesh \param recalculateNormals The normals are recalculated if set, otherwise the original ones are kept. Note that keeping the @@ -257,7 +258,8 @@ namespace scene bool angleWeighted=false, bool recalculateTangents=true) const=0; //! Creates a copy of the mesh, which will only consist of S3DVertex2TCoord vertices. - /** \param mesh Input mesh + /** Note: Only 16-bit meshbuffers supported so far + \param mesh Input mesh \return Mesh consisting only of S3DVertex2TCoord vertices. If you no longer need the cloned mesh, you should call IMesh::drop(). See IReferenceCounted::drop() for more @@ -265,7 +267,8 @@ namespace scene virtual IMesh* createMeshWith2TCoords(IMesh* mesh) const = 0; //! Creates a copy of the mesh, which will only consist of S3DVertex vertices. - /** \param mesh Input mesh + /** Note: Only 16-bit meshbuffers supported so far + \param mesh Input mesh \return Mesh consisting only of S3DVertex vertices. If you no longer need the cloned mesh, you should call IMesh::drop(). See IReferenceCounted::drop() for more @@ -273,15 +276,17 @@ namespace scene virtual IMesh* createMeshWith1TCoords(IMesh* mesh) const = 0; //! Creates a copy of a mesh with all vertices unwelded - /** \param mesh Input mesh + /** Note: Only 16-bit meshbuffers supported so far + \param mesh Input mesh \return Mesh consisting only of unique faces. All vertices which were previously shared are now duplicated. If you no longer need the cloned mesh, you should call IMesh::drop(). See IReferenceCounted::drop() for more information. */ virtual IMesh* createMeshUniquePrimitives(IMesh* mesh) const = 0; - //! Creates a copy of a mesh with vertices welded - /** \param mesh Input mesh + //! Creates a copy of a mesh with vertices welded + /** Note: Only 16-bit meshbuffers supported so far, 32-bit buffer are cloned + \param mesh Input mesh \param tolerance The threshold for vertex comparisons. \return Mesh without redundant vertices. If you no longer need the cloned mesh, you should call IMesh::drop(). See diff --git a/source/Irrlicht/CMeshManipulator.cpp b/source/Irrlicht/CMeshManipulator.cpp index 093ad239..bc02c391 100644 --- a/source/Irrlicht/CMeshManipulator.cpp +++ b/source/Irrlicht/CMeshManipulator.cpp @@ -708,38 +708,45 @@ IMesh* CMeshManipulator::createMeshUniquePrimitives(IMesh* mesh) const // not yet 32bit IMesh* CMeshManipulator::createMeshWelded(IMesh *mesh, f32 tolerance) const { - SMesh* clone = new SMesh(); - clone->BoundingBox = mesh->getBoundingBox(); + SMesh* meshClone = new SMesh(); + meshClone->BoundingBox = mesh->getBoundingBox(); core::array redirects; for (u32 b=0; bgetMeshBufferCount(); ++b) { const IMeshBuffer* const mb = mesh->getMeshBuffer(b); + const u32 vertexCount = mb->getVertexCount(); // reset redirect list - redirects.set_used(mb->getVertexCount()); + redirects.set_used(vertexCount); - const u16* indices = 0; - u32 indexCount = 0; + const video::E_INDEX_TYPE indexType = mb->getIndexType(); + const u16* indices = mb->getIndices(); + const u32 indexCount = mb->getIndexCount(); core::array* outIdx = 0; + if ( indexType == video::EIT_32BIT ) + { + IMeshBuffer* buffer = mb->createClone(); + buffer->setBoundingBox(mb->getBoundingBox()); + buffer->getMaterial() = mb->getMaterial(); + meshClone->addMeshBuffer(buffer); + buffer->drop(); + continue; // TODO: handle 32-bit buffers beside copying them + } + switch(mb->getVertexType()) { case video::EVT_STANDARD: { SMeshBuffer* buffer = new SMeshBuffer(); - buffer->BoundingBox = mb->getBoundingBox(); + buffer->setBoundingBox(mb->getBoundingBox()); buffer->Material = mb->getMaterial(); - clone->addMeshBuffer(buffer); + meshClone->addMeshBuffer(buffer); buffer->drop(); - video::S3DVertex* v = - (video::S3DVertex*)mb->getVertices(); + video::S3DVertex* v = (video::S3DVertex*)mb->getVertices(); - u32 vertexCount = mb->getVertexCount(); - - indices = mb->getIndices(); - indexCount = mb->getIndexCount(); outIdx = &buffer->Indices; buffer->Vertices.reallocate(vertexCount); @@ -771,18 +778,14 @@ IMesh* CMeshManipulator::createMeshWelded(IMesh *mesh, f32 tolerance) const case video::EVT_2TCOORDS: { SMeshBufferLightMap* buffer = new SMeshBufferLightMap(); - buffer->BoundingBox = mb->getBoundingBox(); + buffer->setBoundingBox(mb->getBoundingBox()); buffer->Material = mb->getMaterial(); - clone->addMeshBuffer(buffer); + meshClone->addMeshBuffer(buffer); buffer->drop(); video::S3DVertex2TCoords* v = (video::S3DVertex2TCoords*)mb->getVertices(); - u32 vertexCount = mb->getVertexCount(); - - indices = mb->getIndices(); - indexCount = mb->getIndexCount(); outIdx = &buffer->Indices; buffer->Vertices.reallocate(vertexCount); @@ -814,18 +817,13 @@ IMesh* CMeshManipulator::createMeshWelded(IMesh *mesh, f32 tolerance) const case video::EVT_TANGENTS: { SMeshBufferTangents* buffer = new SMeshBufferTangents(); - buffer->BoundingBox = mb->getBoundingBox(); + buffer->setBoundingBox(mb->getBoundingBox()); buffer->Material = mb->getMaterial(); - clone->addMeshBuffer(buffer); + meshClone->addMeshBuffer(buffer); buffer->drop(); - video::S3DVertexTangents* v = - (video::S3DVertexTangents*)mb->getVertices(); + video::S3DVertexTangents* v = (video::S3DVertexTangents*)mb->getVertices(); - u32 vertexCount = mb->getVertexCount(); - - indices = mb->getIndices(); - indexCount = mb->getIndexCount(); outIdx = &buffer->Indices; buffer->Vertices.reallocate(vertexCount); @@ -860,7 +858,7 @@ IMesh* CMeshManipulator::createMeshWelded(IMesh *mesh, f32 tolerance) const break; } - // Clean up any degenerate tris + // set indices for new buffer core::array &Indices = *outIdx; Indices.clear(); Indices.reallocate(indexCount); @@ -873,6 +871,7 @@ IMesh* CMeshManipulator::createMeshWelded(IMesh *mesh, f32 tolerance) const bool drop = false; + // Clean up any degenerate tris if (a == b || b == c || a == c) drop = true; @@ -885,8 +884,9 @@ IMesh* CMeshManipulator::createMeshWelded(IMesh *mesh, f32 tolerance) const Indices.push_back(c); } } + // indexCount-Indices.size() vertices got welded for this meshbuffer } - return clone; + return meshClone; }