@faicad/faijs 0.30.9 → 0.31.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (284) hide show
  1. package/dist/api/align/index.d.ts +64 -0
  2. package/dist/api/align/index.d.ts.map +1 -0
  3. package/dist/api/align/index.js +101 -0
  4. package/dist/api/align/index.js.map +1 -0
  5. package/dist/api/api-namespace.d.ts +5 -4
  6. package/dist/api/api-namespace.d.ts.map +1 -1
  7. package/dist/api/api-namespace.js +36 -4
  8. package/dist/api/api-namespace.js.map +1 -1
  9. package/dist/api/boolean-op/index.d.ts +65 -0
  10. package/dist/api/boolean-op/index.d.ts.map +1 -0
  11. package/dist/api/boolean-op/index.js +113 -0
  12. package/dist/api/boolean-op/index.js.map +1 -0
  13. package/dist/api/boolean.d.ts.map +1 -1
  14. package/dist/api/boolean.js +15 -27
  15. package/dist/api/boolean.js.map +1 -1
  16. package/dist/api/brep-operations/healingFns.d.ts +13 -0
  17. package/dist/api/brep-operations/healingFns.d.ts.map +1 -1
  18. package/dist/api/brep-operations/healingFns.js +28 -1
  19. package/dist/api/brep-operations/healingFns.js.map +1 -1
  20. package/dist/api/brep-operations/topologyFns.d.ts +27 -6
  21. package/dist/api/brep-operations/topologyFns.d.ts.map +1 -1
  22. package/dist/api/brep-operations/topologyFns.js +46 -22
  23. package/dist/api/brep-operations/topologyFns.js.map +1 -1
  24. package/dist/api/chamfer.d.ts +5 -4
  25. package/dist/api/chamfer.d.ts.map +1 -1
  26. package/dist/api/chamfer.js +12 -11
  27. package/dist/api/chamfer.js.map +1 -1
  28. package/dist/api/curve-sketch/index.d.ts.map +1 -1
  29. package/dist/api/curve-sketch/index.js +9 -3
  30. package/dist/api/curve-sketch/index.js.map +1 -1
  31. package/dist/api/draft.d.ts.map +1 -1
  32. package/dist/api/draft.js +1 -3
  33. package/dist/api/draft.js.map +1 -1
  34. package/dist/api/engrave.d.ts.map +1 -1
  35. package/dist/api/engrave.js +3 -13
  36. package/dist/api/engrave.js.map +1 -1
  37. package/dist/api/export-3mf.d.ts +73 -0
  38. package/dist/api/export-3mf.d.ts.map +1 -0
  39. package/dist/api/export-3mf.js +121 -0
  40. package/dist/api/export-3mf.js.map +1 -0
  41. package/dist/api/export-brep.d.ts +6 -0
  42. package/dist/api/export-brep.d.ts.map +1 -1
  43. package/dist/api/export-brep.js +11 -2
  44. package/dist/api/export-brep.js.map +1 -1
  45. package/dist/api/export-step.d.ts +67 -0
  46. package/dist/api/export-step.d.ts.map +1 -0
  47. package/dist/api/export-step.js +98 -0
  48. package/dist/api/export-step.js.map +1 -0
  49. package/dist/api/export-stl.d.ts +8 -0
  50. package/dist/api/export-stl.d.ts.map +1 -1
  51. package/dist/api/export-stl.js +23 -8
  52. package/dist/api/export-stl.js.map +1 -1
  53. package/dist/api/feature-repair.d.ts +1 -1
  54. package/dist/api/feature-repair.d.ts.map +1 -1
  55. package/dist/api/feature-repair.js +1 -7
  56. package/dist/api/feature-repair.js.map +1 -1
  57. package/dist/api/fillet-variable.d.ts.map +1 -1
  58. package/dist/api/fillet-variable.js +0 -1
  59. package/dist/api/fillet-variable.js.map +1 -1
  60. package/dist/api/fillet.d.ts +3 -3
  61. package/dist/api/fillet.d.ts.map +1 -1
  62. package/dist/api/fillet.js +3 -4
  63. package/dist/api/fillet.js.map +1 -1
  64. package/dist/api/generated/operations.js +6 -6
  65. package/dist/api/generated/operations.js.map +1 -1
  66. package/dist/api/generated/script-face-manifest.d.ts +1 -1
  67. package/dist/api/generated/script-face-manifest.js +3 -3
  68. package/dist/api/generated/script-face-manifest.js.map +1 -1
  69. package/dist/api/generated/script-face.d.ts +1 -1
  70. package/dist/api/generated/script-face.js +1 -1
  71. package/dist/api/generated/script-face.js.map +1 -1
  72. package/dist/api/generated/sketching.js +1 -1
  73. package/dist/api/generated/sketching.js.map +1 -1
  74. package/dist/api/generated/topology.js +10 -10
  75. package/dist/api/generated/topology.js.map +1 -1
  76. package/dist/api/helix.d.ts +1 -1
  77. package/dist/api/helix.js +1 -1
  78. package/dist/api/helix.js.map +1 -1
  79. package/dist/api/index.d.ts +4 -1
  80. package/dist/api/index.d.ts.map +1 -1
  81. package/dist/api/index.js +16 -4
  82. package/dist/api/index.js.map +1 -1
  83. package/dist/api/internal/compat-op.d.ts +6 -6
  84. package/dist/api/internal/compat-op.d.ts.map +1 -1
  85. package/dist/api/internal/compat-op.js +7 -9
  86. package/dist/api/internal/compat-op.js.map +1 -1
  87. package/dist/api/internal/export-members.d.ts +80 -0
  88. package/dist/api/internal/export-members.d.ts.map +1 -0
  89. package/dist/api/internal/export-members.js +104 -0
  90. package/dist/api/internal/export-members.js.map +1 -0
  91. package/dist/api/internal/l3-bridge.d.ts +17 -0
  92. package/dist/api/internal/l3-bridge.d.ts.map +1 -1
  93. package/dist/api/internal/l3-bridge.js +23 -1
  94. package/dist/api/internal/l3-bridge.js.map +1 -1
  95. package/dist/api/measure-query/index.d.ts +262 -0
  96. package/dist/api/measure-query/index.d.ts.map +1 -0
  97. package/dist/api/measure-query/index.js +390 -0
  98. package/dist/api/measure-query/index.js.map +1 -0
  99. package/dist/api/pattern.d.ts.map +1 -1
  100. package/dist/api/pattern.js +0 -3
  101. package/dist/api/pattern.js.map +1 -1
  102. package/dist/api/primitives.d.ts +6 -6
  103. package/dist/api/primitives.d.ts.map +1 -1
  104. package/dist/api/primitives.js +12 -11
  105. package/dist/api/primitives.js.map +1 -1
  106. package/dist/api/profile.d.ts.map +1 -1
  107. package/dist/api/profile.js +0 -1
  108. package/dist/api/profile.js.map +1 -1
  109. package/dist/api/punch-hole.d.ts.map +1 -1
  110. package/dist/api/punch-hole.js +0 -1
  111. package/dist/api/punch-hole.js.map +1 -1
  112. package/dist/api/replicate.d.ts +5 -7
  113. package/dist/api/replicate.d.ts.map +1 -1
  114. package/dist/api/replicate.js +18 -56
  115. package/dist/api/replicate.js.map +1 -1
  116. package/dist/api/section-by-plane.d.ts.map +1 -1
  117. package/dist/api/section-by-plane.js +0 -1
  118. package/dist/api/section-by-plane.js.map +1 -1
  119. package/dist/api/shell.d.ts +1 -1
  120. package/dist/api/shell.d.ts.map +1 -1
  121. package/dist/api/shell.js +11 -2
  122. package/dist/api/shell.js.map +1 -1
  123. package/dist/api/sketch-on-face.d.ts +3 -3
  124. package/dist/api/sketch-on-face.d.ts.map +1 -1
  125. package/dist/api/sketch-on-face.js +6 -4
  126. package/dist/api/sketch-on-face.js.map +1 -1
  127. package/dist/api/sketch-on-plane.d.ts.map +1 -1
  128. package/dist/api/sketch-on-plane.js +0 -1
  129. package/dist/api/sketch-on-plane.js.map +1 -1
  130. package/dist/api/split-by-plane.d.ts.map +1 -1
  131. package/dist/api/split-by-plane.js +0 -1
  132. package/dist/api/split-by-plane.js.map +1 -1
  133. package/dist/api/split.d.ts +1 -1
  134. package/dist/api/split.js +1 -1
  135. package/dist/api/split.js.map +1 -1
  136. package/dist/api/surface/arg-spec.d.ts +3 -12
  137. package/dist/api/surface/arg-spec.d.ts.map +1 -1
  138. package/dist/api/surface/arg-spec.js +19 -26
  139. package/dist/api/surface/arg-spec.js.map +1 -1
  140. package/dist/api/sweep.d.ts +15 -3
  141. package/dist/api/sweep.d.ts.map +1 -1
  142. package/dist/api/sweep.js +5 -3
  143. package/dist/api/sweep.js.map +1 -1
  144. package/dist/api/thicken.d.ts.map +1 -1
  145. package/dist/api/thicken.js +11 -2
  146. package/dist/api/thicken.js.map +1 -1
  147. package/dist/api/transform.d.ts +3 -3
  148. package/dist/api/transform.d.ts.map +1 -1
  149. package/dist/api/transform.js +47 -17
  150. package/dist/api/transform.js.map +1 -1
  151. package/dist/boolean/index.d.ts +23 -0
  152. package/dist/boolean/index.d.ts.map +1 -0
  153. package/dist/boolean/index.js +27 -0
  154. package/dist/boolean/index.js.map +1 -0
  155. package/dist/brep/brep-chain.d.ts +1 -19
  156. package/dist/brep/brep-chain.d.ts.map +1 -1
  157. package/dist/brep/brep-chain.js +0 -1
  158. package/dist/brep/brep-chain.js.map +1 -1
  159. package/dist/brep/brep-ops.d.ts +4 -1
  160. package/dist/brep/brep-ops.d.ts.map +1 -1
  161. package/dist/brep/brep-ops.js +9 -5
  162. package/dist/brep/brep-ops.js.map +1 -1
  163. package/dist/brep/engine/adapters/brep-mock.d.ts.map +1 -1
  164. package/dist/brep/engine/adapters/brep-mock.js +0 -3
  165. package/dist/brep/engine/adapters/brep-mock.js.map +1 -1
  166. package/dist/brep/engine/adapters/brepkit.d.ts +4 -3
  167. package/dist/brep/engine/adapters/brepkit.d.ts.map +1 -1
  168. package/dist/brep/engine/adapters/brepkit.js +4 -98
  169. package/dist/brep/engine/adapters/brepkit.js.map +1 -1
  170. package/dist/brep/engine/adapters/occt.d.ts.map +1 -1
  171. package/dist/brep/engine/adapters/occt.js +0 -144
  172. package/dist/brep/engine/adapters/occt.js.map +1 -1
  173. package/dist/brep/engine/native-history.d.ts +27 -0
  174. package/dist/brep/engine/native-history.d.ts.map +1 -0
  175. package/dist/brep/engine/native-history.js +54 -0
  176. package/dist/brep/engine/native-history.js.map +1 -0
  177. package/dist/brep/engine/registry.d.ts +2 -4
  178. package/dist/brep/engine/registry.d.ts.map +1 -1
  179. package/dist/brep/engine/registry.js +1 -1
  180. package/dist/brep/engine/registry.js.map +1 -1
  181. package/dist/brep/engine/types.d.ts +35 -77
  182. package/dist/brep/engine/types.d.ts.map +1 -1
  183. package/dist/brep/engine/types.js.map +1 -1
  184. package/dist/brep/export/export-model.d.ts +21 -0
  185. package/dist/brep/export/export-model.d.ts.map +1 -1
  186. package/dist/brep/export/export-model.js +171 -73
  187. package/dist/brep/export/export-model.js.map +1 -1
  188. package/dist/brep/export/step.d.ts +17 -1
  189. package/dist/brep/export/step.d.ts.map +1 -1
  190. package/dist/brep/export/step.js +133 -0
  191. package/dist/brep/export/step.js.map +1 -1
  192. package/dist/brep/export/stl.d.ts +22 -1
  193. package/dist/brep/export/stl.d.ts.map +1 -1
  194. package/dist/brep/export/stl.js +58 -10
  195. package/dist/brep/export/stl.js.map +1 -1
  196. package/dist/brep/export/transform12.d.ts +47 -0
  197. package/dist/brep/export/transform12.d.ts.map +1 -0
  198. package/dist/brep/export/transform12.js +87 -0
  199. package/dist/brep/export/transform12.js.map +1 -0
  200. package/dist/brep/face-evolution.d.ts +53 -0
  201. package/dist/brep/face-evolution.d.ts.map +1 -1
  202. package/dist/brep/face-evolution.js +65 -0
  203. package/dist/brep/face-evolution.js.map +1 -1
  204. package/dist/browser-host/index.d.ts +4 -1
  205. package/dist/browser-host/index.d.ts.map +1 -1
  206. package/dist/browser-host/index.js +7 -1
  207. package/dist/browser-host/index.js.map +1 -1
  208. package/dist/browser.d.ts +4 -8
  209. package/dist/browser.d.ts.map +1 -1
  210. package/dist/browser.js +4 -26
  211. package/dist/browser.js.map +1 -1
  212. package/dist/cad-runtime/backend-dispatch.d.ts +13 -58
  213. package/dist/cad-runtime/backend-dispatch.d.ts.map +1 -1
  214. package/dist/cad-runtime/backend-dispatch.js +22 -80
  215. package/dist/cad-runtime/backend-dispatch.js.map +1 -1
  216. package/dist/cad-runtime/content-key.d.ts +3 -3
  217. package/dist/cad-runtime/content-key.js +3 -3
  218. package/dist/cad-runtime/content-key.js.map +1 -1
  219. package/dist/cad-runtime/ports.d.ts +28 -0
  220. package/dist/cad-runtime/ports.d.ts.map +1 -1
  221. package/dist/cad-runtime/ports.js.map +1 -1
  222. package/dist/cad-runtime/runtime.d.ts +33 -12
  223. package/dist/cad-runtime/runtime.d.ts.map +1 -1
  224. package/dist/cad-runtime/runtime.js +44 -48
  225. package/dist/cad-runtime/runtime.js.map +1 -1
  226. package/dist/define-op.d.ts +6 -11
  227. package/dist/define-op.d.ts.map +1 -1
  228. package/dist/define-op.js +3 -20
  229. package/dist/define-op.js.map +1 -1
  230. package/dist/env-agnostic.d.ts +2 -2
  231. package/dist/env-agnostic.d.ts.map +1 -1
  232. package/dist/env-agnostic.js +1 -1
  233. package/dist/env-agnostic.js.map +1 -1
  234. package/dist/index.d.ts +13 -64
  235. package/dist/index.d.ts.map +1 -1
  236. package/dist/index.js +17 -75
  237. package/dist/index.js.map +1 -1
  238. package/dist/lang/symbol-table.generated.d.ts +17 -0
  239. package/dist/lang/symbol-table.generated.d.ts.map +1 -1
  240. package/dist/lang/symbol-table.generated.js +17 -0
  241. package/dist/lang/symbol-table.generated.js.map +1 -1
  242. package/dist/mesh/index.d.ts +18 -23
  243. package/dist/mesh/index.d.ts.map +1 -1
  244. package/dist/mesh/index.js +18 -20
  245. package/dist/mesh/index.js.map +1 -1
  246. package/dist/mesh/io.d.ts +42 -14
  247. package/dist/mesh/io.d.ts.map +1 -1
  248. package/dist/mesh/io.js +77 -13
  249. package/dist/mesh/io.js.map +1 -1
  250. package/dist/mesh/threemf-loader.d.ts +38 -4
  251. package/dist/mesh/threemf-loader.d.ts.map +1 -1
  252. package/dist/mesh/threemf-loader.js +115 -34
  253. package/dist/mesh/threemf-loader.js.map +1 -1
  254. package/dist/mesh/types.d.ts +30 -0
  255. package/dist/mesh/types.d.ts.map +1 -1
  256. package/dist/mesh/types.js.map +1 -1
  257. package/dist/node-host/execute-script.d.ts +2 -1
  258. package/dist/node-host/execute-script.d.ts.map +1 -1
  259. package/dist/node-host/execute-script.js +5 -4
  260. package/dist/node-host/execute-script.js.map +1 -1
  261. package/dist/node-host/index.d.ts +1 -0
  262. package/dist/node-host/index.d.ts.map +1 -1
  263. package/dist/node-host/index.js +4 -0
  264. package/dist/node-host/index.js.map +1 -1
  265. package/dist/primitives/index.d.ts +19 -0
  266. package/dist/primitives/index.d.ts.map +1 -0
  267. package/dist/primitives/index.js +21 -0
  268. package/dist/primitives/index.js.map +1 -0
  269. package/dist/runtime-state.d.ts +63 -29
  270. package/dist/runtime-state.d.ts.map +1 -1
  271. package/dist/runtime-state.js +57 -0
  272. package/dist/runtime-state.js.map +1 -1
  273. package/dist/sdf/index.d.ts +12 -0
  274. package/dist/sdf/index.d.ts.map +1 -0
  275. package/dist/sdf/index.js +13 -0
  276. package/dist/sdf/index.js.map +1 -0
  277. package/dist/sdk.d.ts +0 -1
  278. package/dist/sdk.d.ts.map +1 -1
  279. package/dist/sdk.js.map +1 -1
  280. package/dist/weapp.d.ts +2 -2
  281. package/dist/weapp.d.ts.map +1 -1
  282. package/dist/weapp.js +1 -1
  283. package/dist/weapp.js.map +1 -1
  284. package/package.json +276 -35
