在我的应用程序中,我使用了很多三角形网格,有时我需要减少三角形中的三角形(colapse一些边)。对于网格处理,我使用openmesh (openmesh.org),因为它是现代的( c++ ),但主要是因为它没有拖曳大量依赖项(只依赖于c++ std,任何现代压缩程序都可以处理它(我需要跨平台Linux/Windows/Mac )。
现在我需要减少一些网格( openmesh术语中的抽取),但是我需要保留边界。(所讨论的网格是原始网格(512x512),但在网格中心挤压/添加了一些凸元素,在缩小后网格的外部边缘仍然形成矩形是至关重要的。)
我没有办法在openmesh中抽取它们并保存音量/大纲,所有OpenMesh::Decimater::Mod*抽取模块都使用二次抽取作为它们的基。
在GTS (GNU三角曲面库)中,实现了Lindstrom-Turk还原,这是我的理想需求(我做了一些脏包装来测试它是否是我想要的),但GTS存在一些问题-它不是多线程保存(我在多线程上减少了许多网格),而且使用GTS是不可能的,因为它在库中使用全局变量来禁用/启用一些东西,同时减少了网格:/) (而且它还会拖曳整个网格作为它的依赖项)
还有CGAL,它还实现了Lindstrom,但是它将整个boost和其他依赖关系拖到自己身上:/
是否有任何用于openmesh的抽取模块可以进行边界/卷保存的抽取?(我搜索过,但没有发现:/)
发布于 2015-10-18 15:38:51
据我所知,“网格边界”指的是仅形成单个网格面的网格边缘(如示例中512x512网格的外部边缘),而不是在两个或多个网格面之间共享每个网格边缘的更常见情况。
在OpenMesh中,实际上有一种非常简单的方法可以告诉OpenMesh::Decimater模块保留这些边的原样。更好的是,它不依赖于您实际使用的抽取模块的类型。实际的网格数据结构(即OpenMesh::TriMesh_ArrayKernelT<>)具有一个名为“顶点锁定”的特性。它本质上是一种告诉OpenMesh不要触及特定顶点集的方法,不管在抽取过程中发生了什么。
下面是直接从正式文件中提取出来的代码片段,对C++11做了一些修改:
using Mesh = OpenMesh::TriMesh_ArrayKernelT<>;
void protectMeshBoundariesFromDecimation(Mesh& mesh) {
mesh.request_vertex_status();
for (const auto& halfEdgeHandle : mesh.halfedges()) {
if (mesh.is_boundary(halfEdgeHandle) ) {
mesh.status(mesh.to_vertex_handle(halfEdgeHandle)).set_locked(true);
mesh.status(mesh.from_vertex_handle(halfEdgeHandle)).set_locked(true);
}
}
}如果您想要阅读有关该问题的完整文档,而上面的链接不再有效,请在docs内容树中转到OpenMesh -> OpenMesh Documentation -> OpenMesh OpenMesh Documentation -> Mesh抽取框架。
本质上,这个循环超过了所有的半边(不是边!)你的网格和“锁”顶点,形成半边,没有对(没有下半边)。由于OpenMesh所使用的半边缘数据结构的性质,对于n边缘的网格来说,这具有O(n)复杂性。
如果您不熟悉半边数据结构的细节,我建议您阅读OpenMesh文档的优秀的OpenMesh入门部分。
https://stackoverflow.com/questions/27885606
复制相似问题