我一直在关注 OpenMesh 教程的第一步 -通过一些修改构建一个立方体,我使用的是 TriMesh 而不是 PolyMesh 并且正在构建金字塔而不是立方体。
不知何故,PolymeshT::add_face:complex edge我的第二张脸和第三张脸都出现了错误。这些面应该在点 (0,0,0)、(0,1,0) 和 (0,0,1) 以及点 (0,0,0)、(0,0,1) 和(1,0,0)。
当每个面被构造为 (0,0,0) 到 (0,1,0) 和 (0,0,0) 到 (0,0,1) 时,两条边已经存在,但我应该能够在其中创建面一些边缘已经存在,不是吗?
到目前为止我尝试过的解决方案
我无法发现我正在做的与教程不同的任何其他事情。
#include <OpenMesh/Core/IO/MeshIO.hh>
#include <OpenMesh/Core/Mesh/TriMesh_ArrayKernelT.hh>
typedef OpenMesh::TriMesh_ArrayKernelT<> MyTriMesh;
// Make a pyramid
int main()
{
MyTriMesh tin;
// generate vertices
MyTriMesh::VertexHandle vhandle[4];
vhandle[0] = tin.add_vertex(MyTriMesh::Point(0, 0, 0));
vhandle[1] = tin.add_vertex(MyTriMesh::Point(0, 1, 0));
vhandle[2] = tin.add_vertex(MyTriMesh::Point(1, 0, 0));
vhandle[3] = tin.add_vertex(MyTriMesh::Point(0, 0, 1));
// generate (trianglar) faces
std::vector<MyTriMesh::VertexHandle> face_vhandles;
face_vhandles.clear();
face_vhandles.push_back(vhandle[0]);
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[2]);
tin.add_face(face_vhandles);
printf("Vertices: %u\nEdges: %u\nTriangles: %u\n",
tin.n_vertices(), tin.n_edges(), tin.n_faces());
face_vhandles.clear();
face_vhandles.push_back(vhandle[0]);
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[3]);
tin.add_face(face_vhandles);
printf("Vertices: %u\nEdges: %u\nTriangles: %u\n",
tin.n_vertices(), tin.n_edges(), tin.n_faces());
face_vhandles.clear();
face_vhandles.push_back(vhandle[0]);
face_vhandles.push_back(vhandle[3]);
face_vhandles.push_back(vhandle[2]);
tin.add_face(face_vhandles);
printf("Vertices: %u\nEdges: %u\nTriangles: %u\n",
tin.n_vertices(), tin.n_edges(), tin.n_faces());
face_vhandles.clear();
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[3]);
face_vhandles.push_back(vhandle[2]);
tin.add_face(face_vhandles);
printf("Vertices: %u\nEdges: %u\nTriangles: %u\n",
tin.n_vertices(), tin.n_edges(), tin.n_faces());
}
Run Code Online (Sandbox Code Playgroud)
此错误是由于某些面的顶点以错误的顺序添加所致。
OpenMesh 使用半边结构来描述网格的 3d 结构。半边是顶点之间的有向边。这允许通过跟随属于该面的半边来横切面上的顶点。但是,由于这个原因,顶点添加到面上的顺序非常重要。
通常,顶点应始终按逆时针顺序添加。这导致相邻面的半边指向相反的方向,如下左图所示。如果顶点的顺序不一致,则关于哪条边跟随半边、“A”的底边或“B”的底边存在歧义,如下右图所示。

在问题的代码中,面 1 和 4 逆时针排序,面 2 和 3 顺时针排序。简单的解决方法是切换这两个面的第一个和第三个顶点。
face_vhandles.clear();
face_vhandles.push_back(vhandle[3]);
face_vhandles.push_back(vhandle[1]);
face_vhandles.push_back(vhandle[0]);
tin.add_face(face_vhandles);
face_vhandles.clear();
face_vhandles.push_back(vhandle[2]);
face_vhandles.push_back(vhandle[3]);
face_vhandles.push_back(vhandle[0]);
tin.add_face(face_vhandles);
Run Code Online (Sandbox Code Playgroud)