@@ -11,30 +11,27 @@
11
11
  import * as meshBoolean from '../mesh/boolean.js';
12
12
  import { solidToShape } from '../brep/brep-ops.js';
13
13
  import { booleanWithRoleTable, } from '../brep/face-evolution.js';
14
- import { getCurrentStmt, getBackends, keepHidden, nameOf } from '../runtime-state.js';
14
+ import { getCurrentStmt, keepHidden, nameOf } from '../runtime-state.js';
15
15
  import { getBrepApi } from '../brep/handle-bridge.js';
16
16
  import { fromBrep, brepOf, hasMeshSolid, inputRoleTable } from '../shape.js';
17
17
  import { reconcileBrepInputs } from './reconcile.js';
18
18
  import { OpError } from './internal/result-unwrap.js';
19
19
  import { meshKernelFailure, meshSolidEntry, meshSolidProduct } from './internal/mesh-solid-op.js';
20
20
  import { defineOp } from '../sdk.js';
21
- import { engineCapabilitySet } from '../cad-runtime/backend-dispatch.js';
21
+ import { hasNativeHistory } from '../brep/engine/native-history.js';
22
22
  // ── 共享内部实现 ──
23
23
  /**
24
24
  * BREP 路径:fuse/cut/intersect。
25
25
  *
26
- * 静态双轨(无运行时 try-catch 回退——按引擎**声明**的能力集在执行前定轨):
27
- * - 引擎声明了对应 `*WithHistory`(occt 三员全有)→ `booleanWithRoleTable`:
26
+ * 静态双轨(无运行时 try-catch 回退——按引擎事实在执行前定轨):
27
+ * - 引擎原生有对应 `*WithHistory`(occt 三员全有)→ `booleanWithRoleTable`:
28
28
  * 一次内核调用同时产出结果 + 面演化(faceEvolution)+ roleTable 合流(§3.4)。
29
- * - 引擎只声明了裸布尔方法(brepkit:声明了 `intersect` 但**没有** `intersectWithHistory`)
29
+ * - 引擎只有裸布尔方法(brepkit:有 `intersect` 但**没有** `intersectWithHistory`)
30
30
  * → 走 L1 裸 `kernel[op](a,b)`:几何正确,但**不产生面演化、不传播 roleTable**。
31
31
  * 这是如实降级——绝不用「恒等映射」伪造一张把输入面 hash 指到结果面 hash 的演化表
32
32
  * (结果实体的面 hash 与输入根本不同,恒等映射是假身份)。
33
33
  *
34
- * `intersect` 因此不再声明 `capabilities: ['intersectWithHistory']`(中立 op):
35
- * brepkit 上由本函数静态落到裸 `intersect`;occt 上仍走 `intersectWithHistory`。
36
- * fuse/cut 保留各自 `*WithHistory` 能力声明——dispatchPath 的 gate 保证它们到达本函数时
37
- * 引擎必已声明对应历史方法,故下方 `useHistory` 对 fuse/cut 恒为 true。
34
+ * 定轨只读引擎事实 `hasNativeHistory`(`brep/engine/native-history.ts`),op 侧不声明能力。
38
35
  */
39
36
  function booleanBrep(inputs, operation) {
40
37
  const kernel = getBrepApi();
@@ -77,11 +74,11 @@ function booleanBrep(inputs, operation) {
77
74
  if (operation === 'union' && boolIdx.length === 0) {
78
75
  throw new OpError(`boolean/${operation}`, 'E_BREP_UNSUPPORTED', `[api/boolean] ${operation}: no solid input — wire/face/shell geometry cannot fuse (types: ${inputTypes.join(', ')})`);
79
76
  }
80
- // 静态定轨:当前引擎是否声明了本 op 的面演化核函数(读的是同一声明源 dispatchPath 用的
81
- // 能力集,不是运行时探测)。fuse/cut 因 gate 保证此处恒 true;intersect 在 occt true、
82
- // brepkit/mock false(后者走 L1 裸 `kernel[op]`,该方法是 BrepEngineApi 必需成员,必存在)。
77
+ // 静态定轨:当前引擎是否原生实现本 op 的面演化核函数(引擎事实,非运行时探测)。
78
+ // fuse/cut 的 brep 实现调 `*WithHistory`,在只提供裸布尔的引擎上走不了历史轨——
79
+ // 该分叉由 hasNativeHistory 回答,op 侧不声明任何能力。
83
80
  const historyCap = op === 'fuse' ? 'fuseWithHistory' : op === 'cut' ? 'cutWithHistory' : 'intersectWithHistory';
84
- const useHistory = engineCapabilitySet(getBackends().config.brepCapabilities).has(historyCap);
81
+ const useHistory = hasNativeHistory(historyCap);
85
82
  // 首个 solid 输入作为 target 起点(F 组:可能不是 inputs[0] —— wire/face
86
83
  // 资产常排在前面作为 profile/binder)。
87
84
  resultSolid = inputSolids[boolIdx[0]];
@@ -232,7 +229,8 @@ async function booleanMesh(inputs, operation) {
232
229
  result = await meshBoolean.intersect(result, inputs[i]);
233
230
  return result;
234
231
  }
235
- // ── 三个薄导出(多输入 variadic,defineOp 声明双路径 + 逐核函数 face-evolution 能力) ──
232
+ // ── 三个薄导出(多输入 variadic,defineOp 声明双路径;面演化进路由引擎事实 ──
233
+ // ── `hasNativeHistory` 定,op 不声明、不查表——见下方各 op 的分叉注释) ──
236
234
  // 函数体 keep 声明(keep-syntax 设计 §2.5):union/subtract/intersect 保留其
237
235
  // 输入且隐藏(R5:3d_editor 现状)——keepHidden 使源变量保持终端但 canvas
238
236
  // 不渲染,只有布尔结果正常显示。混合/断链时刻:BREP 侧输入先归约为合法
@@ -261,10 +259,6 @@ export const union = defineOp({
261
259
  keepHidden(...shapes);
262
260
  return booleanBrep(shapes, 'union');
263
261
  },
264
- // 逐核函数声明(Phase 0.2):union 需要内核的 fuseWithHistory。
265
- // 不再声明族级 'evolution'——族级名会让 brepkit(无 intersectWithHistory)等
266
- // 部分实现的内核静默通过静态判定,再死在运行时(红线违规)。
267
- capabilities: ['fuseWithHistory'],
268
262
  schema: { shapes: 'Shape*' },
269
263
  naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } },
270
264
  });
@@ -294,7 +288,6 @@ export const cut = defineOp({
294
288
  keepHidden(base, tool);
295
289
  return booleanBrep([base, tool], 'subtract');
296
290
  },
297
- capabilities: ['cutWithHistory'],
298
291
  naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } },
299
292
  });
