In this section you will learn about some basic operations on a mesh that OpenMesh already provides. Comprising the flipping of edges in a triangle mesh as well as collapsing edges by joining the two adjacent vertices.
Flipping edges in triangle meshes
Considering two adjacent faces of a triangle mesh, there exist exactly two different configurations of the inner edge. Calling the function OpenMesh::TriConnectivity::flip(EdgeHandle _eh) will flip the specified edge to its opposite orientation as shown in the illustration below.
Flipping edges in a triangle mesh
So, the following snippet of code shows how to use this in your applications:
TriMesh mesh;
TriMesh::VertexHandle vhandle[4];
std::vector<TriMesh::VertexHandle> face_vhandles;
face_vhandles.push_back(vhandle[2]);
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[0]);
mesh.add_face(face_vhandles);
face_vhandles.clear();
face_vhandles.push_back(vhandle[2]);
face_vhandles.push_back(vhandle[0]);
face_vhandles.push_back(vhandle[3]);
mesh.add_face(face_vhandles);
for(TriMesh::EdgeIter it = mesh.edges_begin(); it != mesh.edges_end(); ++it) {
if(!mesh.is_boundary(*it)) {
mesh.flip(*it);
}
}
Collapsing edges
In this section you will learn how to collapse edges such that the two adjacent vertices join. OpenMesh provides the function OpenMesh::PolyConnectivity::collapse(HalfedgeHandle _heh) to perform this operation. This will collapse the from-vertex (remeber that halfedges are directed) to the to-vertex of the halfedge as illustrated below. Note that collapsing edges might cause topological inconsistencies to your mesh. You should verify consistency after collapsing edges by calling OpenMesh::PolyConnectivity::is_collapse_ok().
- Note
- You have to request status attributes in order to use the collapse and delete functions!
Collapsing will always be performed in the direction the halfedge points to.
A simple code example related to the illustration might look like this:
PolyMesh mesh;
mesh.request_vertex_status();
mesh.request_edge_status();
mesh.request_face_status();
PolyMesh::VertexHandle vhandle[7];
std::vector<PolyMesh::VertexHandle> face_vhandles;
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[0]);
face_vhandles.push_back(vhandle[2]);
face_vhandles.push_back(vhandle[3]);
mesh.add_face(face_vhandles);
face_vhandles.clear();
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[3]);
face_vhandles.push_back(vhandle[5]);
face_vhandles.push_back(vhandle[4]);
mesh.add_face(face_vhandles);
face_vhandles.clear();
face_vhandles.push_back(vhandle[3]);
face_vhandles.push_back(vhandle[2]);
face_vhandles.push_back(vhandle[6]);
face_vhandles.push_back(vhandle[5]);
mesh.add_face(face_vhandles);
for(PolyMesh::HalfedgeIter it = mesh.halfedges_begin(); it != mesh.halfedges_end(); ++it) {
if( mesh.to_vertex_handle(*it) == vhandle[3] &&
mesh.from_vertex_handle(*it) == vhandle[2])
{
mesh.collapse(*it);
break;
}
}