/**************************************************************************** * VCGLib o o * * Visual and Computer Graphics Library o o * * _ O _ * * Copyright(C) 2004 \/)\/ * * Visual Computing Lab /\/| * * ISTI - Italian National Research Council | * * \ * * All rights reserved. * * * * This program is free software; you can redistribute it and/or modify * * it under the terms of the GNU General Public License as published by * * the Free Software Foundation; either version 2 of the License, or * * (at your option) any later version. * * * * This program is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU General Public License (http://www.gnu.org/licenses/gpl.txt) * * for more details. * * * ****************************************************************************/ /**************************************************************************** History Revision 1.1 2004/22/04 14:32 pietroni Initial commit ****************************************************************************/ #ifndef __VCG_TETRA_TRI_CONVERTER #define __VCG_TETRA_TRI_CONVERTER #include #include #include namespace vcg { namespace tetra { /** Class TriConverter. This is class for convetr tetrahedral mesh into triangle mesh @param STL_VERT_CONT (Template Parameter) Specifies the type of the vertices container any the vertex type. @param STL_TETRA_CONT (Template Parameter) Specifies the type of the tetrahedrons container any the tetrahedrons type. */ template < class TETRA_MESH ,class TRI_MESH > class TriConverter { public: /// The tetrahedral mesh type typedef TETRA_MESH TetraMeshType; /// The triangle mesh type typedef TRI_MESH TriangleMeshType; /// The tetrahedron type typedef typename TetraMeshType::TetraType TetraType; /// The triangle type typedef typename TriangleMeshType::FaceType FaceType; /// The vertex type of tetrahedreal Mesh typedef typename TetraMeshType::VertexType TetraVertexType; /// The vertex type of triangular Mesh typedef typename TriangleMeshType::VertexType TriVertexType; /// The type of vertex iterator on tetrahedral mesh typedef typename TetraMeshType::VertexIterator TetraVertexIterator; /// The type of vertex iterator on tetrahedral mesh typedef typename TriangleMeshType::VertexIterator TriVertexIterator; /// The type of tetra iterator typedef typename TetraMeshType::TetraIterator TetraIterator; /// The type of tetra iterator typedef typename TriangleMeshType::FaceIterator FaceIterator; /// The type of const tetra iterator typedef typename TetraMeshType::const_TetraIterator const_TetraIterator; /// The type of const face iterator typedef typename TriangleMeshType::ConstFaceIterator ConstFaceIterator; /// The type of tetrahedrons container typedef typename TetraMeshType::TetraContainer TetraContainer; /// The type of const vertex pointer of tetrahedral mesh typedef typename TetraMeshType::const_VertexPointer const_VertexPointer; public: /***********************************************/ /** @Convert to triangle-mesh functions **/ //@{ ///this function build a triangle mesh using the same pointers to the tetrahedral mesh vertex void Convert(TetraContainer &tetra,TriangleMeshType &trim) { TetraIterator ti; TetraVertexType *v0; TetraVertexType *v1; TetraVertexType *v2; trim.Clear(); for (ti=tetra.begin();tiIsD())) { if ((ti->IsBorderF(0))||(ti->IsBorderF(1))||(ti->IsBorderF(2))||(ti->IsBorderF(3))) for (int i=0;i<4;i++) if (ti->IsBorderF(i)) { v0=ti->V(Tetra::VofF(i,0)); v1=ti->V(Tetra::VofF(i,1)); v2=ti->V(Tetra::VofF(i,2)); FaceType f=FaceType(); f.ClearFlags(); f.V(0)=v0; f.V(1)=v1; f.V(2)=v2; trim.face.push_back(f); } } } } struct InsertedV{ InsertedV( TriVertexType *_v, FaceType* _f, int _z):v(_v),f(_f),z(_z){} TriVertexType *v; FaceType* f; int z; const bool operator <(const InsertedV & o){ return (v newVertices; typename vector::iterator curr,next; TriVertexIterator vi; vector redirect; Convert(tetra,trim); FaceIterator fi; for(fi = trim.face.begin(); fi != trim.face.end(); ++fi){ newVertices.push_back(InsertedV( (*fi).V(0),&(*fi),0)); newVertices.push_back(InsertedV( (*fi).V(1),&(*fi),1)); newVertices.push_back(InsertedV( (*fi).V(2),&(*fi),2)); } sort(newVertices.begin(),newVertices.end()); int pos = 0; curr = next = newVertices.begin(); while( next != newVertices.end()){ if((*curr)!=(*next)) pos++; (*next).f->V( (*next).z) = (TriVertexType*)pos; curr = next; next++; } typename vector::iterator newE = unique(newVertices.begin(),newVertices.end()); for(curr = newVertices.begin();curr!= newE;++curr) trim.vert.push_back(*((*curr).v)); for(vi = trim.vert.begin(); vi != trim.vert.end(); ++vi) redirect.push_back(&(*vi)); for(fi = trim.face.begin(); fi != trim.face.end(); ++fi){ (*fi).V(0) = redirect[(int)(*fi).V(0)]; (*fi).V(1) = redirect[(int)(*fi).V(1)]; (*fi).V(2) = redirect[(int)(*fi).V(2)]; } trim.vn = trim.vert.size(); trim.fn = trim.face.size(); } };// End class } // End namespace } // End namespace #endif