300
293
  /**
@@ -321,8 +314,6 @@ export const subtract = defineOp({
321
314
  keepHidden(...shapes);
322
315
  return booleanBrep(shapes, 'subtract');
323
316
  },
324
- // 逐核函数声明(Phase 0.2):subtract 需要内核的 cutWithHistory。
325
- capabilities: ['cutWithHistory'],
326
317
  naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } },
327
318
  });
328
319
  /**
@@ -349,12 +340,9 @@ export const intersect = defineOp({
349
340
  keepHidden(...shapes);
350
341
  return booleanBrep(shapes, 'intersect');
351
342
  },
352
- // 不声明 `capabilities: ['intersectWithHistory']`(中立 op):
353
- // brepkit 声明了裸 `intersect` 但没有 `intersectWithHistory`——若硬声明历史能力,
354
- // brepkit brep 模式会在执行前静态报 `lacks capability 'intersectWithHistory'`。
355
- // 现由 booleanBrep 按引擎声明的能力集静态分派:occt(声明 intersectWithHistory)
356
- // 走历史路径保留面演化/naming;brepkit(只声明裸 intersect)走 L1 裸 `kernel.intersect`,
357
- // 几何正确但无面演化(如实降级,不伪造恒等映射)。
343
+ // intersect 不声明任何能力:brepkit 只有裸 `intersect`(无 `intersectWithHistory`),
344
+ // 由 booleanBrep 按引擎事实静态分派——occt 走历史路径保留面演化/naming;
345
+ // brepkit 走 L1 裸 `kernel.intersect`,几何正确但无面演化(如实降级,不伪造恒等映射)。
358
346
  naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } },
359
347
  });
360
348
  //# sourceMappingURL=boolean.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"boolean.js","sourceRoot":"","sources":["../../src/api/boolean.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * api boolean — 布尔库函数(union/subtract/intersect,多输入)\n *\n *\n * dispatchPath 静态判定 brep/mesh,BREP 路径用 *WithHistory 收集面演化。\n *\n * 阶段 1:拆为三个薄函数 union/subtract/intersect + 兼容 boolean 导出(过渡)。\n * 阶段 3 将删除 boolean 兼容导出。\n */\n\nimport type { Shape } from '../mesh/types'\n// B3 correction (2026-10-06): no library-face cad aggregate — import the impl from its own module.\nimport * as meshBoolean from '../mesh/boolean'\nimport { solidToShape } from '../brep/brep-ops'\nimport {\n booleanWithRoleTable,\n} from '../brep/face-evolution'\nimport { getCurrentStmt, getBackends, keepHidden, nameOf } from '../runtime-state'\nimport { getBrepApi } from '../brep/handle-bridge'\nimport { fromBrep, brepOf, hasMeshSolid, inputRoleTable } from '../shape'\nimport { reconcileBrepInputs } from './reconcile'\nimport { OpError } from './internal/result-unwrap'\nimport { meshKernelFailure, meshSolidEntry, meshSolidProduct } from './internal/mesh-solid-op'\nimport { defineOp } from '../sdk'\nimport { engineCapabilitySet } from '../cad-runtime/backend-dispatch'\nimport type { Provenance } from '../topology/naming/lineage'\nimport type { BrepHandle } from '../brep/engine/types'\n\ntype BooleanOperation = 'union' | 'subtract' | 'intersect'\n\n// ── 共享内部实现 ──\n\n/**\n * BREP 路径:fuse/cut/intersect。\n *\n * 静态双轨(无运行时 try-catch 回退——按引擎**声明**的能力集在执行前定轨):\n * - 引擎声明了对应 `*WithHistory`(occt 三员全有)→ `booleanWithRoleTable`:\n * 一次内核调用同时产出结果 + 面演化(faceEvolution)+ roleTable 合流(§3.4)。\n * - 引擎只声明了裸布尔方法(brepkit:声明了 `intersect` 但**没有** `intersectWithHistory`)\n * → 走 L1 裸 `kernel[op](a,b)`:几何正确,但**不产生面演化、不传播 roleTable**。\n * 这是如实降级——绝不用「恒等映射」伪造一张把输入面 hash 指到结果面 hash 的演化表\n * (结果实体的面 hash 与输入根本不同,恒等映射是假身份)。\n *\n * `intersect` 因此不再声明 `capabilities: ['intersectWithHistory']`(中立 op):\n * brepkit 上由本函数静态落到裸 `intersect`;occt 上仍走 `intersectWithHistory`。\n * fuse/cut 保留各自 `*WithHistory` 能力声明——dispatchPath 的 gate 保证它们到达本函数时\n * 引擎必已声明对应历史方法,故下方 `useHistory` 对 fuse/cut 恒为 true。\n */\nfunction booleanBrep(inputs: Shape[], operation: BooleanOperation): Shape {\n const kernel = getBrepApi()\n\n const inputSolids = inputs.map((s) => brepOf(s) as BrepHandle | undefined)\n if (inputSolids.some((s) => !s)) {\n // V-C8 (C6): a non-solid import (wire/face/shell via cad.import_brep) has\n // no OCCT handle yet — booleans must fail HERE with an explicit, op-named\n // error, not with OCCT's raw \"boolean operation failed\" (or silently).\n const offenders = inputs\n .map((s, i) => (inputSolids[i] ? undefined : nameOf(s) ?? `input[${i}]`))\n .filter((x): x is string => x !== undefined)\n throw new OpError(\n `boolean/${operation}`,\n 'E_BREP_UNSUPPORTED',\n `[api/boolean] ${operation}: input is not on the BREP chain (no OCCT handle) — ` +\n `non-solid geometry (wire/face/shell) cannot take part in a boolean. offenders: ${offenders.join(', ')}`,\n )\n }\n\n let resultSolid: BrepHandle\n let lastEvolution: Map<number, number[]> | undefined\n let roleTable: ReadonlyMap<unknown, unknown> | undefined\n\n // 链式布尔:每步 target(累积结果)与下一个 tool 合流\n const op: 'fuse' | 'cut' | 'intersect' =\n operation === 'union' ? 'fuse' : operation === 'subtract' ? 'cut' : 'intersect'\n\n // F 组(2026-10-03,FAULHABER/Beam-coupling 语料):import_brep 资产可能是\n // wire/face(ShapeBinder 冻结几何)——它们带 OCCT handle、能通过上面的\n // 「无 handle」守卫,但 OCCT 的 BOP 只接受 solid:fuse(wire, solid) 直接\n // \"operation failed\"(内核直测实证,PartShape5/PartShape6/PartShape93 均\n // wire/face、vol=0)。C3c-1 已实证 0 体积线框成员对 compound invariants\n // 零影响 ⇒ union 的语义是 solid 合流,非 solid 输入如实跳过(keepHidden\n // 语义不变);全非 solid 才抛错。cut/intersect 语义不变(工具/交域必须 solid)。\n const NON_SOLID = new Set(['wire', 'face', 'shell', 'vertex', 'edge'])\n const inputTypes = inputSolids.map((h) => {\n try { return h ? (kernel.shapeType(h) as string) : 'solid' } catch { return 'solid' }\n })\n // compound/compsolid 可能含 solid,是合法 fuse 输入——只跳过确定的非 solid 类型。\n const boolIdx = operation === 'union'\n ? inputTypes.map((t, i) => (NON_SOLID.has(t) ? -1 : i)).filter((i) => i >= 0)\n : inputs.map((_, i) => i)\n if (operation === 'union' && boolIdx.length === 0) {\n throw new OpError(\n `boolean/${operation}`,\n 'E_BREP_UNSUPPORTED',\n `[api/boolean] ${operation}: no solid input — wire/face/shell geometry cannot fuse (types: ${inputTypes.join(', ')})`,\n )\n }\n\n // 静态定轨:当前引擎是否声明了本 op 的面演化核函数(读的是同一声明源 dispatchPath 用的\n // 能力集,不是运行时探测)。fuse/cut 因 gate 保证此处恒 true;intersect 在 occt true、\n // brepkit/mock false(后者走 L1 裸 `kernel[op]`,该方法是 BrepEngineApi 必需成员,必存在)。\n const historyCap = op === 'fuse' ? 'fuseWithHistory' : op === 'cut' ? 'cutWithHistory' : 'intersectWithHistory'\n const useHistory = engineCapabilitySet(getBackends().config.brepCapabilities).has(historyCap)\n\n // 首个 solid 输入作为 target 起点(F 组:可能不是 inputs[0] —— wire/face\n // 资产常排在前面作为 profile/binder)。\n resultSolid = inputSolids[boolIdx[0]!]!\n roleTable = useHistory\n ? (inputRoleTable(inputs[boolIdx[0]!]) as ReadonlyMap<unknown, unknown> | undefined)\n : undefined\n\n for (let bi = 1; bi < boolIdx.length; bi++) {\n const i = boolIdx[bi]!\n const prev = resultSolid\n const tool = inputSolids[i]!\n\n if (useHistory) {\n // §3.4:一次内核调用,A/B 拆流各自传播后合表(缝面 origin=本次语句 StmtId)\n // V-C8:内核裸错误在此包一层——带上 op 名、两个输入的变量名与 cause。\n const prevTable = roleTable\n const toolTable = inputRoleTable(inputs[i]) as ReadonlyMap<unknown, unknown> | undefined\n // Phase 1.6:新 origin = 本次语句的 StmtId。\n const outStmt = String(getCurrentStmt()?.id ?? '')\n let r: ReturnType<typeof booleanWithRoleTable>\n try {\n r = booleanWithRoleTable(\n kernel,\n op,\n prev,\n tool,\n prevTable ?? new Map(),\n toolTable ?? new Map(),\n outStmt,\n )\n } catch (cause) {\n // GOTCHA: OCCT 的 *WithHistory 在两输入共享子结构/历史(如布尔产物的布尔)\n // 时可能 \"operation failed\",而同一几何的裸布尔可以成功。降级重试一次裸\n // kernel[op]:几何结果正确,代价是丢本次面演化/roleTable(如实降级,同下方\n // 裸路径语义)。裸布尔也失败时,再试 unifySameDomain(两输入) 后重算——\n // 真实语料(disk-drive)中 tool 是布尔产物且与 target 共享子域,裸 cut 仍失败、\n // unify 后成功。全部失败才真正抛错。\n try {\n resultSolid = kernel[op](prev, tool)\n lastEvolution = undefined\n roleTable = undefined\n if (i > 1) kernel.release(prev)\n continue\n } catch {\n try {\n const uPrev = kernel.unifySameDomain(prev)\n const uTool = kernel.unifySameDomain(tool)\n resultSolid = kernel[op](uPrev, uTool)\n kernel.release(uPrev)\n kernel.release(uTool)\n lastEvolution = undefined\n roleTable = undefined\n if (i > 1) kernel.release(prev)\n continue\n } catch {\n const msg = cause instanceof Error ? cause.message : String(cause)\n throw new OpError(\n `boolean/${operation}`,\n 'E_OP_FAILED',\n `[api/boolean] ${operation}: kernel ${op} failed for inputs ` +\n `${nameOf(inputs[0]!) ?? 'input[0]'} × ${nameOf(inputs[i]!) ?? `input[${i}]`} — ${msg}`,\n { cause },\n )\n }\n }\n }\n resultSolid = r.result\n lastEvolution = r.faceEvolution\n roleTable = r.roleTable\n } else {\n // 裸布尔降级路径:几何正确,但无面演化、无 roleTable 传播(如实降级,不伪造映射)。\n try {\n resultSolid = kernel[op](prev, tool)\n } catch (cause) {\n const msg = cause instanceof Error ? cause.message : String(cause)\n throw new OpError(\n `boolean/${operation}`,\n 'E_OP_FAILED',\n `[api/boolean] ${operation}: kernel ${op} failed for inputs ` +\n `${nameOf(inputs[0]!) ?? 'input[0]'} × ${nameOf(inputs[i]!) ?? `input[${i}]`} — ${msg}`,\n { cause },\n )\n }\n lastEvolution = undefined\n roleTable = undefined\n }\n if (i > 1) kernel.release(prev)\n }\n\n return fromBrep(\n solidToShape(kernel, resultSolid),\n lastEvolution ? { solid: resultSolid, faceEvolution: lastEvolution, roleTable } : { solid: resultSolid, roleTable },\n )\n}\n\n/**\n * 网格实体路径:brepkit 网格内核的布尔(方案 2026-10-01 §3.5 三明治)。\n *\n * 输入**全部**是网格实体——这一点由 `dispatchPath` 的链门禁保证\n * (`E_MESH_SOLID_MIXED`:网格实体不得与链外几何同处一次调用),此处只复核不补救。\n *\n * 无面演化、无 roleTable:近似拓扑没有 hash 演化,造一张恒等映射就是假身份\n * (与 brepkit 裸布尔降级同一条纪律)。\n *\n * 中间结果是本实现自己造的句柄(不是任何输入),故 i>1 步及时释放;**输入句柄一概\n * 不释放**——生命周期归链(与 BREP 路径 booleanBrep 的 `if (i > 1) kernel.release(prev)`\n * 同构)。\n *\n * @param inputs - the mesh-solid inputs (≥1).\n * @param operation - union / subtract / intersect.\n * @returns the boolean result as a new mesh part.\n */\nfunction booleanMeshSolid(inputs: Shape[], operation: BooleanOperation): Shape {\n const opLabel = `boolean/${operation}`\n const entries = inputs.map((s) => meshSolidEntry(s, opLabel))\n const first = entries[0]!\n const kernel = first.kernel\n const op: 'fuse' | 'cut' | 'intersect' =\n operation === 'union' ? 'fuse' : operation === 'subtract' ? 'cut' : 'intersect'\n\n let result = first.solid\n for (let i = 1; i < entries.length; i++) {\n const prev = result\n try {\n result = kernel[op](prev, entries[i]!.solid)\n } catch (cause) {\n throw meshKernelFailure(\n opLabel,\n 'E_OP_FAILED',\n `${op}(${nameOf(inputs[0]!) ?? 'input[0]'} × ${nameOf(inputs[i]!) ?? `input[${i}]`})`,\n cause,\n )\n }\n // i>1:prev 是本实现上一步造出的中间实体,释放它(i=1 时 prev 是**输入**,不碰)。\n if (i > 1) first.backend.release(prev)\n }\n return meshSolidProduct(first, result)\n}\n\n/**\n * 网格路径分流(方案 2026-10-01 §3.4 规则 4):输入含网格实体 → brepkit 网格内核;\n * 否则保持历史上限(内置 `mesh/` 的 manifold CSG)。两条路**互不冒充**——\n * manifold 不认识网格实体(静态门禁),网格内核也不接受裸网格(无句柄)。\n *\n * @param inputs - the geometry inputs.\n * @param operation - union / subtract / intersect.\n * @returns the boolean product (mesh solid or manifold mesh shape).\n */\nfunction booleanMeshPath(inputs: Shape[], operation: BooleanOperation): Shape | Promise<Shape> {\n if (inputs.some(hasMeshSolid)) return booleanMeshSolid(inputs, operation)\n return booleanMesh(inputs, operation)\n}\n\n/** mesh 路径:manifold-3d mesh-CSG。 */\nasync function booleanMesh(inputs: Shape[], operation: BooleanOperation): Promise<Shape> {\n if (inputs.length < 2) {\n if (inputs.length === 1) return inputs[0]\n throw new Error('[api/boolean] boolean needs at least 1 input')\n }\n if (operation === 'union') return meshBoolean.union(inputs[0], inputs[1], ...inputs.slice(2))\n if (operation === 'subtract') {\n let result = await meshBoolean.subtract(inputs[0], inputs[1])\n for (let i = 2; i < inputs.length; i++) result = await meshBoolean.subtract(result, inputs[i])\n return result\n }\n let result = await meshBoolean.intersect(inputs[0], inputs[1])\n for (let i = 2; i < inputs.length; i++) result = await meshBoolean.intersect(result, inputs[i])\n return result\n}\n\n// ── 三个薄导出(多输入 variadic,defineOp 声明双路径 + 逐核函数 face-evolution 能力) ──\n// 函数体 keep 声明(keep-syntax 设计 §2.5):union/subtract/intersect 保留其\n// 输入且隐藏(R5:3d_editor 现状)——keepHidden 使源变量保持终端但 canvas\n// 不渲染,只有布尔结果正常显示。混合/断链时刻:BREP 侧输入先归约为合法\n// 2-manifold 网格(reconcileBrepInputs),mesh 侧原样透传。\n\n/**\n * 布尔并集:合并所有输入几何(≥2 个输入)。\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name union\n * @param shapes - 参与运算的几何(变量引用,≥2 个)。type:Shape[] required:true\n * @returns Shape 所有输入的并集。函数名即操作,输入全是变量引用,可用 `cad.union(a, b, c)` 多输入。\n * @example\n * const a = await cad.union(part0, part1)\n */\nexport const union = defineOp({\n meshEngines: ['brepkit'],\n mesh: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanMeshPath(reconcileBrepInputs(shapes), 'union')\n },\n brep: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanBrep(shapes, 'union')\n },\n // 逐核函数声明(Phase 0.2):union 需要内核的 fuseWithHistory。\n // 不再声明族级 'evolution'——族级名会让 brepkit(无 intersectWithHistory)等\n // 部分实现的内核静默通过静态判定,再死在运行时(红线违规)。\n capabilities: ['fuseWithHistory'],\n schema: { shapes: 'Shape*' },\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n\n/**\n * Boolean cut (subtract): remove `tool` from `base`. Same semantics as\n * {@link subtract} but with the brepjs-compatible `(base, tool, options?)` signature.\n * Overrides the generated projection (compatOp) to do roleTable propagation\n * (Phase 3: L2 requires wall:<i> to survive cut).\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name cut\n * @param base - the target shape. type:Shape required:true\n * @param tool - the shape to subtract. type:Shape required:true\n * @returns Shape base minus tool.\n * @example\n * const b = await cad.cut(part0, part1)\n */\nexport const cut = defineOp({\n meshEngines: ['brepkit'],\n mesh: (base: Shape, tool: Shape) => {\n keepHidden(base, tool)\n return booleanMeshPath(reconcileBrepInputs([base, tool]), 'subtract')\n },\n brep: (base: Shape, tool: Shape) => {\n keepHidden(base, tool)\n return booleanBrep([base, tool], 'subtract')\n },\n capabilities: ['cutWithHistory'],\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n\n/**\n * 布尔差集:第一个为主体,减去其余输入。\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name subtract\n * @param shapes - 参与运算的几何(变量引用,第一个为主体)。type:Shape[] required:true\n * @returns Shape part0 减 part1 的差集(第一个为主体)。\n * @example\n * const b = await cad.subtract(part0, part1)\n */\nexport const subtract = defineOp({\n meshEngines: ['brepkit'],\n mesh: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanMeshPath(reconcileBrepInputs(shapes), 'subtract')\n },\n brep: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanBrep(shapes, 'subtract')\n },\n // 逐核函数声明(Phase 0.2):subtract 需要内核的 cutWithHistory。\n capabilities: ['cutWithHistory'],\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n\n/**\n * 布尔交集:所有输入的重叠部分。\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name intersect\n * @param shapes - 参与运算的几何(变量引用)。type:Shape[] required:true\n * @returns Shape 所有输入的交集。\n * @example\n * const c = await cad.intersect(part0, part1)\n */\nexport const intersect = defineOp({\n meshEngines: ['brepkit'],\n mesh: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanMeshPath(reconcileBrepInputs(shapes), 'intersect')\n },\n brep: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanBrep(shapes, 'intersect')\n },\n // 不声明 `capabilities: ['intersectWithHistory']`(中立 op):\n // brepkit 声明了裸 `intersect` 但没有 `intersectWithHistory`——若硬声明历史能力,\n // brepkit brep 模式会在执行前静态报 `lacks capability 'intersectWithHistory'`。\n // 现由 booleanBrep 按引擎声明的能力集静态分派:occt(声明 intersectWithHistory)\n // 走历史路径保留面演化/naming;brepkit(只声明裸 intersect)走 L1 裸 `kernel.intersect`,\n // 几何正确但无面演化(如实降级,不伪造恒等映射)。\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n"]}
