markdown
# MeshBoolean.hpp 代码分析
## 功能概述
本头文件提供三维网格布尔运算功能,支持差集、并集、交集操作。实现基于CGAL和Mcut两种底层库,包含数据结构转换、运算接口及辅助功能。
## 核心结构
### 数据结构
```cpp
using EigenMesh = std::pair<Eigen::MatrixXd, Eigen::MatrixXi>; // Eigen矩阵存储网格
struct CGALMesh; // CGAL网格抽象(使用PIMPL模式)
struct McutMesh; // Mcut网格抽象
智能指针管理
cpp
// CGAL网格指针(RAII管理)
using CGALMeshPtr = std::unique_ptr<CGALMesh, CGALMeshDeleter>;
// Mcut网格指针
using McutMeshPtr = std::unique_ptr<McutMesh, McutMeshDeleter>;
主要功能模块
数据转换接口
转换方向 | 函数 |
---|---|
Eigen ↔ TriangleMesh | eigen_to_triangle_mesh() triangle_mesh_to_eigen() |
TriangleMesh ↔ CGAL | triangle_mesh_to_cgal() cgal_to_triangle_mesh() |
TriangleMesh ↔ Mcut | triangle_mesh_to_mcut() mcut_to_triangle_mesh() |
布尔运算接口
cpp
// 基础运算类型
void minus(A, B); // 差集 A - B
void plus(A, B); // 并集 A ∪ B
void intersect(A, B);// 交集 A ∩ B
// 支持数据类型重载
• TriangleMesh
• indexed_triangle_set
• CGALMesh
• McutMesh
高级功能
cpp
// 网格分割与合并
std::vector<TriangleMesh> segment(...); // 网格分割
TriangleMesh merge(...); // 多网格合并
// 网格分析
bool does_self_intersect(...); // 自相交检测
bool does_bound_a_volume(...); // 闭合体积检查
bool empty(...); // 空网格检测
实现细节
双引擎架构
输入网格 CGAL引擎 Mcut引擎 精确布尔运算 高效大规模运算 结果网格
CGAL引擎特点:
- 基于计算几何算法库
- 支持复杂拓扑结构
- 提供自相交检测等高级功能
Mcut引擎特点:
- 处理大规模网格高效
- 支持多体积布尔运算
- 单独
make_boolean
接口
关键设计模式
-
PIMPL模式:
- 隐藏CGAL/Mcut具体实现
- 减少头文件依赖
cppstruct CGALMesh; // 前置声明 struct CGALMeshDeleter; // 定制删除器
-
RAII资源管理:
cppCGALMeshPtr ptr = triangle_mesh_to_cgal(...); // 自动调用删除器释放资源
-
多态接口设计:
cpp// 统一接口支持不同数据结构 void minus(TriangleMesh&, const TriangleMesh&); void minus(CGALMesh&, CGALMesh&);
性能优化
数据转换优化
- 避免深拷贝:转换函数直接操作原始网格数据
- 矩阵存储优化:Eigen矩阵列优先存储提升缓存利用率
运算选择策略
场景 | 推荐引擎 |
---|---|
高精度要求 | CGAL |
大规模网格 | Mcut |
多体积运算 | Mcut |
使用示例
基本布尔差集
cpp
TriangleMesh A, B;
MeshBoolean::minus(A, B); // A = A - B
多引擎运算
cpp
// 使用CGAL检测自相交
if (!MeshBoolean::cgal::does_self_intersect(A)) {
// 使用Mcut执行布尔运算
McutMeshPtr mA = MeshBoolean::mcut::triangle_mesh_to_mcut(A);
McutMeshPtr mB = MeshBoolean::mcut::triangle_mesh_to_mcut(B);
MeshBoolean::mcut::do_boolean(*mA, *mB, "difference");
}
扩展接口
自定义网格处理
cpp
// 添加网格光滑处理
void smooth(CGALMesh& mesh, double factor) {
// 调用CGAL平滑算法
}
进阶分析
cpp
// 计算网格体积
double calculate_volume(const CGALMesh& mesh) {
// 使用CGAL体积计算功能
}
注意事项
-
精度控制:
- CGAL使用精确数值计算
- Mcut适合工程级精度
-
内存管理:
- 避免大规模网格多次转换
- 及时释放McutMesh资源
-
异常处理:
cpptry { MeshBoolean::minus(A, B); } catch (const std::exception& e) { // 处理布尔运算失败 }