Go to the documentation of this file.00001 #ifndef OPENTISSUE_CORE_CONTAINERS_MESH_POLYMESH_UTIL_POLYMESH_COMPUTE_DUAL_H
00002 #define OPENTISSUE_CORE_CONTAINERS_MESH_POLYMESH_UTIL_POLYMESH_COMPUTE_DUAL_H
00003
00004
00005
00006
00007
00008
00009
00010 #include <OpenTissue/configuration.h>
00011
00012 #include <OpenTissue/core/containers/mesh/common/util/mesh_compute_face_center.h>
00013 #include <OpenTissue/core/containers/mesh/polymesh/util/polymesh_is_boundary.h>
00014 #include <boost/vector_property_map.hpp>
00015 #include <list>
00016 #include <stdexcept>
00017
00018 namespace OpenTissue
00019 {
00020 namespace polymesh
00021 {
00022
00027 struct center_vertex_policy
00028 {
00029
00030 template<typename face_type, typename vector3_type>
00031 static void compute_position( face_type const & face, vector3_type & coord )
00032 {
00033 mesh::compute_face_center( face, coord );
00034 }
00035
00036 template<typename face_type, typename vector3_type>
00037 static void compute_normal( face_type const & face, vector3_type & normal )
00038 {
00039 normal.clear();
00040 }
00041
00042 };
00043
00044
00054 template< typename mesh_type, typename vertex_policy >
00055 void compute_dual(mesh_type const & original, mesh_type & dual, vertex_policy const & )
00056 {
00057 typedef typename mesh_type::math_types math_types;
00058 typedef typename math_types::vector3_type vector3_type;
00059 typedef typename mesh_type::vertex_handle vertex_handle;
00060 typedef typename mesh_type::const_face_iterator const_face_iterator;
00061 typedef typename mesh_type::const_vertex_iterator const_vertex_iterator;
00062 typedef typename mesh_type::const_vertex_face_circulator const_vertex_face_circulator;
00063
00064 if(&original == &dual)
00065 throw std::invalid_argument("polymesh::compute_dual(): original and dual meshes must not be the same");
00066
00067 dual.clear();
00068
00069 boost::vector_property_map<vertex_handle> handles;
00070 {
00071 const_face_iterator face = original.face_begin();
00072 const_face_iterator fend = original.face_end();
00073 for(;face!=fend;++face)
00074 {
00075 vector3_type coord;
00076
00077 vertex_policy::compute_position( *face, coord );
00078
00079 vertex_handle h = dual.add_vertex( coord );
00080 handles[ face->get_handle().get_idx() ] = h;
00081
00082 vertex_policy::compute_normal( *face, dual.get_vertex_iterator(h)->m_normal );
00083 }
00084 }
00085 {
00086 const_vertex_iterator vertex = original.vertex_begin();
00087 const_vertex_iterator vend = original.vertex_end();
00088 for(;vertex!=vend;++vertex)
00089 {
00090
00091 if( is_boundary( *vertex ) )
00092 continue;
00093
00094 std::list<vertex_handle> vertices;
00095
00096 const_vertex_face_circulator face(*vertex), fend;
00097 for(;face!=fend;++face)
00098 vertices.push_back( handles[face->get_handle().get_idx()] );
00099
00100 if(vertices.size()<3)
00101 continue;
00102
00103 dual.add_face(vertices.begin(),vertices.end());
00104 }
00105 }
00106
00107 }
00108
00109
00110
00120 template< typename mesh_type >
00121 void compute_dual(mesh_type const & original, mesh_type & dual )
00122 {
00123 compute_dual( original, dual, center_vertex_policy() );
00124 }
00125
00126
00127
00128
00129 }
00130 }
00131
00132
00133 #endif