1
+ {"version":3,"file":"boolean.js","sourceRoot":"","sources":["../../src/api/boolean.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * api boolean — 布尔库函数(union/subtract/intersect,多输入)\n *\n *\n * dispatchPath 静态判定 brep/mesh,BREP 路径用 *WithHistory 收集面演化。\n *\n * 阶段 1:拆为三个薄函数 union/subtract/intersect + 兼容 boolean 导出(过渡)。\n * 阶段 3 将删除 boolean 兼容导出。\n */\n\nimport type { Shape } from '../mesh/types'\n// B3 correction (2026-10-06): no library-face cad aggregate — import the impl from its own module.\nimport * as meshBoolean from '../mesh/boolean'\nimport { solidToShape } from '../brep/brep-ops'\nimport {\n booleanWithRoleTable,\n} from '../brep/face-evolution'\nimport { getCurrentStmt, keepHidden, nameOf } from '../runtime-state'\nimport { getBrepApi } from '../brep/handle-bridge'\nimport { fromBrep, brepOf, hasMeshSolid, inputRoleTable } from '../shape'\nimport { reconcileBrepInputs } from './reconcile'\nimport { OpError } from './internal/result-unwrap'\nimport { meshKernelFailure, meshSolidEntry, meshSolidProduct } from './internal/mesh-solid-op'\nimport { defineOp } from '../sdk'\nimport { hasNativeHistory } from '../brep/engine/native-history'\nimport type { Provenance } from '../topology/naming/lineage'\nimport type { BrepEvolutionKind, BrepHandle } from '../brep/engine/types'\n\ntype BooleanOperation = 'union' | 'subtract' | 'intersect'\n\n// ── 共享内部实现 ──\n\n/**\n * BREP 路径:fuse/cut/intersect。\n *\n * 静态双轨(无运行时 try-catch 回退——按引擎事实在执行前定轨):\n * - 引擎原生有对应 `*WithHistory`(occt 三员全有)→ `booleanWithRoleTable`:\n * 一次内核调用同时产出结果 + 面演化(faceEvolution)+ roleTable 合流(§3.4)。\n * - 引擎只有裸布尔方法(brepkit:有 `intersect` 但**没有** `intersectWithHistory`)\n * → 走 L1 裸 `kernel[op](a,b)`:几何正确,但**不产生面演化、不传播 roleTable**。\n * 这是如实降级——绝不用「恒等映射」伪造一张把输入面 hash 指到结果面 hash 的演化表\n * (结果实体的面 hash 与输入根本不同,恒等映射是假身份)。\n *\n * 定轨只读引擎事实 `hasNativeHistory`(`brep/engine/native-history.ts`),op 侧不声明能力。\n */\nfunction booleanBrep(inputs: Shape[], operation: BooleanOperation): Shape {\n const kernel = getBrepApi()\n\n const inputSolids = inputs.map((s) => brepOf(s) as BrepHandle | undefined)\n if (inputSolids.some((s) => !s)) {\n // V-C8 (C6): a non-solid import (wire/face/shell via cad.import_brep) has\n // no OCCT handle yet — booleans must fail HERE with an explicit, op-named\n // error, not with OCCT's raw \"boolean operation failed\" (or silently).\n const offenders = inputs\n .map((s, i) => (inputSolids[i] ? undefined : nameOf(s) ?? `input[${i}]`))\n .filter((x): x is string => x !== undefined)\n throw new OpError(\n `boolean/${operation}`,\n 'E_BREP_UNSUPPORTED',\n `[api/boolean] ${operation}: input is not on the BREP chain (no OCCT handle) — ` +\n `non-solid geometry (wire/face/shell) cannot take part in a boolean. offenders: ${offenders.join(', ')}`,\n )\n }\n\n let resultSolid: BrepHandle\n let lastEvolution: Map<number, number[]> | undefined\n let roleTable: ReadonlyMap<unknown, unknown> | undefined\n\n // 链式布尔:每步 target(累积结果)与下一个 tool 合流\n const op: 'fuse' | 'cut' | 'intersect' =\n operation === 'union' ? 'fuse' : operation === 'subtract' ? 'cut' : 'intersect'\n\n // F 组(2026-10-03,FAULHABER/Beam-coupling 语料):import_brep 资产可能是\n // wire/face(ShapeBinder 冻结几何)——它们带 OCCT handle、能通过上面的\n // 「无 handle」守卫,但 OCCT 的 BOP 只接受 solid:fuse(wire, solid) 直接\n // \"operation failed\"(内核直测实证,PartShape5/PartShape6/PartShape93 均\n // wire/face、vol=0)。C3c-1 已实证 0 体积线框成员对 compound invariants\n // 零影响 ⇒ union 的语义是 solid 合流,非 solid 输入如实跳过(keepHidden\n // 语义不变);全非 solid 才抛错。cut/intersect 语义不变(工具/交域必须 solid)。\n const NON_SOLID = new Set(['wire', 'face', 'shell', 'vertex', 'edge'])\n const inputTypes = inputSolids.map((h) => {\n try { return h ? (kernel.shapeType(h) as string) : 'solid' } catch { return 'solid' }\n })\n // compound/compsolid 可能含 solid,是合法 fuse 输入——只跳过确定的非 solid 类型。\n const boolIdx = operation === 'union'\n ? inputTypes.map((t, i) => (NON_SOLID.has(t) ? -1 : i)).filter((i) => i >= 0)\n : inputs.map((_, i) => i)\n if (operation === 'union' && boolIdx.length === 0) {\n throw new OpError(\n `boolean/${operation}`,\n 'E_BREP_UNSUPPORTED',\n `[api/boolean] ${operation}: no solid input — wire/face/shell geometry cannot fuse (types: ${inputTypes.join(', ')})`,\n )\n }\n\n // 静态定轨:当前引擎是否原生实现本 op 的面演化核函数(引擎事实,非运行时探测)。\n // fuse/cut 的 brep 实现调 `*WithHistory`,在只提供裸布尔的引擎上走不了历史轨——\n // 该分叉由 hasNativeHistory 回答,op 侧不声明任何能力。\n const historyCap: BrepEvolutionKind = op === 'fuse' ? 'fuseWithHistory' : op === 'cut' ? 'cutWithHistory' : 'intersectWithHistory'\n const useHistory = hasNativeHistory(historyCap)\n\n // 首个 solid 输入作为 target 起点(F 组:可能不是 inputs[0] —— wire/face\n // 资产常排在前面作为 profile/binder)。\n resultSolid = inputSolids[boolIdx[0]!]!\n roleTable = useHistory\n ? (inputRoleTable(inputs[boolIdx[0]!]) as ReadonlyMap<unknown, unknown> | undefined)\n : undefined\n\n for (let bi = 1; bi < boolIdx.length; bi++) {\n const i = boolIdx[bi]!\n const prev = resultSolid\n const tool = inputSolids[i]!\n\n if (useHistory) {\n // §3.4:一次内核调用,A/B 拆流各自传播后合表(缝面 origin=本次语句 StmtId)\n // V-C8:内核裸错误在此包一层——带上 op 名、两个输入的变量名与 cause。\n const prevTable = roleTable\n const toolTable = inputRoleTable(inputs[i]) as ReadonlyMap<unknown, unknown> | undefined\n // Phase 1.6:新 origin = 本次语句的 StmtId。\n const outStmt = String(getCurrentStmt()?.id ?? '')\n let r: ReturnType<typeof booleanWithRoleTable>\n try {\n r = booleanWithRoleTable(\n kernel,\n op,\n prev,\n tool,\n prevTable ?? new Map(),\n toolTable ?? new Map(),\n outStmt,\n )\n } catch (cause) {\n // GOTCHA: OCCT 的 *WithHistory 在两输入共享子结构/历史(如布尔产物的布尔)\n // 时可能 \"operation failed\",而同一几何的裸布尔可以成功。降级重试一次裸\n // kernel[op]:几何结果正确,代价是丢本次面演化/roleTable(如实降级,同下方\n // 裸路径语义)。裸布尔也失败时,再试 unifySameDomain(两输入) 后重算——\n // 真实语料(disk-drive)中 tool 是布尔产物且与 target 共享子域,裸 cut 仍失败、\n // unify 后成功。全部失败才真正抛错。\n try {\n resultSolid = kernel[op](prev, tool)\n lastEvolution = undefined\n roleTable = undefined\n if (i > 1) kernel.release(prev)\n continue\n } catch {\n try {\n const uPrev = kernel.unifySameDomain(prev)\n const uTool = kernel.unifySameDomain(tool)\n resultSolid = kernel[op](uPrev, uTool)\n kernel.release(uPrev)\n kernel.release(uTool)\n lastEvolution = undefined\n roleTable = undefined\n if (i > 1) kernel.release(prev)\n continue\n } catch {\n const msg = cause instanceof Error ? cause.message : String(cause)\n throw new OpError(\n `boolean/${operation}`,\n 'E_OP_FAILED',\n `[api/boolean] ${operation}: kernel ${op} failed for inputs ` +\n `${nameOf(inputs[0]!) ?? 'input[0]'} × ${nameOf(inputs[i]!) ?? `input[${i}]`} — ${msg}`,\n { cause },\n )\n }\n }\n }\n resultSolid = r.result\n lastEvolution = r.faceEvolution\n roleTable = r.roleTable\n } else {\n // 裸布尔降级路径:几何正确,但无面演化、无 roleTable 传播(如实降级,不伪造映射)。\n try {\n resultSolid = kernel[op](prev, tool)\n } catch (cause) {\n const msg = cause instanceof Error ? cause.message : String(cause)\n throw new OpError(\n `boolean/${operation}`,\n 'E_OP_FAILED',\n `[api/boolean] ${operation}: kernel ${op} failed for inputs ` +\n `${nameOf(inputs[0]!) ?? 'input[0]'} × ${nameOf(inputs[i]!) ?? `input[${i}]`} — ${msg}`,\n { cause },\n )\n }\n lastEvolution = undefined\n roleTable = undefined\n }\n if (i > 1) kernel.release(prev)\n }\n\n return fromBrep(\n solidToShape(kernel, resultSolid),\n lastEvolution ? { solid: resultSolid, faceEvolution: lastEvolution, roleTable } : { solid: resultSolid, roleTable },\n )\n}\n\n/**\n * 网格实体路径:brepkit 网格内核的布尔(方案 2026-10-01 §3.5 三明治)。\n *\n * 输入**全部**是网格实体——这一点由 `dispatchPath` 的链门禁保证\n * (`E_MESH_SOLID_MIXED`:网格实体不得与链外几何同处一次调用),此处只复核不补救。\n *\n * 无面演化、无 roleTable:近似拓扑没有 hash 演化,造一张恒等映射就是假身份\n * (与 brepkit 裸布尔降级同一条纪律)。\n *\n * 中间结果是本实现自己造的句柄(不是任何输入),故 i>1 步及时释放;**输入句柄一概\n * 不释放**——生命周期归链(与 BREP 路径 booleanBrep 的 `if (i > 1) kernel.release(prev)`\n * 同构)。\n *\n * @param inputs - the mesh-solid inputs (≥1).\n * @param operation - union / subtract / intersect.\n * @returns the boolean result as a new mesh part.\n */\nfunction booleanMeshSolid(inputs: Shape[], operation: BooleanOperation): Shape {\n const opLabel = `boolean/${operation}`\n const entries = inputs.map((s) => meshSolidEntry(s, opLabel))\n const first = entries[0]!\n const kernel = first.kernel\n const op: 'fuse' | 'cut' | 'intersect' =\n operation === 'union' ? 'fuse' : operation === 'subtract' ? 'cut' : 'intersect'\n\n let result = first.solid\n for (let i = 1; i < entries.length; i++) {\n const prev = result\n try {\n result = kernel[op](prev, entries[i]!.solid)\n } catch (cause) {\n throw meshKernelFailure(\n opLabel,\n 'E_OP_FAILED',\n `${op}(${nameOf(inputs[0]!) ?? 'input[0]'} × ${nameOf(inputs[i]!) ?? `input[${i}]`})`,\n cause,\n )\n }\n // i>1:prev 是本实现上一步造出的中间实体,释放它(i=1 时 prev 是**输入**,不碰)。\n if (i > 1) first.backend.release(prev)\n }\n return meshSolidProduct(first, result)\n}\n\n/**\n * 网格路径分流(方案 2026-10-01 §3.4 规则 4):输入含网格实体 → brepkit 网格内核;\n * 否则保持历史上限(内置 `mesh/` 的 manifold CSG)。两条路**互不冒充**——\n * manifold 不认识网格实体(静态门禁),网格内核也不接受裸网格(无句柄)。\n *\n * @param inputs - the geometry inputs.\n * @param operation - union / subtract / intersect.\n * @returns the boolean product (mesh solid or manifold mesh shape).\n */\nfunction booleanMeshPath(inputs: Shape[], operation: BooleanOperation): Shape | Promise<Shape> {\n if (inputs.some(hasMeshSolid)) return booleanMeshSolid(inputs, operation)\n return booleanMesh(inputs, operation)\n}\n\n/** mesh 路径:manifold-3d mesh-CSG。 */\nasync function booleanMesh(inputs: Shape[], operation: BooleanOperation): Promise<Shape> {\n if (inputs.length < 2) {\n if (inputs.length === 1) return inputs[0]\n throw new Error('[api/boolean] boolean needs at least 1 input')\n }\n if (operation === 'union') return meshBoolean.union(inputs[0], inputs[1], ...inputs.slice(2))\n if (operation === 'subtract') {\n let result = await meshBoolean.subtract(inputs[0], inputs[1])\n for (let i = 2; i < inputs.length; i++) result = await meshBoolean.subtract(result, inputs[i])\n return result\n }\n let result = await meshBoolean.intersect(inputs[0], inputs[1])\n for (let i = 2; i < inputs.length; i++) result = await meshBoolean.intersect(result, inputs[i])\n return result\n}\n\n// ── 三个薄导出(多输入 variadic,defineOp 声明双路径;面演化进路由引擎事实 ──\n// ── `hasNativeHistory` 定,op 不声明、不查表——见下方各 op 的分叉注释) ──\n// 函数体 keep 声明(keep-syntax 设计 §2.5):union/subtract/intersect 保留其\n// 输入且隐藏(R5:3d_editor 现状)——keepHidden 使源变量保持终端但 canvas\n// 不渲染,只有布尔结果正常显示。混合/断链时刻:BREP 侧输入先归约为合法\n// 2-manifold 网格(reconcileBrepInputs),mesh 侧原样透传。\n\n/**\n * 布尔并集:合并所有输入几何(≥2 个输入)。\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name union\n * @param shapes - 参与运算的几何(变量引用,≥2 个)。type:Shape[] required:true\n * @returns Shape 所有输入的并集。函数名即操作,输入全是变量引用,可用 `cad.union(a, b, c)` 多输入。\n * @example\n * const a = await cad.union(part0, part1)\n */\nexport const union = defineOp({\n meshEngines: ['brepkit'],\n mesh: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanMeshPath(reconcileBrepInputs(shapes), 'union')\n },\n brep: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanBrep(shapes, 'union')\n },\n schema: { shapes: 'Shape*' },\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n\n/**\n * Boolean cut (subtract): remove `tool` from `base`. Same semantics as\n * {@link subtract} but with the brepjs-compatible `(base, tool, options?)` signature.\n * Overrides the generated projection (compatOp) to do roleTable propagation\n * (Phase 3: L2 requires wall:<i> to survive cut).\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name cut\n * @param base - the target shape. type:Shape required:true\n * @param tool - the shape to subtract. type:Shape required:true\n * @returns Shape base minus tool.\n * @example\n * const b = await cad.cut(part0, part1)\n */\nexport const cut = defineOp({\n meshEngines: ['brepkit'],\n mesh: (base: Shape, tool: Shape) => {\n keepHidden(base, tool)\n return booleanMeshPath(reconcileBrepInputs([base, tool]), 'subtract')\n },\n brep: (base: Shape, tool: Shape) => {\n keepHidden(base, tool)\n return booleanBrep([base, tool], 'subtract')\n },\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n\n/**\n * 布尔差集:第一个为主体,减去其余输入。\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name subtract\n * @param shapes - 参与运算的几何(变量引用,第一个为主体)。type:Shape[] required:true\n * @returns Shape part0 减 part1 的差集(第一个为主体)。\n * @example\n * const b = await cad.subtract(part0, part1)\n */\nexport const subtract = defineOp({\n meshEngines: ['brepkit'],\n mesh: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanMeshPath(reconcileBrepInputs(shapes), 'subtract')\n },\n brep: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanBrep(shapes, 'subtract')\n },\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n\n/**\n * 布尔交集:所有输入的重叠部分。\n * @group 特征\n * @inputs 2\n * @async true\n * @qual ok\n * @name intersect\n * @param shapes - 参与运算的几何(变量引用)。type:Shape[] required:true\n * @returns Shape 所有输入的交集。\n * @example\n * const c = await cad.intersect(part0, part1)\n */\nexport const intersect = defineOp({\n meshEngines: ['brepkit'],\n mesh: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanMeshPath(reconcileBrepInputs(shapes), 'intersect')\n },\n brep: (...shapes: Shape[]) => {\n if (shapes.length > 0) keepHidden(...shapes)\n return booleanBrep(shapes, 'intersect')\n },\n // intersect 不声明任何能力:brepkit 只有裸 `intersect`(无 `intersectWithHistory`),\n // 由 booleanBrep 按引擎事实静态分派——occt 走历史路径保留面演化/naming;\n // brepkit 走 L1 裸 `kernel.intersect`,几何正确但无面演化(如实降级,不伪造恒等映射)。\n naming: { kind: 'kernel', newFaces: { via: 'byAdjacency' } } as Provenance,\n})\n"]}
@@ -19,6 +19,19 @@ import { type Result } from '../../result/result.js';
19
19
  * @returns The healed solid as a `BrepHandle`.
