#pragma once #include "vde/curves/nurbs_surface.h" #include "vde/curves/nurbs_curve.h" #include "vde/core/point.h" #include #include namespace vde::curves { using core::Point3D; using core::Vector3D; /** * @brief 连续性级别 * @ingroup curves */ enum class Continuity { C0 = 0, ///< 仅位置连续 G1 = 1, ///< 切线/切平面连续 G2 = 2, ///< 曲率连续 }; /** * @brief 曲面延伸 * * 沿等参边界延伸曲面,支持 G1 切平面连续。 * 对于 G2 连续,在约束方向构造 3 排控制点以保持曲率。 * * @param surface 输入 NURBS 曲面 * @param edge_id 边界边索引(0=umin, 1=umax, 2=vmin, 3=vmax) * @param distance 延伸距离(参数空间) * @param continuity 期望的连续性级别(默认 G1) * @return 延伸后的 NURBS 曲面 * * @note G1 模式:追加 1 排控制点,沿切向延伸 * @note G2 模式:追加 2 排控制点,第 2 排由曲率约束计算 * @note 延伸仅沿切向线性/二次外推,不保证与原曲面精确 G2 连续 * * @code{.cpp} * auto ext = extend_surface(surf, 1, 0.5, Continuity::G1); * @endcode * @ingroup curves */ [[nodiscard]] NurbsSurface extend_surface(const NurbsSurface& surface, int edge_id, double distance, Continuity continuity = Continuity::G1); /** * @brief N 边孔洞填充 * * 用 N 条边界曲线构造 Coons patch 泛化的填充曲面。 * 支持三角形(N=3)、四边形(N=4)、五边形(N=5)等任意边数。 * * 算法:将边界曲线映射到单位圆参数域,使用径向基函数插值 * 构造中心点,再以双线性 Coons 方式生成内部控制点。 * * @param boundary_curves N 条边界曲线,需围成闭合环(首尾相连) * @param continuity 期望的连续性级别(默认 G2) * @return 填充 NURBS 曲面 * * @note G1 模式:单层中间环,线性插值 * @note G2 模式:双层中间环,保持曲率衰减 * @note 至少需要 3 条边界曲线 * * @code{.cpp} * auto fill = n_sided_fill({c1, c2, c3}, Continuity::G2); // 三角形孔 * @endcode * @ingroup curves */ [[nodiscard]] NurbsSurface n_sided_fill(const std::vector& boundary_curves, Continuity continuity = Continuity::G2); /** * @brief 两面间过渡曲面 * * 检测两面公共边界,沿该边构造圆弧或 S 形过渡曲面。 * 与 nurbs_operations 中的 blend_surfaces 不同,此版本自动检测公共边。 * * 算法: * 1. 检测 surf_a 和 surf_b 的共享边界 * 2. 沿共享边界两侧各偏移 radius 提取曲线 * 3. 在两条偏移曲线间构造过渡曲面(直纹面或 Coons 面) * * @param surf_a 第一个曲面 * @param surf_b 第二个曲面 * @param radius 过渡半径 * @return 过渡 NURBS 曲面 * * @note 如果两面无公共边界,返回退化的空曲面 * @note 过渡面在边界处与原曲面 G1 连续(等参方向) * * @code{.cpp} * auto blend = blend_surfaces(surf_a, surf_b, 0.3); * @endcode * @ingroup curves */ [[nodiscard]] NurbsSurface blend_surfaces(const NurbsSurface& surf_a, const NurbsSurface& surf_b, double radius); /** * @brief 检查两曲面沿共享边界的 G1 连续性 * * @param surf_a 第一个曲面 * @param surf_b 第二个曲面 * @param edge surf_a 的边界边索引(0=umin, 1=umax, 2=vmin, 3=vmax) * @param samples 沿边界的采样点数(默认 10) * @return 所有采样点均满足 G1 连续时返回 true * * @ingroup curves */ [[nodiscard]] bool is_g1_continuous(const NurbsSurface& surf_a, const NurbsSurface& surf_b, int edge, int samples = 10); } // namespace vde::curves