@itwin/core-geometry 3.1.0-dev.8 → 3.2.0-dev.12

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 (286) hide show
  1. package/CHANGELOG.md +48 -3
  2. package/lib/cjs/bspline/AkimaCurve3d.d.ts +2 -8
  3. package/lib/cjs/bspline/AkimaCurve3d.d.ts.map +1 -1
  4. package/lib/cjs/bspline/AkimaCurve3d.js +2 -17
  5. package/lib/cjs/bspline/AkimaCurve3d.js.map +1 -1
  6. package/lib/cjs/bspline/BSpline1dNd.d.ts +11 -6
  7. package/lib/cjs/bspline/BSpline1dNd.d.ts.map +1 -1
  8. package/lib/cjs/bspline/BSpline1dNd.js +64 -6
  9. package/lib/cjs/bspline/BSpline1dNd.js.map +1 -1
  10. package/lib/cjs/bspline/BSplineCurve.d.ts +18 -14
  11. package/lib/cjs/bspline/BSplineCurve.d.ts.map +1 -1
  12. package/lib/cjs/bspline/BSplineCurve.js +54 -32
  13. package/lib/cjs/bspline/BSplineCurve.js.map +1 -1
  14. package/lib/cjs/bspline/BSplineCurve3dH.d.ts +0 -2
  15. package/lib/cjs/bspline/BSplineCurve3dH.d.ts.map +1 -1
  16. package/lib/cjs/bspline/BSplineCurve3dH.js +0 -6
  17. package/lib/cjs/bspline/BSplineCurve3dH.js.map +1 -1
  18. package/lib/cjs/bspline/BSplineCurveOps.d.ts.map +1 -1
  19. package/lib/cjs/bspline/BSplineCurveOps.js +4 -6
  20. package/lib/cjs/bspline/BSplineCurveOps.js.map +1 -1
  21. package/lib/cjs/bspline/Bezier1dNd.d.ts +8 -11
  22. package/lib/cjs/bspline/Bezier1dNd.d.ts.map +1 -1
  23. package/lib/cjs/bspline/Bezier1dNd.js +13 -14
  24. package/lib/cjs/bspline/Bezier1dNd.js.map +1 -1
  25. package/lib/cjs/bspline/BezierCurve3d.d.ts +0 -6
  26. package/lib/cjs/bspline/BezierCurve3d.d.ts.map +1 -1
  27. package/lib/cjs/bspline/BezierCurve3d.js +0 -14
  28. package/lib/cjs/bspline/BezierCurve3d.js.map +1 -1
  29. package/lib/cjs/bspline/BezierCurve3dH.d.ts +0 -4
  30. package/lib/cjs/bspline/BezierCurve3dH.d.ts.map +1 -1
  31. package/lib/cjs/bspline/BezierCurve3dH.js +0 -8
  32. package/lib/cjs/bspline/BezierCurve3dH.js.map +1 -1
  33. package/lib/cjs/bspline/BezierCurveBase.d.ts +17 -0
  34. package/lib/cjs/bspline/BezierCurveBase.d.ts.map +1 -1
  35. package/lib/cjs/bspline/BezierCurveBase.js +31 -1
  36. package/lib/cjs/bspline/BezierCurveBase.js.map +1 -1
  37. package/lib/cjs/bspline/InterpolationCurve3d.d.ts +2 -8
  38. package/lib/cjs/bspline/InterpolationCurve3d.d.ts.map +1 -1
  39. package/lib/cjs/bspline/InterpolationCurve3d.js +2 -17
  40. package/lib/cjs/bspline/InterpolationCurve3d.js.map +1 -1
  41. package/lib/cjs/bspline/KnotVector.d.ts +24 -9
  42. package/lib/cjs/bspline/KnotVector.d.ts.map +1 -1
  43. package/lib/cjs/bspline/KnotVector.js +86 -26
  44. package/lib/cjs/bspline/KnotVector.js.map +1 -1
  45. package/lib/cjs/curve/Arc3d.d.ts +8 -2
  46. package/lib/cjs/curve/Arc3d.d.ts.map +1 -1
  47. package/lib/cjs/curve/Arc3d.js +32 -2
  48. package/lib/cjs/curve/Arc3d.js.map +1 -1
  49. package/lib/cjs/curve/CurveChainWithDistanceIndex.d.ts +11 -4
  50. package/lib/cjs/curve/CurveChainWithDistanceIndex.d.ts.map +1 -1
  51. package/lib/cjs/curve/CurveChainWithDistanceIndex.js +25 -9
  52. package/lib/cjs/curve/CurveChainWithDistanceIndex.js.map +1 -1
  53. package/lib/cjs/curve/CurveCollection.d.ts +2 -2
  54. package/lib/cjs/curve/CurveCollection.d.ts.map +1 -1
  55. package/lib/cjs/curve/CurveCollection.js.map +1 -1
  56. package/lib/cjs/curve/CurveCurveIntersectXY.d.ts.map +1 -1
  57. package/lib/cjs/curve/CurveCurveIntersectXY.js +5 -3
  58. package/lib/cjs/curve/CurveCurveIntersectXY.js.map +1 -1
  59. package/lib/cjs/curve/CurveFactory.d.ts +7 -3
  60. package/lib/cjs/curve/CurveFactory.d.ts.map +1 -1
  61. package/lib/cjs/curve/CurveFactory.js +30 -15
  62. package/lib/cjs/curve/CurveFactory.js.map +1 -1
  63. package/lib/cjs/curve/CurvePrimitive.d.ts +27 -9
  64. package/lib/cjs/curve/CurvePrimitive.d.ts.map +1 -1
  65. package/lib/cjs/curve/CurvePrimitive.js +18 -0
  66. package/lib/cjs/curve/CurvePrimitive.js.map +1 -1
  67. package/lib/cjs/curve/LineSegment3d.d.ts +8 -2
  68. package/lib/cjs/curve/LineSegment3d.d.ts.map +1 -1
  69. package/lib/cjs/curve/LineSegment3d.js +14 -0
  70. package/lib/cjs/curve/LineSegment3d.js.map +1 -1
  71. package/lib/cjs/curve/LineString3d.d.ts +11 -4
  72. package/lib/cjs/curve/LineString3d.d.ts.map +1 -1
  73. package/lib/cjs/curve/LineString3d.js +72 -22
  74. package/lib/cjs/curve/LineString3d.js.map +1 -1
  75. package/lib/cjs/curve/ProxyCurve.d.ts +12 -4
  76. package/lib/cjs/curve/ProxyCurve.d.ts.map +1 -1
  77. package/lib/cjs/curve/ProxyCurve.js +16 -2
  78. package/lib/cjs/curve/ProxyCurve.js.map +1 -1
  79. package/lib/cjs/curve/Query/CurveSplitContext.d.ts.map +1 -1
  80. package/lib/cjs/curve/Query/CurveSplitContext.js +1 -3
  81. package/lib/cjs/curve/Query/CurveSplitContext.js.map +1 -1
  82. package/lib/cjs/curve/Query/PlanarSubdivision.d.ts +11 -0
  83. package/lib/cjs/curve/Query/PlanarSubdivision.d.ts.map +1 -1
  84. package/lib/cjs/curve/Query/PlanarSubdivision.js +26 -17
  85. package/lib/cjs/curve/Query/PlanarSubdivision.js.map +1 -1
  86. package/lib/cjs/curve/RegionOps.d.ts +15 -16
  87. package/lib/cjs/curve/RegionOps.d.ts.map +1 -1
  88. package/lib/cjs/curve/RegionOps.js +14 -16
  89. package/lib/cjs/curve/RegionOps.js.map +1 -1
  90. package/lib/cjs/curve/RegionOpsClassificationSweeps.d.ts.map +1 -1
  91. package/lib/cjs/curve/RegionOpsClassificationSweeps.js +3 -1
  92. package/lib/cjs/curve/RegionOpsClassificationSweeps.js.map +1 -1
  93. package/lib/cjs/curve/StrokeOptions.d.ts +6 -0
  94. package/lib/cjs/curve/StrokeOptions.d.ts.map +1 -1
  95. package/lib/cjs/curve/StrokeOptions.js +21 -0
  96. package/lib/cjs/curve/StrokeOptions.js.map +1 -1
  97. package/lib/cjs/curve/internalContexts/CloneCurvesContext.js.map +1 -1
  98. package/lib/cjs/curve/internalContexts/CloneWithExpandedLineStrings.d.ts +2 -2
  99. package/lib/cjs/curve/internalContexts/CloneWithExpandedLineStrings.d.ts.map +1 -1
  100. package/lib/cjs/curve/internalContexts/CloneWithExpandedLineStrings.js.map +1 -1
  101. package/lib/cjs/curve/internalContexts/CurveOffsetXYHandler.d.ts +36 -0
  102. package/lib/cjs/curve/internalContexts/CurveOffsetXYHandler.d.ts.map +1 -0
  103. package/lib/cjs/curve/internalContexts/CurveOffsetXYHandler.js +73 -0
  104. package/lib/cjs/curve/internalContexts/CurveOffsetXYHandler.js.map +1 -0
  105. package/lib/cjs/curve/internalContexts/PolygonOffsetContext.d.ts +48 -24
  106. package/lib/cjs/curve/internalContexts/PolygonOffsetContext.d.ts.map +1 -1
  107. package/lib/cjs/curve/internalContexts/PolygonOffsetContext.js +113 -112
  108. package/lib/cjs/curve/internalContexts/PolygonOffsetContext.js.map +1 -1
  109. package/lib/cjs/curve/spiral/DirectSpiral3d.d.ts +0 -4
  110. package/lib/cjs/curve/spiral/DirectSpiral3d.d.ts.map +1 -1
  111. package/lib/cjs/curve/spiral/DirectSpiral3d.js +0 -15
  112. package/lib/cjs/curve/spiral/DirectSpiral3d.js.map +1 -1
  113. package/lib/cjs/curve/spiral/IntegratedSpiral3d.d.ts +0 -4
  114. package/lib/cjs/curve/spiral/IntegratedSpiral3d.d.ts.map +1 -1
  115. package/lib/cjs/curve/spiral/IntegratedSpiral3d.js +33 -22
  116. package/lib/cjs/curve/spiral/IntegratedSpiral3d.js.map +1 -1
  117. package/lib/cjs/curve/spiral/TransitionSpiral3d.d.ts +16 -0
  118. package/lib/cjs/curve/spiral/TransitionSpiral3d.d.ts.map +1 -1
  119. package/lib/cjs/curve/spiral/TransitionSpiral3d.js +29 -0
  120. package/lib/cjs/curve/spiral/TransitionSpiral3d.js.map +1 -1
  121. package/lib/cjs/geometry3d/Matrix3d.d.ts +4 -4
  122. package/lib/cjs/geometry3d/Matrix3d.js +4 -4
  123. package/lib/cjs/geometry3d/Matrix3d.js.map +1 -1
  124. package/lib/cjs/geometry4d/Matrix4d.d.ts.map +1 -1
  125. package/lib/cjs/geometry4d/Matrix4d.js +21 -8
  126. package/lib/cjs/geometry4d/Matrix4d.js.map +1 -1
  127. package/lib/cjs/numerics/ClusterableArray.d.ts +1 -1
  128. package/lib/cjs/numerics/ClusterableArray.d.ts.map +1 -1
  129. package/lib/cjs/numerics/ClusterableArray.js +2 -2
  130. package/lib/cjs/numerics/ClusterableArray.js.map +1 -1
  131. package/lib/cjs/polyface/PolyfaceBuilder.d.ts +15 -1
  132. package/lib/cjs/polyface/PolyfaceBuilder.d.ts.map +1 -1
  133. package/lib/cjs/polyface/PolyfaceBuilder.js +17 -11
  134. package/lib/cjs/polyface/PolyfaceBuilder.js.map +1 -1
  135. package/lib/cjs/serialization/IModelJsonSchema.d.ts +4 -0
  136. package/lib/cjs/serialization/IModelJsonSchema.d.ts.map +1 -1
  137. package/lib/cjs/serialization/IModelJsonSchema.js.map +1 -1
  138. package/lib/cjs/solid/RuledSweep.js.map +1 -1
  139. package/lib/cjs/solid/SweepContour.js.map +1 -1
  140. package/lib/cjs/topology/Merging.d.ts +22 -3
  141. package/lib/cjs/topology/Merging.d.ts.map +1 -1
  142. package/lib/cjs/topology/Merging.js +97 -1
  143. package/lib/cjs/topology/Merging.js.map +1 -1
  144. package/lib/esm/bspline/AkimaCurve3d.d.ts +2 -8
  145. package/lib/esm/bspline/AkimaCurve3d.d.ts.map +1 -1
  146. package/lib/esm/bspline/AkimaCurve3d.js +2 -17
  147. package/lib/esm/bspline/AkimaCurve3d.js.map +1 -1
  148. package/lib/esm/bspline/BSpline1dNd.d.ts +11 -6
  149. package/lib/esm/bspline/BSpline1dNd.d.ts.map +1 -1
  150. package/lib/esm/bspline/BSpline1dNd.js +65 -7
  151. package/lib/esm/bspline/BSpline1dNd.js.map +1 -1
  152. package/lib/esm/bspline/BSplineCurve.d.ts +18 -14
  153. package/lib/esm/bspline/BSplineCurve.d.ts.map +1 -1
  154. package/lib/esm/bspline/BSplineCurve.js +54 -32
  155. package/lib/esm/bspline/BSplineCurve.js.map +1 -1
  156. package/lib/esm/bspline/BSplineCurve3dH.d.ts +0 -2
  157. package/lib/esm/bspline/BSplineCurve3dH.d.ts.map +1 -1
  158. package/lib/esm/bspline/BSplineCurve3dH.js +0 -6
  159. package/lib/esm/bspline/BSplineCurve3dH.js.map +1 -1
  160. package/lib/esm/bspline/BSplineCurveOps.d.ts.map +1 -1
  161. package/lib/esm/bspline/BSplineCurveOps.js +4 -6
  162. package/lib/esm/bspline/BSplineCurveOps.js.map +1 -1
  163. package/lib/esm/bspline/Bezier1dNd.d.ts +8 -11
  164. package/lib/esm/bspline/Bezier1dNd.d.ts.map +1 -1
  165. package/lib/esm/bspline/Bezier1dNd.js +13 -14
  166. package/lib/esm/bspline/Bezier1dNd.js.map +1 -1
  167. package/lib/esm/bspline/BezierCurve3d.d.ts +0 -6
  168. package/lib/esm/bspline/BezierCurve3d.d.ts.map +1 -1
  169. package/lib/esm/bspline/BezierCurve3d.js +0 -14
  170. package/lib/esm/bspline/BezierCurve3d.js.map +1 -1
  171. package/lib/esm/bspline/BezierCurve3dH.d.ts +0 -4
  172. package/lib/esm/bspline/BezierCurve3dH.d.ts.map +1 -1
  173. package/lib/esm/bspline/BezierCurve3dH.js +0 -8
  174. package/lib/esm/bspline/BezierCurve3dH.js.map +1 -1
  175. package/lib/esm/bspline/BezierCurveBase.d.ts +17 -0
  176. package/lib/esm/bspline/BezierCurveBase.d.ts.map +1 -1
  177. package/lib/esm/bspline/BezierCurveBase.js +31 -1
  178. package/lib/esm/bspline/BezierCurveBase.js.map +1 -1
  179. package/lib/esm/bspline/InterpolationCurve3d.d.ts +2 -8
  180. package/lib/esm/bspline/InterpolationCurve3d.d.ts.map +1 -1
  181. package/lib/esm/bspline/InterpolationCurve3d.js +2 -17
  182. package/lib/esm/bspline/InterpolationCurve3d.js.map +1 -1
  183. package/lib/esm/bspline/KnotVector.d.ts +24 -9
  184. package/lib/esm/bspline/KnotVector.d.ts.map +1 -1
  185. package/lib/esm/bspline/KnotVector.js +86 -26
  186. package/lib/esm/bspline/KnotVector.js.map +1 -1
  187. package/lib/esm/curve/Arc3d.d.ts +8 -2
  188. package/lib/esm/curve/Arc3d.d.ts.map +1 -1
  189. package/lib/esm/curve/Arc3d.js +32 -2
  190. package/lib/esm/curve/Arc3d.js.map +1 -1
  191. package/lib/esm/curve/CurveChainWithDistanceIndex.d.ts +11 -4
  192. package/lib/esm/curve/CurveChainWithDistanceIndex.d.ts.map +1 -1
  193. package/lib/esm/curve/CurveChainWithDistanceIndex.js +25 -9
  194. package/lib/esm/curve/CurveChainWithDistanceIndex.js.map +1 -1
  195. package/lib/esm/curve/CurveCollection.d.ts +2 -2
  196. package/lib/esm/curve/CurveCollection.d.ts.map +1 -1
  197. package/lib/esm/curve/CurveCollection.js.map +1 -1
  198. package/lib/esm/curve/CurveCurveIntersectXY.d.ts.map +1 -1
  199. package/lib/esm/curve/CurveCurveIntersectXY.js +5 -3
  200. package/lib/esm/curve/CurveCurveIntersectXY.js.map +1 -1
  201. package/lib/esm/curve/CurveFactory.d.ts +7 -3
  202. package/lib/esm/curve/CurveFactory.d.ts.map +1 -1
  203. package/lib/esm/curve/CurveFactory.js +30 -15
  204. package/lib/esm/curve/CurveFactory.js.map +1 -1
  205. package/lib/esm/curve/CurvePrimitive.d.ts +27 -9
  206. package/lib/esm/curve/CurvePrimitive.d.ts.map +1 -1
  207. package/lib/esm/curve/CurvePrimitive.js +18 -0
  208. package/lib/esm/curve/CurvePrimitive.js.map +1 -1
  209. package/lib/esm/curve/LineSegment3d.d.ts +8 -2
  210. package/lib/esm/curve/LineSegment3d.d.ts.map +1 -1
  211. package/lib/esm/curve/LineSegment3d.js +15 -1
  212. package/lib/esm/curve/LineSegment3d.js.map +1 -1
  213. package/lib/esm/curve/LineString3d.d.ts +11 -4
  214. package/lib/esm/curve/LineString3d.d.ts.map +1 -1
  215. package/lib/esm/curve/LineString3d.js +72 -22
  216. package/lib/esm/curve/LineString3d.js.map +1 -1
  217. package/lib/esm/curve/ProxyCurve.d.ts +12 -4
  218. package/lib/esm/curve/ProxyCurve.d.ts.map +1 -1
  219. package/lib/esm/curve/ProxyCurve.js +16 -2
  220. package/lib/esm/curve/ProxyCurve.js.map +1 -1
  221. package/lib/esm/curve/Query/CurveSplitContext.d.ts.map +1 -1
  222. package/lib/esm/curve/Query/CurveSplitContext.js +1 -3
  223. package/lib/esm/curve/Query/CurveSplitContext.js.map +1 -1
  224. package/lib/esm/curve/Query/PlanarSubdivision.d.ts +11 -0
  225. package/lib/esm/curve/Query/PlanarSubdivision.d.ts.map +1 -1
  226. package/lib/esm/curve/Query/PlanarSubdivision.js +26 -17
  227. package/lib/esm/curve/Query/PlanarSubdivision.js.map +1 -1
  228. package/lib/esm/curve/RegionOps.d.ts +15 -16
  229. package/lib/esm/curve/RegionOps.d.ts.map +1 -1
  230. package/lib/esm/curve/RegionOps.js +15 -17
  231. package/lib/esm/curve/RegionOps.js.map +1 -1
  232. package/lib/esm/curve/RegionOpsClassificationSweeps.d.ts.map +1 -1
  233. package/lib/esm/curve/RegionOpsClassificationSweeps.js +3 -1
  234. package/lib/esm/curve/RegionOpsClassificationSweeps.js.map +1 -1
  235. package/lib/esm/curve/StrokeOptions.d.ts +6 -0
  236. package/lib/esm/curve/StrokeOptions.d.ts.map +1 -1
  237. package/lib/esm/curve/StrokeOptions.js +21 -0
  238. package/lib/esm/curve/StrokeOptions.js.map +1 -1
  239. package/lib/esm/curve/internalContexts/CloneCurvesContext.js.map +1 -1
  240. package/lib/esm/curve/internalContexts/CloneWithExpandedLineStrings.d.ts +2 -2
  241. package/lib/esm/curve/internalContexts/CloneWithExpandedLineStrings.d.ts.map +1 -1
  242. package/lib/esm/curve/internalContexts/CloneWithExpandedLineStrings.js.map +1 -1
  243. package/lib/esm/curve/internalContexts/CurveOffsetXYHandler.d.ts +36 -0
  244. package/lib/esm/curve/internalContexts/CurveOffsetXYHandler.d.ts.map +1 -0
  245. package/lib/esm/curve/internalContexts/CurveOffsetXYHandler.js +69 -0
  246. package/lib/esm/curve/internalContexts/CurveOffsetXYHandler.js.map +1 -0
  247. package/lib/esm/curve/internalContexts/PolygonOffsetContext.d.ts +48 -24
  248. package/lib/esm/curve/internalContexts/PolygonOffsetContext.d.ts.map +1 -1
  249. package/lib/esm/curve/internalContexts/PolygonOffsetContext.js +111 -111
  250. package/lib/esm/curve/internalContexts/PolygonOffsetContext.js.map +1 -1
  251. package/lib/esm/curve/spiral/DirectSpiral3d.d.ts +0 -4
  252. package/lib/esm/curve/spiral/DirectSpiral3d.d.ts.map +1 -1
  253. package/lib/esm/curve/spiral/DirectSpiral3d.js +0 -15
  254. package/lib/esm/curve/spiral/DirectSpiral3d.js.map +1 -1
  255. package/lib/esm/curve/spiral/IntegratedSpiral3d.d.ts +0 -4
  256. package/lib/esm/curve/spiral/IntegratedSpiral3d.d.ts.map +1 -1
  257. package/lib/esm/curve/spiral/IntegratedSpiral3d.js +33 -22
  258. package/lib/esm/curve/spiral/IntegratedSpiral3d.js.map +1 -1
  259. package/lib/esm/curve/spiral/TransitionSpiral3d.d.ts +16 -0
  260. package/lib/esm/curve/spiral/TransitionSpiral3d.d.ts.map +1 -1
  261. package/lib/esm/curve/spiral/TransitionSpiral3d.js +29 -0
  262. package/lib/esm/curve/spiral/TransitionSpiral3d.js.map +1 -1
  263. package/lib/esm/geometry3d/Matrix3d.d.ts +4 -4
  264. package/lib/esm/geometry3d/Matrix3d.js +4 -4
  265. package/lib/esm/geometry3d/Matrix3d.js.map +1 -1
  266. package/lib/esm/geometry4d/Matrix4d.d.ts.map +1 -1
  267. package/lib/esm/geometry4d/Matrix4d.js +21 -8
  268. package/lib/esm/geometry4d/Matrix4d.js.map +1 -1
  269. package/lib/esm/numerics/ClusterableArray.d.ts +1 -1
  270. package/lib/esm/numerics/ClusterableArray.d.ts.map +1 -1
  271. package/lib/esm/numerics/ClusterableArray.js +2 -2
  272. package/lib/esm/numerics/ClusterableArray.js.map +1 -1
  273. package/lib/esm/polyface/PolyfaceBuilder.d.ts +15 -1
  274. package/lib/esm/polyface/PolyfaceBuilder.d.ts.map +1 -1
  275. package/lib/esm/polyface/PolyfaceBuilder.js +17 -11
  276. package/lib/esm/polyface/PolyfaceBuilder.js.map +1 -1
  277. package/lib/esm/serialization/IModelJsonSchema.d.ts +4 -0
  278. package/lib/esm/serialization/IModelJsonSchema.d.ts.map +1 -1
  279. package/lib/esm/serialization/IModelJsonSchema.js.map +1 -1
  280. package/lib/esm/solid/RuledSweep.js.map +1 -1
  281. package/lib/esm/solid/SweepContour.js.map +1 -1
  282. package/lib/esm/topology/Merging.d.ts +22 -3
  283. package/lib/esm/topology/Merging.d.ts.map +1 -1
  284. package/lib/esm/topology/Merging.js +95 -0
  285. package/lib/esm/topology/Merging.js.map +1 -1
  286. package/package.json +7 -5