20
20
  */
21
21
  export declare function healSolidBrep(...args: unknown[]): Result<BrepHandle>;
22
+ /**
23
+ * Fix a wire to lie on a face's surface (`fixWireOnFace`, occt-wasm 5.6).
24
+ *
25
+ * Geometric precondition for `sketchOnFace`: the wire produced by UV-space
26
+ * sampling may not exactly lie on the host face's surface. This snaps it.
27
+ * On failure (wire already on surface, or shape mismatch) returns the wire
28
+ * unchanged — it is a supplement, not a hard requirement.
29
+ *
30
+ * @param wire - the wire to fix.
31
+ * @param face - the host face the wire must lie on.
32
+ * @returns the fixed wire (or the original on failure).
33
+ */
34
+ export declare function fixWireOnFaceBrep(wire: BrepHandle, face: BrepHandle): BrepHandle;
22
35
  /**
23
36
  * Dispatch healing by shape type (solid/face/wire); other types pass through
24
37
  * unchanged (brepjs `heal`).
@@ -1 +1 @@
1
- {"version":3,"file":"healingFns.d.ts","sourceRoot":"","sources":["../../../src/api/brep-operations/healingFns.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAA;AAGzD,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,qBAAqB,CAAA;AAqB1D;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAoBpE;AA4BD;;;;;;GAMG;AACH,wBAAgB,QAAQ,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAQ/D;AAMD;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAQnE;AAED;;;;GAIG;AACH,wBAAgB,uBAAuB,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAW9E;AAED;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAOnE;AAMD,UAAU,qBAAqB;IAC7B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAA;IAC3B,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAA;IAC3B,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CACzB;AAUD,UAAU,aAAa;IACrB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAA;IACzB,QAAQ,CAAC,YAAY,EAAE,OAAO,CAAA;IAC9B,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAA;IAC5B,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAA;IAC5B,QAAQ,CAAC,WAAW,EAAE,OAAO,CAAA;IAC7B,QAAQ,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,CAAC,CAAA;IACrC,QAAQ,CAAC,WAAW,EAAE,aAAa,CAAC,qBAAqB,CAAC,CAAA;CAC3D;AAOD;;;;;;;;;GASG;AACH,wBAAgB,YAAY,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC;IAAE,KAAK,EAAE,UAAU,CAAC;IAAC,MAAM,EAAE,aAAa,CAAA;CAAE,CAAC,CA8HrG"}
1
+ {"version":3,"file":"healingFns.d.ts","sourceRoot":"","sources":["../../../src/api/brep-operations/healingFns.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAA;AAGzD,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,qBAAqB,CAAA;AAqB1D;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAoBpE;AAgCD;;;;;;;;;;;GAWG;AACH,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,UAAU,EAAE,IAAI,EAAE,UAAU,GAAG,UAAU,CAMhF;AAED;;;;;;GAMG;AACH,wBAAgB,QAAQ,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAQ/D;AAMD;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAQnE;AAED;;;;GAIG;AACH,wBAAgB,uBAAuB,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAW9E;AAED;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAOnE;AAMD,UAAU,qBAAqB;IAC7B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAA;IAC3B,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAA;IAC3B,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CACzB;AAUD,UAAU,aAAa;IACrB,QAAQ,CAAC,OAAO,EAAE,OAAO,CAAA;IACzB,QAAQ,CAAC,YAAY,EAAE,OAAO,CAAA;IAC9B,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAA;IAC5B,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAA;IAC5B,QAAQ,CAAC,WAAW,EAAE,OAAO,CAAA;IAC7B,QAAQ,CAAC,KAAK,EAAE,aAAa,CAAC,MAAM,CAAC,CAAA;IACrC,QAAQ,CAAC,WAAW,EAAE,aAAa,CAAC,qBAAqB,CAAC,CAAA;CAC3D;AAOD;;;;;;;;;GASG;AACH,wBAAgB,YAAY,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC;IAAE,KAAK,EAAE,UAAU,CAAC;IAAC,MAAM,EAAE,aAAa,CAAA;CAAE,CAAC,CA8HrG"}
@@ -73,10 +73,17 @@ function healFaceBrep(handle) {
73
73
  return err(kernelError('HEAL_FACE_FAILED', 'Face healing failed', e));
74
74
  }
75
75
  }
76
- /** Heal a wire (`ShapeFix_Wire`, occt platform method). */
76
+ /** Heal a wire (`ShapeFix_Wire` + `buildCurves3d`, occt platform method). */
77
77
  function healWireBrep(handle) {
78
78
  try {
79
79
  const result = getOcctKernel().healWire(handle, 1e-6);
80
+ // buildCurves3d: rebuild 3D curves on the wire in-place (occt-wasm 5.6).
81
+ // Supplement to healWire — some wires carry only 2D curves in surface
82
+ // parameter space; this ensures a 3D representation exists. Idempotent.
83
+ try {
84
+ getOcctKernel().buildCurves3d(result);
85
+ }
86
+ catch { /* not applicable */ }
80
87
  if (getOcctKernel().getShapeType(result) !== 'wire') {
81
88
  return err(kernelError('HEAL_RESULT_NOT_WIRE', 'Healed result is not a wire'));
82
89
  }
@@ -86,6 +93,26 @@ function healWireBrep(handle) {
86
93
  return err(kernelError('HEAL_WIRE_FAILED', 'Wire healing failed', e));
87
94
  }
88
95
  }
96
+ /**
97
+ * Fix a wire to lie on a face's surface (`fixWireOnFace`, occt-wasm 5.6).
98
+ *
99
+ * Geometric precondition for `sketchOnFace`: the wire produced by UV-space
100
+ * sampling may not exactly lie on the host face's surface. This snaps it.
101
+ * On failure (wire already on surface, or shape mismatch) returns the wire
102
+ * unchanged — it is a supplement, not a hard requirement.
103
+ *
104
+ * @param wire - the wire to fix.
105
+ * @param face - the host face the wire must lie on.
106
+ * @returns the fixed wire (or the original on failure).
107
+ */
108
+ export function fixWireOnFaceBrep(wire, face) {
109
+ try {
110
+ return getOcctKernel().fixWireOnFace(wire, face, 1e-6);
111
+ }
112
+ catch {
113
+ return wire;
114
+ }
115
+ }
89
116
  /**
90
117
  * Dispatch healing by shape type (solid/face/wire); other types pass through
91
118
  * unchanged (brepjs `heal`).
@@ -1 +1 @@
1
- {"version":3,"file":"healingFns.js","sourceRoot":"","sources":["../../../src/api/brep-operations/healingFns.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Self-hosted compat-op implementations — shape healing family\n * (core-decouple Phase 3, §5.4).\n *\n * @platform occt\n *\n * Brep-shaped implementations for `heal`, `healSolid`, `fixShape`, `autoHeal`,\n * `fixSelfIntersection`, `simplify`. Semantics mirror brepjs\n * `topology/healingFns.ts` / `topology/shapeFns.ts` (error codes preserved),\n * with the brepjs object model (castResultShape / cache invalidation) dropped:\n * occt-wasm handles only. Platform-native methods (`healFace`, `healWire`,\n * `simplify`, `fixSelfIntersection`) go through `getOcctKernel()` (D3).\n */\n\nimport type { BrepHandle } from '../../brep/engine/types'\nimport { getBrepApi } from '../../brep/handle-bridge'\nimport { getOcctKernel } from '../../occt-kernel/occtKernel'\nimport { ok, err, type Result } from '../../result/result'\nimport { kernelError, validationError } from '../../result/errors'\nimport type { FormClass } from '../internal/dual-form-args'\nimport { resolveArgs } from '../internal/dual-form-args'\nimport { brepHandleOf } from './brepHelpers'\n\nconst HEAL_PARAMS = { name: 'heal', params: ['shape'], formClass: 'A' as FormClass }\nconst HEAL_SOLID_PARAMS = { name: 'healSolid', params: ['solid'], formClass: 'A' as FormClass }\nconst FIX_SHAPE_PARAMS = { name: 'fixShape', params: ['shape'], formClass: 'A' as FormClass }\nconst AUTO_HEAL_PARAMS = { name: 'autoHeal', params: ['shape', 'options'], formClass: 'A' as FormClass }\nconst FIX_SELF_INTERSECTION_PARAMS = {\n name: 'fixSelfIntersection',\n params: ['shape'],\n formClass: 'A' as FormClass,\n}\nconst SIMPLIFY_PARAMS = { name: 'simplify', params: ['shape'], formClass: 'A' as FormClass }\n\n// ---------------------------------------------------------------------------\n// heal (type-dispatching)\n// ---------------------------------------------------------------------------\n\n/** Heal a solid (`ShapeFix_Solid`); error codes match brepjs `healSolid`.\n *\n * @param args - Resolved arguments (solid shape).\n * @returns The healed solid as a `BrepHandle`.\n */\nexport function healSolidBrep(...args: unknown[]): Result<BrepHandle> {\n const [solid] = resolveArgs(args, HEAL_SOLID_PARAMS)\n const kernel = getBrepApi()\n const h = brepHandleOf(solid)\n if (!kernel.isSolid(h)) return err(validationError('NOT_A_SOLID', 'Input shape is not a solid'))\n const alreadyValid = kernel.isValid(h)\n try {\n const result = kernel.healSolid(h)\n if (result == null || result === h) {\n if (alreadyValid) return ok(h)\n return err(kernelError('HEAL_NO_EFFECT', 'Solid healing had no effect — shape is still invalid'))\n }\n if (!kernel.isSolid(result)) return err(kernelError('HEAL_RESULT_NOT_SOLID', 'Healed result is not a solid'))\n if (!kernel.isValid(result)) {\n return err(kernelError('HEAL_SOLID_INCOMPLETE', 'Healed result is still invalid after ShapeFix_Solid'))\n }\n return ok(result)\n } catch (e) {\n return err(kernelError('HEAL_SOLID_FAILED', 'Solid healing failed', e))\n }\n}\n\n/** Heal a face (`ShapeFix_Face`, occt platform method). */\nfunction healFaceBrep(handle: BrepHandle): Result<BrepHandle> {\n try {\n const result = getOcctKernel().healFace(handle as never, 1e-6)\n if (getOcctKernel().getShapeType(result as never) !== 'face') {\n return err(kernelError('HEAL_RESULT_NOT_FACE', 'Healed result is not a face'))\n }\n return ok(result as never as BrepHandle)\n } catch (e) {\n return err(kernelError('HEAL_FACE_FAILED', 'Face healing failed', e))\n }\n}\n\n/** Heal a wire (`ShapeFix_Wire`, occt platform method). */\nfunction healWireBrep(handle: BrepHandle): Result<BrepHandle> {\n try {\n const result = getOcctKernel().healWire(handle as never, 1e-6)\n if (getOcctKernel().getShapeType(result as never) !== 'wire') {\n return err(kernelError('HEAL_RESULT_NOT_WIRE', 'Healed result is not a wire'))\n }\n return ok(result as never as BrepHandle)\n } catch (e) {\n return err(kernelError('HEAL_WIRE_FAILED', 'Wire healing failed', e))\n }\n}\n\n/**\n * Dispatch healing by shape type (solid/face/wire); other types pass through\n * unchanged (brepjs `heal`).\n *\n * @param args - Resolved arguments (shape).\n * @returns The healed shape as a `BrepHandle`.\n */\nexport function healBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, HEAL_PARAMS)\n const h = brepHandleOf(shape)\n const type = getOcctKernel().getShapeType(h as never)\n if (type === 'solid') return healSolidBrep(shape)\n if (type === 'face') return healFaceBrep(h)\n if (type === 'wire') return healWireBrep(h)\n return ok(h)\n}\n\n// ---------------------------------------------------------------------------\n// fixShape / fixSelfIntersection / simplify\n// ---------------------------------------------------------------------------\n\n/** General-purpose repair (`ShapeFix_Shape`).\n *\n * @param args - Resolved arguments (shape).\n * @returns The repaired shape as a `BrepHandle`.\n */\nexport function fixShapeBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, FIX_SHAPE_PARAMS)\n const kernel = getBrepApi()\n try {\n return ok(kernel.fixShape(brepHandleOf(shape)))\n } catch (e) {\n return err(kernelError('FIX_SHAPE_FAILED', 'ShapeFix_Shape failed', e))\n }\n}\n\n/** Fix wire self-intersection (occt platform method).\n *\n * @param args - Resolved arguments (wire shape).\n * @returns The fixed wire as a `BrepHandle`.\n */\nexport function fixSelfIntersectionBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, FIX_SELF_INTERSECTION_PARAMS)\n try {\n const result = getOcctKernel().healWire(brepHandleOf(shape) as never, 1e-6)\n if (getOcctKernel().getShapeType(result as never) !== 'wire') {\n return err(kernelError('FIX_SELF_INTERSECTION_FAILED', 'Result is not a wire'))\n }\n return ok(result as never as BrepHandle)\n } catch (e) {\n return err(kernelError('FIX_SELF_INTERSECTION_FAILED', 'Failed to fix wire self-intersection', e))\n }\n}\n\n/** Simplify a shape (occt platform method).\n *\n * @param args - Resolved arguments (shape).\n * @returns The simplified shape as a `BrepHandle`.\n */\nexport function simplifyBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, SIMPLIFY_PARAMS)\n try {\n return ok(getOcctKernel().simplify(brepHandleOf(shape) as never) as never as BrepHandle)\n } catch (e) {\n return err(kernelError('SIMPLIFY_FAILED', 'Kernel simplify failed', e))\n }\n}\n\n// ---------------------------------------------------------------------------\n// autoHeal pipeline\n// ---------------------------------------------------------------------------\n\ninterface HealingStepDiagnostic {\n readonly name: string\n readonly attempted: boolean\n readonly succeeded: boolean\n readonly detail?: string\n}\n\ninterface AutoHealOptions {\n fixWires?: boolean\n fixFaces?: boolean\n fixSolids?: boolean\n sewTolerance?: number\n fixSelfIntersection?: boolean\n}\n\ninterface HealingReport {\n readonly isValid: boolean\n readonly alreadyValid: boolean\n readonly wiresHealed: number\n readonly facesHealed: number\n readonly solidHealed: boolean\n readonly steps: ReadonlyArray<string>\n readonly diagnostics: ReadonlyArray<HealingStepDiagnostic>\n}\n\n/** Shape-kind check on a raw handle (occt `shapeType`). */\nfunction kindOf(h: BrepHandle): string {\n return getOcctKernel().getShapeType(h as never)\n}\n\n/**\n * Auto-heal pipeline (brepjs `autoHeal`): short-circuit on valid, optional\n * sew / wire self-intersection pass, shape-level heal, sub-shape delta report.\n *\n * The returned record carries the healed shape as a raw BREP handle; the\n * projection wraps it via `fromHandle` so callers receive a faijs Shape.\n *\n * @param args - Resolved arguments (shape, auto-heal options).\n * @returns The healed shape with a diagnostic healing report.\n */\nexport function autoHealBrep(...args: unknown[]): Result<{ shape: BrepHandle; report: HealingReport }> {\n const [shape, options] = resolveArgs(args, AUTO_HEAL_PARAMS)\n const opts = (options ?? {}) as AutoHealOptions\n const fixWires = opts.fixWires !== false\n const fixFaces = opts.fixFaces !== false\n const fixSolids = opts.fixSolids !== false\n const fixSelfIntersectionOpt = opts.fixSelfIntersection === true\n const sewTolerance = opts.sewTolerance\n\n const steps: string[] = []\n const diagnostics: HealingStepDiagnostic[] = []\n const kernel = getBrepApi()\n const input = brepHandleOf(shape)\n\n const valid = kernel.isValid(input)\n if (valid) {\n return ok({\n shape: input,\n report: {\n isValid: true,\n alreadyValid: true,\n wiresHealed: 0,\n facesHealed: 0,\n solidHealed: false,\n steps: ['Shape already valid'],\n diagnostics: [{ name: 'validation', attempted: true, succeeded: true }],\n },\n })\n }\n\n steps.push('Shape invalid — applying shape-level healing')\n\n const wiresBefore = kernel.getSubShapes(input, 'wire').length\n const facesBefore = kernel.getSubShapes(input, 'face').length\n\n let current = input\n let solidHealed = false\n const setCurrent = (next: BrepHandle): void => {\n const prev = current\n current = next\n if (prev !== input && prev !== next) kernel.release(prev)\n }\n\n if (sewTolerance !== undefined) {\n try {\n setCurrent(kernel.sew([current], sewTolerance))\n steps.push(`Applied sewing with tolerance ${sewTolerance}`)\n diagnostics.push({ name: 'sew', attempted: true, succeeded: true, detail: `tolerance=${sewTolerance}` })\n } catch (e) {\n const detail = e instanceof Error ? e.message : String(e)\n steps.push(`Sewing failed: ${detail}`)\n diagnostics.push({ name: 'sew', attempted: true, succeeded: false, detail })\n }\n }\n\n if (fixSelfIntersectionOpt && fixWires) {\n const wires = kernel.getSubShapes(current, 'wire')\n let fixCount = 0\n for (const wire of wires) {\n try {\n getOcctKernel().healWire(wire as never, 1e-6)\n fixCount++\n } catch {\n // Ignore individual wire failures\n }\n }\n steps.push(`Self-intersection fix: ${fixCount}/${wires.length} wires`)\n diagnostics.push({\n name: 'fixSelfIntersection',\n attempted: true,\n succeeded: fixCount > 0,\n detail: `${fixCount}/${wires.length} wires fixed`,\n })\n }\n\n const kind = kindOf(current)\n const shouldHealShape =\n (kind === 'solid' && fixSolids) || (kind === 'face' && fixFaces) || (kind === 'wire' && fixWires)\n\n if (shouldHealShape) {\n const healResult = kind === 'solid' ? healSolidBrep(current) : kind === 'face' ? healFaceBrep(current) : healWireBrep(current)\n if (healResult.ok) {\n setCurrent(healResult.value)\n if (kind === 'solid') {\n solidHealed = true\n steps.push('Applied ShapeFix_Solid')\n diagnostics.push({ name: 'healSolid', attempted: true, succeeded: true })\n } else if (kind === 'face') {\n steps.push('Applied ShapeFix_Face')\n diagnostics.push({ name: 'healFace', attempted: true, succeeded: true })\n } else {\n steps.push('Applied ShapeFix_Wire')\n diagnostics.push({ name: 'healWire', attempted: true, succeeded: true })\n }\n } else {\n steps.push('Shape-level healing failed')\n diagnostics.push({ name: 'healShape', attempted: true, succeeded: false })\n }\n } else {\n diagnostics.push({ name: 'healShape', attempted: false, succeeded: false, detail: 'skipped by options' })\n }\n\n const wiresAfter = kernel.getSubShapes(current, 'wire').length\n const facesAfter = kernel.getSubShapes(current, 'face').length\n const wiresHealed = Math.abs(wiresAfter - wiresBefore)\n const facesHealed = Math.abs(facesAfter - facesBefore)\n\n if (wiresHealed > 0) steps.push(`Wire count changed by ${wiresHealed}`)\n if (facesHealed > 0) steps.push(`Face count changed by ${facesHealed}`)\n\n const finalValid = kernel.isValid(current)\n steps.push(finalValid ? 'Final validation: valid' : 'Final validation: still invalid')\n diagnostics.push({ name: 'finalValidation', attempted: true, succeeded: finalValid })\n\n return ok({\n shape: current,\n report: {\n isValid: finalValid,\n alreadyValid: false,\n wiresHealed,\n facesHealed,\n solidHealed,\n steps,\n diagnostics,\n },\n })\n}\n"]}
1
+ {"version":3,"file":"healingFns.js","sourceRoot":"","sources":["../../../src/api/brep-operations/healingFns.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * Self-hosted compat-op implementations — shape healing family\n * (core-decouple Phase 3, §5.4).\n *\n * @platform occt\n *\n * Brep-shaped implementations for `heal`, `healSolid`, `fixShape`, `autoHeal`,\n * `fixSelfIntersection`, `simplify`. Semantics mirror brepjs\n * `topology/healingFns.ts` / `topology/shapeFns.ts` (error codes preserved),\n * with the brepjs object model (castResultShape / cache invalidation) dropped:\n * occt-wasm handles only. Platform-native methods (`healFace`, `healWire`,\n * `simplify`, `fixSelfIntersection`) go through `getOcctKernel()` (D3).\n */\n\nimport type { BrepHandle } from '../../brep/engine/types'\nimport { getBrepApi } from '../../brep/handle-bridge'\nimport { getOcctKernel } from '../../occt-kernel/occtKernel'\nimport { ok, err, type Result } from '../../result/result'\nimport { kernelError, validationError } from '../../result/errors'\nimport type { FormClass } from '../internal/dual-form-args'\nimport { resolveArgs } from '../internal/dual-form-args'\nimport { brepHandleOf } from './brepHelpers'\n\nconst HEAL_PARAMS = { name: 'heal', params: ['shape'], formClass: 'A' as FormClass }\nconst HEAL_SOLID_PARAMS = { name: 'healSolid', params: ['solid'], formClass: 'A' as FormClass }\nconst FIX_SHAPE_PARAMS = { name: 'fixShape', params: ['shape'], formClass: 'A' as FormClass }\nconst AUTO_HEAL_PARAMS = { name: 'autoHeal', params: ['shape', 'options'], formClass: 'A' as FormClass }\nconst FIX_SELF_INTERSECTION_PARAMS = {\n name: 'fixSelfIntersection',\n params: ['shape'],\n formClass: 'A' as FormClass,\n}\nconst SIMPLIFY_PARAMS = { name: 'simplify', params: ['shape'], formClass: 'A' as FormClass }\n\n// ---------------------------------------------------------------------------\n// heal (type-dispatching)\n// ---------------------------------------------------------------------------\n\n/** Heal a solid (`ShapeFix_Solid`); error codes match brepjs `healSolid`.\n *\n * @param args - Resolved arguments (solid shape).\n * @returns The healed solid as a `BrepHandle`.\n */\nexport function healSolidBrep(...args: unknown[]): Result<BrepHandle> {\n const [solid] = resolveArgs(args, HEAL_SOLID_PARAMS)\n const kernel = getBrepApi()\n const h = brepHandleOf(solid)\n if (!kernel.isSolid(h)) return err(validationError('NOT_A_SOLID', 'Input shape is not a solid'))\n const alreadyValid = kernel.isValid(h)\n try {\n const result = kernel.healSolid(h)\n if (result == null || result === h) {\n if (alreadyValid) return ok(h)\n return err(kernelError('HEAL_NO_EFFECT', 'Solid healing had no effect — shape is still invalid'))\n }\n if (!kernel.isSolid(result)) return err(kernelError('HEAL_RESULT_NOT_SOLID', 'Healed result is not a solid'))\n if (!kernel.isValid(result)) {\n return err(kernelError('HEAL_SOLID_INCOMPLETE', 'Healed result is still invalid after ShapeFix_Solid'))\n }\n return ok(result)\n } catch (e) {\n return err(kernelError('HEAL_SOLID_FAILED', 'Solid healing failed', e))\n }\n}\n\n/** Heal a face (`ShapeFix_Face`, occt platform method). */\nfunction healFaceBrep(handle: BrepHandle): Result<BrepHandle> {\n try {\n const result = getOcctKernel().healFace(handle as never, 1e-6)\n if (getOcctKernel().getShapeType(result as never) !== 'face') {\n return err(kernelError('HEAL_RESULT_NOT_FACE', 'Healed result is not a face'))\n }\n return ok(result as never as BrepHandle)\n } catch (e) {\n return err(kernelError('HEAL_FACE_FAILED', 'Face healing failed', e))\n }\n}\n\n/** Heal a wire (`ShapeFix_Wire` + `buildCurves3d`, occt platform method). */\nfunction healWireBrep(handle: BrepHandle): Result<BrepHandle> {\n try {\n const result = getOcctKernel().healWire(handle as never, 1e-6)\n // buildCurves3d: rebuild 3D curves on the wire in-place (occt-wasm 5.6).\n // Supplement to healWire — some wires carry only 2D curves in surface\n // parameter space; this ensures a 3D representation exists. Idempotent.\n try { getOcctKernel().buildCurves3d(result as never) } catch { /* not applicable */ }\n if (getOcctKernel().getShapeType(result as never) !== 'wire') {\n return err(kernelError('HEAL_RESULT_NOT_WIRE', 'Healed result is not a wire'))\n }\n return ok(result as never as BrepHandle)\n } catch (e) {\n return err(kernelError('HEAL_WIRE_FAILED', 'Wire healing failed', e))\n }\n}\n\n/**\n * Fix a wire to lie on a face's surface (`fixWireOnFace`, occt-wasm 5.6).\n *\n * Geometric precondition for `sketchOnFace`: the wire produced by UV-space\n * sampling may not exactly lie on the host face's surface. This snaps it.\n * On failure (wire already on surface, or shape mismatch) returns the wire\n * unchanged — it is a supplement, not a hard requirement.\n *\n * @param wire - the wire to fix.\n * @param face - the host face the wire must lie on.\n * @returns the fixed wire (or the original on failure).\n */\nexport function fixWireOnFaceBrep(wire: BrepHandle, face: BrepHandle): BrepHandle {\n try {\n return getOcctKernel().fixWireOnFace(wire as never, face as never, 1e-6) as never as BrepHandle\n } catch {\n return wire\n }\n}\n\n/**\n * Dispatch healing by shape type (solid/face/wire); other types pass through\n * unchanged (brepjs `heal`).\n *\n * @param args - Resolved arguments (shape).\n * @returns The healed shape as a `BrepHandle`.\n */\nexport function healBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, HEAL_PARAMS)\n const h = brepHandleOf(shape)\n const type = getOcctKernel().getShapeType(h as never)\n if (type === 'solid') return healSolidBrep(shape)\n if (type === 'face') return healFaceBrep(h)\n if (type === 'wire') return healWireBrep(h)\n return ok(h)\n}\n\n// ---------------------------------------------------------------------------\n// fixShape / fixSelfIntersection / simplify\n// ---------------------------------------------------------------------------\n\n/** General-purpose repair (`ShapeFix_Shape`).\n *\n * @param args - Resolved arguments (shape).\n * @returns The repaired shape as a `BrepHandle`.\n */\nexport function fixShapeBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, FIX_SHAPE_PARAMS)\n const kernel = getBrepApi()\n try {\n return ok(kernel.fixShape(brepHandleOf(shape)))\n } catch (e) {\n return err(kernelError('FIX_SHAPE_FAILED', 'ShapeFix_Shape failed', e))\n }\n}\n\n/** Fix wire self-intersection (occt platform method).\n *\n * @param args - Resolved arguments (wire shape).\n * @returns The fixed wire as a `BrepHandle`.\n */\nexport function fixSelfIntersectionBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, FIX_SELF_INTERSECTION_PARAMS)\n try {\n const result = getOcctKernel().healWire(brepHandleOf(shape) as never, 1e-6)\n if (getOcctKernel().getShapeType(result as never) !== 'wire') {\n return err(kernelError('FIX_SELF_INTERSECTION_FAILED', 'Result is not a wire'))\n }\n return ok(result as never as BrepHandle)\n } catch (e) {\n return err(kernelError('FIX_SELF_INTERSECTION_FAILED', 'Failed to fix wire self-intersection', e))\n }\n}\n\n/** Simplify a shape (occt platform method).\n *\n * @param args - Resolved arguments (shape).\n * @returns The simplified shape as a `BrepHandle`.\n */\nexport function simplifyBrep(...args: unknown[]): Result<BrepHandle> {\n const [shape] = resolveArgs(args, SIMPLIFY_PARAMS)\n try {\n return ok(getOcctKernel().simplify(brepHandleOf(shape) as never) as never as BrepHandle)\n } catch (e) {\n return err(kernelError('SIMPLIFY_FAILED', 'Kernel simplify failed', e))\n }\n}\n\n// ---------------------------------------------------------------------------\n// autoHeal pipeline\n// ---------------------------------------------------------------------------\n\ninterface HealingStepDiagnostic {\n readonly name: string\n readonly attempted: boolean\n readonly succeeded: boolean\n readonly detail?: string\n}\n\ninterface AutoHealOptions {\n fixWires?: boolean\n fixFaces?: boolean\n fixSolids?: boolean\n sewTolerance?: number\n fixSelfIntersection?: boolean\n}\n\ninterface HealingReport {\n readonly isValid: boolean\n readonly alreadyValid: boolean\n readonly wiresHealed: number\n readonly facesHealed: number\n readonly solidHealed: boolean\n readonly steps: ReadonlyArray<string>\n readonly diagnostics: ReadonlyArray<HealingStepDiagnostic>\n}\n\n/** Shape-kind check on a raw handle (occt `shapeType`). */\nfunction kindOf(h: BrepHandle): string {\n return getOcctKernel().getShapeType(h as never)\n}\n\n/**\n * Auto-heal pipeline (brepjs `autoHeal`): short-circuit on valid, optional\n * sew / wire self-intersection pass, shape-level heal, sub-shape delta report.\n *\n * The returned record carries the healed shape as a raw BREP handle; the\n * projection wraps it via `fromHandle` so callers receive a faijs Shape.\n *\n * @param args - Resolved arguments (shape, auto-heal options).\n * @returns The healed shape with a diagnostic healing report.\n */\nexport function autoHealBrep(...args: unknown[]): Result<{ shape: BrepHandle; report: HealingReport }> {\n const [shape, options] = resolveArgs(args, AUTO_HEAL_PARAMS)\n const opts = (options ?? {}) as AutoHealOptions\n const fixWires = opts.fixWires !== false\n const fixFaces = opts.fixFaces !== false\n const fixSolids = opts.fixSolids !== false\n const fixSelfIntersectionOpt = opts.fixSelfIntersection === true\n const sewTolerance = opts.sewTolerance\n\n const steps: string[] = []\n const diagnostics: HealingStepDiagnostic[] = []\n const kernel = getBrepApi()\n const input = brepHandleOf(shape)\n\n const valid = kernel.isValid(input)\n if (valid) {\n return ok({\n shape: input,\n report: {\n isValid: true,\n alreadyValid: true,\n wiresHealed: 0,\n facesHealed: 0,\n solidHealed: false,\n steps: ['Shape already valid'],\n diagnostics: [{ name: 'validation', attempted: true, succeeded: true }],\n },\n })\n }\n\n steps.push('Shape invalid — applying shape-level healing')\n\n const wiresBefore = kernel.getSubShapes(input, 'wire').length\n const facesBefore = kernel.getSubShapes(input, 'face').length\n\n let current = input\n let solidHealed = false\n const setCurrent = (next: BrepHandle): void => {\n const prev = current\n current = next\n if (prev !== input && prev !== next) kernel.release(prev)\n }\n\n if (sewTolerance !== undefined) {\n try {\n setCurrent(kernel.sew([current], sewTolerance))\n steps.push(`Applied sewing with tolerance ${sewTolerance}`)\n diagnostics.push({ name: 'sew', attempted: true, succeeded: true, detail: `tolerance=${sewTolerance}` })\n } catch (e) {\n const detail = e instanceof Error ? e.message : String(e)\n steps.push(`Sewing failed: ${detail}`)\n diagnostics.push({ name: 'sew', attempted: true, succeeded: false, detail })\n }\n }\n\n if (fixSelfIntersectionOpt && fixWires) {\n const wires = kernel.getSubShapes(current, 'wire')\n let fixCount = 0\n for (const wire of wires) {\n try {\n getOcctKernel().healWire(wire as never, 1e-6)\n fixCount++\n } catch {\n // Ignore individual wire failures\n }\n }\n steps.push(`Self-intersection fix: ${fixCount}/${wires.length} wires`)\n diagnostics.push({\n name: 'fixSelfIntersection',\n attempted: true,\n succeeded: fixCount > 0,\n detail: `${fixCount}/${wires.length} wires fixed`,\n })\n }\n\n const kind = kindOf(current)\n const shouldHealShape =\n (kind === 'solid' && fixSolids) || (kind === 'face' && fixFaces) || (kind === 'wire' && fixWires)\n\n if (shouldHealShape) {\n const healResult = kind === 'solid' ? healSolidBrep(current) : kind === 'face' ? healFaceBrep(current) : healWireBrep(current)\n if (healResult.ok) {\n setCurrent(healResult.value)\n if (kind === 'solid') {\n solidHealed = true\n steps.push('Applied ShapeFix_Solid')\n diagnostics.push({ name: 'healSolid', attempted: true, succeeded: true })\n } else if (kind === 'face') {\n steps.push('Applied ShapeFix_Face')\n diagnostics.push({ name: 'healFace', attempted: true, succeeded: true })\n } else {\n steps.push('Applied ShapeFix_Wire')\n diagnostics.push({ name: 'healWire', attempted: true, succeeded: true })\n }\n } else {\n steps.push('Shape-level healing failed')\n diagnostics.push({ name: 'healShape', attempted: true, succeeded: false })\n }\n } else {\n diagnostics.push({ name: 'healShape', attempted: false, succeeded: false, detail: 'skipped by options' })\n }\n\n const wiresAfter = kernel.getSubShapes(current, 'wire').length\n const facesAfter = kernel.getSubShapes(current, 'face').length\n const wiresHealed = Math.abs(wiresAfter - wiresBefore)\n const facesHealed = Math.abs(facesAfter - facesBefore)\n\n if (wiresHealed > 0) steps.push(`Wire count changed by ${wiresHealed}`)\n if (facesHealed > 0) steps.push(`Face count changed by ${facesHealed}`)\n\n const finalValid = kernel.isValid(current)\n steps.push(finalValid ? 'Final validation: valid' : 'Final validation: still invalid')\n diagnostics.push({ name: 'finalValidation', attempted: true, succeeded: finalValid })\n\n return ok({\n shape: current,\n report: {\n isValid: finalValid,\n alreadyValid: false,\n wiresHealed,\n facesHealed,\n solidHealed,\n steps,\n diagnostics,\n },\n })\n}\n"]}
@@ -62,17 +62,31 @@ export declare function locateBrep(...args: unknown[]): Result<BrepHandle>;
62
62
  /**
63
63
  * Mirror across a plane defined by `options.at` (origin) and `options.normal`.
64
64
  *
65
+ * C5 实现面接入(静态双轨):occt 原生有 `mirrorWithHistory` → 走权威面演化;
66
+ * brepkit 没有 → 显式回退裸 `mirror`(**不报错**),镜像保面序故挂恒等序号演化。
67
+ *
65
68
  * @param args - Resolved arguments (shape, mirror options).
66
- * @returns The mirrored shape as a `BrepHandle`.
69
+ * @returns The mirrored shape plus its face evolution.
67
70
  */
68
- export declare function mirrorBrep(...args: unknown[]): Result<BrepHandle>;
71
+ export declare function mirrorBrep(...args: unknown[]): Result<{
72
+ solid: BrepHandle;
73
+ faceEvolution: Map<number, number[]>;
74
+ }>;
69
75
  /**
70
76
  * Rotate the shape around an axis (brepjs topology/api.js#rotate + transformFns.ts#rotate).
71
77
  *
78
+ * C5 实现面接入(静态双轨):occt 原生有 `rotateWithHistory` → 走权威面演化
79
+ * (`rotateWithHistory` 产物 STEP 导出安全,与原生 `rotate` 的 GOTCHA 无关);
80
+ * brepkit 没有 → 退回 Rodrigues 矩阵 + STEP-safe `transform`(**不报错**),
81
+ * 挂恒等序号演化。
82
+ *
72
83
  * @param args - Resolved arguments (shape, angle in degrees, axis options).
73
- * @returns The rotated shape as a `BrepHandle`.
84
+ * @returns The rotated shape plus its face evolution.
74
85
  */
75
- export declare function rotateBrep(...args: unknown[]): Result<BrepHandle>;
86
+ export declare function rotateBrep(...args: unknown[]): Result<{
87
+ solid: BrepHandle;
88
+ faceEvolution: Map<number, number[]>;
89
+ }>;
76
90
  /**
77
91
  * Shell — hollow the shape by removing faces (brepjs topology/api.js#shell + modifierFns.ts#shell).
78
92
  *
@@ -83,8 +97,15 @@ export declare function shellBrep(...args: unknown[]): Result<BrepHandle>;
83
97
  /**
84
98
  * Offset all faces of the shape (brepjs topology/api.js#offset + modifierFns.ts#offset).
85
99
  *
100
+ * C5 实现面接入:occt 提供 `offsetWithHistory` ⇒ 用权威面演化,不用无历史 `offset`。
101
+ * `offset` 是 occt-only 平台 op(arg-spec `engines:['occt']`),brepkit 侧本就不支持,
102
+ * 不存在「有裸方法却因无 history 而报错」的回退分支。
103
+ *
86
104
  * @param args - Resolved arguments (shape, distance, options).
87
- * @returns The offset shape as a `BrepHandle`.
105
+ * @returns The offset shape plus its face evolution.
88
106
  */
89
- export declare function offsetBrep(...args: unknown[]): Result<BrepHandle>;
107
+ export declare function offsetBrep(...args: unknown[]): Result<{
108
+ solid: BrepHandle;
109
+ faceEvolution: Map<number, number[]>;
110
+ }>;
90
111
  //# sourceMappingURL=topologyFns.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"topologyFns.d.ts","sourceRoot":"","sources":["../../../src/api/brep-operations/topologyFns.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,yBAAyB,CAAA;AAEzD,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,qBAAqB,CAAA;AAqD1D;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AACH,wBAAgB,eAAe,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CA8BtE;AAQD;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAchE;AAmBD;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAoBjE;AAQD;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAiBjE;AAQD;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAmCjE;AAOD;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAmBhE;AAOD;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAejE"}
1
+ {"version":3,"file":"topologyFns.d.ts","sourceRoot":"","sources":["../../../src/api/brep-operations/topologyFns.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AAEH,OAAO,KAAK,EAAqB,UAAU,EAAE,MAAM,yBAAyB,CAAA;AAW5E,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,qBAAqB,CAAA;AAqD1D;;;;;;;;;;;;;;;;;;;;;;;;;;GA0BG;AACH,wBAAgB,eAAe,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CA8BtE;AAQD;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAchE;AAmBD;;;;;;GAMG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAoBjE;AAQD;;;;;;;;GAQG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC;IAAE,KAAK,EAAE,UAAU,CAAC;IAAC,aAAa,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAA;CAAE,CAAC,CAuBlH;AAQD;;;;;;;;;;GAUG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC;IAAE,KAAK,EAAE,UAAU,CAAC;IAAC,aAAa,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAA;CAAE,CAAC,CAmClH;AAOD;;;;;GAKG;AACH,wBAAgB,SAAS,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC,UAAU,CAAC,CAmBhE;AAOD;;;;;;;;;GASG;AACH,wBAAgB,UAAU,CAAC,GAAG,IAAI,EAAE,OAAO,EAAE,GAAG,MAAM,CAAC;IAAE,KAAK,EAAE,UAAU,CAAC;IAAC,aAAa,EAAE,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC,CAAA;CAAE,CAAC,CAyBlH"}