#pragma once /** * @file explode_view.h * @brief 装配体爆炸视图 * * 将装配体零件沿约束/层级方向展开,生成爆炸视图。 * 每个零件的世界变换被修改以产生分解效果。 * * @ingroup brep */ #include "vde/brep/assembly.h" #include "vde/core/point.h" #include #include #include namespace vde::brep { /** * @brief 爆炸视图配置 */ struct ExplodeConfig { double factor = 1.0; ///< 爆炸距离系数(越大越分散) core::Vector3D direction; ///< 全局爆炸方向(世界坐标),零向量 = 自动 bool use_constraint_dirs = true; ///< 是否沿约束方向展开 bool preserve_subassemblies = true; ///< 子装配体内部不分解 }; /** * @brief 爆炸步信息(用于动画) */ struct ExplodeStep { std::string part_name; ///< 零件名称 core::Transform3D original_transform; ///< 原始变换 core::Transform3D exploded_transform; ///< 爆炸后变换 core::Vector3D displacement; ///< 位移向量 }; /** * @brief 爆炸视图结果 */ struct ExplodeResult { std::vector steps; ///< 各零件爆炸步 core::AABB3D original_bounds; ///< 原始包围盒 core::AABB3D exploded_bounds; ///< 爆炸后包围盒 /// 获取爆炸总位移范围 [[nodiscard]] double max_displacement() const; }; // ═══════════════════════════════════════════════════════════ // API // ═══════════════════════════════════════════════════════════ /** * @brief 生成爆炸视图 * * 沿装配层级方向展开零件。根部零件居中,子节点沿 * 相对于父节点的位移方向向外扩散。 * * @param assembly 装配体(会被原地修改零件变换) * @param config 爆炸配置 * @return 爆炸结果(含各零件位移信息) * * @code{.cpp} * Assembly assy("engine"); * // ... 添加零件 ... * * ExplodeConfig cfg; * cfg.factor = 2.0; * * auto result = explode_view(assy, cfg); * for (auto& step : result.steps) { * std::cout << step.part_name << " → " * << step.displacement.norm() << "\n"; * } * @endcode */ [[nodiscard]] ExplodeResult explode_view( Assembly& assembly, const ExplodeConfig& config = {}); /** * @brief 取消爆炸(恢复原始变换) * * @param assembly 装配体(原地修改) * @param result 之前 explode_view 返回的结果 */ void un_explode(Assembly& assembly, const ExplodeResult& result); /** * @brief 单零件爆炸位移 * * 计算一个零件在装配体中的爆炸方向。 * * @param node 零件节点 * @param parent_tf 父节点世界变换 * @param factor 爆炸系数 * @return 位移向量 */ [[nodiscard]] core::Vector3D compute_explode_displacement( const AssemblyNode& node, const core::Transform3D& parent_tf, double factor); } // namespace vde::brep