@@ -1 +1 @@
1
- {"version":3,"file":"RuledSweep.js","sourceRoot":"","sources":["../../../src/solid/RuledSweep.ts"],"names":[],"mappings":"AAAA;;;+FAG+F;AAE/F;;GAEG;AAEH,OAAO,EAAE,2BAA2B,EAAE,MAAM,sCAAsC,CAAC;AACnF,OAAO,EAAE,UAAU,EAAE,eAAe,EAAE,MAAM,0BAA0B,CAAC;AACvE,OAAO,EAAE,cAAc,EAAE,MAAM,yBAAyB,CAAC;AAEzD,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AAIvC,OAAO,EAAE,cAAc,EAAE,MAAM,kBAAkB,CAAC;AAClD,OAAO,EAAE,YAAY,EAAE,MAAM,gBAAgB,CAAC;AAQ9C;;;;GAIG;AACH,MAAM,OAAO,UAAW,SAAQ,cAAc;IAK5C,YAAoB,QAAwB,EAAE,MAAe;QAC3D,KAAK,CAAC,MAAM,CAAC,CAAC;QALhB,wCAAwC;QACxB,uBAAkB,GAAG,YAAY,CAAC;QAKhD,IAAI,CAAC,SAAS,GAAG,QAAQ,CAAC;IAC5B,CAAC;IACD;;;OAGG;IACI,MAAM,CAAC,MAAM,CAAC,QAA2B,EAAE,MAAe;QAC/D,MAAM,aAAa,GAAG,EAAE,CAAC;QACzB,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE;YAC9B,MAAM,SAAS,GAAG,YAAY,CAAC,oBAAoB,CAAC,OAAO,CAAC,CAAC;YAC7D,IAAI,SAAS,KAAK,SAAS;gBAAE,OAAO,SAAS,CAAC;YAC9C,aAAa,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;SAC/B;QACD,OAAO,IAAI,UAAU,CAAC,aAAa,EAAE,MAAM,CAAC,CAAC;IAC/C,CAAC;IACD,uDAAuD;IAChD,gBAAgB,KAAqB,OAAO,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC;IACpE;;OAEG;IACI,kBAAkB;QACvB,MAAM,MAAM,GAAG,EAAE,CAAC;QAClB,KAAK,MAAM,SAAS,IAAI,IAAI,CAAC,SAAS,EAAE;YACtC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,KAAK,EAAE,CAAC,CAAC;SAChC;QACD,OAAO,MAAM,CAAC;IAChB,CAAC;IACD;;OAEG;IACI,aAAa;QAClB,MAAM,MAAM,GAAG,EAAE,CAAC;QAClB,KAAK,MAAM,SAAS,IAAI,IAAI,CAAC,SAAS,EAAE;YACtC,MAAM,CAAC,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC,KAAK,EAAqB,CAAC,CAAC;SAC1D;QACD,OAAO,MAAM,CAAC;IAChB,CAAC;IACD,0BAA0B;IACnB,KAAK;QACV,OAAO,IAAI,UAAU,CAAC,IAAI,CAAC,kBAAkB,EAAE,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;IAChE,CAAC;IACD,uCAAuC;IAChC,mBAAmB,CAAC,SAAoB;QAC7C,IAAI,SAAS,CAAC,MAAM,CAAC,UAAU,EAAE;YAC/B,OAAO,KAAK,CAAC;QACf,KAAK,MAAM,OAAO,IAAI,IAAI,CAAC,SAAS,EAAE;YACpC,OAAO,CAAC,mBAAmB,CAAC,SAAS,CAAC,CAAC;SACxC;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IACD,iCAAiC;IAC1B,gBAAgB,CAAC,SAAoB;QAC1C,MAAM,MAAM,GAAG,IAAI,CAAC,KAAK,EAAE,CAAC;QAC5B,MAAM,CAAC,mBAAmB,CAAC,SAAS,CAAC,CAAC;QACtC,OAAO,MAAM,CAAC;IAChB,CAAC;IACD;;;;OAIG;IACI,oBAAoB;QACzB,IAAI,IAAI,CAAC,SAAS,CAAC,MAAM,KAAK,CAAC;YAAE,OAAO,SAAS,CAAC;QAClD,OAAO,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,YAAY,CAAC,UAAU,EAAE,CAAC;IACrD,CAAC;IACD,uDAAuD;IAChD,mBAAmB,CAAC,KAAU,IAAa,OAAO,KAAK,YAAY,UAAU,CAAC,CAAC,CAAC;IACvF,8CAA8C;IAC9B,aAAa,CAAC,KAAoB;QAChD,IAAI,KAAK,YAAY,UAAU,EAAE;YAC/B,IAAI,IAAI,CAAC,MAAM,KAAK,KAAK,CAAC,MAAM;gBAAE,OAAO,KAAK,CAAC;YAC/C,IAAI,IAAI,CAAC,SAAS,CAAC,MAAM,KAAK,KAAK,CAAC,SAAS,CAAC,MAAM;gBAAE,OAAO,KAAK,CAAC;YACnE,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;gBAC9C,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,aAAa,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC;oBACtD,OAAO,KAAK,CAAC;aAChB;YACD,OAAO,IAAI,CAAC;SACb;QACD,OAAO,KAAK,CAAC;IACf,CAAC;IACD,kEAAkE;IAC3D,yBAAyB,CAAC,OAAwB;QACvD,OAAO,OAAO,CAAC,gBAAgB,CAAC,IAAI,CAAC,CAAC;IACxC,CAAC;IACD;;;OAGG;IACI,gBAAgB,CAAC,SAAiB;QACvC,MAAM,UAAU,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC;QACzC,IAAI,UAAU,GAAG,CAAC;YAChB,OAAO,SAAS,CAAC;QACnB,MAAM,CAAC,GAAG,SAAS,GAAG,UAAU,CAAC;QACjC,IAAI,QAAQ,GAAG,CAAC,CAAC;QACjB,IAAI,SAAS,IAAI,GAAG;YAClB,QAAQ,GAAG,UAAU,GAAG,CAAC,CAAC;;YAE1B,QAAQ,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC;QAC3B,IAAI,QAAQ,GAAG,CAAC,IAAI,UAAU;YAC5B,QAAQ,GAAG,UAAU,GAAG,CAAC,CAAC;QAC5B,MAAM,QAAQ,GAAG,QAAQ,GAAG,CAAC,CAAC;QAC9B,MAAM,aAAa,GAAG,QAAQ,CAAC,eAAe,CAAC,CAAC,GAAG,QAAQ,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;QACnE,OAAO,UAAU,CAAC,cAAc,CAAC,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,CAAC,MAAM,EAAE,IAAI,CAAC,SAAS,CAAC,QAAQ,CAAC,CAAC,MAAM,EAC/F,CAAC,UAA0B,EAAE,UAA0B,EAA8B,EAAE;YACrF,MAAM,YAAY,GAAG,2BAA2B,CAAC,kBAAkB,CAAC,UAAU,EAAE,aAAa,EAAE,UAAU,CAAC,CAAC;YAC3G,IAAI,YAAY,YAAY,cAAc;gBAAE,OAAO,YAAY,CAAC;YAChE,OAAO,SAAS,CAAC;QACnB,CAAC,CAAC,CAAC;IACP,CAAC;IACD,yCAAyC;IAClC,WAAW,CAAC,aAAsB,EAAE,SAAqB;QAC9D,KAAK,MAAM,OAAO,IAAI,IAAI,CAAC,SAAS;YAClC,OAAO,CAAC,MAAM,CAAC,WAAW,CAAC,aAAa,EAAE,SAAS,CAAC,CAAC;IACzD,CAAC;IAED;;OAEG;IACI,MAAM,CAAC,cAAc,CAAC,WAA4B,EAAE,WAA4B,EAAE,gBAAuC;QAC9H,IAAI,CAAC,WAAW,CAAC,mBAAmB,CAAC,WAAW,CAAC;YAC/C,OAAO,SAAS,CAAC;QACnB,IAAI,WAAW,YAAY,UAAU,IAAI,WAAW,YAAY,UAAU,EAAE;YAC1E,MAAM,MAAM,GAAG,WAAW,CAAC;YAC3B,MAAM,MAAM,GAAG,WAAW,CAAC;YAC3B,MAAM,MAAM,GAAG,MAAM,CAAC,cAAc,EAAgB,CAAC;YACrD,MAAM,SAAS,GAAG,MAAM,CAAC,QAAQ,CAAC;YAClC,MAAM,SAAS,GAAG,MAAM,CAAC,QAAQ,CAAC;YAClC,IAAI,SAAS,CAAC,MAAM,KAAK,SAAS,CAAC,MAAM;gBACvC,OAAO,SAAS,CAAC;YACnB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,SAAS,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;gBACzC,MAAM,QAAQ,GAAG,gBAAgB,CAAC,SAAS,CAAC,CAAC,CAAC,EAAE,SAAS,CAAC,CAAC,CAAC,CAAC,CAAC;gBAC9D,IAAI,CAAC,QAAQ;oBACX,OAAO,SAAS,CAAC;gBACnB,MAAM,CAAC,QAAQ,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;aAChC;YACD,OAAO,MAAM,CAAC;SACf;aAAM,IAAI,WAAW,YAAY,eAAe,IAAI,WAAW,YAAY,eAAe,EAAE;YAC3F,MAAM,WAAW,GAAG,WAAW,CAAC,cAAc,EAAE,CAAC;YACjD,MAAM,SAAS,GAAG,WAAW,CAAC,QAAQ,CAAC;YACvC,MAAM,SAAS,GAAG,WAAW,CAAC,QAAQ,CAAC;YACvC,MAAM,SAAS,GAAG,WAAW,CAAC,QAAQ,CAAC;YACvC,IAAI,SAAS,KAAK,SAAS,IAAI,SAAS,KAAK,SAAS,IAAI,SAAS,KAAK,SAAS,IAAI,SAAS,CAAC,MAAM,KAAK,SAAS,CAAC,MAAM;gBACxH,OAAO,SAAS,CAAC;YACnB,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,SAAS,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;gBACzC,MAAM,MAAM,GAAG,SAAS,CAAC,CAAC,CAAC,CAAC;gBAC5B,MAAM,MAAM,GAAG,SAAS,CAAC,CAAC,CAAC,CAAC;gBAC5B,IAAI,MAAM,YAAY,cAAc,IAAI,MAAM,YAAY,cAAc,EAAE;oBACxE,MAAM,YAAY,GAAG,gBAAgB,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;oBACtD,IAAI,CAAC,YAAY;wBACf,OAAO,SAAS,CAAC;oBACnB,SAAS,CAAC,IAAI,CAAC,YAAY,CAAC,CAAC;iBAC9B;qBAAM,IAAI,MAAM,YAAY,eAAe,IAAI,MAAM,YAAY,eAAe,EAAE;oBACjF,MAAM,QAAQ,GAAG,IAAI,CAAC,cAAc,CAAC,MAAM,EAAE,MAAM,EAAE,gBAAgB,CAAC,CAAC;oBACvE,IAAI,CAAC,QAAQ;wBACX,OAAO,SAAS,CAAC;oBACnB,IAAI,QAAQ,YAAY,eAAe;wBACrC,SAAS,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;iBAC5B;aACF;YACD,OAAO,WAAW,CAAC;SACpB;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;IACD;;;;OAIG;IACH,IAAW,cAAc;QACvB,MAAM,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,MAAM,CAAC;QAChC,OAAO,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,MAAM,IAAI,IAAI,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,aAAa,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;IAC1F,CAAC;CAEF","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Solid\r\n */\r\n\r\nimport { ConstructCurveBetweenCurves } from \"../curve/ConstructCurveBetweenCurves\";\r\nimport { CurveChain, CurveCollection } from \"../curve/CurveCollection\";\r\nimport { CurvePrimitive } from \"../curve/CurvePrimitive\";\r\nimport { GeometryQuery } from \"../curve/GeometryQuery\";\r\nimport { Geometry } from \"../Geometry\";\r\nimport { GeometryHandler } from \"../geometry3d/GeometryHandler\";\r\nimport { Range3d } from \"../geometry3d/Range\";\r\nimport { Transform } from \"../geometry3d/Transform\";\r\nimport { SolidPrimitive } from \"./SolidPrimitive\";\r\nimport { SweepContour } from \"./SweepContour\";\r\n\r\n/**\r\n * * type for a function argument taking 2 curves and returning another curve or failing with undefined.\r\n * * This is used (for instance) by `RuleSweep.mutatePartners`\r\n * @public\r\n */\r\nexport type CurvePrimitiveMutator = (primitiveA: CurvePrimitive, primitiveB: CurvePrimitive) => CurvePrimitive | undefined;\r\n/**\r\n * A ruled sweep (surface) is a collection of 2 or more contours.\r\n * * All contours must have identical number and type of geometry. (paths, loops, parity regions, lines, arcs, other curves)\r\n * @public\r\n */\r\nexport class RuledSweep extends SolidPrimitive {\r\n /** String name for schema properties */\r\n public readonly solidPrimitiveType = \"ruledSweep\";\r\n\r\n private _contours: SweepContour[];\r\n private constructor(contours: SweepContour[], capped: boolean) {\r\n super(capped);\r\n this._contours = contours;\r\n }\r\n /**\r\n * Create a ruled sweep from an array of contours.\r\n * * the contours are CAPTURED (not cloned)\r\n */\r\n public static create(contours: CurveCollection[], capped: boolean): RuledSweep | undefined {\r\n const sweepContours = [];\r\n for (const contour of contours) {\r\n const sweepable = SweepContour.createForLinearSweep(contour);\r\n if (sweepable === undefined) return undefined;\r\n sweepContours.push(sweepable);\r\n }\r\n return new RuledSweep(sweepContours, capped);\r\n }\r\n /** Return a reference to the array of SweepContour. */\r\n public sweepContoursRef(): SweepContour[] { return this._contours; }\r\n /** Return clones of all the sweep contours\r\n * * See also cloneContours, which returns the spatial contours without their local coordinate system definitions)\r\n */\r\n public cloneSweepContours(): SweepContour[] {\r\n const result = [];\r\n for (const sweepable of this._contours) {\r\n result.push(sweepable.clone());\r\n }\r\n return result;\r\n }\r\n /** Return clones of all the contours\r\n * * See also cloneContours, which returns the contours in their local coordinate systems\r\n */\r\n public cloneContours(): CurveCollection[] {\r\n const result = [];\r\n for (const sweepable of this._contours) {\r\n result.push(sweepable.curves.clone() as CurveCollection);\r\n }\r\n return result;\r\n }\r\n /** Return a deep clone */\r\n public clone(): RuledSweep {\r\n return new RuledSweep(this.cloneSweepContours(), this.capped);\r\n }\r\n /** Transform all contours in place. */\r\n public tryTransformInPlace(transform: Transform): boolean {\r\n if (transform.matrix.isSingular())\r\n return false;\r\n for (const contour of this._contours) {\r\n contour.tryTransformInPlace(transform);\r\n }\r\n return true;\r\n }\r\n /** Return a cloned transform. */\r\n public cloneTransformed(transform: Transform): RuledSweep {\r\n const result = this.clone();\r\n result.tryTransformInPlace(transform);\r\n return result;\r\n }\r\n /** Return a coordinate frame (right handed unit vectors)\r\n * * origin on base contour\r\n * * x, y directions from base contour.\r\n * * z direction perpendicular\r\n */\r\n public getConstructiveFrame(): Transform | undefined {\r\n if (this._contours.length === 0) return undefined;\r\n return this._contours[0].localToWorld.cloneRigid();\r\n }\r\n /** Test if `other` is an instance of a `RuledSweep` */\r\n public isSameGeometryClass(other: any): boolean { return other instanceof RuledSweep; }\r\n /** test same contour geometry and capping. */\r\n public override isAlmostEqual(other: GeometryQuery): boolean {\r\n if (other instanceof RuledSweep) {\r\n if (this.capped !== other.capped) return false;\r\n if (this._contours.length !== other._contours.length) return false;\r\n for (let i = 0; i < this._contours.length; i++) {\r\n if (!this._contours[i].isAlmostEqual(other._contours[i]))\r\n return false;\r\n }\r\n return true;\r\n }\r\n return false;\r\n }\r\n /** dispatch to strongly typed `handler.handleRuledSweep(this)` */\r\n public dispatchToGeometryHandler(handler: GeometryHandler): any {\r\n return handler.handleRuledSweep(this);\r\n }\r\n /**\r\n * Return the section curves at a fraction of the sweep\r\n * @param vFraction fractional position along the sweep direction\r\n */\r\n public constantVSection(vFraction: number): CurveCollection | undefined {\r\n const numSection = this._contours.length;\r\n if (numSection < 2)\r\n return undefined;\r\n const q = vFraction * numSection;\r\n let section0 = 0;\r\n if (vFraction >= 1.0)\r\n section0 = numSection - 1;\r\n else\r\n section0 = Math.floor(q);\r\n if (section0 + 1 >= numSection)\r\n section0 = numSection - 2;\r\n const section1 = section0 + 1;\r\n const localFraction = Geometry.clampToStartEnd(q - section0, 0, 1);\r\n return RuledSweep.mutatePartners(this._contours[section0].curves, this._contours[section1].curves,\r\n (primitive0: CurvePrimitive, primitive1: CurvePrimitive): CurvePrimitive | undefined => {\r\n const newPrimitive = ConstructCurveBetweenCurves.interpolateBetween(primitive0, localFraction, primitive1);\r\n if (newPrimitive instanceof CurvePrimitive) return newPrimitive;\r\n return undefined;\r\n });\r\n }\r\n /** Pass each contour to `extendRange` */\r\n public extendRange(rangeToExtend: Range3d, transform?: Transform): void {\r\n for (const contour of this._contours)\r\n contour.curves.extendRange(rangeToExtend, transform);\r\n }\r\n\r\n /** Construct a CurveCollection with the same structure as collectionA and collectionB, with primitives constructed by the caller-supplied primitiveMutator function.\r\n * @returns Returns undefined if there is any type mismatch between the two collections.\r\n */\r\n public static mutatePartners(collectionA: CurveCollection, collectionB: CurveCollection, primitiveMutator: CurvePrimitiveMutator): CurveCollection | undefined {\r\n if (!collectionA.isSameGeometryClass(collectionB))\r\n return undefined;\r\n if (collectionA instanceof CurveChain && collectionB instanceof CurveChain) {\r\n const chainA = collectionA;\r\n const chainB = collectionB;\r\n const chainC = chainA.cloneEmptyPeer() as CurveChain;\r\n const childrenA = chainA.children;\r\n const childrenB = chainB.children;\r\n if (childrenA.length !== childrenB.length)\r\n return undefined;\r\n for (let i = 0; i < childrenA.length; i++) {\r\n const newChild = primitiveMutator(childrenA[i], childrenB[i]);\r\n if (!newChild)\r\n return undefined;\r\n chainC.children.push(newChild);\r\n }\r\n return chainC;\r\n } else if (collectionA instanceof CurveCollection && collectionB instanceof CurveCollection) {\r\n const collectionC = collectionA.cloneEmptyPeer();\r\n const childrenA = collectionA.children;\r\n const childrenB = collectionB.children;\r\n const childrenC = collectionC.children;\r\n if (childrenA === undefined || childrenB === undefined || childrenC === undefined || childrenA.length !== childrenB.length)\r\n return undefined;\r\n for (let i = 0; i < childrenA.length; i++) {\r\n const childA = childrenA[i];\r\n const childB = childrenB[i];\r\n if (childA instanceof CurvePrimitive && childB instanceof CurvePrimitive) {\r\n const newPrimitive = primitiveMutator(childA, childB);\r\n if (!newPrimitive)\r\n return undefined;\r\n childrenC.push(newPrimitive);\r\n } else if (childA instanceof CurveCollection && childB instanceof CurveCollection) {\r\n const newChild = this.mutatePartners(childA, childB, primitiveMutator);\r\n if (!newChild)\r\n return undefined;\r\n if (newChild instanceof CurveCollection)\r\n childrenC.push(newChild);\r\n }\r\n }\r\n return collectionC;\r\n }\r\n return undefined;\r\n }\r\n /**\r\n * Return true if this is a closed volume, as observed by\r\n * * cap flag\r\n * identical first and last contours.\r\n */\r\n public get isClosedVolume(): boolean {\r\n const n = this._contours.length;\r\n return n > 1 && (this.capped || this._contours[0].isAlmostEqual(this._contours[n - 1]));\r\n }\r\n\r\n}\r\n"]}
1
+ {"version":3,"file":"RuledSweep.js","sourceRoot":"","sources":["../../../src/solid/RuledSweep.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Solid\r\n */\r\n\r\nimport { ConstructCurveBetweenCurves } from \"../curve/ConstructCurveBetweenCurves\";\r\nimport { CurveChain, CurveCollection } from \"../curve/CurveCollection\";\r\nimport { CurvePrimitive } from \"../curve/CurvePrimitive\";\r\nimport { GeometryQuery } from \"../curve/GeometryQuery\";\r\nimport { Geometry } from \"../Geometry\";\r\nimport { GeometryHandler } from \"../geometry3d/GeometryHandler\";\r\nimport { Range3d } from \"../geometry3d/Range\";\r\nimport { Transform } from \"../geometry3d/Transform\";\r\nimport { SolidPrimitive } from \"./SolidPrimitive\";\r\nimport { SweepContour } from \"./SweepContour\";\r\n\r\n/**\r\n * * type for a function argument taking 2 curves and returning another curve or failing with undefined.\r\n * * This is used (for instance) by `RuleSweep.mutatePartners`\r\n * @public\r\n */\r\nexport type CurvePrimitiveMutator = (primitiveA: CurvePrimitive, primitiveB: CurvePrimitive) => CurvePrimitive | undefined;\r\n/**\r\n * A ruled sweep (surface) is a collection of 2 or more contours.\r\n * * All contours must have identical number and type of geometry. (paths, loops, parity regions, lines, arcs, other curves)\r\n * @public\r\n */\r\nexport class RuledSweep extends SolidPrimitive {\r\n /** String name for schema properties */\r\n public readonly solidPrimitiveType = \"ruledSweep\";\r\n\r\n private _contours: SweepContour[];\r\n private constructor(contours: SweepContour[], capped: boolean) {\r\n super(capped);\r\n this._contours = contours;\r\n }\r\n /**\r\n * Create a ruled sweep from an array of contours.\r\n * * the contours are CAPTURED (not cloned)\r\n */\r\n public static create(contours: CurveCollection[], capped: boolean): RuledSweep | undefined {\r\n const sweepContours = [];\r\n for (const contour of contours) {\r\n const sweepable = SweepContour.createForLinearSweep(contour);\r\n if (sweepable === undefined) return undefined;\r\n sweepContours.push(sweepable);\r\n }\r\n return new RuledSweep(sweepContours, capped);\r\n }\r\n /** Return a reference to the array of SweepContour. */\r\n public sweepContoursRef(): SweepContour[] { return this._contours; }\r\n /** Return clones of all the sweep contours\r\n * * See also cloneContours, which returns the spatial contours without their local coordinate system definitions)\r\n */\r\n public cloneSweepContours(): SweepContour[] {\r\n const result = [];\r\n for (const sweepable of this._contours) {\r\n result.push(sweepable.clone());\r\n }\r\n return result;\r\n }\r\n /** Return clones of all the contours\r\n * * See also cloneContours, which returns the contours in their local coordinate systems\r\n */\r\n public cloneContours(): CurveCollection[] {\r\n const result = [];\r\n for (const sweepable of this._contours) {\r\n result.push(sweepable.curves.clone());\r\n }\r\n return result;\r\n }\r\n /** Return a deep clone */\r\n public clone(): RuledSweep {\r\n return new RuledSweep(this.cloneSweepContours(), this.capped);\r\n }\r\n /** Transform all contours in place. */\r\n public tryTransformInPlace(transform: Transform): boolean {\r\n if (transform.matrix.isSingular())\r\n return false;\r\n for (const contour of this._contours) {\r\n contour.tryTransformInPlace(transform);\r\n }\r\n return true;\r\n }\r\n /** Return a cloned transform. */\r\n public cloneTransformed(transform: Transform): RuledSweep {\r\n const result = this.clone();\r\n result.tryTransformInPlace(transform);\r\n return result;\r\n }\r\n /** Return a coordinate frame (right handed unit vectors)\r\n * * origin on base contour\r\n * * x, y directions from base contour.\r\n * * z direction perpendicular\r\n */\r\n public getConstructiveFrame(): Transform | undefined {\r\n if (this._contours.length === 0) return undefined;\r\n return this._contours[0].localToWorld.cloneRigid();\r\n }\r\n /** Test if `other` is an instance of a `RuledSweep` */\r\n public isSameGeometryClass(other: any): boolean { return other instanceof RuledSweep; }\r\n /** test same contour geometry and capping. */\r\n public override isAlmostEqual(other: GeometryQuery): boolean {\r\n if (other instanceof RuledSweep) {\r\n if (this.capped !== other.capped) return false;\r\n if (this._contours.length !== other._contours.length) return false;\r\n for (let i = 0; i < this._contours.length; i++) {\r\n if (!this._contours[i].isAlmostEqual(other._contours[i]))\r\n return false;\r\n }\r\n return true;\r\n }\r\n return false;\r\n }\r\n /** dispatch to strongly typed `handler.handleRuledSweep(this)` */\r\n public dispatchToGeometryHandler(handler: GeometryHandler): any {\r\n return handler.handleRuledSweep(this);\r\n }\r\n /**\r\n * Return the section curves at a fraction of the sweep\r\n * @param vFraction fractional position along the sweep direction\r\n */\r\n public constantVSection(vFraction: number): CurveCollection | undefined {\r\n const numSection = this._contours.length;\r\n if (numSection < 2)\r\n return undefined;\r\n const q = vFraction * numSection;\r\n let section0 = 0;\r\n if (vFraction >= 1.0)\r\n section0 = numSection - 1;\r\n else\r\n section0 = Math.floor(q);\r\n if (section0 + 1 >= numSection)\r\n section0 = numSection - 2;\r\n const section1 = section0 + 1;\r\n const localFraction = Geometry.clampToStartEnd(q - section0, 0, 1);\r\n return RuledSweep.mutatePartners(this._contours[section0].curves, this._contours[section1].curves,\r\n (primitive0: CurvePrimitive, primitive1: CurvePrimitive): CurvePrimitive | undefined => {\r\n const newPrimitive = ConstructCurveBetweenCurves.interpolateBetween(primitive0, localFraction, primitive1);\r\n if (newPrimitive instanceof CurvePrimitive) return newPrimitive;\r\n return undefined;\r\n });\r\n }\r\n /** Pass each contour to `extendRange` */\r\n public extendRange(rangeToExtend: Range3d, transform?: Transform): void {\r\n for (const contour of this._contours)\r\n contour.curves.extendRange(rangeToExtend, transform);\r\n }\r\n\r\n /** Construct a CurveCollection with the same structure as collectionA and collectionB, with primitives constructed by the caller-supplied primitiveMutator function.\r\n * @returns Returns undefined if there is any type mismatch between the two collections.\r\n */\r\n public static mutatePartners(collectionA: CurveCollection, collectionB: CurveCollection, primitiveMutator: CurvePrimitiveMutator): CurveCollection | undefined {\r\n if (!collectionA.isSameGeometryClass(collectionB))\r\n return undefined;\r\n if (collectionA instanceof CurveChain && collectionB instanceof CurveChain) {\r\n const chainA = collectionA;\r\n const chainB = collectionB;\r\n const chainC = chainA.cloneEmptyPeer() as CurveChain;\r\n const childrenA = chainA.children;\r\n const childrenB = chainB.children;\r\n if (childrenA.length !== childrenB.length)\r\n return undefined;\r\n for (let i = 0; i < childrenA.length; i++) {\r\n const newChild = primitiveMutator(childrenA[i], childrenB[i]);\r\n if (!newChild)\r\n return undefined;\r\n chainC.children.push(newChild);\r\n }\r\n return chainC;\r\n } else if (collectionA instanceof CurveCollection && collectionB instanceof CurveCollection) {\r\n const collectionC = collectionA.cloneEmptyPeer();\r\n const childrenA = collectionA.children;\r\n const childrenB = collectionB.children;\r\n const childrenC = collectionC.children;\r\n if (childrenA === undefined || childrenB === undefined || childrenC === undefined || childrenA.length !== childrenB.length)\r\n return undefined;\r\n for (let i = 0; i < childrenA.length; i++) {\r\n const childA = childrenA[i];\r\n const childB = childrenB[i];\r\n if (childA instanceof CurvePrimitive && childB instanceof CurvePrimitive) {\r\n const newPrimitive = primitiveMutator(childA, childB);\r\n if (!newPrimitive)\r\n return undefined;\r\n childrenC.push(newPrimitive);\r\n } else if (childA instanceof CurveCollection && childB instanceof CurveCollection) {\r\n const newChild = this.mutatePartners(childA, childB, primitiveMutator);\r\n if (!newChild)\r\n return undefined;\r\n if (newChild instanceof CurveCollection)\r\n childrenC.push(newChild);\r\n }\r\n }\r\n return collectionC;\r\n }\r\n return undefined;\r\n }\r\n /**\r\n * Return true if this is a closed volume, as observed by\r\n * * cap flag\r\n * identical first and last contours.\r\n */\r\n public get isClosedVolume(): boolean {\r\n const n = this._contours.length;\r\n return n > 1 && (this.capped || this._contours[0].isAlmostEqual(this._contours[n - 1]));\r\n }\r\n\r\n}\r\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"SweepContour.js","sourceRoot":"","sources":["../../../src/solid/SweepContour.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Solid\r\n */\r\n\r\nimport { ClipPlane } from \"../clipping/ClipPlane\";\r\nimport { ConvexClipPlaneSet } from \"../clipping/ConvexClipPlaneSet\";\r\nimport { UnionOfConvexClipPlaneSets } from \"../clipping/UnionOfConvexClipPlaneSets\";\r\nimport { AnyCurve } from \"../curve/CurveChain\";\r\nimport { CurveCollection } from \"../curve/CurveCollection\";\r\nimport { LineString3d } from \"../curve/LineString3d\";\r\nimport { Loop } from \"../curve/Loop\";\r\nimport { ParityRegion } from \"../curve/ParityRegion\";\r\nimport { RegionOps } from \"../curve/RegionOps\";\r\nimport { StrokeOptions } from \"../curve/StrokeOptions\";\r\nimport { FrameBuilder } from \"../geometry3d/FrameBuilder\";\r\nimport { Point3d, Vector3d } from \"../geometry3d/Point3dVector3d\";\r\nimport { PolygonOps } from \"../geometry3d/PolygonOps\";\r\nimport { Ray3d } from \"../geometry3d/Ray3d\";\r\nimport { Transform } from \"../geometry3d/Transform\";\r\nimport { IndexedPolyface } from \"../polyface/Polyface\";\r\nimport { PolyfaceBuilder } from \"../polyface/PolyfaceBuilder\";\r\nimport { HalfEdgeGraphSearch } from \"../topology/HalfEdgeGraphSearch\";\r\nimport { MultiLineStringDataVariant, Triangulator } from \"../topology/Triangulation\";\r\n\r\n/**\r\n * Sweepable contour with Transform for local to world interaction.\r\n * * The surface/solid classes `LinearSweep`, `RotationalSweep`, `RuledSweep` use this for their swept contours.\r\n * @public\r\n */\r\nexport class SweepContour {\r\n /** The underlying curve collection, in its world coordinates position. */\r\n public curves: CurveCollection;\r\n /** coordinate frame that in which the curves are all in the xy plane. */\r\n public localToWorld: Transform;\r\n /** Axis used only in rotational case. */\r\n public axis: Ray3d | undefined;\r\n\r\n private constructor(contour: CurveCollection, map: Transform, axis: Ray3d | undefined) {\r\n this.curves = contour;\r\n this.localToWorld = map;\r\n this.axis = axis;\r\n }\r\n /** Create for linear sweep.\r\n * * The optional default normal may be useful for guiding coordinate frame setup.\r\n * * the contour is CAPTURED.\r\n */\r\n public static createForLinearSweep(contour: CurveCollection, defaultNormal?: Vector3d): SweepContour | undefined {\r\n const localToWorld = FrameBuilder.createRightHandedFrame(defaultNormal, contour);\r\n if (localToWorld) {\r\n return new SweepContour(contour, localToWorld, undefined);\r\n }\r\n return undefined;\r\n }\r\n\r\n /** Create for linear sweep.\r\n * * The optional default normal may be useful for guiding coordinate frame setup.\r\n * * the points are captured into linestrings and Loops as needed.\r\n */\r\n public static createForPolygon(points: MultiLineStringDataVariant, defaultNormal?: Vector3d): SweepContour | undefined {\r\n const localToWorld = FrameBuilder.createRightHandedFrame(defaultNormal, points);\r\n if (localToWorld) {\r\n if (defaultNormal !== undefined) {\r\n if (localToWorld.matrix.dotColumnZ(defaultNormal))\r\n localToWorld.matrix.scaleColumnsInPlace(1.0, -1.0, -1.0);\r\n }\r\n const linestrings = LineString3d.createArrayOfLineString3d(points);\r\n const loops = [];\r\n for (const ls of linestrings) {\r\n ls.addClosurePoint();\r\n loops.push(Loop.create(ls));\r\n }\r\n if (loops.length === 1) {\r\n return new SweepContour(loops[0], localToWorld, undefined);\r\n } else if (loops.length > 1) {\r\n return new SweepContour(ParityRegion.createLoops(loops), localToWorld, undefined);\r\n }\r\n }\r\n return undefined;\r\n }\r\n\r\n /** Create for rotational sweep.\r\n * * The axis ray is retained.\r\n * * the contour is CAPTURED.\r\n */\r\n public static createForRotation(contour: CurveCollection, axis: Ray3d): SweepContour | undefined {\r\n // createRightHandedFrame -- the axis is a last-gasp resolver for in-plane vectors.\r\n const localToWorld = FrameBuilder.createRightHandedFrame(undefined, contour, axis);\r\n if (localToWorld) {\r\n return new SweepContour(contour, localToWorld, axis.clone());\r\n }\r\n return undefined;\r\n }\r\n /** Return (Reference to) the curves */\r\n public getCurves(): CurveCollection { return this.curves; }\r\n /** Apply `transform` to the curves, axis.\r\n * * The local to world frame is reconstructed for the transformed curves.\r\n */\r\n public tryTransformInPlace(transform: Transform): boolean {\r\n if (this.curves.tryTransformInPlace(transform)) {\r\n if (this.axis)\r\n this.axis.transformInPlace(transform);\r\n\r\n const localToWorld = this.axis !== undefined\r\n ? FrameBuilder.createRightHandedFrame(undefined, this.curves, this.axis)\r\n : FrameBuilder.createRightHandedFrame(undefined, this.curves);\r\n if (localToWorld) {\r\n this.localToWorld.setFrom(localToWorld);\r\n return true;\r\n }\r\n }\r\n return false;\r\n }\r\n /** Return a deep clone. */\r\n public clone(): SweepContour {\r\n return new SweepContour(this.curves.clone() as CurveCollection, this.localToWorld.clone(), this.axis);\r\n }\r\n /** Return a transformed clone. */\r\n public cloneTransformed(transform: Transform): SweepContour | undefined {\r\n const newContour = this.clone();\r\n if (newContour.tryTransformInPlace(transform))\r\n return newContour;\r\n return undefined;\r\n }\r\n /** Test for near equality of cures and local frame. */\r\n public isAlmostEqual(other: any): boolean {\r\n if (other instanceof SweepContour) {\r\n return this.curves.isAlmostEqual(other.curves) && this.localToWorld.isAlmostEqual(other.localToWorld);\r\n }\r\n return false;\r\n }\r\n\r\n private _xyStrokes?: AnyCurve;\r\n private _facets?: IndexedPolyface;\r\n public get xyStrokes(): AnyCurve | undefined { return this._xyStrokes;}\r\n /**\r\n * build the (cached) internal facets.\r\n * @param options options for stroking the curves.\r\n */\r\n public buildFacets(options: StrokeOptions | undefined): void {\r\n if (!this._facets) {\r\n if (this.curves instanceof Loop) {\r\n this._xyStrokes = this.curves.cloneStroked(options);\r\n if (this._xyStrokes instanceof Loop && this._xyStrokes.children.length === 1) {\r\n const children = this._xyStrokes.children;\r\n const linestring = children[0] as LineString3d;\r\n const points = linestring.points;\r\n this.localToWorld.multiplyInversePoint3dArrayInPlace(points);\r\n if (PolygonOps.sumTriangleAreasXY(points) < 0)\r\n points.reverse();\r\n const graph = Triangulator.createTriangulatedGraphFromSingleLoop(points);\r\n if (graph) {\r\n Triangulator.flipTriangles(graph);\r\n const unflippedPoly = PolyfaceBuilder.graphToPolyface(graph, options);\r\n this._facets = unflippedPoly;\r\n this._facets.tryTransformInPlace(this.localToWorld);\r\n }\r\n }\r\n } else if (this.curves instanceof ParityRegion) {\r\n this._xyStrokes = this.curves.cloneStroked(options);\r\n if (this._xyStrokes instanceof (ParityRegion)) {\r\n const worldToLocal = this.localToWorld.inverse()!;\r\n this._xyStrokes.tryTransformInPlace(worldToLocal);\r\n const strokes = [];\r\n for (const childLoop of this._xyStrokes.children) {\r\n const loopCurves = childLoop.children;\r\n if (loopCurves.length === 1) {\r\n const c = loopCurves[0];\r\n if (c instanceof LineString3d)\r\n strokes.push(c.packedPoints);\r\n }\r\n }\r\n const numLoops = strokes.length;\r\n /** Try the earcut algorithm first -- lots less machinery, but can't handle any form of overlap */\r\n const graph = Triangulator.createTriangulatedGraphFromLoops(strokes);\r\n if (graph && HalfEdgeGraphSearch.isTriangulatedCCW(graph, true, numLoops - 1)) {\r\n Triangulator.flipTriangles(graph);\r\n const unflippedPoly = PolyfaceBuilder.graphToPolyface(graph, options);\r\n this._facets = unflippedPoly;\r\n this._facets.tryTransformInPlace(this.localToWorld);\r\n } else {\r\n // earcut failed. Restart with full merge and parity analysis.\r\n const polyface = RegionOps.polygonXYAreaUnionLoopsToPolyface(strokes, [], true);\r\n if (polyface) {\r\n this._facets = polyface as IndexedPolyface;\r\n this._facets.tryTransformInPlace(this.localToWorld);\r\n }\r\n }\r\n\r\n }\r\n }\r\n }\r\n }\r\n /** delete existing facets.\r\n * * This protects against PolyfaceBuilder reusing facets constructed with different options settings.\r\n */\r\n public purgeFacets() {\r\n this._facets = undefined;\r\n }\r\n\r\n /** Emit facets to a builder.\r\n * This method may cache and reuse facets over multiple calls.\r\n */\r\n public emitFacets(builder: PolyfaceBuilder, reverse: boolean, transform?: Transform) {\r\n this.buildFacets(builder.options);\r\n if (this._facets)\r\n builder.addIndexedPolyface(this._facets, reverse, transform);\r\n }\r\n\r\n /** Emit facets to a function\r\n * This method may cache and reuse facets over multiple calls.\r\n */\r\n public announceFacets(announce: (facets: IndexedPolyface) => void, options: StrokeOptions | undefined) {\r\n this.buildFacets(options);\r\n if (this._facets)\r\n announce(this._facets);\r\n }\r\n\r\n /**\r\n * Triangulate the region.\r\n * Create a UnionOfConvexClipPlaneSets that clips to the swept region.\r\n * * If sweepVector is not given, the sweep direction is perpendicular to the plane of the contour.\r\n * * If sweepVector is given, it is the sweep direction and does not have to be perpendicular to the contour.\r\n * * cap0 and cap1 indicate construction of clip planes parallel to the contour plane.\r\n * * If cap1 is true, the cap plane is at `anyPointOnPlane + sweepVector`. That is, the sweep vector indicates both direction and distance.\r\n * * caps are NOT created of sweepVector is not given.\r\n */\r\n public sweepToUnionOfConvexClipPlaneSets(sweepVector?: Vector3d, cap0: boolean = false, cap1: boolean = false): UnionOfConvexClipPlaneSets | undefined {\r\n const builder = PolyfaceBuilder.create();\r\n // It's a trip around the barn, but it's easy to make a polyface and scan it . . .\r\n if (!sweepVector)\r\n cap0 = cap1 = false;\r\n this.buildFacets(builder.options);\r\n if (sweepVector === undefined)\r\n sweepVector = this.localToWorld.matrix.columnZ();\r\n const zVector = this.localToWorld.matrix.columnZ();\r\n const facets = this._facets;\r\n const point0 = Point3d.create();\r\n const point1 = Point3d.create();\r\n if (facets) {\r\n const plane0Origin = this.localToWorld.getOrigin();\r\n const plane1Origin = plane0Origin.plus(sweepVector);\r\n const inwardNormal0 = zVector.clone();\r\n const inwardNormal1 = zVector.negate();\r\n\r\n const result = UnionOfConvexClipPlaneSets.createEmpty();\r\n const visitor = facets.createVisitor(1);\r\n for (visitor.reset(); visitor.moveToNextFacet();) {\r\n const numEdges = visitor.point.length - 1;\r\n const clipper = ConvexClipPlaneSet.createEmpty();\r\n for (let i = 0; i < numEdges; i++) {\r\n visitor.point.getPoint3dAtUncheckedPointIndex(i, point0);\r\n visitor.point.getPoint3dAtUncheckedPointIndex(i + 1, point1);\r\n const plane = ClipPlane.createEdgeAndUpVector(point1, point0, sweepVector);\r\n const visible = visitor.edgeVisible[i];\r\n plane?.setFlags(!visible, !visible);\r\n clipper.addPlaneToConvexSet(plane);\r\n }\r\n if (cap0)\r\n clipper.addPlaneToConvexSet(ClipPlane.createNormalAndPoint(inwardNormal0, plane0Origin));\r\n if (cap1)\r\n clipper.addPlaneToConvexSet(ClipPlane.createNormalAndPoint(inwardNormal1, plane1Origin));\r\n result.addConvexSet(clipper);\r\n }\r\n return result;\r\n }\r\n return undefined;\r\n }\r\n}\r\n"]}
1
+ {"version":3,"file":"SweepContour.js","sourceRoot":"","sources":["../../../src/solid/SweepContour.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Solid\r\n */\r\n\r\nimport { ClipPlane } from \"../clipping/ClipPlane\";\r\nimport { ConvexClipPlaneSet } from \"../clipping/ConvexClipPlaneSet\";\r\nimport { UnionOfConvexClipPlaneSets } from \"../clipping/UnionOfConvexClipPlaneSets\";\r\nimport { AnyCurve } from \"../curve/CurveChain\";\r\nimport { CurveCollection } from \"../curve/CurveCollection\";\r\nimport { LineString3d } from \"../curve/LineString3d\";\r\nimport { Loop } from \"../curve/Loop\";\r\nimport { ParityRegion } from \"../curve/ParityRegion\";\r\nimport { RegionOps } from \"../curve/RegionOps\";\r\nimport { StrokeOptions } from \"../curve/StrokeOptions\";\r\nimport { FrameBuilder } from \"../geometry3d/FrameBuilder\";\r\nimport { Point3d, Vector3d } from \"../geometry3d/Point3dVector3d\";\r\nimport { PolygonOps } from \"../geometry3d/PolygonOps\";\r\nimport { Ray3d } from \"../geometry3d/Ray3d\";\r\nimport { Transform } from \"../geometry3d/Transform\";\r\nimport { IndexedPolyface } from \"../polyface/Polyface\";\r\nimport { PolyfaceBuilder } from \"../polyface/PolyfaceBuilder\";\r\nimport { HalfEdgeGraphSearch } from \"../topology/HalfEdgeGraphSearch\";\r\nimport { MultiLineStringDataVariant, Triangulator } from \"../topology/Triangulation\";\r\n\r\n/**\r\n * Sweepable contour with Transform for local to world interaction.\r\n * * The surface/solid classes `LinearSweep`, `RotationalSweep`, `RuledSweep` use this for their swept contours.\r\n * @public\r\n */\r\nexport class SweepContour {\r\n /** The underlying curve collection, in its world coordinates position. */\r\n public curves: CurveCollection;\r\n /** coordinate frame that in which the curves are all in the xy plane. */\r\n public localToWorld: Transform;\r\n /** Axis used only in rotational case. */\r\n public axis: Ray3d | undefined;\r\n\r\n private constructor(contour: CurveCollection, map: Transform, axis: Ray3d | undefined) {\r\n this.curves = contour;\r\n this.localToWorld = map;\r\n this.axis = axis;\r\n }\r\n /** Create for linear sweep.\r\n * * The optional default normal may be useful for guiding coordinate frame setup.\r\n * * the contour is CAPTURED.\r\n */\r\n public static createForLinearSweep(contour: CurveCollection, defaultNormal?: Vector3d): SweepContour | undefined {\r\n const localToWorld = FrameBuilder.createRightHandedFrame(defaultNormal, contour);\r\n if (localToWorld) {\r\n return new SweepContour(contour, localToWorld, undefined);\r\n }\r\n return undefined;\r\n }\r\n\r\n /** Create for linear sweep.\r\n * * The optional default normal may be useful for guiding coordinate frame setup.\r\n * * the points are captured into linestrings and Loops as needed.\r\n */\r\n public static createForPolygon(points: MultiLineStringDataVariant, defaultNormal?: Vector3d): SweepContour | undefined {\r\n const localToWorld = FrameBuilder.createRightHandedFrame(defaultNormal, points);\r\n if (localToWorld) {\r\n if (defaultNormal !== undefined) {\r\n if (localToWorld.matrix.dotColumnZ(defaultNormal))\r\n localToWorld.matrix.scaleColumnsInPlace(1.0, -1.0, -1.0);\r\n }\r\n const linestrings = LineString3d.createArrayOfLineString3d(points);\r\n const loops = [];\r\n for (const ls of linestrings) {\r\n ls.addClosurePoint();\r\n loops.push(Loop.create(ls));\r\n }\r\n if (loops.length === 1) {\r\n return new SweepContour(loops[0], localToWorld, undefined);\r\n } else if (loops.length > 1) {\r\n return new SweepContour(ParityRegion.createLoops(loops), localToWorld, undefined);\r\n }\r\n }\r\n return undefined;\r\n }\r\n\r\n /** Create for rotational sweep.\r\n * * The axis ray is retained.\r\n * * the contour is CAPTURED.\r\n */\r\n public static createForRotation(contour: CurveCollection, axis: Ray3d): SweepContour | undefined {\r\n // createRightHandedFrame -- the axis is a last-gasp resolver for in-plane vectors.\r\n const localToWorld = FrameBuilder.createRightHandedFrame(undefined, contour, axis);\r\n if (localToWorld) {\r\n return new SweepContour(contour, localToWorld, axis.clone());\r\n }\r\n return undefined;\r\n }\r\n /** Return (Reference to) the curves */\r\n public getCurves(): CurveCollection { return this.curves; }\r\n /** Apply `transform` to the curves, axis.\r\n * * The local to world frame is reconstructed for the transformed curves.\r\n */\r\n public tryTransformInPlace(transform: Transform): boolean {\r\n if (this.curves.tryTransformInPlace(transform)) {\r\n if (this.axis)\r\n this.axis.transformInPlace(transform);\r\n\r\n const localToWorld = this.axis !== undefined\r\n ? FrameBuilder.createRightHandedFrame(undefined, this.curves, this.axis)\r\n : FrameBuilder.createRightHandedFrame(undefined, this.curves);\r\n if (localToWorld) {\r\n this.localToWorld.setFrom(localToWorld);\r\n return true;\r\n }\r\n }\r\n return false;\r\n }\r\n /** Return a deep clone. */\r\n public clone(): SweepContour {\r\n return new SweepContour(this.curves.clone(), this.localToWorld.clone(), this.axis);\r\n }\r\n /** Return a transformed clone. */\r\n public cloneTransformed(transform: Transform): SweepContour | undefined {\r\n const newContour = this.clone();\r\n if (newContour.tryTransformInPlace(transform))\r\n return newContour;\r\n return undefined;\r\n }\r\n /** Test for near equality of cures and local frame. */\r\n public isAlmostEqual(other: any): boolean {\r\n if (other instanceof SweepContour) {\r\n return this.curves.isAlmostEqual(other.curves) && this.localToWorld.isAlmostEqual(other.localToWorld);\r\n }\r\n return false;\r\n }\r\n\r\n private _xyStrokes?: AnyCurve;\r\n private _facets?: IndexedPolyface;\r\n public get xyStrokes(): AnyCurve | undefined { return this._xyStrokes;}\r\n /**\r\n * build the (cached) internal facets.\r\n * @param options options for stroking the curves.\r\n */\r\n public buildFacets(options: StrokeOptions | undefined): void {\r\n if (!this._facets) {\r\n if (this.curves instanceof Loop) {\r\n this._xyStrokes = this.curves.cloneStroked(options);\r\n if (this._xyStrokes instanceof Loop && this._xyStrokes.children.length === 1) {\r\n const children = this._xyStrokes.children;\r\n const linestring = children[0] as LineString3d;\r\n const points = linestring.points;\r\n this.localToWorld.multiplyInversePoint3dArrayInPlace(points);\r\n if (PolygonOps.sumTriangleAreasXY(points) < 0)\r\n points.reverse();\r\n const graph = Triangulator.createTriangulatedGraphFromSingleLoop(points);\r\n if (graph) {\r\n Triangulator.flipTriangles(graph);\r\n const unflippedPoly = PolyfaceBuilder.graphToPolyface(graph, options);\r\n this._facets = unflippedPoly;\r\n this._facets.tryTransformInPlace(this.localToWorld);\r\n }\r\n }\r\n } else if (this.curves instanceof ParityRegion) {\r\n this._xyStrokes = this.curves.cloneStroked(options);\r\n if (this._xyStrokes instanceof (ParityRegion)) {\r\n const worldToLocal = this.localToWorld.inverse()!;\r\n this._xyStrokes.tryTransformInPlace(worldToLocal);\r\n const strokes = [];\r\n for (const childLoop of this._xyStrokes.children) {\r\n const loopCurves = childLoop.children;\r\n if (loopCurves.length === 1) {\r\n const c = loopCurves[0];\r\n if (c instanceof LineString3d)\r\n strokes.push(c.packedPoints);\r\n }\r\n }\r\n const numLoops = strokes.length;\r\n /** Try the earcut algorithm first -- lots less machinery, but can't handle any form of overlap */\r\n const graph = Triangulator.createTriangulatedGraphFromLoops(strokes);\r\n if (graph && HalfEdgeGraphSearch.isTriangulatedCCW(graph, true, numLoops - 1)) {\r\n Triangulator.flipTriangles(graph);\r\n const unflippedPoly = PolyfaceBuilder.graphToPolyface(graph, options);\r\n this._facets = unflippedPoly;\r\n this._facets.tryTransformInPlace(this.localToWorld);\r\n } else {\r\n // earcut failed. Restart with full merge and parity analysis.\r\n const polyface = RegionOps.polygonXYAreaUnionLoopsToPolyface(strokes, [], true);\r\n if (polyface) {\r\n this._facets = polyface as IndexedPolyface;\r\n this._facets.tryTransformInPlace(this.localToWorld);\r\n }\r\n }\r\n\r\n }\r\n }\r\n }\r\n }\r\n /** delete existing facets.\r\n * * This protects against PolyfaceBuilder reusing facets constructed with different options settings.\r\n */\r\n public purgeFacets() {\r\n this._facets = undefined;\r\n }\r\n\r\n /** Emit facets to a builder.\r\n * This method may cache and reuse facets over multiple calls.\r\n */\r\n public emitFacets(builder: PolyfaceBuilder, reverse: boolean, transform?: Transform) {\r\n this.buildFacets(builder.options);\r\n if (this._facets)\r\n builder.addIndexedPolyface(this._facets, reverse, transform);\r\n }\r\n\r\n /** Emit facets to a function\r\n * This method may cache and reuse facets over multiple calls.\r\n */\r\n public announceFacets(announce: (facets: IndexedPolyface) => void, options: StrokeOptions | undefined) {\r\n this.buildFacets(options);\r\n if (this._facets)\r\n announce(this._facets);\r\n }\r\n\r\n /**\r\n * Triangulate the region.\r\n * Create a UnionOfConvexClipPlaneSets that clips to the swept region.\r\n * * If sweepVector is not given, the sweep direction is perpendicular to the plane of the contour.\r\n * * If sweepVector is given, it is the sweep direction and does not have to be perpendicular to the contour.\r\n * * cap0 and cap1 indicate construction of clip planes parallel to the contour plane.\r\n * * If cap1 is true, the cap plane is at `anyPointOnPlane + sweepVector`. That is, the sweep vector indicates both direction and distance.\r\n * * caps are NOT created of sweepVector is not given.\r\n */\r\n public sweepToUnionOfConvexClipPlaneSets(sweepVector?: Vector3d, cap0: boolean = false, cap1: boolean = false): UnionOfConvexClipPlaneSets | undefined {\r\n const builder = PolyfaceBuilder.create();\r\n // It's a trip around the barn, but it's easy to make a polyface and scan it . . .\r\n if (!sweepVector)\r\n cap0 = cap1 = false;\r\n this.buildFacets(builder.options);\r\n if (sweepVector === undefined)\r\n sweepVector = this.localToWorld.matrix.columnZ();\r\n const zVector = this.localToWorld.matrix.columnZ();\r\n const facets = this._facets;\r\n const point0 = Point3d.create();\r\n const point1 = Point3d.create();\r\n if (facets) {\r\n const plane0Origin = this.localToWorld.getOrigin();\r\n const plane1Origin = plane0Origin.plus(sweepVector);\r\n const inwardNormal0 = zVector.clone();\r\n const inwardNormal1 = zVector.negate();\r\n\r\n const result = UnionOfConvexClipPlaneSets.createEmpty();\r\n const visitor = facets.createVisitor(1);\r\n for (visitor.reset(); visitor.moveToNextFacet();) {\r\n const numEdges = visitor.point.length - 1;\r\n const clipper = ConvexClipPlaneSet.createEmpty();\r\n for (let i = 0; i < numEdges; i++) {\r\n visitor.point.getPoint3dAtUncheckedPointIndex(i, point0);\r\n visitor.point.getPoint3dAtUncheckedPointIndex(i + 1, point1);\r\n const plane = ClipPlane.createEdgeAndUpVector(point1, point0, sweepVector);\r\n const visible = visitor.edgeVisible[i];\r\n plane?.setFlags(!visible, !visible);\r\n clipper.addPlaneToConvexSet(plane);\r\n }\r\n if (cap0)\r\n clipper.addPlaneToConvexSet(ClipPlane.createNormalAndPoint(inwardNormal0, plane0Origin));\r\n if (cap1)\r\n clipper.addPlaneToConvexSet(ClipPlane.createNormalAndPoint(inwardNormal1, plane1Origin));\r\n result.addConvexSet(clipper);\r\n }\r\n return result;\r\n }\r\n return undefined;\r\n }\r\n}\r\n"]}
@@ -1,8 +1,6 @@
1
- /** @packageDocumentation
2
- * @module Topology
3
- */
4
1
  import { LineSegment3d } from "../curve/LineSegment3d";
5
2
  import { Range3d } from "../geometry3d/Range";
3
+ import { ClusterableArray } from "../numerics/ClusterableArray";
6
4
  import { HalfEdge, HalfEdgeGraph, HalfEdgeMask } from "./Graph";
7
5
  import { MultiLineStringDataVariant } from "./Triangulation";
8
6
  export declare class GraphSplitData {
@@ -14,6 +12,18 @@ export declare class GraphSplitData {
14
12
  numA0B1: number;
15
13
  constructor();
16
14
  }
15
+ /**
16
+ * Structure for data used when sorting outbound edges "around a node"
17
+ */
18
+ export declare class VertexNeighborhoodSortData {
19
+ index: number;
20
+ radiusOfCurvature: number;
21
+ node: HalfEdge;
22
+ radians?: number;
23
+ constructor(index: number, key: number, node: HalfEdge, radians?: number);
24
+ }
25
+ /** Function signature for announcing a vertex neighborhood during sorting. */
26
+ export declare type AnnounceVertexNeighborhoodSortData = (data: VertexNeighborhoodSortData[]) => any;
17
27
  /**
18
28
  * * Assorted methods used in algorithms on HalfEdgeGraph.
19
29
  * @internal
@@ -87,6 +97,15 @@ export declare class HalfEdgeGraphOps {
87
97
  * @internal
88
98
  */
89
99
  export declare class HalfEdgeGraphMerge {
100
+ static getCommonThetaEndIndex(clusters: ClusterableArray, order: Uint32Array, kA: number, kB: number): number;
101
+ private static _announceVertexNeighborhoodFunction?;
102
+ /**
103
+ * public property setter for a function to be called with sorted edge data around a vertex.
104
+ */
105
+ static set announceVertexNeighborhoodFunction(func: AnnounceVertexNeighborhoodSortData | undefined);
106
+ private static doAnnounceVertexNeighborhood;
107
+ private static secondarySortAroundVertex;
108
+ private static curvatureSortKey;
90
109
  /** Simplest merge algorithm:
91
110
  * * collect array of (x,y,theta) at all nodes
92
111
  * * lexical sort of the array.
@@ -1 +1 @@
1
- {"version":3,"file":"Merging.d.ts","sourceRoot":"","sources":["../../../src/topology/Merging.ts"],"names":[],"mappings":"AAKA;;GAEG;AAEH,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAIvD,OAAO,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAC;AAG9C,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAGhE,OAAO,EAAE,0BAA0B,EAAgB,MAAM,iBAAiB,CAAC;AAE3E,qBAAa,cAAc;IAClB,SAAS,SAAK;IACd,mBAAmB,SAAK;IACxB,QAAQ,SAAK;IACb,SAAS,SAAK;IACd,OAAO,SAAK;IACZ,OAAO,SAAK;;CAGpB;AAED;;;GAGG;AACH,qBAAa,gBAAgB;IAE3B,iFAAiF;WACnE,gBAAgB,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,QAAQ;IAgBvD,mIAAmI;WACrH,UAAU,CAAC,KAAK,EAAE,QAAQ;IAQxC;;;;OAIG;WACW,qBAAqB,CAAC,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,GAAG,MAAM;WAOnF,UAAU,CAAC,KAAK,EAAE,aAAa,GAAG,OAAO;IAOvD,gFAAgF;WAClE,wBAAwB,CAAC,QAAQ,EAAE,aAAa,EAAE,EAAE,WAAW,EAAE,aAAa,EAAE,IAAI,EAAE,YAAY,GAAG,QAAQ,EAAE;IAwB7H;;;;;OAKG;WACW,eAAe,CAAC,KAAK,EAAE,aAAa;IAOlD;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,CAAC,8BAA8B;IAoB7C;;;;;;;;OAQG;WACW,qCAAqC,CAAC,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE,YAAY,EAAE,OAAO,GAAE,YAAyC,GAAG,MAAM;IAmBzJ;;;;;;;OAOG;WACW,wCAAwC,CAAC,KAAK,EAAE,aAAa,EAAE,OAAO,GAAE,YAAyC,GAAG,QAAQ,EAAE,GAAG,SAAS;IAiBxJ;;;;;;;OAOG;WACW,iBAAiB,CAAC,KAAK,EAAE,aAAa,EAAE,OAAO,GAAE,YAAyC,GAAG,MAAM;IASjH;;;;;OAKG;WACW,iBAAiB,CAAC,KAAK,EAAE,aAAa,EAAE,KAAK,GAAE,YAAoC,GAAG,OAAO;CAU5G;AAED;;GAEG;AACH,qBAAa,kBAAkB;IAC7B;;;;;;;OAOG;WACW,sBAAsB,CAAC,KAAK,EAAE,aAAa,EAAE,uBAAuB,CAAC,EAAE,CAAC,EAAE,EAAE,QAAQ,KAAK,MAAM;IAqG7G,OAAO,CAAC,MAAM,CAAC,+BAA+B;IAU9C,OAAO,CAAC,MAAM,CAAC,kBAAkB;IAKjC,OAAO,CAAC,MAAM,CAAC,mCAAmC;IAyBlD;;;;OAIG;WACW,sBAAsB,CAAC,KAAK,EAAE,aAAa,GAAG,cAAc;IA+C1E;;;;;;;;OAQG;WACW,qBAAqB,CAAC,YAAY,EAAE,aAAa,EAAE,GAAG,aAAa;IAUjF;;;;OAIG;WACW,mBAAmB,CAAC,MAAM,EAAE,0BAA0B,EAAE,UAAU,GAAE,OAAc,EAAE,IAAI,GAAE,YAAwC,GAAG,aAAa,GAAG,SAAS;CAiB7K"}
1
+ {"version":3,"file":"Merging.d.ts","sourceRoot":"","sources":["../../../src/topology/Merging.ts"],"names":[],"mappings":"AAUA,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAIvD,OAAO,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAC;AAC9C,OAAO,EAAE,gBAAgB,EAAE,MAAM,8BAA8B,CAAC;AAEhE,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAGhE,OAAO,EAAE,0BAA0B,EAAgB,MAAM,iBAAiB,CAAC;AAE3E,qBAAa,cAAc;IAClB,SAAS,SAAK;IACd,mBAAmB,SAAK;IACxB,QAAQ,SAAK;IACb,SAAS,SAAK;IACd,OAAO,SAAK;IACZ,OAAO,SAAK;;CAGpB;AACD;;GAEG;AACH,qBAAa,0BAA0B;IAC9B,KAAK,EAAE,MAAM,CAAC;IACd,iBAAiB,EAAE,MAAM,CAAC;IAC1B,IAAI,EAAE,QAAQ,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC;gBACL,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,OAAO,CAAC,EAAE,MAAM;CAMhF;AAED,8EAA8E;AAC9E,oBAAY,kCAAkC,GAAG,CAAC,IAAI,EAAE,0BAA0B,EAAE,KAAK,GAAG,CAAC;AAC7F;;;GAGG;AACH,qBAAa,gBAAgB;IAE3B,iFAAiF;WACnE,gBAAgB,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,QAAQ;IAgBvD,mIAAmI;WACrH,UAAU,CAAC,KAAK,EAAE,QAAQ;IAQxC;;;;OAIG;WACW,qBAAqB,CAAC,IAAI,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,EAAE,OAAO,EAAE,QAAQ,GAAG,MAAM;WAOnF,UAAU,CAAC,KAAK,EAAE,aAAa,GAAG,OAAO;IAOvD,gFAAgF;WAClE,wBAAwB,CAAC,QAAQ,EAAE,aAAa,EAAE,EAAE,WAAW,EAAE,aAAa,EAAE,IAAI,EAAE,YAAY,GAAG,QAAQ,EAAE;IAwB7H;;;;;OAKG;WACW,eAAe,CAAC,KAAK,EAAE,aAAa;IAOlD;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,CAAC,8BAA8B;IAoB7C;;;;;;;;OAQG;WACW,qCAAqC,CAAC,KAAK,EAAE,aAAa,EAAE,IAAI,EAAE,YAAY,EAAE,OAAO,GAAE,YAAyC,GAAG,MAAM;IAmBzJ;;;;;;;OAOG;WACW,wCAAwC,CAAC,KAAK,EAAE,aAAa,EAAE,OAAO,GAAE,YAAyC,GAAG,QAAQ,EAAE,GAAG,SAAS;IAiBxJ;;;;;;;OAOG;WACW,iBAAiB,CAAC,KAAK,EAAE,aAAa,EAAE,OAAO,GAAE,YAAyC,GAAG,MAAM;IASjH;;;;;OAKG;WACW,iBAAiB,CAAC,KAAK,EAAE,aAAa,EAAE,KAAK,GAAE,YAAoC,GAAG,OAAO;CAU5G;AAED;;GAEG;AACH,qBAAa,kBAAkB;WAGf,sBAAsB,CAAC,QAAQ,EAAE,gBAAgB,EAAE,KAAK,EAAE,WAAW,EAAE,EAAE,EAAE,MAAM,EAAE,EAAE,EAAE,MAAM,GAAG,MAAM;IAYpH,OAAO,CAAC,MAAM,CAAC,mCAAmC,CAAC,CAAqC;IAC1F;;OAEG;IACD,WAAkB,kCAAkC,CAAC,IAAI,EAAE,kCAAkC,GAAG,SAAS,EAAsD;IAC/J,OAAO,CAAC,MAAM,CAAC,4BAA4B;IAqB3C,OAAO,CAAC,MAAM,CAAC,yBAAyB;IAwBxC,OAAO,CAAC,MAAM,CAAC,gBAAgB;IAc/B;;;;;;;OAOG;WACW,sBAAsB,CAAC,KAAK,EAAE,aAAa,EAAE,uBAAuB,CAAC,EAAE,CAAC,EAAE,EAAE,QAAQ,KAAK,MAAM;IA8G7G,OAAO,CAAC,MAAM,CAAC,+BAA+B;IAU9C,OAAO,CAAC,MAAM,CAAC,kBAAkB;IAKjC,OAAO,CAAC,MAAM,CAAC,mCAAmC;IA0BlD;;;;OAIG;WACW,sBAAsB,CAAC,KAAK,EAAE,aAAa,GAAG,cAAc;IA+C1E;;;;;;;;OAQG;WACW,qBAAqB,CAAC,YAAY,EAAE,aAAa,EAAE,GAAG,aAAa;IAUjF;;;;OAIG;WACW,mBAAmB,CAAC,MAAM,EAAE,0BAA0B,EAAE,UAAU,GAAE,OAAc,EAAE,IAAI,GAAE,YAAwC,GAAG,aAAa,GAAG,SAAS;CAiB7K"}
@@ -22,6 +22,17 @@ export class GraphSplitData {
22
22
  this.numA0B1 = 0;
23
23
  }
24
24
  }
25
+ /**
26
+ * Structure for data used when sorting outbound edges "around a node"
27
+ */
28
+ export class VertexNeighborhoodSortData {
29
+ constructor(index, key, node, radians) {
30
+ this.index = index;
31
+ this.radiusOfCurvature = key;
32
+ this.node = node;
33
+ this.radians = radians;
34
+ }
35
+ }
25
36
  /**
26
37
  * * Assorted methods used in algorithms on HalfEdgeGraph.
27
38
  * @internal
@@ -209,6 +220,81 @@ export class HalfEdgeGraphOps {
209
220
  * @internal
210
221
  */
211
222
  export class HalfEdgeGraphMerge {
223
+ // return k2 <= kB such that stored angles (at extra data index 0 !) kA<=k<kC match.
224
+ // * Note that the usual case (when angle at k0 is not repeated) is k0+1 === kC
225
+ static getCommonThetaEndIndex(clusters, order, kA, kB) {
226
+ let kC = kA + 1;
227
+ const thetaA = clusters.getExtraData(order[kA], 0);
228
+ while (kC < kB) {
229
+ const thetaB = clusters.getExtraData(order[kC], 0);
230
+ if (!Angle.isAlmostEqualRadiansAllowPeriodShift(thetaA, thetaB)) {
231
+ return kC;
232
+ }
233
+ kC++;
234
+ }
235
+ return kC;
236
+ }
237
+ /**
238
+ * public property setter for a function to be called with sorted edge data around a vertex.
239
+ */
240
+ static set announceVertexNeighborhoodFunction(func) { this._announceVertexNeighborhoodFunction = func; }
241
+ static doAnnounceVertexNeighborhood(clusters, order, allNodes, k0, k1) {
242
+ if (this._announceVertexNeighborhoodFunction) {
243
+ const sortData = [];
244
+ // build and share the entire vertex order
245
+ for (let k = k0; k < k1; k++) {
246
+ const index = clusters.getExtraData(order[k], 1);
247
+ const theta = clusters.getExtraData(order[k], 0);
248
+ const node = allNodes[index];
249
+ const signedDistance = this.curvatureSortKey(node);
250
+ sortData.push(new VertexNeighborhoodSortData(order[k], signedDistance, node, theta));
251
+ }
252
+ this._announceVertexNeighborhoodFunction(sortData);
253
+ }
254
+ }
255
+ // assumptions about cluster array:
256
+ // * data order is: x,y,theta, nodeIndex
257
+ // * theta and nodeIndex are the "extra" data.
258
+ // * only want to do anything here when curves are present.
259
+ // * k0<=k<k1 are around a vertex
260
+ // * These are sorted by theta.
261
+ static secondarySortAroundVertex(clusters, order, allNodes, k0, k1) {
262
+ const sortData = [];
263
+ for (let k = k0; k < k1;) {
264
+ const kB = this.getCommonThetaEndIndex(clusters, order, k, k1);
265
+ if (k + 1 < kB) {
266
+ sortData.length = 0;
267
+ for (let kA = k; kA < kB; kA++) {
268
+ const index = clusters.getExtraData(order[kA], 1);
269
+ const node = allNodes[index];
270
+ const signedDistance = this.curvatureSortKey(node);
271
+ sortData.push(new VertexNeighborhoodSortData(order[kA], signedDistance, node));
272
+ }
273
+ sortData.sort((a, b) => (a.radiusOfCurvature - b.radiusOfCurvature));
274
+ for (let i = 0; i < sortData.length; i++) {
275
+ order[k + i] = sortData[i].index;
276
+ }
277
+ }
278
+ k = kB;
279
+ }
280
+ }
281
+ // Return the sort key for sorting by curvature.
282
+ // This is the signed distance from the curve to center of curvature.
283
+ // This should need to be upgraded to account for higher derivatives in the case of higher-than-tangent match.
284
+ static curvatureSortKey(node) {
285
+ const cld = node.edgeTag;
286
+ if (cld !== undefined) {
287
+ const fraction = cld.fraction;
288
+ const curve = cld.curve;
289
+ if (curve) {
290
+ let radius = curve.fractionToSignedXYRadiusOfCurvature(fraction);
291
+ if (node.sortData !== undefined && node.sortData < 0)
292
+ radius = -radius;
293
+ return radius;
294
+ }
295
+ }
296
+ return 0.0;
297
+ }
212
298
  /** Simplest merge algorithm:
213
299
  * * collect array of (x,y,theta) at all nodes
214
300
  * * lexical sort of the array.
@@ -266,11 +352,19 @@ export class HalfEdgeGraphMerge {
266
352
  const unmatchedNullFaceNodes = [];
267
353
  k0 = 0;
268
354
  let thetaA, thetaB;
355
+ // eslint-disable-next-line no-console
356
+ // console.log("START VERTEX LINKS");
269
357
  // now pinch each neighboring pair together
270
358
  for (let k1 = 0; k1 < numK; k1++) {
271
359
  if (order[k1] === ClusterableArray.clusterTerminator) {
272
360
  // nodes identified in order[k0]..order[k1] are properly sorted around a vertex.
273
361
  if (k1 > k0) {
362
+ // const xy = clusters.getPoint2d(order[k0]);
363
+ // eslint-disable-next-line no-console
364
+ // console.log({ k0, k1, x: xy.x, y: xy.y });
365
+ if (k1 > k0 + 1)
366
+ this.secondarySortAroundVertex(clusters, order, allNodes, k0, k1);
367
+ this.doAnnounceVertexNeighborhood(clusters, order, allNodes, k0, k1);
274
368
  const iA = clusters.getExtraData(order[k0], 1);
275
369
  thetaA = clusters.getExtraData(order[k0], 0);
276
370
  const nodeA0 = allNodes[iA];
@@ -343,6 +437,7 @@ export class HalfEdgeGraphMerge {
343
437
  const by0 = nodeB0.y;
344
438
  const vx = nodeB1.x - bx0;
345
439
  const vy = nodeB1.y - by0;
440
+ // cspell:word lineSegmentXYUVTransverseIntersectionUnbounded
346
441
  if (SmallSystem.lineSegmentXYUVTransverseIntersectionUnbounded(ax0, ay0, ux, uy, bx0, by0, vx, vy, fractions)) {
347
442
  pointA.x = ax0 + fractions.x * ux;
348
443
  pointA.y = ay0 + fractions.x * uy;
@@ -1 +1 @@
1
- {"version":3,"file":"Merging.js","sourceRoot":"","sources":["../../../src/topology/Merging.ts"],"names":[],"mappings":"AAAA;;;+FAG+F;AAO/F,OAAO,EAAE,QAAQ,EAAE,MAAM,aAAa,CAAC;AACvC,OAAO,EAAE,KAAK,EAAE,MAAM,qBAAqB,CAAC;AAC5C,OAAO,EAAE,OAAO,EAAE,QAAQ,EAAE,MAAM,+BAA+B,CAAC;AAClE,OAAO,EAAE,OAAO,EAAE,MAAM,qBAAqB,CAAC;AAC9C,OAAO,EAAE,gBAAgB,EAAE,MAAM,8BAA8B,CAAC;AAChE,OAAO,EAAE,WAAW,EAAE,MAAM,yBAAyB,CAAC;AACtD,OAAO,EAAE,QAAQ,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAChE,OAAO,EAAE,qCAAqC,EAAE,MAAM,yBAAyB,CAAC;AAChF,OAAO,EAAE,qBAAqB,EAAE,MAAM,kBAAkB,CAAC;AACzD,OAAO,EAA8B,YAAY,EAAE,MAAM,iBAAiB,CAAC;AAE3E,MAAM,OAAO,cAAc;IAOzB;QANO,cAAS,GAAG,CAAC,CAAC;QACd,wBAAmB,GAAG,CAAC,CAAC;QACxB,aAAQ,GAAG,CAAC,CAAC;QACb,cAAS,GAAG,CAAC,CAAC;QACd,YAAO,GAAG,CAAC,CAAC;QACZ,YAAO,GAAG,CAAC,CAAC;IAEnB,CAAC;CACF;AAED;;;GAGG;AACH,MAAM,OAAO,gBAAgB;IAE3B,iFAAiF;IAC1E,MAAM,CAAC,gBAAgB,CAAC,CAAW,EAAE,CAAW;QACrD,YAAY;QACZ,4CAA4C;QAC5C,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;YACX,OAAO,CAAC,CAAC,CAAC;aACP,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;YAChB,OAAO,CAAC,CAAC;QACX,YAAY;QACZ,4CAA4C;QAC5C,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;YACX,OAAO,CAAC,CAAC,CAAC;aACP,IAAI,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;YAChB,OAAO,CAAC,CAAC;QACX,OAAO,CAAC,CAAC;IACX,CAAC;IAED,mIAAmI;IAC5H,MAAM,CAAC,UAAU,CAAC,KAAe;QACtC,MAAM,KAAK,GAAG,KAAK,CAAC,eAAe,CAAC;QACpC,MAAM,KAAK,GAAG,KAAK,CAAC,aAAa,CAAC;QAClC,OAAO,IAAI,CAAC,gBAAgB,CAAC,KAAK,EAAE,KAAK,CAAC,GAAG,CAAC;eACzC,IAAI,CAAC,gBAAgB,CAAC,KAAK,EAAE,KAAK,CAAC,GAAG,CAAC;eACvC,IAAI,CAAC,qBAAqB,CAAC,KAAK,EAAE,KAAK,EAAE,KAAK,CAAC,GAAG,CAAC,CAAC;IAC3D,CAAC;IAED;;;;OAIG;IACI,MAAM,CAAC,qBAAqB,CAAC,IAAc,EAAE,OAAiB,EAAE,OAAiB;QACtF,OAAO,QAAQ,CAAC,gBAAgB,CAAC,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAAC,CAAC;IACnH,CAAC;IAED,wHAAwH;IACxH,yHAAyH;IAElH,MAAM,CAAC,UAAU,CAAC,KAAoB;QAC3C,MAAM,KAAK,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;QAC/B,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,YAAY,EAAE;YACrC,KAAK,CAAC,SAAS,CAAC,IAAI,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,CAAC,CAAC;SACzC;QACD,OAAO,KAAK,CAAC;IACf,CAAC;IACD,gFAAgF;IACzE,MAAM,CAAC,wBAAwB,CAAC,QAAyB,EAAE,WAA0B,EAAE,IAAkB;QAC9G,MAAM,MAAM,GAAG,EAAE,CAAC;QAClB,IAAI,UAAU,GAAG,CAAC,CAAC;QAEnB,kFAAkF;QAClF,KAAK,MAAM,OAAO,IAAI,QAAQ,EAAE;YAE9B,MAAM,KAAK,GAAG,WAAW,CAAC,gBAAgB,CACxC,OAAO,CAAC,SAAS,CAAC,CAAC,EAAE,OAAO,CAAC,SAAS,CAAC,CAAC,EAAE,OAAO,CAAC,SAAS,CAAC,CAAC,EAC7D,UAAU,EACV,OAAO,CAAC,SAAS,CAAC,CAAC,EAAE,OAAO,CAAC,SAAS,CAAC,CAAC,EAAE,OAAO,CAAC,SAAS,CAAC,CAAC,EAC7D,UAAU,GAAG,CAAC,CAAC,CAAC;YAElB,MAAM,KAAK,GAAG,KAAK,CAAC,QAAQ,CAAC;YAC7B,UAAU,IAAI,CAAC,CAAC;YAEhB,KAAK,CAAC,iBAAiB,CAAC,IAAI,CAAC,CAAC,CAAG,sDAAsD;YACvF,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;YACnB,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;SACpB;QAED,OAAO,MAAM,CAAC;IAChB,CAAC;IAED;;;;;OAKG;IACI,MAAM,CAAC,eAAe,CAAC,KAAoB;QAChD,KAAK,MAAM,KAAK,IAAI,KAAK,CAAC,YAAY,EAAE;YACtC,MAAM,KAAK,GAAG,KAAK,CAAC,iBAAiB,CAAC;YACtC,QAAQ,CAAC,KAAK,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;SAC9B;IACH,CAAC;IAED;;;;;;OAMG;IACK,MAAM,CAAC,8BAA8B,CAAC,IAAc,EAAE,MAAoB,EAAE,OAAqB;QACvG,IAAI,EAAE,GAAG,IAAI,CAAC;QACd,GAAG,EAAE,8DAA8D;YACjE,IAAI,EAAE,CAAC,SAAS,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC,QAAQ,CAAC,SAAS,CAAC,OAAO,CAAC;gBACzD,MAAM;YACR,EAAE,GAAG,EAAE,CAAC,eAAe,CAAC;SACzB,QAAQ,EAAE,KAAK,IAAI,IAAI,EAAE,CAAC,SAAS,CAAC,MAAM,CAAC,EAAE;QAC9C,IAAI,EAAE,KAAK,IAAI;YACb,OAAO,KAAK,CAAC;QACf,IAAI,EAAE,GAAG,IAAI,CAAC;QACd,GAAG,EAAE,2DAA2D;YAC9D,IAAI,EAAE,CAAC,SAAS,CAAC,OAAO,CAAC,IAAI,EAAE,CAAC,QAAQ,CAAC,SAAS,CAAC,OAAO,CAAC;gBACzD,MAAM;YACR,EAAE,GAAG,EAAE,CAAC,iBAAiB,CAAC;SAC3B,QAAQ,EAAE,KAAK,IAAI,IAAI,EAAE,CAAC,SAAS,CAAC,MAAM,CAAC,EAAE;QAC9C,IAAI,EAAE,KAAK,IAAI;YACb,OAAO,KAAK,CAAC;QACf,OAAO,QAAQ,CAAC,cAAc,CAAC,EAAE,CAAC,QAAQ,EAAE,IAAI,EAAE,EAAE,CAAC,aAAa,CAAC,CAAC;IACtE,CAAC;IAED;;;;;;;;OAQG;IACI,MAAM,CAAC,qCAAqC,CAAC,KAAoB,EAAE,IAAkB,EAAE,UAAwB,YAAY,CAAC,aAAa;QAC9I,IAAI,YAAY,CAAC,SAAS,KAAK,IAAI;YACjC,OAAO,CAAC,CAAC;QACX,MAAM,KAAK,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QACnC,IAAI,SAAS,GAAG,CAAC,CAAC;QAClB,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,YAAY,EAAE;YACrC,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,EAAE;gBAC1B,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE;oBACjE,IAAI,IAAI,CAAC,8BAA8B,CAAC,IAAI,EAAE,IAAI,EAAE,OAAO,CAAC,IAAI,IAAI,CAAC,8BAA8B,CAAC,IAAI,CAAC,QAAQ,EAAE,IAAI,EAAE,OAAO,CAAC,EAAE;wBACjI,IAAI,CAAC,iBAAiB,CAAC,IAAI,CAAC,CAAC;wBAC7B,EAAE,SAAS,CAAC;qBACb;iBACF;aACF;YACH,IAAI,CAAC,iBAAiB,CAAC,KAAK,CAAC,CAAC;SAC7B;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;IAED;;;;;;;OAOG;IACI,MAAM,CAAC,wCAAwC,CAAC,KAAoB,EAAE,UAAwB,YAAY,CAAC,aAAa;QAC7H,MAAM,SAAS,GAAe,EAAE,CAAC;QACjC,MAAM,IAAI,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QAClC,IAAI,CAAC,GAAG,IAAI,CAAC,qCAAqC,CAAC,KAAK,EAAE,IAAI,EAAE,OAAO,CAAC,EAAE;YACxE,MAAM,OAAO,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;YACrC,KAAK,MAAM,IAAI,IAAI,KAAK,CAAC,YAAY,EAAE;gBACrC,IAAI,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,SAAS,CAAC,OAAO,CAAC,EAAE;oBACpD,IAAI,CAAC,iBAAiB,CAAC,OAAO,CAAC,CAAC;oBAChC,SAAS,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;iBACtB;aACF;YACD,KAAK,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;SACzB;QACD,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QACrB,OAAO,SAAS,CAAC;IACnB,CAAC;IAED;;;;;;;OAOG;IACI,MAAM,CAAC,iBAAiB,CAAC,KAAoB,EAAE,UAAwB,YAAY,CAAC,aAAa;QACtG,MAAM,IAAI,GAAG,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QAClC,MAAM,eAAe,GAAG,IAAI,CAAC,qCAAqC,CAAC,KAAK,EAAE,IAAI,EAAE,OAAO,CAAC,CAAC;QACzF,IAAI,eAAe,GAAG,CAAC;YACrB,KAAK,CAAC,kBAAkB,CAAC,CAAC,IAAc,EAAE,EAAE,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC;QACnE,KAAK,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;QACrB,OAAO,eAAe,CAAC;IACzB,CAAC;IAED;;;;;OAKG;IACI,MAAM,CAAC,iBAAiB,CAAC,KAAoB,EAAE,QAAsB,YAAY,CAAC,QAAQ;QAC/F,MAAM,QAAQ,GAAG,KAAK,CAAC,gBAAgB,EAAE,CAAC;QAC1C,KAAK,MAAM,IAAI,IAAI,QAAQ,EAAE;YAC3B,IAAI,IAAI,CAAC,kBAAkB,CAAC,KAAK,CAAC;gBAChC,SAAS;YACX,IAAI,CAAC,IAAI,CAAC,YAAY,EAAE;gBACtB,OAAO,KAAK,CAAC;SACd;QACH,OAAO,IAAI,CAAC;IACd,CAAC;CACF;AAED;;GAEG;AACH,MAAM,OAAO,kBAAkB;IAC7B;;;;;;;OAOG;IACI,MAAM,CAAC,sBAAsB,CAAC,KAAoB,EAAE,uBAAkD;QAC3G,MAAM,QAAQ,GAAG,KAAK,CAAC,YAAY,CAAC;QACpC,MAAM,QAAQ,GAAG,QAAQ,CAAC,MAAM,CAAC;QACjC,KAAK,CAAC,SAAS,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC;QACxC,MAAM,QAAQ,GAAG,IAAI,gBAAgB,CAAC,CAAC,EAAE,CAAC,EAAE,QAAQ,CAAC,CAAC,CAAE,0EAA0E;QAClI,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,QAAQ,EAAE,CAAC,EAAE,EAAE;YACjC,MAAM,KAAK,GAAG,QAAQ,CAAC,CAAC,CAAC,CAAC;YAC1B,MAAM,EAAE,GAAG,KAAK,CAAC,CAAC,CAAC;YACnB,MAAM,EAAE,GAAG,KAAK,CAAC,CAAC,CAAC;YACnB,QAAQ,CAAC,KAAK,CAAC,KAAK,EAAE,KAAK,CAAC,eAAe,CAAC,CAAC,CAAE,0CAA0C;YACzF,QAAQ,CAAC,SAAS,CAAC,EAAE,EAAE,EAAE,EAAE,GAAG,EAAE,CAAC,CAAC,CAAC;SACpC;QACD,MAAM,KAAK,GAAG,QAAQ,CAAC,qBAAqB,EAAE,CAAC;QAC/C,IAAI,EAAE,GAAG,CAAC,CAAC;QACX,MAAM,IAAI,GAAG,KAAK,CAAC,MAAM,CAAC;QAC1B,KAAK,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,GAAG,IAAI,EAAE,EAAE,EAAE,EAAE;YAChC,IAAI,KAAK,CAAC,EAAE,CAAC,KAAK,gBAAgB,CAAC,iBAAiB,EAAE;gBACpD,gFAAgF;gBAChF,IAAI,EAAE,GAAG,EAAE,EAAE;oBACX,MAAM,EAAE,GAAG,QAAQ,CAAC,YAAY,CAAC,KAAK,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;oBAC/C,MAAM,MAAM,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAC;oBAC5B,KAAK,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,EAAE,CAAC,GAAG,EAAE,EAAE,CAAC,EAAE,EAAE;wBAChC,MAAM,EAAE,GAAG,QAAQ,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;wBAC9C,MAAM,KAAK,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAC;wBAC3B,KAAK,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC;wBACnB,KAAK,CAAC,CAAC,GAAG,MAAM,CAAC,CAAC,CAAC;qBACpB;iBACF;gBACD,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC;aACb;SACF;QACD,MAAM;QACN,4EAA4E;QAC5E,qDAAqD;QAErD,qDAAqD;QACrD,KAAK,MAAM,iBAAiB,IAAI,KAAK,EAAE;YACrC,IAAI,iBAAiB,KAAK,gBAAgB,CAAC,iBAAiB,EAAE;gBAC5D,MAAM,KAAK,GAAG,QAAQ,CAAC,iBAAiB,CAAC,CAAC;gBAC1C,MAAM,KAAK,GAAG,KAAK,CAAC,aAAa,CAAC;gBAClC,IAAI,OAAO,GAAG,uBAAuB,CAAC,CAAC,CAAC,uBAAuB,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,GAAG,KAAK,CAAC,CAAC,EAAE,KAAK,CAAC,CAAC,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC;gBAC1H,IAAI,KAAK,CAAC,oCAAoC,CAAC,OAAO,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC;oBAC/D,OAAO,GAAG,IAAI,CAAC,EAAE,CAAC;gBACpB,QAAQ,CAAC,YAAY,CAAC,iBAAiB,EAAE,CAAC,EAAE,OAAO,CAAC,CAAC;aACtD;SACF;QACD,QAAQ,CAAC,sBAAsB,CAAC,KAAK,EAAE,CAAC,CAAC,CAAC;QAC1C,MAAM,sBAAsB,GAAe,EAAE,CAAC;QAC9C,EAAE,GAAG,CAAC,CAAC;QACP,IAAI,MAAM,EAAE,MAAM,CAAC;QACnB,2CAA2C;QAC3C,KAAK,IAAI,EAAE,GAAG,CAAC,EAAE,EAAE,GAAG,IAAI,EAAE,EAAE,EAAE,EAAE;YAChC,IAAI,KAAK,CAAC,EAAE,CAAC,KAAK,gBAAgB,CAAC,iBAAiB,EAAE;gBACpD,gFAAgF;gBAChF,IAAI,EAAE,GAAG,EAAE,EAAE;oBACX,MAAM,EAAE,GAAG,QAAQ,CAAC,YAAY,CAAC,KAAK,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;oBAC/C,MAAM,GAAG,QAAQ,CAAC,YAAY,CAAC,KAAK,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC;oBAC7C,MAAM,MAAM,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAC;oBAC5B,IAAI,KAAK,GAAG,MAAM,CAAC;oBACnB,KAAK,IAAI,CAAC,GAAG,EAAE,GAAG,CAAC,EAAE,CAAC,GAAG,EAAE,EAAE,CAAC,EAAE,EAAE;wBAChC,MAAM,EAAE,GAAG,QAAQ,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;wBAC9C,MAAM,GAAG,QAAQ,CAAC,YAAY,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;wBAC5C,MAAM,KAAK,GAAG,QAAQ,CAAC,EAAE,CAAC,CAAC;wBAC3B,IAAI,KAAK,CAAC,SAAS,CAAC,YAAY,CAAC,SAAS,CAAC,EAAE;4BAC3C,8DAA8D;4BAC9D,MAAM,CAAC,GAAG,sBAAsB,CAAC,SAAS,CAAC,CAAC,IAAc,EAAE,EAAE,CAAC,KAAK,KAAK,IAAI,CAAC,CAAC;4BAC/E,IAAI,CAAC,IAAI,CAAC,EAAE;gCACV,sBAAsB,CAAC,CAAC,CAAC,GAAG,sBAAsB,CAAC,sBAAsB,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;gCACtF,sBAAsB,CAAC,GAAG,EAAE,CAAC;6BAC9B;4BACD,KAAK,GAAG,KAAK,CAAC;4BACd,MAAM,GAAG,MAAM,CAAC;yBACjB;6BAAM,IAAI,KAAK,CAAC,SAAS,CAAC,YAAY,CAAC,SAAS,CAAC,EAAE;4BAClD,MAAM,CAAC,GAAG,sBAAsB,CAAC,SAAS,CAAC,CAAC,IAAc,EAAE,EAAE,CAAC,KAAK,KAAK,IAAI,CAAC,CAAC;4BAC/E,IAAI,CAAC,IAAI,CAAC,EAAE;gCACV,sBAAsB,CAAC,CAAC,CAAC,GAAG,sBAAsB,CAAC,sBAAsB,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;gCACtF,sBAAsB,CAAC,GAAG,EAAE,CAAC;6BAC9B;4BACD,6FAA6F;yBAC9F;6BAAM;4BACL,QAAQ,CAAC,KAAK,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;4BAC7B,IAAI,KAAK,CAAC,oCAAoC,CAAC,MAAM,EAAE,MAAM,CAAC,EAAE;gCAC9D,MAAM,MAAM,GAAG,KAAK,CAAC,aAAa,CAAC;gCACnC,MAAM,MAAM,GAAG,KAAK,CAAC,QAAQ,CAAC;gCAC9B,yDAAyD;gCACzD,wDAAwD;gCACxD,QAAQ,CAAC,KAAK,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;gCAC/B,KAAK,CAAC,OAAO,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC;gCACtC,MAAM,CAAC,OAAO,CAAC,YAAY,CAAC,SAAS,CAAC,CAAC;gCACvC,sBAAsB,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;6BACrC;4BACD,KAAK,GAAG,KAAK,CAAC;4BACd,MAAM,GAAG,MAAM,CAAC;yBACjB;qBACF;iBACF;gBACD,EAAE,GAAG,EAAE,GAAG,CAAC,CAAC;aACb;SACF;IACH,CAAC;IAEO,MAAM,CAAC,+BAA+B,CAAC,KAAoB;QACjE,MAAM,SAAS,GAAG,IAAI,qCAAqC,EAAE,CAAC;QAC9D,KAAK,MAAM,CAAC,IAAI,KAAK,CAAC,YAAY,EAAE;YAElC,IAAI,gBAAgB,CAAC,gBAAgB,CAAC,CAAC,EAAE,CAAC,CAAC,aAAa,CAAC,GAAG,CAAC,EAAE;gBAC7D,SAAS,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;aACjC;SACF;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;IACO,MAAM,CAAC,kBAAkB,CAAC,EAAW,EAAE,QAAgB,EAAE,IAAc,EAAE,YAAoB;QACnG,IAAI,QAAQ,CAAC,gBAAgB,CAAC,EAAE,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,CAAC,IAAI,QAAQ,CAAC,gBAAgB,CAAC,EAAE,CAAC,CAAC,EAAE,IAAI,CAAC,CAAC,CAAC;YACpF,OAAO,YAAY,CAAC;QACtB,OAAO,QAAQ,CAAC;IACpB,CAAC;IACS,MAAM,CAAC,mCAAmC,CAAC,MAAgB,EAAE,MAAgB,EAAE,SAAmB,EAAE,MAAe,EAAE,MAAe;QAC1I,MAAM,MAAM,GAAG,MAAM,CAAC,aAAa,CAAC;QACpC,MAAM,GAAG,GAAG,MAAM,CAAC,CAAC,CAAC;QACrB,MAAM,GAAG,GAAG,MAAM,CAAC,CAAC,CAAC;QACrB,MAAM,EAAE,GAAG,MAAM,CAAC,CAAC,GAAG,GAAG,CAAC;QAC1B,MAAM,EAAE,GAAG,MAAM,CAAC,CAAC,GAAG,GAAG,CAAC;QAC1B,MAAM,MAAM,GAAG,MAAM,CAAC,aAAa,CAAC;QACpC,MAAM,GAAG,GAAG,MAAM,CAAC,CAAC,CAAC;QACrB,MAAM,GAAG,GAAG,MAAM,CAAC,CAAC,CAAC;QACrB,MAAM,EAAE,GAAG,MAAM,CAAC,CAAC,GAAG,GAAG,CAAC;QAC1B,MAAM,EAAE,GAAG,MAAM,CAAC,CAAC,GAAG,GAAG,CAAC;QAC1B,IAAI,WAAW,CAAC,8CAA8C,CAAC,GAAG,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,EAC7E,GAAG,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,EAAE,SAAS,CAAC,EAAE;YAC9B,MAAM,CAAC,CAAC,GAAG,GAAG,GAAG,SAAS,CAAC,CAAC,GAAG,EAAE,CAAC;YAClC,MAAM,CAAC,CAAC,GAAG,GAAG,GAAG,SAAS,CAAC,CAAC,GAAG,EAAE,CAAC;YAClC,MAAM,CAAC,CAAC,GAAG,GAAG,GAAG,SAAS,CAAC,CAAC,GAAG,EAAE,CAAC;YAClC,MAAM,CAAC,CAAC,GAAG,GAAG,GAAG,SAAS,CAAC,CAAC,GAAG,EAAE,CAAC;YAClC,SAAS,CAAC,CAAC,GAAG,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,CAAC,CAAC;YACxE,SAAS,CAAC,CAAC,GAAG,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,CAAC,CAAC;YACxE,SAAS,CAAC,CAAC,GAAG,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,CAAC,CAAC;YACxE,SAAS,CAAC,CAAC,GAAG,IAAI,CAAC,kBAAkB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC,EAAE,MAAM,EAAE,GAAG,CAAC,CAAC;YACxE,OAAO,QAAQ,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,IAAI,QAAQ,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC;SACrE;QACD,OAAO,KAAK,CAAC;IACf,CAAC;IACD;;;;OAIG;IACI,MAAM,CAAC,sBAAsB,CAAC,KAAoB;QACvD,MAAM,IAAI,GAAG,IAAI,cAAc,EAAE,CAAC;QAClC,MAAM,SAAS,GAAG,IAAI,CAAC,+BAA+B,CAAC,KAAK,CAAC,CAAC;QAC9D,IAAI,MAAM,EAAE,MAAM,CAAC;QACnB,MAAM,aAAa,GAAG,MAAM,CAAC;QAC7B,MAAM,aAAa,GAAG,GAAG,GAAG,aAAa,CAAC;QAC1C,IAAI,CAAC,CAAC;QACN,MAAM,SAAS,GAAG,QAAQ,CAAC,MAAM,EAAE,CAAC;QACpC,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;QAChC,MAAM,MAAM,GAAG,OAAO,CAAC,MAAM,EAAE,CAAC;QAChC,IAAI,MAAM,CAAC;QACX,MAAM,YAAY,GAAG,QAAQ,CAAC,mBAAmB,CAAC;QAClD,OAAO,SAAS,KAAK,CAAC,MAAM,GAAG,SAAS,CAAC,aAAa,CAAC,GAAG,EAAE,CAAC,EAAE;YAC7D,IAAI,CAAC,SAAS,EAAE,CAAC;YACjB,MAAM,EAAE,GAAG,SAAS,CAAC,WAAW,CAAC,MAAM,CAAC;YACxC,SAAS,CAAC,6BAA6B,CAAC,MAAM,CAAC,CAAC,GAAG,YAAY,CAAC,CAAC;YACjE,IAAI,CAAC,SAAS,IAAI,EAAE,GAAG,SAAS,CAAC,WAAW,CAAC,MAAM,CAAC;YACpD,KAAK,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,SAAS,CAAC,WAAW,CAAC,MAAM,EAAE,CAAC,EAAE,EAAE;gBACjD,MAAM,GAAG,SAAS,CAAC,WAAW,CAAC,CAAC,CAAC,CAAC;gBAClC,MAAM,GAAG,MAAM,CAAC,aAAa,CAAC;gBAC9B,uCAAuC;gBACvC,IAAI,QAAQ,CAAC,kBAAkB,CAAC,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE;oBACvE,IAAI,CAAC,OAAO,EAAE,CAAC;iBAChB;qBAAM,IAAI,QAAQ,CAAC,kBAAkB,CAAC,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE;oBAC9E,IAAI,CAAC,OAAO,EAAE,CAAC;iBAChB;qBAAM;oBACL,IAAI,CAAC,mBAAmB,EAAE,CAAC;oBAC3B,IAAI,IAAI,CAAC,mCAAmC,CAAC,MAAM,EAAE,MAAM,EAAE,SAAS,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE;wBACvF,IAAI,SAAS,CAAC,CAAC,GAAG,aAAa,IAAI,SAAS,CAAC,CAAC,GAAG,aAAa,EAAE;4BAC9D,MAAM,MAAM,GAAG,KAAK,CAAC,mBAAmB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC,CAAC,CAAC;4BAC9D,SAAS,CAAC,aAAa,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAE,2DAA2D;4BAClG,IAAI,CAAC,QAAQ,EAAE,CAAC;yBACjB;wBACD,IAAI,SAAS,CAAC,CAAC,GAAG,aAAa,IAAI,SAAS,CAAC,CAAC,GAAG,aAAa,EAAE;4BAC9D,MAAM,MAAM,GAAG,KAAK,CAAC,mBAAmB,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC,CAAC,CAAC;4BAC9D,SAAS,CAAC,aAAa,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,CAAE,2DAA2D;4BAClG,IAAI,CAAC,QAAQ,EAAE,CAAC;yBACjB;wBACD,0EAA0E;qBAC3E;iBACF;aACF;YACD,SAAS,CAAC,WAAW,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;SACpC;QACD,OAAO,IAAI,CAAC;IACd,CAAC;IAED;;;;;;;;OAQG;IACI,MAAM,CAAC,qBAAqB,CAAC,YAA6B;QAC/D,uEAAuE;QACvE,MAAM,KAAK,GAAG,IAAI,aAAa,EAAE,CAAC;QAClC,gBAAgB,CAAC,wBAAwB,CAAC,YAAY,EAAE,KAAK,EAAE,YAAY,CAAC,aAAa,CAAC,CAAC;QAC3F,IAAI,CAAC,sBAAsB,CAAC,KAAK,CAAC,CAAC;QACnC,IAAI,CAAC,sBAAsB,CAAC,KAAK,CAAC,CAAC;QAEnC,OAAO,KAAK,CAAC;IACf,CAAC;IAED;;;;OAIG;IACI,MAAM,CAAC,mBAAmB,CAAC,MAAkC,EAAE,aAAsB,IAAI,EAAE,OAAqB,YAAY,CAAC,YAAY;QAC9I,IAAI,MAAM,CAAC,MAAM,GAAG,CAAC;YACnB,OAAO,SAAS,CAAC;QACnB,MAAM,KAAK,GAAG,IAAI,aAAa,EAAE,CAAC;QAClC,MAAM,UAAU,GAAG,YAAY,CAAC,iCAAiC,CAAC,KAAK,EAAE,MAAM,CAAC,CAAC;QACjF,KAAK,MAAM,IAAI,IAAI,UAAU;YAC3B,IAAI,CAAC,iBAAiB,CAAC,IAAI,CAAC,CAAC;QAE/B,IAAI,CAAC,sBAAsB,CAAC,KAAK,CAAC,CAAC;QACnC,IAAI,CAAC,sBAAsB,CAAC,KAAK,CAAC,CAAC;QACnC,IAAI,UAAU,EAAE;YACd,MAAM,OAAO,GAAG,IAAI,qBAAqB,CAAC,KAAK,CAAC,CAAC;YACjD,OAAO,CAAC,eAAe,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;SACrC;QACD,OAAO,KAAK,CAAC;IACf,CAAC;CAEF","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Topology\r\n */\r\n\r\nimport { LineSegment3d } from \"../curve/LineSegment3d\";\r\nimport { Geometry } from \"../Geometry\";\r\nimport { Angle } from \"../geometry3d/Angle\";\r\nimport { Point2d, Vector2d } from \"../geometry3d/Point2dVector2d\";\r\nimport { Range3d } from \"../geometry3d/Range\";\r\nimport { ClusterableArray } from \"../numerics/ClusterableArray\";\r\nimport { SmallSystem } from \"../numerics/Polynomials\";\r\nimport { HalfEdge, HalfEdgeGraph, HalfEdgeMask } from \"./Graph\";\r\nimport { HalfEdgePriorityQueueWithPartnerArray } from \"./HalfEdgePriorityQueue\";\r\nimport { RegularizationContext } from \"./RegularizeFace\";\r\nimport { MultiLineStringDataVariant, Triangulator } from \"./Triangulation\";\r\n\r\nexport class GraphSplitData {\r\n public numUpEdge = 0;\r\n public numIntersectionTest = 0;\r\n public numSplit = 0;\r\n public numPopOut = 0;\r\n public numA0B0 = 0;\r\n public numA0B1 = 0;\r\n public constructor() {\r\n }\r\n}\r\n\r\n/**\r\n * * Assorted methods used in algorithms on HalfEdgeGraph.\r\n * @internal\r\n */\r\nexport class HalfEdgeGraphOps {\r\n\r\n /** Compare function for sorting with primary y compare, secondary x compare. */\r\n public static compareNodesYXUp(a: HalfEdge, b: HalfEdge) {\r\n // Check y's\r\n // if (!Geometry.isSameCoordinate(a.y, b.y))\r\n if (a.y < b.y)\r\n return -1;\r\n else if (a.y > b.y)\r\n return 1;\r\n // Check x's\r\n // if (!Geometry.isSameCoordinate(a.x, b.x))\r\n if (a.x < b.x)\r\n return -1;\r\n else if (a.x > b.x)\r\n return 1;\r\n return 0;\r\n }\r\n\r\n /** Return true if nodeB (a) is lower than both its neighbors and (b) inflects as a downward peak (rather than an upward trough) */\r\n public static isDownPeak(nodeB: HalfEdge) {\r\n const nodeA = nodeB.facePredecessor;\r\n const nodeC = nodeB.faceSuccessor;\r\n return this.compareNodesYXUp(nodeB, nodeA) < 0\r\n && this.compareNodesYXUp(nodeB, nodeC) < 0\r\n && this.crossProductToTargets(nodeB, nodeA, nodeC) > 0;\r\n }\r\n\r\n /** return the cross product of vectors from base to targetA and base to targetB\r\n * @param base base vertex of both vectors.\r\n * @param targetA target vertex of first vector\r\n * @param targetB target vertex of second vector\r\n */\r\n public static crossProductToTargets(base: HalfEdge, targetA: HalfEdge, targetB: HalfEdge): number {\r\n return Geometry.crossProductXYXY(targetA.x - base.x, targetA.y - base.y, targetB.x - base.x, targetB.y - base.y);\r\n }\r\n\r\n // ---------------------------------------------------------------------------------------------------------------------\r\n // ----------------------------------------------------------------------------------------------------------------------\r\n\r\n public static graphRange(graph: HalfEdgeGraph): Range3d {\r\n const range = Range3d.create();\r\n for (const node of graph.allHalfEdges) {\r\n range.extendXYZ(node.x, node.y, node.z);\r\n }\r\n return range;\r\n }\r\n /** Returns an array of all nodes (both ends) of edges created from segments. */\r\n public static segmentArrayToGraphEdges(segments: LineSegment3d[], returnGraph: HalfEdgeGraph, mask: HalfEdgeMask): HalfEdge[] {\r\n const result = [];\r\n let idxCounter = 0;\r\n\r\n // Push the endpoints of each segment onto arr[] in the form {(x, y, theta), Node}\r\n for (const segment of segments) {\r\n\r\n const node0 = returnGraph.createEdgeXYZXYZ(\r\n segment.point0Ref.x, segment.point0Ref.y, segment.point0Ref.z,\r\n idxCounter,\r\n segment.point1Ref.x, segment.point1Ref.y, segment.point1Ref.z,\r\n idxCounter + 1);\r\n\r\n const node1 = node0.edgeMate;\r\n idxCounter += 2;\r\n\r\n node0.setMaskAroundFace(mask); // Original given coordinates must be part of boundary\r\n result.push(node0);\r\n result.push(node1);\r\n }\r\n\r\n return result;\r\n }\r\n\r\n /**\r\n * * Visit all nodes in `graph`.\r\n * * invoke `pinch(node, vertexPredecessor)`\r\n * * this leaves the graph as isolated edges.\r\n * @param graph graph to modify\r\n */\r\n public static isolateAllEdges(graph: HalfEdgeGraph) {\r\n for (const nodeA of graph.allHalfEdges) {\r\n const nodeB = nodeA.vertexPredecessor;\r\n HalfEdge.pinch(nodeA, nodeB);\r\n }\r\n }\r\n\r\n /**\r\n * Compute convexity of a sector of a super-face.\r\n * @param base node whose edge is to be tested for removal\r\n * @param ignore edges with this mask (on either side) are ignored for the purposes of computing convexity\r\n * @param barrier edges with this mask (on either side) will not be removed\r\n * @return whether removing the edge at base would create a convex sector in the super-face\r\n */\r\n private static isSectorConvexAfterEdgeRemoval(base: HalfEdge, ignore: HalfEdgeMask, barrier: HalfEdgeMask): boolean {\r\n let vs = base;\r\n do { // loop ccw around vertex looking for a super-face predecessor\r\n if (vs.isMaskSet(barrier) || vs.edgeMate.isMaskSet(barrier))\r\n break;\r\n vs = vs.vertexSuccessor;\r\n } while (vs !== base && vs.isMaskSet(ignore));\r\n if (vs === base)\r\n return false;\r\n let vp = base;\r\n do { // loop cw around vertex looking for a super-face successor\r\n if (vp.isMaskSet(barrier) || vp.edgeMate.isMaskSet(barrier))\r\n break;\r\n vp = vp.vertexPredecessor;\r\n } while (vp !== base && vp.isMaskSet(ignore));\r\n if (vp === base)\r\n return false;\r\n return HalfEdge.isSectorConvex(vs.edgeMate, base, vp.faceSuccessor);\r\n }\r\n\r\n /**\r\n * Mask edges between faces if the union of the faces is convex.\r\n * Uses a greedy algorithm with no regard to quality of resulting convex faces.\r\n * Best results when input faces are convex.\r\n * @param graph graph to examine and mark\r\n * @param mark the mask used to mark (both sides of) removable edges\r\n * @param barrier edges with this mask (on either side) will not be marked. Defaults to HalfEdgeMask.BOUNDARY_EDGE.\r\n * @return number of edges masked (half the number of HalfEdges masked)\r\n */\r\n public static markRemovableEdgesToExpandConvexFaces(graph: HalfEdgeGraph, mark: HalfEdgeMask, barrier: HalfEdgeMask = HalfEdgeMask.BOUNDARY_EDGE): number {\r\n if (HalfEdgeMask.NULL_MASK === mark)\r\n return 0;\r\n const visit = graph.grabMask(true);\r\n let numMarked = 0;\r\n for (const node of graph.allHalfEdges) {\r\n if (!node.isMaskSet(visit)) {\r\n if (!node.isMaskSet(barrier) && !node.edgeMate.isMaskSet(barrier)) {\r\n if (this.isSectorConvexAfterEdgeRemoval(node, mark, barrier) && this.isSectorConvexAfterEdgeRemoval(node.edgeMate, mark, barrier)) {\r\n node.setMaskAroundEdge(mark);\r\n ++numMarked;\r\n }\r\n }\r\n }\r\n node.setMaskAroundEdge(visit);\r\n }\r\n return numMarked;\r\n }\r\n\r\n /**\r\n * Collect edges between faces if the union of the faces is convex.\r\n * Uses a greedy algorithm with no regard to quality of resulting convex faces.\r\n * Best results when input faces are convex.\r\n * @param graph graph to examine\r\n * @param barrier edges with this mask (on either side) will not be collected. Defaults to HalfEdgeMask.BOUNDARY_EDGE.\r\n * @return one HalfEdge per removable edge\r\n */\r\n public static collectRemovableEdgesToExpandConvexFaces(graph: HalfEdgeGraph, barrier: HalfEdgeMask = HalfEdgeMask.BOUNDARY_EDGE): HalfEdge[] | undefined {\r\n const removable: HalfEdge[] = [];\r\n const mark = graph.grabMask(true);\r\n if (0 < this.markRemovableEdgesToExpandConvexFaces(graph, mark, barrier)) {\r\n const visited = graph.grabMask(true);\r\n for (const node of graph.allHalfEdges) {\r\n if (node.isMaskSet(mark) && !node.isMaskSet(visited)) {\r\n node.setMaskAroundEdge(visited);\r\n removable.push(node);\r\n }\r\n }\r\n graph.dropMask(visited);\r\n }\r\n graph.dropMask(mark);\r\n return removable;\r\n }\r\n\r\n /**\r\n * Remove edges between faces if the union of the faces is convex.\r\n * Uses a greedy algorithm with no regard to quality of resulting convex faces.\r\n * Best results when input faces are convex.\r\n * @param graph graph to modify\r\n * @param barrier edges with this mask (on either side) will not be removed. Defaults to HalfEdgeMask.BOUNDARY_EDGE.\r\n * @return number of edges deleted\r\n */\r\n public static expandConvexFaces(graph: HalfEdgeGraph, barrier: HalfEdgeMask = HalfEdgeMask.BOUNDARY_EDGE): number {\r\n const mark = graph.grabMask(true);\r\n const numRemovedEdges = this.markRemovableEdgesToExpandConvexFaces(graph, mark, barrier);\r\n if (numRemovedEdges > 0)\r\n graph.yankAndDeleteEdges((node: HalfEdge) => node.getMask(mark));\r\n graph.dropMask(mark);\r\n return numRemovedEdges;\r\n }\r\n\r\n /**\r\n * Test desired faces for convexity.\r\n * @param graph graph to examine\r\n * @param avoid faces with this mask will not be examined. Defaults to HalfEdgeMask.EXTERIOR.\r\n * @return whether every face in the graph is convex\r\n */\r\n public static isEveryFaceConvex(graph: HalfEdgeGraph, avoid: HalfEdgeMask = HalfEdgeMask.EXTERIOR): boolean {\r\n const allFaces = graph.collectFaceLoops();\r\n for (const node of allFaces) {\r\n if (node.isMaskedAroundFace(avoid))\r\n continue;\r\n if (!node.isFaceConvex())\r\n return false;\r\n }\r\n return true;\r\n }\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport class HalfEdgeGraphMerge {\r\n /** Simplest merge algorithm:\r\n * * collect array of (x,y,theta) at all nodes\r\n * * lexical sort of the array.\r\n * * twist all vertices together.\r\n * * This effectively creates valid face loops for a planar subdivision if there are no edge crossings.\r\n * * If there are edge crossings, the graph can be a (highly complicated) Klein bottle topology.\r\n * * Mask.NULL_FACE is cleared throughout and applied within null faces.\r\n */\r\n public static clusterAndMergeXYTheta(graph: HalfEdgeGraph, outboundRadiansFunction?: (he: HalfEdge) => number) {\r\n const allNodes = graph.allHalfEdges;\r\n const numNodes = allNodes.length;\r\n graph.clearMask(HalfEdgeMask.NULL_FACE);\r\n const clusters = new ClusterableArray(2, 2, numNodes); // data order: x,y,theta, nodeIndex. But theta is not set in first round.\r\n for (let i = 0; i < numNodes; i++) {\r\n const nodeA = allNodes[i];\r\n const xA = nodeA.x;\r\n const yA = nodeA.y;\r\n HalfEdge.pinch(nodeA, nodeA.vertexSuccessor); // pull it out of its current vertex loop.\r\n clusters.addDirect(xA, yA, 0.0, i);\r\n }\r\n const order = clusters.clusterIndicesLexical();\r\n let k0 = 0;\r\n const numK = order.length;\r\n for (let k1 = 0; k1 < numK; k1++) {\r\n if (order[k1] === ClusterableArray.clusterTerminator) {\r\n // nodes identified in order[k0]..order[k1] are properly sorted around a vertex.\r\n if (k1 > k0) {\r\n const iA = clusters.getExtraData(order[k0], 1);\r\n const nodeA0 = allNodes[iA];\r\n for (let k = k0 + 1; k < k1; k++) {\r\n const iB = clusters.getExtraData(order[k], 1);\r\n const nodeB = allNodes[iB];\r\n nodeB.x = nodeA0.x;\r\n nodeB.y = nodeA0.y;\r\n }\r\n }\r\n k0 = k1 + 1;\r\n }\r\n }\r\n // NOW\r\n // 1) There are identical coordinates at all nodes around each vertex loop.\r\n // 2) Hence ready do sort (at each vertex) by theta.\r\n\r\n // insert theta as extra data in the sort table . . .\r\n for (const clusterTableIndex of order) {\r\n if (clusterTableIndex !== ClusterableArray.clusterTerminator) {\r\n const nodeA = allNodes[clusterTableIndex];\r\n const nodeB = nodeA.faceSuccessor;\r\n let radians = outboundRadiansFunction ? outboundRadiansFunction(nodeA) : Math.atan2(nodeB.y - nodeA.y, nodeB.x - nodeA.x);\r\n if (Angle.isAlmostEqualRadiansAllowPeriodShift(radians, -Math.PI))\r\n radians = Math.PI;\r\n clusters.setExtraData(clusterTableIndex, 0, radians);\r\n }\r\n }\r\n clusters.sortSubsetsBySingleKey(order, 2);\r\n const unmatchedNullFaceNodes: HalfEdge[] = [];\r\n k0 = 0;\r\n let thetaA, thetaB;\r\n // now pinch each neighboring pair together\r\n for (let k1 = 0; k1 < numK; k1++) {\r\n if (order[k1] === ClusterableArray.clusterTerminator) {\r\n // nodes identified in order[k0]..order[k1] are properly sorted around a vertex.\r\n if (k1 > k0) {\r\n const iA = clusters.getExtraData(order[k0], 1);\r\n thetaA = clusters.getExtraData(order[k0], 0);\r\n const nodeA0 = allNodes[iA];\r\n let nodeA = nodeA0;\r\n for (let k = k0 + 1; k < k1; k++) {\r\n const iB = clusters.getExtraData(order[k], 1);\r\n thetaB = clusters.getExtraData(order[k], 0);\r\n const nodeB = allNodes[iB];\r\n if (nodeA.isMaskSet(HalfEdgeMask.NULL_FACE)) {\r\n // nope, this edge was flagged and pinched from the other end.\r\n const j = unmatchedNullFaceNodes.findIndex((node: HalfEdge) => nodeA === node);\r\n if (j >= 0) {\r\n unmatchedNullFaceNodes[j] = unmatchedNullFaceNodes[unmatchedNullFaceNodes.length - 1];\r\n unmatchedNullFaceNodes.pop();\r\n }\r\n nodeA = nodeB;\r\n thetaA = thetaB;\r\n } else if (nodeB.isMaskSet(HalfEdgeMask.NULL_FACE)) {\r\n const j = unmatchedNullFaceNodes.findIndex((node: HalfEdge) => nodeA === node);\r\n if (j >= 0) {\r\n unmatchedNullFaceNodes[j] = unmatchedNullFaceNodes[unmatchedNullFaceNodes.length - 1];\r\n unmatchedNullFaceNodes.pop();\r\n }\r\n // NO leave nodeA and thetaA ignore nodeB -- later step will get the outside of its banana.\r\n } else {\r\n HalfEdge.pinch(nodeA, nodeB);\r\n if (Angle.isAlmostEqualRadiansAllowPeriodShift(thetaA, thetaB)) {\r\n const nodeA1 = nodeA.faceSuccessor;\r\n const nodeB1 = nodeB.edgeMate;\r\n // WE TRUST -- nodeA1 and node B1 must have identical xy.\r\n // pinch them together and mark the face loop as null ..\r\n HalfEdge.pinch(nodeA1, nodeB1);\r\n nodeA.setMask(HalfEdgeMask.NULL_FACE);\r\n nodeB1.setMask(HalfEdgeMask.NULL_FACE);\r\n unmatchedNullFaceNodes.push(nodeB1);\r\n }\r\n nodeA = nodeB;\r\n thetaA = thetaB;\r\n }\r\n }\r\n }\r\n k0 = k1 + 1;\r\n }\r\n }\r\n }\r\n\r\n private static buildVerticalSweepPriorityQueue(graph: HalfEdgeGraph): HalfEdgePriorityQueueWithPartnerArray {\r\n const sweepHeap = new HalfEdgePriorityQueueWithPartnerArray();\r\n for (const p of graph.allHalfEdges) {\r\n\r\n if (HalfEdgeGraphOps.compareNodesYXUp(p, p.faceSuccessor) < 0) {\r\n sweepHeap.priorityQueue.push(p);\r\n }\r\n }\r\n return sweepHeap;\r\n }\r\n private static snapFractionToNode(xy: Point2d, fraction: number, node: HalfEdge, nodeFraction: number): number{\r\n if (Geometry.isSameCoordinate(xy.x, node.x) && Geometry.isSameCoordinate(xy.y, node.y))\r\n return nodeFraction;\r\n return fraction;\r\n}\r\n private static computeIntersectionFractionsOnEdges(nodeA0: HalfEdge, nodeB0: HalfEdge, fractions: Vector2d, pointA: Point2d, pointB: Point2d): boolean {\r\n const nodeA1 = nodeA0.faceSuccessor;\r\n const ax0 = nodeA0.x;\r\n const ay0 = nodeA0.y;\r\n const ux = nodeA1.x - ax0;\r\n const uy = nodeA1.y - ay0;\r\n const nodeB1 = nodeB0.faceSuccessor;\r\n const bx0 = nodeB0.x;\r\n const by0 = nodeB0.y;\r\n const vx = nodeB1.x - bx0;\r\n const vy = nodeB1.y - by0;\r\n if (SmallSystem.lineSegmentXYUVTransverseIntersectionUnbounded(ax0, ay0, ux, uy,\r\n bx0, by0, vx, vy, fractions)) {\r\n pointA.x = ax0 + fractions.x * ux;\r\n pointA.y = ay0 + fractions.x * uy;\r\n pointB.x = bx0 + fractions.y * vx;\r\n pointB.y = by0 + fractions.y * vy;\r\n fractions.x = this.snapFractionToNode(pointA, fractions.x, nodeA0, 0.0);\r\n fractions.x = this.snapFractionToNode(pointA, fractions.x, nodeA1, 1.0);\r\n fractions.y = this.snapFractionToNode(pointB, fractions.y, nodeB0, 0.0);\r\n fractions.y = this.snapFractionToNode(pointB, fractions.y, nodeB1, 1.0);\r\n return Geometry.isIn01(fractions.x) && Geometry.isIn01(fractions.y);\r\n }\r\n return false;\r\n }\r\n /**\r\n * Split edges at intersections.\r\n * * This is a large operation.\r\n * @param graph\r\n */\r\n public static splitIntersectingEdges(graph: HalfEdgeGraph): GraphSplitData {\r\n const data = new GraphSplitData();\r\n const sweepHeap = this.buildVerticalSweepPriorityQueue(graph);\r\n let nodeA0, nodeB1;\r\n const smallFraction = 1.0e-8;\r\n const largeFraction = 1.0 - smallFraction;\r\n let i;\r\n const fractions = Vector2d.create();\r\n const pointA = Point2d.create();\r\n const pointB = Point2d.create();\r\n let nodeB0;\r\n const popTolerance = Geometry.smallMetricDistance;\r\n while (undefined !== (nodeA0 = sweepHeap.priorityQueue.pop())) {\r\n data.numUpEdge++;\r\n const n0 = sweepHeap.activeEdges.length;\r\n sweepHeap.removeArrayMembersWithY1Below(nodeA0.y - popTolerance);\r\n data.numPopOut += n0 - sweepHeap.activeEdges.length;\r\n for (i = 0; i < sweepHeap.activeEdges.length; i++) {\r\n nodeB0 = sweepHeap.activeEdges[i];\r\n nodeB1 = nodeB0.faceSuccessor;\r\n // const nodeB1 = nodeB0.faceSuccessor;\r\n if (Geometry.isSameCoordinateXY(nodeA0.x, nodeA0.y, nodeB0.x, nodeB0.y)) {\r\n data.numA0B0++;\r\n } else if (Geometry.isSameCoordinateXY(nodeB1.x, nodeB1.y, nodeA0.x, nodeA0.y)) {\r\n data.numA0B1++;\r\n } else {\r\n data.numIntersectionTest++;\r\n if (this.computeIntersectionFractionsOnEdges(nodeA0, nodeB0, fractions, pointA, pointB)) {\r\n if (fractions.x > smallFraction && fractions.x < largeFraction) {\r\n const nodeC0 = graph.splitEdgeAtFraction(nodeA0, fractions.x);\r\n sweepHeap.priorityQueue.push(nodeC0); // The upper portion will be reviewed as a nodeA0 later !!!\r\n data.numSplit++;\r\n }\r\n if (fractions.y > smallFraction && fractions.y < largeFraction) {\r\n const nodeD0 = graph.splitEdgeAtFraction(nodeB0, fractions.y);\r\n sweepHeap.priorityQueue.push(nodeD0); // The upper portion will be reviewed as a nodeA0 later !!!\r\n data.numSplit++;\r\n }\r\n // existing nodeA0 and its shortened edge remain for further intersections\r\n }\r\n }\r\n }\r\n sweepHeap.activeEdges.push(nodeA0);\r\n }\r\n return data;\r\n }\r\n\r\n /**\r\n * Returns a graph structure formed from the given LineSegment array\r\n *\r\n * * Find all intersections among segments, and split them if necessary\r\n * * Record endpoints of every segment in the form X, Y, Theta; This information is stored as a new node and sorted to match up\r\n * vertices.\r\n * * For vertices that match up, pinch the nodes to create vertex loops, which in closed objects, will also eventually form face\r\n * loops\r\n */\r\n public static formGraphFromSegments(lineSegments: LineSegment3d[]): HalfEdgeGraph {\r\n // Structure of an index of the array: { xyTheta: Point3d, node: Node }\r\n const graph = new HalfEdgeGraph();\r\n HalfEdgeGraphOps.segmentArrayToGraphEdges(lineSegments, graph, HalfEdgeMask.BOUNDARY_EDGE);\r\n this.splitIntersectingEdges(graph);\r\n this.clusterAndMergeXYTheta(graph);\r\n\r\n return graph;\r\n }\r\n\r\n /**\r\n * * Input is random linestrings, not necessarily loops\r\n * * Graph gets full splitEdges, regularize, and triangulate.\r\n * @returns triangulated graph, or undefined if bad data.\r\n */\r\n public static formGraphFromChains(chains: MultiLineStringDataVariant, regularize: boolean = true, mask: HalfEdgeMask = HalfEdgeMask.PRIMARY_EDGE): HalfEdgeGraph | undefined {\r\n if (chains.length < 1)\r\n return undefined;\r\n const graph = new HalfEdgeGraph();\r\n const chainSeeds = Triangulator.directCreateChainsFromCoordinates(graph, chains);\r\n for (const seed of chainSeeds)\r\n seed.setMaskAroundFace(mask);\r\n\r\n this.splitIntersectingEdges(graph);\r\n this.clusterAndMergeXYTheta(graph);\r\n if (regularize) {\r\n const context = new RegularizationContext(graph);\r\n context.regularizeGraph(true, true);\r\n }\r\n return graph;\r\n }\r\n\r\n}\r\n"]}
1
+ {"version":3,"file":"Merging.js","sourceRoot":"","sources":["../../../src/topology/Merging.ts"],"names":[],"mappings":"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","sourcesContent":["/*---------------------------------------------------------------------------------------------\r\n* Copyright (c) Bentley Systems, Incorporated. All rights reserved.\r\n* See LICENSE.md in the project root for license terms and full copyright notice.\r\n*--------------------------------------------------------------------------------------------*/\r\n\r\n/** @packageDocumentation\r\n * @module Topology\r\n */\r\n\r\nimport { CurveLocationDetail } from \"../curve/CurveLocationDetail\";\r\nimport { LineSegment3d } from \"../curve/LineSegment3d\";\r\nimport { Geometry } from \"../Geometry\";\r\nimport { Angle } from \"../geometry3d/Angle\";\r\nimport { Point2d, Vector2d } from \"../geometry3d/Point2dVector2d\";\r\nimport { Range3d } from \"../geometry3d/Range\";\r\nimport { ClusterableArray } from \"../numerics/ClusterableArray\";\r\nimport { SmallSystem } from \"../numerics/Polynomials\";\r\nimport { HalfEdge, HalfEdgeGraph, HalfEdgeMask } from \"./Graph\";\r\nimport { HalfEdgePriorityQueueWithPartnerArray } from \"./HalfEdgePriorityQueue\";\r\nimport { RegularizationContext } from \"./RegularizeFace\";\r\nimport { MultiLineStringDataVariant, Triangulator } from \"./Triangulation\";\r\n\r\nexport class GraphSplitData {\r\n public numUpEdge = 0;\r\n public numIntersectionTest = 0;\r\n public numSplit = 0;\r\n public numPopOut = 0;\r\n public numA0B0 = 0;\r\n public numA0B1 = 0;\r\n public constructor() {\r\n }\r\n}\r\n/**\r\n * Structure for data used when sorting outbound edges \"around a node\"\r\n */\r\nexport class VertexNeighborhoodSortData {\r\n public index: number;\r\n public radiusOfCurvature: number;\r\n public node: HalfEdge;\r\n public radians?: number;\r\n public constructor(index: number, key: number, node: HalfEdge, radians?: number) {\r\n this.index = index;\r\n this.radiusOfCurvature = key;\r\n this.node = node;\r\n this.radians = radians;\r\n }\r\n}\r\n\r\n/** Function signature for announcing a vertex neighborhood during sorting. */\r\nexport type AnnounceVertexNeighborhoodSortData = (data: VertexNeighborhoodSortData[]) => any;\r\n/**\r\n * * Assorted methods used in algorithms on HalfEdgeGraph.\r\n * @internal\r\n */\r\nexport class HalfEdgeGraphOps {\r\n\r\n /** Compare function for sorting with primary y compare, secondary x compare. */\r\n public static compareNodesYXUp(a: HalfEdge, b: HalfEdge) {\r\n // Check y's\r\n // if (!Geometry.isSameCoordinate(a.y, b.y))\r\n if (a.y < b.y)\r\n return -1;\r\n else if (a.y > b.y)\r\n return 1;\r\n // Check x's\r\n // if (!Geometry.isSameCoordinate(a.x, b.x))\r\n if (a.x < b.x)\r\n return -1;\r\n else if (a.x > b.x)\r\n return 1;\r\n return 0;\r\n }\r\n\r\n /** Return true if nodeB (a) is lower than both its neighbors and (b) inflects as a downward peak (rather than an upward trough) */\r\n public static isDownPeak(nodeB: HalfEdge) {\r\n const nodeA = nodeB.facePredecessor;\r\n const nodeC = nodeB.faceSuccessor;\r\n return this.compareNodesYXUp(nodeB, nodeA) < 0\r\n && this.compareNodesYXUp(nodeB, nodeC) < 0\r\n && this.crossProductToTargets(nodeB, nodeA, nodeC) > 0;\r\n }\r\n\r\n /** return the cross product of vectors from base to targetA and base to targetB\r\n * @param base base vertex of both vectors.\r\n * @param targetA target vertex of first vector\r\n * @param targetB target vertex of second vector\r\n */\r\n public static crossProductToTargets(base: HalfEdge, targetA: HalfEdge, targetB: HalfEdge): number {\r\n return Geometry.crossProductXYXY(targetA.x - base.x, targetA.y - base.y, targetB.x - base.x, targetB.y - base.y);\r\n }\r\n\r\n // ---------------------------------------------------------------------------------------------------------------------\r\n // ----------------------------------------------------------------------------------------------------------------------\r\n\r\n public static graphRange(graph: HalfEdgeGraph): Range3d {\r\n const range = Range3d.create();\r\n for (const node of graph.allHalfEdges) {\r\n range.extendXYZ(node.x, node.y, node.z);\r\n }\r\n return range;\r\n }\r\n /** Returns an array of all nodes (both ends) of edges created from segments. */\r\n public static segmentArrayToGraphEdges(segments: LineSegment3d[], returnGraph: HalfEdgeGraph, mask: HalfEdgeMask): HalfEdge[] {\r\n const result = [];\r\n let idxCounter = 0;\r\n\r\n // Push the endpoints of each segment onto arr[] in the form {(x, y, theta), Node}\r\n for (const segment of segments) {\r\n\r\n const node0 = returnGraph.createEdgeXYZXYZ(\r\n segment.point0Ref.x, segment.point0Ref.y, segment.point0Ref.z,\r\n idxCounter,\r\n segment.point1Ref.x, segment.point1Ref.y, segment.point1Ref.z,\r\n idxCounter + 1);\r\n\r\n const node1 = node0.edgeMate;\r\n idxCounter += 2;\r\n\r\n node0.setMaskAroundFace(mask); // Original given coordinates must be part of boundary\r\n result.push(node0);\r\n result.push(node1);\r\n }\r\n\r\n return result;\r\n }\r\n\r\n /**\r\n * * Visit all nodes in `graph`.\r\n * * invoke `pinch(node, vertexPredecessor)`\r\n * * this leaves the graph as isolated edges.\r\n * @param graph graph to modify\r\n */\r\n public static isolateAllEdges(graph: HalfEdgeGraph) {\r\n for (const nodeA of graph.allHalfEdges) {\r\n const nodeB = nodeA.vertexPredecessor;\r\n HalfEdge.pinch(nodeA, nodeB);\r\n }\r\n }\r\n\r\n /**\r\n * Compute convexity of a sector of a super-face.\r\n * @param base node whose edge is to be tested for removal\r\n * @param ignore edges with this mask (on either side) are ignored for the purposes of computing convexity\r\n * @param barrier edges with this mask (on either side) will not be removed\r\n * @return whether removing the edge at base would create a convex sector in the super-face\r\n */\r\n private static isSectorConvexAfterEdgeRemoval(base: HalfEdge, ignore: HalfEdgeMask, barrier: HalfEdgeMask): boolean {\r\n let vs = base;\r\n do { // loop ccw around vertex looking for a super-face predecessor\r\n if (vs.isMaskSet(barrier) || vs.edgeMate.isMaskSet(barrier))\r\n break;\r\n vs = vs.vertexSuccessor;\r\n } while (vs !== base && vs.isMaskSet(ignore));\r\n if (vs === base)\r\n return false;\r\n let vp = base;\r\n do { // loop cw around vertex looking for a super-face successor\r\n if (vp.isMaskSet(barrier) || vp.edgeMate.isMaskSet(barrier))\r\n break;\r\n vp = vp.vertexPredecessor;\r\n } while (vp !== base && vp.isMaskSet(ignore));\r\n if (vp === base)\r\n return false;\r\n return HalfEdge.isSectorConvex(vs.edgeMate, base, vp.faceSuccessor);\r\n }\r\n\r\n /**\r\n * Mask edges between faces if the union of the faces is convex.\r\n * Uses a greedy algorithm with no regard to quality of resulting convex faces.\r\n * Best results when input faces are convex.\r\n * @param graph graph to examine and mark\r\n * @param mark the mask used to mark (both sides of) removable edges\r\n * @param barrier edges with this mask (on either side) will not be marked. Defaults to HalfEdgeMask.BOUNDARY_EDGE.\r\n * @return number of edges masked (half the number of HalfEdges masked)\r\n */\r\n public static markRemovableEdgesToExpandConvexFaces(graph: HalfEdgeGraph, mark: HalfEdgeMask, barrier: HalfEdgeMask = HalfEdgeMask.BOUNDARY_EDGE): number {\r\n if (HalfEdgeMask.NULL_MASK === mark)\r\n return 0;\r\n const visit = graph.grabMask(true);\r\n let numMarked = 0;\r\n for (const node of graph.allHalfEdges) {\r\n if (!node.isMaskSet(visit)) {\r\n if (!node.isMaskSet(barrier) && !node.edgeMate.isMaskSet(barrier)) {\r\n if (this.isSectorConvexAfterEdgeRemoval(node, mark, barrier) && this.isSectorConvexAfterEdgeRemoval(node.edgeMate, mark, barrier)) {\r\n node.setMaskAroundEdge(mark);\r\n ++numMarked;\r\n }\r\n }\r\n }\r\n node.setMaskAroundEdge(visit);\r\n }\r\n return numMarked;\r\n }\r\n\r\n /**\r\n * Collect edges between faces if the union of the faces is convex.\r\n * Uses a greedy algorithm with no regard to quality of resulting convex faces.\r\n * Best results when input faces are convex.\r\n * @param graph graph to examine\r\n * @param barrier edges with this mask (on either side) will not be collected. Defaults to HalfEdgeMask.BOUNDARY_EDGE.\r\n * @return one HalfEdge per removable edge\r\n */\r\n public static collectRemovableEdgesToExpandConvexFaces(graph: HalfEdgeGraph, barrier: HalfEdgeMask = HalfEdgeMask.BOUNDARY_EDGE): HalfEdge[] | undefined {\r\n const removable: HalfEdge[] = [];\r\n const mark = graph.grabMask(true);\r\n if (0 < this.markRemovableEdgesToExpandConvexFaces(graph, mark, barrier)) {\r\n const visited = graph.grabMask(true);\r\n for (const node of graph.allHalfEdges) {\r\n if (node.isMaskSet(mark) && !node.isMaskSet(visited)) {\r\n node.setMaskAroundEdge(visited);\r\n removable.push(node);\r\n }\r\n }\r\n graph.dropMask(visited);\r\n }\r\n graph.dropMask(mark);\r\n return removable;\r\n }\r\n\r\n /**\r\n * Remove edges between faces if the union of the faces is convex.\r\n * Uses a greedy algorithm with no regard to quality of resulting convex faces.\r\n * Best results when input faces are convex.\r\n * @param graph graph to modify\r\n * @param barrier edges with this mask (on either side) will not be removed. Defaults to HalfEdgeMask.BOUNDARY_EDGE.\r\n * @return number of edges deleted\r\n */\r\n public static expandConvexFaces(graph: HalfEdgeGraph, barrier: HalfEdgeMask = HalfEdgeMask.BOUNDARY_EDGE): number {\r\n const mark = graph.grabMask(true);\r\n const numRemovedEdges = this.markRemovableEdgesToExpandConvexFaces(graph, mark, barrier);\r\n if (numRemovedEdges > 0)\r\n graph.yankAndDeleteEdges((node: HalfEdge) => node.getMask(mark));\r\n graph.dropMask(mark);\r\n return numRemovedEdges;\r\n }\r\n\r\n /**\r\n * Test desired faces for convexity.\r\n * @param graph graph to examine\r\n * @param avoid faces with this mask will not be examined. Defaults to HalfEdgeMask.EXTERIOR.\r\n * @return whether every face in the graph is convex\r\n */\r\n public static isEveryFaceConvex(graph: HalfEdgeGraph, avoid: HalfEdgeMask = HalfEdgeMask.EXTERIOR): boolean {\r\n const allFaces = graph.collectFaceLoops();\r\n for (const node of allFaces) {\r\n if (node.isMaskedAroundFace(avoid))\r\n continue;\r\n if (!node.isFaceConvex())\r\n return false;\r\n }\r\n return true;\r\n }\r\n}\r\n\r\n/**\r\n * @internal\r\n */\r\nexport class HalfEdgeGraphMerge {\r\n // return k2 <= kB such that stored angles (at extra data index 0 !) kA<=k<kC match.\r\n // * Note that the usual case (when angle at k0 is not repeated) is k0+1 === kC\r\n public static getCommonThetaEndIndex(clusters: ClusterableArray, order: Uint32Array, kA: number, kB: number): number{\r\n let kC = kA + 1;\r\n const thetaA = clusters.getExtraData(order[kA], 0);\r\n while (kC < kB) {\r\n const thetaB = clusters.getExtraData(order[kC], 0);\r\n if (!Angle.isAlmostEqualRadiansAllowPeriodShift(thetaA, thetaB)) {\r\n return kC;\r\n }\r\n kC++;\r\n }\r\n return kC;\r\n }\r\n private static _announceVertexNeighborhoodFunction?: AnnounceVertexNeighborhoodSortData;\r\n/**\r\n * public property setter for a function to be called with sorted edge data around a vertex.\r\n */\r\n public static set announceVertexNeighborhoodFunction(func: AnnounceVertexNeighborhoodSortData | undefined) { this._announceVertexNeighborhoodFunction = func; }\r\n private static doAnnounceVertexNeighborhood(clusters: ClusterableArray, order: Uint32Array, allNodes: HalfEdge[], k0: number, k1: number) {\r\n if (this._announceVertexNeighborhoodFunction) {\r\n const sortData: VertexNeighborhoodSortData[] = [];\r\n // build and share the entire vertex order\r\n for (let k = k0; k < k1; k++){\r\n const index = clusters.getExtraData(order[k], 1);\r\n const theta = clusters.getExtraData(order[k], 0);\r\n const node = allNodes[index];\r\n const signedDistance = this.curvatureSortKey(node);\r\n sortData.push(new VertexNeighborhoodSortData(order[k], signedDistance, node, theta));\r\n }\r\n this._announceVertexNeighborhoodFunction(sortData);\r\n }\r\n\r\n }\r\n // assumptions about cluster array:\r\n // * data order is: x,y,theta, nodeIndex\r\n // * theta and nodeIndex are the \"extra\" data.\r\n // * only want to do anything here when curves are present.\r\n // * k0<=k<k1 are around a vertex\r\n // * These are sorted by theta.\r\n private static secondarySortAroundVertex(clusters: ClusterableArray, order: Uint32Array, allNodes: HalfEdge[], k0: number, k1: number) {\r\n const sortData: VertexNeighborhoodSortData[] = [];\r\n\r\n for (let k = k0; k < k1;) {\r\n const kB = this.getCommonThetaEndIndex(clusters, order,k, k1);\r\n if (k + 1 < kB) {\r\n sortData.length = 0;\r\n for (let kA = k; kA < kB; kA++) {\r\n const index = clusters.getExtraData(order[kA], 1);\r\n const node = allNodes[index];\r\n const signedDistance = this.curvatureSortKey(node);\r\n sortData.push(new VertexNeighborhoodSortData(order[kA], signedDistance, node));\r\n }\r\n sortData.sort((a: VertexNeighborhoodSortData, b: VertexNeighborhoodSortData) => (a.radiusOfCurvature - b.radiusOfCurvature));\r\n for (let i = 0; i < sortData.length; i++){\r\n order[k + i] = sortData[i].index;\r\n }\r\n }\r\n k = kB;\r\n }\r\n }\r\n // Return the sort key for sorting by curvature.\r\n // This is the signed distance from the curve to center of curvature.\r\n // This should need to be upgraded to account for higher derivatives in the case of higher-than-tangent match.\r\n private static curvatureSortKey(node: HalfEdge): number {\r\n const cld = node.edgeTag as CurveLocationDetail;\r\n if (cld !== undefined) {\r\n const fraction = cld.fraction;\r\n const curve = cld.curve;\r\n if (curve) {\r\n let radius = curve.fractionToSignedXYRadiusOfCurvature(fraction);\r\n if (node.sortData !== undefined && node.sortData < 0)\r\n radius = -radius;\r\n return radius;\r\n }\r\n }\r\n return 0.0;\r\n }\r\n /** Simplest merge algorithm:\r\n * * collect array of (x,y,theta) at all nodes\r\n * * lexical sort of the array.\r\n * * twist all vertices together.\r\n * * This effectively creates valid face loops for a planar subdivision if there are no edge crossings.\r\n * * If there are edge crossings, the graph can be a (highly complicated) Klein bottle topology.\r\n * * Mask.NULL_FACE is cleared throughout and applied within null faces.\r\n */\r\n public static clusterAndMergeXYTheta(graph: HalfEdgeGraph, outboundRadiansFunction?: (he: HalfEdge) => number) {\r\n const allNodes = graph.allHalfEdges;\r\n const numNodes = allNodes.length;\r\n graph.clearMask(HalfEdgeMask.NULL_FACE);\r\n const clusters = new ClusterableArray(2, 2, numNodes); // data order: x,y,theta, nodeIndex. But theta is not set in first round.\r\n for (let i = 0; i < numNodes; i++) {\r\n const nodeA = allNodes[i];\r\n const xA = nodeA.x;\r\n const yA = nodeA.y;\r\n HalfEdge.pinch(nodeA, nodeA.vertexSuccessor); // pull it out of its current vertex loop.\r\n clusters.addDirect(xA, yA, 0.0, i);\r\n }\r\n const order = clusters.clusterIndicesLexical();\r\n let k0 = 0;\r\n const numK = order.length;\r\n for (let k1 = 0; k1 < numK; k1++) {\r\n if (order[k1] === ClusterableArray.clusterTerminator) {\r\n // nodes identified in order[k0]..order[k1] are properly sorted around a vertex.\r\n if (k1 > k0) {\r\n const iA = clusters.getExtraData(order[k0], 1);\r\n const nodeA0 = allNodes[iA];\r\n for (let k = k0 + 1; k < k1; k++) {\r\n const iB = clusters.getExtraData(order[k], 1);\r\n const nodeB = allNodes[iB];\r\n nodeB.x = nodeA0.x;\r\n nodeB.y = nodeA0.y;\r\n }\r\n }\r\n k0 = k1 + 1;\r\n }\r\n }\r\n // NOW\r\n // 1) There are identical coordinates at all nodes around each vertex loop.\r\n // 2) Hence ready do sort (at each vertex) by theta.\r\n\r\n // insert theta as extra data in the sort table . . .\r\n for (const clusterTableIndex of order) {\r\n if (clusterTableIndex !== ClusterableArray.clusterTerminator) {\r\n const nodeA = allNodes[clusterTableIndex];\r\n const nodeB = nodeA.faceSuccessor;\r\n let radians = outboundRadiansFunction ? outboundRadiansFunction(nodeA) : Math.atan2(nodeB.y - nodeA.y, nodeB.x - nodeA.x);\r\n if (Angle.isAlmostEqualRadiansAllowPeriodShift(radians, -Math.PI))\r\n radians = Math.PI;\r\n clusters.setExtraData(clusterTableIndex, 0, radians);\r\n }\r\n }\r\n clusters.sortSubsetsBySingleKey(order, 2);\r\n const unmatchedNullFaceNodes: HalfEdge[] = [];\r\n k0 = 0;\r\n let thetaA, thetaB;\r\n // eslint-disable-next-line no-console\r\n // console.log(\"START VERTEX LINKS\");\r\n\r\n // now pinch each neighboring pair together\r\n for (let k1 = 0; k1 < numK; k1++) {\r\n if (order[k1] === ClusterableArray.clusterTerminator) {\r\n // nodes identified in order[k0]..order[k1] are properly sorted around a vertex.\r\n if (k1 > k0) {\r\n // const xy = clusters.getPoint2d(order[k0]);\r\n // eslint-disable-next-line no-console\r\n // console.log({ k0, k1, x: xy.x, y: xy.y });\r\n if (k1 > k0 + 1)\r\n this.secondarySortAroundVertex(clusters, order, allNodes, k0, k1);\r\n this.doAnnounceVertexNeighborhood(clusters, order, allNodes, k0, k1);\r\n const iA = clusters.getExtraData(order[k0], 1);\r\n thetaA = clusters.getExtraData(order[k0], 0);\r\n const nodeA0 = allNodes[iA];\r\n let nodeA = nodeA0;\r\n for (let k = k0 + 1; k < k1; k++) {\r\n const iB = clusters.getExtraData(order[k], 1);\r\n thetaB = clusters.getExtraData(order[k], 0);\r\n const nodeB = allNodes[iB];\r\n if (nodeA.isMaskSet(HalfEdgeMask.NULL_FACE)) {\r\n // nope, this edge was flagged and pinched from the other end.\r\n const j = unmatchedNullFaceNodes.findIndex((node: HalfEdge) => nodeA === node);\r\n if (j >= 0) {\r\n unmatchedNullFaceNodes[j] = unmatchedNullFaceNodes[unmatchedNullFaceNodes.length - 1];\r\n unmatchedNullFaceNodes.pop();\r\n }\r\n nodeA = nodeB;\r\n thetaA = thetaB;\r\n } else if (nodeB.isMaskSet(HalfEdgeMask.NULL_FACE)) {\r\n const j = unmatchedNullFaceNodes.findIndex((node: HalfEdge) => nodeA === node);\r\n if (j >= 0) {\r\n unmatchedNullFaceNodes[j] = unmatchedNullFaceNodes[unmatchedNullFaceNodes.length - 1];\r\n unmatchedNullFaceNodes.pop();\r\n }\r\n // NO leave nodeA and thetaA ignore nodeB -- later step will get the outside of its banana.\r\n } else {\r\n HalfEdge.pinch(nodeA, nodeB);\r\n if (Angle.isAlmostEqualRadiansAllowPeriodShift(thetaA, thetaB)) {\r\n const nodeA1 = nodeA.faceSuccessor;\r\n const nodeB1 = nodeB.edgeMate;\r\n // WE TRUST -- nodeA1 and node B1 must have identical xy.\r\n // pinch them together and mark the face loop as null ..\r\n HalfEdge.pinch(nodeA1, nodeB1);\r\n nodeA.setMask(HalfEdgeMask.NULL_FACE);\r\n nodeB1.setMask(HalfEdgeMask.NULL_FACE);\r\n unmatchedNullFaceNodes.push(nodeB1);\r\n }\r\n nodeA = nodeB;\r\n thetaA = thetaB;\r\n }\r\n }\r\n }\r\n k0 = k1 + 1;\r\n }\r\n }\r\n }\r\n\r\n private static buildVerticalSweepPriorityQueue(graph: HalfEdgeGraph): HalfEdgePriorityQueueWithPartnerArray {\r\n const sweepHeap = new HalfEdgePriorityQueueWithPartnerArray();\r\n for (const p of graph.allHalfEdges) {\r\n\r\n if (HalfEdgeGraphOps.compareNodesYXUp(p, p.faceSuccessor) < 0) {\r\n sweepHeap.priorityQueue.push(p);\r\n }\r\n }\r\n return sweepHeap;\r\n }\r\n private static snapFractionToNode(xy: Point2d, fraction: number, node: HalfEdge, nodeFraction: number): number{\r\n if (Geometry.isSameCoordinate(xy.x, node.x) && Geometry.isSameCoordinate(xy.y, node.y))\r\n return nodeFraction;\r\n return fraction;\r\n}\r\n private static computeIntersectionFractionsOnEdges(nodeA0: HalfEdge, nodeB0: HalfEdge, fractions: Vector2d, pointA: Point2d, pointB: Point2d): boolean {\r\n const nodeA1 = nodeA0.faceSuccessor;\r\n const ax0 = nodeA0.x;\r\n const ay0 = nodeA0.y;\r\n const ux = nodeA1.x - ax0;\r\n const uy = nodeA1.y - ay0;\r\n const nodeB1 = nodeB0.faceSuccessor;\r\n const bx0 = nodeB0.x;\r\n const by0 = nodeB0.y;\r\n const vx = nodeB1.x - bx0;\r\n const vy = nodeB1.y - by0;\r\n // cspell:word lineSegmentXYUVTransverseIntersectionUnbounded\r\n if (SmallSystem.lineSegmentXYUVTransverseIntersectionUnbounded(ax0, ay0, ux, uy,\r\n bx0, by0, vx, vy, fractions)) {\r\n pointA.x = ax0 + fractions.x * ux;\r\n pointA.y = ay0 + fractions.x * uy;\r\n pointB.x = bx0 + fractions.y * vx;\r\n pointB.y = by0 + fractions.y * vy;\r\n fractions.x = this.snapFractionToNode(pointA, fractions.x, nodeA0, 0.0);\r\n fractions.x = this.snapFractionToNode(pointA, fractions.x, nodeA1, 1.0);\r\n fractions.y = this.snapFractionToNode(pointB, fractions.y, nodeB0, 0.0);\r\n fractions.y = this.snapFractionToNode(pointB, fractions.y, nodeB1, 1.0);\r\n return Geometry.isIn01(fractions.x) && Geometry.isIn01(fractions.y);\r\n }\r\n return false;\r\n }\r\n /**\r\n * Split edges at intersections.\r\n * * This is a large operation.\r\n * @param graph\r\n */\r\n public static splitIntersectingEdges(graph: HalfEdgeGraph): GraphSplitData {\r\n const data = new GraphSplitData();\r\n const sweepHeap = this.buildVerticalSweepPriorityQueue(graph);\r\n let nodeA0, nodeB1;\r\n const smallFraction = 1.0e-8;\r\n const largeFraction = 1.0 - smallFraction;\r\n let i;\r\n const fractions = Vector2d.create();\r\n const pointA = Point2d.create();\r\n const pointB = Point2d.create();\r\n let nodeB0;\r\n const popTolerance = Geometry.smallMetricDistance;\r\n while (undefined !== (nodeA0 = sweepHeap.priorityQueue.pop())) {\r\n data.numUpEdge++;\r\n const n0 = sweepHeap.activeEdges.length;\r\n sweepHeap.removeArrayMembersWithY1Below(nodeA0.y - popTolerance);\r\n data.numPopOut += n0 - sweepHeap.activeEdges.length;\r\n for (i = 0; i < sweepHeap.activeEdges.length; i++) {\r\n nodeB0 = sweepHeap.activeEdges[i];\r\n nodeB1 = nodeB0.faceSuccessor;\r\n // const nodeB1 = nodeB0.faceSuccessor;\r\n if (Geometry.isSameCoordinateXY(nodeA0.x, nodeA0.y, nodeB0.x, nodeB0.y)) {\r\n data.numA0B0++;\r\n } else if (Geometry.isSameCoordinateXY(nodeB1.x, nodeB1.y, nodeA0.x, nodeA0.y)) {\r\n data.numA0B1++;\r\n } else {\r\n data.numIntersectionTest++;\r\n if (this.computeIntersectionFractionsOnEdges(nodeA0, nodeB0, fractions, pointA, pointB)) {\r\n if (fractions.x > smallFraction && fractions.x < largeFraction) {\r\n const nodeC0 = graph.splitEdgeAtFraction(nodeA0, fractions.x);\r\n sweepHeap.priorityQueue.push(nodeC0); // The upper portion will be reviewed as a nodeA0 later !!!\r\n data.numSplit++;\r\n }\r\n if (fractions.y > smallFraction && fractions.y < largeFraction) {\r\n const nodeD0 = graph.splitEdgeAtFraction(nodeB0, fractions.y);\r\n sweepHeap.priorityQueue.push(nodeD0); // The upper portion will be reviewed as a nodeA0 later !!!\r\n data.numSplit++;\r\n }\r\n // existing nodeA0 and its shortened edge remain for further intersections\r\n }\r\n }\r\n }\r\n sweepHeap.activeEdges.push(nodeA0);\r\n }\r\n return data;\r\n }\r\n\r\n /**\r\n * Returns a graph structure formed from the given LineSegment array\r\n *\r\n * * Find all intersections among segments, and split them if necessary\r\n * * Record endpoints of every segment in the form X, Y, Theta; This information is stored as a new node and sorted to match up\r\n * vertices.\r\n * * For vertices that match up, pinch the nodes to create vertex loops, which in closed objects, will also eventually form face\r\n * loops\r\n */\r\n public static formGraphFromSegments(lineSegments: LineSegment3d[]): HalfEdgeGraph {\r\n // Structure of an index of the array: { xyTheta: Point3d, node: Node }\r\n const graph = new HalfEdgeGraph();\r\n HalfEdgeGraphOps.segmentArrayToGraphEdges(lineSegments, graph, HalfEdgeMask.BOUNDARY_EDGE);\r\n this.splitIntersectingEdges(graph);\r\n this.clusterAndMergeXYTheta(graph);\r\n\r\n return graph;\r\n }\r\n\r\n /**\r\n * * Input is random linestrings, not necessarily loops\r\n * * Graph gets full splitEdges, regularize, and triangulate.\r\n * @returns triangulated graph, or undefined if bad data.\r\n */\r\n public static formGraphFromChains(chains: MultiLineStringDataVariant, regularize: boolean = true, mask: HalfEdgeMask = HalfEdgeMask.PRIMARY_EDGE): HalfEdgeGraph | undefined {\r\n if (chains.length < 1)\r\n return undefined;\r\n const graph = new HalfEdgeGraph();\r\n const chainSeeds = Triangulator.directCreateChainsFromCoordinates(graph, chains);\r\n for (const seed of chainSeeds)\r\n seed.setMaskAroundFace(mask);\r\n\r\n this.splitIntersectingEdges(graph);\r\n this.clusterAndMergeXYTheta(graph);\r\n if (regularize) {\r\n const context = new RegularizationContext(graph);\r\n context.regularizeGraph(true, true);\r\n }\r\n return graph;\r\n }\r\n\r\n}\r\n"]}
package/package.json CHANGED
@@ -1,13 +1,15 @@
1
1
  {
2
2
  "name": "@itwin/core-geometry",
3
- "version": "3.1.0-dev.8",
3
+ "version": "3.2.0-dev.12",
4
4
  "description": "iTwin.js Core Geometry library",
5
5
  "main": "lib/cjs/core-geometry.js",
6
6
  "module": "lib/esm/core-geometry.js",
7
7
  "typings": "lib/cjs/core-geometry",
8
8
  "imodeljsSharedLibrary": true,
9
9
  "license": "MIT",
10
- "sideEffects": false,
10
+ "sideEffects": [
11
+ "./lib/esm/core-geometry.js"
12
+ ],
11
13
  "repository": {
12
14
  "type": "git",
13
15
  "url": "https://github.com/iTwin/itwinjs-core/tree/master/core/geometry"
@@ -21,8 +23,8 @@
21
23
  "url": "http://www.bentley.com"
22
24
  },
23
25
  "devDependencies": {
24
- "@itwin/build-tools": "3.1.0-dev.8",
25
- "@itwin/eslint-plugin": "3.1.0-dev.8",
26
+ "@itwin/build-tools": "3.2.0-dev.12",
27
+ "@itwin/eslint-plugin": "3.2.0-dev.12",
26
28
  "@types/chai": "^4.1.4",
27
29
  "@types/flatbuffers": "~1.10.0",
28
30
  "@types/mocha": "^8.2.2",
@@ -37,7 +39,7 @@
37
39
  "typescript": "~4.4.0"
38
40
  },
39
41
  "dependencies": {
40
- "@itwin/core-bentley": "3.1.0-dev.8",
42
+ "@itwin/core-bentley": "3.2.0-dev.12",
41
43
  "flatbuffers": "~1.12.0"
42
44
  },
43
45
  "nyc": {