@itwin/core-geometry 3.4.0-dev.9 → 3.4.0
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.
- package/CHANGELOG.md +59 -1
- package/lib/cjs/clipping/ClipPrimitive.d.ts +3 -3
- package/lib/cjs/clipping/ClipPrimitive.js +3 -3
- package/lib/cjs/clipping/ClipPrimitive.js.map +1 -1
- package/lib/cjs/clipping/ClipUtils.d.ts +1 -1
- package/lib/cjs/clipping/ClipUtils.js +1 -1
- package/lib/cjs/clipping/ClipUtils.js.map +1 -1
- package/lib/cjs/clipping/ClipVector.d.ts +1 -1
- package/lib/cjs/clipping/ClipVector.js +1 -1
- package/lib/cjs/clipping/ClipVector.js.map +1 -1
- package/lib/cjs/clipping/ConvexClipPlaneSet.d.ts +16 -1
- package/lib/cjs/clipping/ConvexClipPlaneSet.d.ts.map +1 -1
- package/lib/cjs/clipping/ConvexClipPlaneSet.js +43 -1
- package/lib/cjs/clipping/ConvexClipPlaneSet.js.map +1 -1
- package/lib/cjs/core-geometry.d.ts +1 -0
- package/lib/cjs/core-geometry.d.ts.map +1 -1
- package/lib/cjs/core-geometry.js +1 -0
- package/lib/cjs/core-geometry.js.map +1 -1
- package/lib/cjs/curve/LineString3d.d.ts +3 -0
- package/lib/cjs/curve/LineString3d.d.ts.map +1 -1
- package/lib/cjs/curve/LineString3d.js +24 -0
- package/lib/cjs/curve/LineString3d.js.map +1 -1
- package/lib/cjs/curve/Query/PlanarSubdivision.d.ts.map +1 -1
- package/lib/cjs/curve/Query/PlanarSubdivision.js +16 -4
- package/lib/cjs/curve/Query/PlanarSubdivision.js.map +1 -1
- package/lib/cjs/curve/internalContexts/MultiChainCollector.d.ts +4 -1
- package/lib/cjs/curve/internalContexts/MultiChainCollector.d.ts.map +1 -1
- package/lib/cjs/curve/internalContexts/MultiChainCollector.js +26 -1
- package/lib/cjs/curve/internalContexts/MultiChainCollector.js.map +1 -1
- package/lib/cjs/geometry3d/AngleSweep.d.ts +1 -1
- package/lib/cjs/geometry3d/AngleSweep.js +1 -1
- package/lib/cjs/geometry3d/AngleSweep.js.map +1 -1
- package/lib/cjs/geometry3d/Point3dVector3d.d.ts +3 -1
- package/lib/cjs/geometry3d/Point3dVector3d.d.ts.map +1 -1
- package/lib/cjs/geometry3d/Point3dVector3d.js +3 -1
- package/lib/cjs/geometry3d/Point3dVector3d.js.map +1 -1
- package/lib/cjs/geometry3d/PointHelpers.d.ts +8 -1
- package/lib/cjs/geometry3d/PointHelpers.d.ts.map +1 -1
- package/lib/cjs/geometry3d/PointHelpers.js +37 -3
- package/lib/cjs/geometry3d/PointHelpers.js.map +1 -1
- package/lib/cjs/geometry3d/PolygonOps.d.ts +11 -3
- package/lib/cjs/geometry3d/PolygonOps.d.ts.map +1 -1
- package/lib/cjs/geometry3d/PolygonOps.js +44 -6
- package/lib/cjs/geometry3d/PolygonOps.js.map +1 -1
- package/lib/cjs/geometry3d/PolylineOps.d.ts +5 -0
- package/lib/cjs/geometry3d/PolylineOps.d.ts.map +1 -1
- package/lib/cjs/geometry3d/PolylineOps.js +20 -0
- package/lib/cjs/geometry3d/PolylineOps.js.map +1 -1
- package/lib/cjs/numerics/ClusterableArray.d.ts +4 -4
- package/lib/cjs/numerics/ClusterableArray.js +5 -5
- package/lib/cjs/numerics/ClusterableArray.js.map +1 -1
- package/lib/cjs/polyface/PolyfaceBuilder.d.ts +3 -3
- package/lib/cjs/polyface/PolyfaceBuilder.d.ts.map +1 -1
- package/lib/cjs/polyface/PolyfaceBuilder.js +8 -6
- package/lib/cjs/polyface/PolyfaceBuilder.js.map +1 -1
- package/lib/cjs/polyface/PolyfaceQuery.d.ts +69 -11
- package/lib/cjs/polyface/PolyfaceQuery.d.ts.map +1 -1
- package/lib/cjs/polyface/PolyfaceQuery.js +163 -15
- package/lib/cjs/polyface/PolyfaceQuery.js.map +1 -1
- package/lib/cjs/serialization/BGFBWriter.d.ts.map +1 -1
- package/lib/cjs/serialization/BGFBWriter.js +1 -0
- package/lib/cjs/serialization/BGFBWriter.js.map +1 -1
- package/lib/cjs/serialization/GeometrySamples.d.ts +11 -0
- package/lib/cjs/serialization/GeometrySamples.d.ts.map +1 -1
- package/lib/cjs/serialization/GeometrySamples.js +51 -0
- package/lib/cjs/serialization/GeometrySamples.js.map +1 -1
- package/lib/cjs/serialization/IModelJsonSchema.d.ts +23 -15
- package/lib/cjs/serialization/IModelJsonSchema.d.ts.map +1 -1
- package/lib/cjs/serialization/IModelJsonSchema.js +17 -8
- package/lib/cjs/serialization/IModelJsonSchema.js.map +1 -1
- package/lib/cjs/solid/Box.d.ts +4 -4
- package/lib/cjs/solid/Box.d.ts.map +1 -1
- package/lib/cjs/solid/Box.js +7 -7
- package/lib/cjs/solid/Box.js.map +1 -1
- package/lib/cjs/topology/Graph.d.ts +3 -3
- package/lib/cjs/topology/Graph.d.ts.map +1 -1
- package/lib/cjs/topology/Graph.js +2 -2
- package/lib/cjs/topology/Graph.js.map +1 -1
- package/lib/cjs/topology/HalfEdgeGraphSearch.d.ts +2 -2
- package/lib/cjs/topology/HalfEdgeGraphSearch.js +2 -2
- package/lib/cjs/topology/HalfEdgeGraphSearch.js.map +1 -1
- package/lib/cjs/topology/Merging.d.ts +5 -1
- package/lib/cjs/topology/Merging.d.ts.map +1 -1
- package/lib/cjs/topology/Merging.js +27 -15
- package/lib/cjs/topology/Merging.js.map +1 -1
- package/lib/cjs/topology/SpaceTriangulation.d.ts +47 -0
- package/lib/cjs/topology/SpaceTriangulation.d.ts.map +1 -0
- package/lib/cjs/topology/SpaceTriangulation.js +135 -0
- package/lib/cjs/topology/SpaceTriangulation.js.map +1 -0
- package/lib/esm/clipping/ClipPrimitive.d.ts +3 -3
- package/lib/esm/clipping/ClipPrimitive.js +3 -3
- package/lib/esm/clipping/ClipPrimitive.js.map +1 -1
- package/lib/esm/clipping/ClipUtils.d.ts +1 -1
- package/lib/esm/clipping/ClipUtils.js +1 -1
- package/lib/esm/clipping/ClipUtils.js.map +1 -1
- package/lib/esm/clipping/ClipVector.d.ts +1 -1
- package/lib/esm/clipping/ClipVector.js +1 -1
- package/lib/esm/clipping/ClipVector.js.map +1 -1
- package/lib/esm/clipping/ConvexClipPlaneSet.d.ts +16 -1
- package/lib/esm/clipping/ConvexClipPlaneSet.d.ts.map +1 -1
- package/lib/esm/clipping/ConvexClipPlaneSet.js +43 -1
- package/lib/esm/clipping/ConvexClipPlaneSet.js.map +1 -1
- package/lib/esm/core-geometry.d.ts +1 -0
- package/lib/esm/core-geometry.d.ts.map +1 -1
- package/lib/esm/core-geometry.js +1 -0
- package/lib/esm/core-geometry.js.map +1 -1
- package/lib/esm/curve/LineString3d.d.ts +3 -0
- package/lib/esm/curve/LineString3d.d.ts.map +1 -1
- package/lib/esm/curve/LineString3d.js +24 -0
- package/lib/esm/curve/LineString3d.js.map +1 -1
- package/lib/esm/curve/Query/PlanarSubdivision.d.ts.map +1 -1
- package/lib/esm/curve/Query/PlanarSubdivision.js +16 -4
- package/lib/esm/curve/Query/PlanarSubdivision.js.map +1 -1
- package/lib/esm/curve/internalContexts/MultiChainCollector.d.ts +4 -1
- package/lib/esm/curve/internalContexts/MultiChainCollector.d.ts.map +1 -1
- package/lib/esm/curve/internalContexts/MultiChainCollector.js +26 -1
- package/lib/esm/curve/internalContexts/MultiChainCollector.js.map +1 -1
- package/lib/esm/geometry3d/AngleSweep.d.ts +1 -1
- package/lib/esm/geometry3d/AngleSweep.js +1 -1
- package/lib/esm/geometry3d/AngleSweep.js.map +1 -1
- package/lib/esm/geometry3d/Point3dVector3d.d.ts +3 -1
- package/lib/esm/geometry3d/Point3dVector3d.d.ts.map +1 -1
- package/lib/esm/geometry3d/Point3dVector3d.js +3 -1
- package/lib/esm/geometry3d/Point3dVector3d.js.map +1 -1
- package/lib/esm/geometry3d/PointHelpers.d.ts +8 -1
- package/lib/esm/geometry3d/PointHelpers.d.ts.map +1 -1
- package/lib/esm/geometry3d/PointHelpers.js +37 -3
- package/lib/esm/geometry3d/PointHelpers.js.map +1 -1
- package/lib/esm/geometry3d/PolygonOps.d.ts +11 -3
- package/lib/esm/geometry3d/PolygonOps.d.ts.map +1 -1
- package/lib/esm/geometry3d/PolygonOps.js +44 -6
- package/lib/esm/geometry3d/PolygonOps.js.map +1 -1
- package/lib/esm/geometry3d/PolylineOps.d.ts +5 -0
- package/lib/esm/geometry3d/PolylineOps.d.ts.map +1 -1
- package/lib/esm/geometry3d/PolylineOps.js +20 -0
- package/lib/esm/geometry3d/PolylineOps.js.map +1 -1
- package/lib/esm/numerics/ClusterableArray.d.ts +4 -4
- package/lib/esm/numerics/ClusterableArray.js +5 -5
- package/lib/esm/numerics/ClusterableArray.js.map +1 -1
- package/lib/esm/polyface/PolyfaceBuilder.d.ts +3 -3
- package/lib/esm/polyface/PolyfaceBuilder.d.ts.map +1 -1
- package/lib/esm/polyface/PolyfaceBuilder.js +8 -6
- package/lib/esm/polyface/PolyfaceBuilder.js.map +1 -1
- package/lib/esm/polyface/PolyfaceQuery.d.ts +69 -11
- package/lib/esm/polyface/PolyfaceQuery.d.ts.map +1 -1
- package/lib/esm/polyface/PolyfaceQuery.js +164 -16
- package/lib/esm/polyface/PolyfaceQuery.js.map +1 -1
- package/lib/esm/serialization/BGFBWriter.d.ts.map +1 -1
- package/lib/esm/serialization/BGFBWriter.js +1 -0
- package/lib/esm/serialization/BGFBWriter.js.map +1 -1
- package/lib/esm/serialization/GeometrySamples.d.ts +11 -0
- package/lib/esm/serialization/GeometrySamples.d.ts.map +1 -1
- package/lib/esm/serialization/GeometrySamples.js +51 -0
- package/lib/esm/serialization/GeometrySamples.js.map +1 -1
- package/lib/esm/serialization/IModelJsonSchema.d.ts +23 -15
- package/lib/esm/serialization/IModelJsonSchema.d.ts.map +1 -1
- package/lib/esm/serialization/IModelJsonSchema.js +17 -8
- package/lib/esm/serialization/IModelJsonSchema.js.map +1 -1
- package/lib/esm/solid/Box.d.ts +4 -4
- package/lib/esm/solid/Box.d.ts.map +1 -1
- package/lib/esm/solid/Box.js +7 -7
- package/lib/esm/solid/Box.js.map +1 -1
- package/lib/esm/topology/Graph.d.ts +3 -3
- package/lib/esm/topology/Graph.d.ts.map +1 -1
- package/lib/esm/topology/Graph.js +2 -2
- package/lib/esm/topology/Graph.js.map +1 -1
- package/lib/esm/topology/HalfEdgeGraphSearch.d.ts +2 -2
- package/lib/esm/topology/HalfEdgeGraphSearch.js +2 -2
- package/lib/esm/topology/HalfEdgeGraphSearch.js.map +1 -1
- package/lib/esm/topology/Merging.d.ts +5 -1
- package/lib/esm/topology/Merging.d.ts.map +1 -1
- package/lib/esm/topology/Merging.js +27 -15
- package/lib/esm/topology/Merging.js.map +1 -1
- package/lib/esm/topology/SpaceTriangulation.d.ts +47 -0
- package/lib/esm/topology/SpaceTriangulation.d.ts.map +1 -0
- package/lib/esm/topology/SpaceTriangulation.js +131 -0
- package/lib/esm/topology/SpaceTriangulation.js.map +1 -0
- package/package.json +8 -6
|
@@ -1,6 +1,3 @@
|
|
|
1
|
-
/** @packageDocumentation
|
|
2
|
-
* @module Polyface
|
|
3
|
-
*/
|
|
4
1
|
import { BagOfCurves, CurveCollection } from "../curve/CurveCollection";
|
|
5
2
|
import { LineSegment3d } from "../curve/LineSegment3d";
|
|
6
3
|
import { LineString3d } from "../curve/LineString3d";
|
|
@@ -14,6 +11,22 @@ import { MomentData } from "../geometry4d/MomentData";
|
|
|
14
11
|
import { IndexedEdgeMatcher } from "./IndexedEdgeMatcher";
|
|
15
12
|
import { IndexedPolyface, Polyface, PolyfaceVisitor } from "./Polyface";
|
|
16
13
|
import { RangeLengthData } from "./RangeLengthData";
|
|
14
|
+
/**
|
|
15
|
+
* Options carrier for cloneWithHolesFilled
|
|
16
|
+
* @public
|
|
17
|
+
*/
|
|
18
|
+
export interface HoleFillOptions {
|
|
19
|
+
/** REJECT hole candidates if its boundary chain is longer than this limit. */
|
|
20
|
+
maxPerimeter?: number;
|
|
21
|
+
/** REJECT hole candidates if they have more than this number of edges */
|
|
22
|
+
maxEdgesAroundHole?: number;
|
|
23
|
+
/** REJECT hole candidates if their orientation is not COUNTERCLOCKWISE around this vector.
|
|
24
|
+
* * For instance, use an upward Z vector for a DTM whose facets face upward. This suppresses incorrectly treating the outer boundary as a hole.
|
|
25
|
+
*/
|
|
26
|
+
upVector?: Vector3d;
|
|
27
|
+
/** requests that all content from the original mesh be copied to the mesh with filled holes. */
|
|
28
|
+
includeOriginalMesh?: boolean;
|
|
29
|
+
}
|
|
17
30
|
/**
|
|
18
31
|
* Structure to return multiple results from volume between facets and plane
|
|
19
32
|
* @public
|
|
@@ -96,11 +109,25 @@ export declare class PolyfaceQuery {
|
|
|
96
109
|
*/
|
|
97
110
|
static isPolyfaceManifold(source: Polyface, allowSimpleBoundaries?: boolean): boolean;
|
|
98
111
|
/**
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
112
|
+
* construct a CurveCollection containing boundary edges.
|
|
113
|
+
* * each edge is a LineSegment3d
|
|
114
|
+
* @param source polyface or visitor
|
|
115
|
+
* @param includeDanglers true to in include typical boundary edges with a single incident facet
|
|
116
|
+
* @param includeMismatch true to include edges with more than 2 incident facets
|
|
117
|
+
* @param includeNull true to include edges with identical start and end vertex indices.
|
|
118
|
+
* @returns
|
|
119
|
+
*/
|
|
103
120
|
static boundaryEdges(source: Polyface | PolyfaceVisitor | undefined, includeDanglers?: boolean, includeMismatch?: boolean, includeNull?: boolean): CurveCollection | undefined;
|
|
121
|
+
/**
|
|
122
|
+
* Test if the facets in `source` occur in perfectly mated pairs, as is required for a closed manifold volume.
|
|
123
|
+
* If not, extract the boundary edges as lines.
|
|
124
|
+
* @param source polyface or visitor
|
|
125
|
+
* @param announceEdge function to be called with each boundary edge. The announcement is start and end points, start and end indices, and facet index.
|
|
126
|
+
* @param includeDanglers true to in include typical boundary edges with a single incident facet
|
|
127
|
+
* @param includeMismatch true to include edges with more than 2 incident facets
|
|
128
|
+
* @param includeNull true to include edges with identical start and end vertex indices.
|
|
129
|
+
*/
|
|
130
|
+
static announceBoundaryEdges(source: Polyface | PolyfaceVisitor | undefined, announceEdge: (pointA: Point3d, pointB: Point3d, indexA: number, indexB: number, facetIndex: number) => void, includeDanglers?: boolean, includeMismatch?: boolean, includeNull?: boolean): void;
|
|
104
131
|
/** Find segments (within the linestring) which project to facets.
|
|
105
132
|
* * Announce each pair of linestring segment and on-facet segment through a callback.
|
|
106
133
|
* * Facets are ASSUMED to be convex and planar.
|
|
@@ -154,9 +181,40 @@ export declare class PolyfaceQuery {
|
|
|
154
181
|
* @param sideAngleTolerance
|
|
155
182
|
*/
|
|
156
183
|
static boundaryOfVisibleSubset(polyface: IndexedPolyface, visibilitySelect: 0 | 1 | 2, vectorToEye: Vector3d, sideAngleTolerance?: Angle): CurveCollection | undefined;
|
|
157
|
-
/**
|
|
158
|
-
*
|
|
184
|
+
/**
|
|
185
|
+
* Search for edges with only 1 incident facet.
|
|
186
|
+
* * chain them into loops
|
|
187
|
+
* * emit the loops to the announceLoop function
|
|
188
|
+
* @param mesh
|
|
159
189
|
*/
|
|
190
|
+
static announceBoundaryChainsAsLineString3d(mesh: Polyface | PolyfaceVisitor, announceLoop: (points: LineString3d) => void): void;
|
|
191
|
+
/**
|
|
192
|
+
* Return a mesh with
|
|
193
|
+
* * clusters of adjacent, coplanar facets merged into larger facets.
|
|
194
|
+
* * other facets included unchanged.
|
|
195
|
+
* @param mesh existing mesh
|
|
196
|
+
* @returns
|
|
197
|
+
*/
|
|
198
|
+
static cloneWithMaximalPlanarFacets(mesh: IndexedPolyface): IndexedPolyface | undefined;
|
|
199
|
+
/**
|
|
200
|
+
* Return a mesh with "some" holes filled in with new facets.
|
|
201
|
+
* * The candidates to be filled are all loops returned by boundaryChainsAsLineString3d
|
|
202
|
+
* * unclosed chains are rejected.
|
|
203
|
+
* * optionally also copy the original mesh, so the composite is a clone with holes filled.
|
|
204
|
+
* * The options structure enforces restrictions on how complicated the hole filling can be:
|
|
205
|
+
* * maxEdgesAroundHole -- holes with more edges are skipped
|
|
206
|
+
* * maxPerimeter -- holes with larger summed edge lengths are skipped.
|
|
207
|
+
* * upVector -- holes that do not have positive area along this view are skipped.
|
|
208
|
+
* * includeOriginalMesh -- includes the original mesh in the output mesh.
|
|
209
|
+
* @param mesh existing mesh
|
|
210
|
+
* @param options options controlling the hole fill.
|
|
211
|
+
* @param unfilledChains optional array to receive the points around holes that were not filled.
|
|
212
|
+
* @returns
|
|
213
|
+
*/
|
|
214
|
+
static fillSimpleHoles(mesh: IndexedPolyface | PolyfaceVisitor, options: HoleFillOptions, unfilledChains?: LineString3d[]): IndexedPolyface | undefined;
|
|
215
|
+
/** Clone the facets in each partition to a separate polyface.
|
|
216
|
+
*
|
|
217
|
+
*/
|
|
160
218
|
static clonePartitions(polyface: Polyface | PolyfaceVisitor, partitions: number[][]): Polyface[];
|
|
161
219
|
/** Clone facets that pass an filter function
|
|
162
220
|
*/
|
|
@@ -168,7 +226,7 @@ export declare class PolyfaceQuery {
|
|
|
168
226
|
/** Search the facets for facet subsets that are connected with at least edge contact.
|
|
169
227
|
* * Return array of arrays of facet indices.
|
|
170
228
|
*/
|
|
171
|
-
static partitionFacetIndicesByEdgeConnectedComponent(polyface: Polyface | PolyfaceVisitor): number[][];
|
|
229
|
+
static partitionFacetIndicesByEdgeConnectedComponent(polyface: Polyface | PolyfaceVisitor, stopAtVisibleEdges?: boolean): number[][];
|
|
172
230
|
/** Find segments (within the linestring) which project to facets.
|
|
173
231
|
* * Assemble each segment pair as a facet in a new polyface
|
|
174
232
|
* * Facets are ASSUMED to be convex and planar.
|
|
@@ -252,7 +310,7 @@ export declare class PolyfaceQuery {
|
|
|
252
310
|
/**
|
|
253
311
|
* * Find mated pairs among facet edges.
|
|
254
312
|
* * Mated pairs have the same vertex indices appearing in opposite order.
|
|
255
|
-
* * Mark all non-mated pairs
|
|
313
|
+
* * Mark all non-mated pairs visible.
|
|
256
314
|
* * At mated pairs
|
|
257
315
|
* * if angle across the edge is larger than `sharpEdgeAngle`, mark visible
|
|
258
316
|
* * otherwise mark invisible.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"PolyfaceQuery.d.ts","sourceRoot":"","sources":["../../../src/polyface/PolyfaceQuery.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"PolyfaceQuery.d.ts","sourceRoot":"","sources":["../../../src/polyface/PolyfaceQuery.ts"],"names":[],"mappings":"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"}
|
|
@@ -7,13 +7,16 @@
|
|
|
7
7
|
*/
|
|
8
8
|
// import { Point2d } from "./Geometry2d";
|
|
9
9
|
/* eslint-disable @typescript-eslint/naming-convention, no-empty */
|
|
10
|
+
import { Point3dArray } from "../geometry3d/PointHelpers";
|
|
10
11
|
import { BagOfCurves } from "../curve/CurveCollection";
|
|
12
|
+
import { MultiChainCollector, OffsetHelpers } from "../curve/internalContexts/MultiChainCollector";
|
|
11
13
|
import { LineSegment3d } from "../curve/LineSegment3d";
|
|
12
14
|
import { LineString3d } from "../curve/LineString3d";
|
|
13
15
|
import { Loop } from "../curve/Loop";
|
|
14
16
|
import { StrokeOptions } from "../curve/StrokeOptions";
|
|
15
17
|
import { Geometry } from "../Geometry";
|
|
16
18
|
import { Angle } from "../geometry3d/Angle";
|
|
19
|
+
import { FrameBuilder } from "../geometry3d/FrameBuilder";
|
|
17
20
|
import { Point3d, Vector3d } from "../geometry3d/Point3dVector3d";
|
|
18
21
|
import { PolygonOps } from "../geometry3d/PolygonOps";
|
|
19
22
|
import { Range3d } from "../geometry3d/Range";
|
|
@@ -21,15 +24,19 @@ import { Matrix4d } from "../geometry4d/Matrix4d";
|
|
|
21
24
|
import { MomentData } from "../geometry4d/MomentData";
|
|
22
25
|
import { UnionFindContext } from "../numerics/UnionFind";
|
|
23
26
|
import { ChainMergeContext } from "../topology/ChainMerge";
|
|
27
|
+
import { HalfEdgeMask } from "../topology/Graph";
|
|
28
|
+
import { HalfEdgeGraphSearch, HalfEdgeMaskTester } from "../topology/HalfEdgeGraphSearch";
|
|
29
|
+
import { HalfEdgeGraphMerge } from "../topology/Merging";
|
|
24
30
|
import { FacetOrientationFixup } from "./FacetOrientation";
|
|
25
31
|
import { IndexedEdgeMatcher, SortableEdge } from "./IndexedEdgeMatcher";
|
|
26
32
|
import { IndexedPolyfaceSubsetVisitor } from "./IndexedPolyfaceVisitor";
|
|
27
33
|
import { BuildAverageNormalsContext } from "./multiclip/BuildAverageNormalsContext";
|
|
28
34
|
import { SweepLineStringToFacetContext } from "./multiclip/SweepLineStringToFacetContext";
|
|
29
35
|
import { XYPointBuckets } from "./multiclip/XYPointBuckets";
|
|
30
|
-
import { Polyface } from "./Polyface";
|
|
36
|
+
import { IndexedPolyface, Polyface } from "./Polyface";
|
|
31
37
|
import { PolyfaceBuilder } from "./PolyfaceBuilder";
|
|
32
38
|
import { RangeLengthData } from "./RangeLengthData";
|
|
39
|
+
import { SpacePolygonTriangulation } from "../topology/SpaceTriangulation";
|
|
33
40
|
/**
|
|
34
41
|
* Enumeration of cases for retaining facets among duplicates
|
|
35
42
|
* @public
|
|
@@ -256,15 +263,39 @@ export class PolyfaceQuery {
|
|
|
256
263
|
return badClusters.length === 0;
|
|
257
264
|
}
|
|
258
265
|
/**
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
266
|
+
* construct a CurveCollection containing boundary edges.
|
|
267
|
+
* * each edge is a LineSegment3d
|
|
268
|
+
* @param source polyface or visitor
|
|
269
|
+
* @param includeDanglers true to in include typical boundary edges with a single incident facet
|
|
270
|
+
* @param includeMismatch true to include edges with more than 2 incident facets
|
|
271
|
+
* @param includeNull true to include edges with identical start and end vertex indices.
|
|
272
|
+
* @returns
|
|
273
|
+
*/
|
|
263
274
|
static boundaryEdges(source, includeDanglers = true, includeMismatch = true, includeNull = true) {
|
|
275
|
+
const result = new BagOfCurves();
|
|
276
|
+
const announceEdge = (pointA, pointB, _indexA, _indexB, _readIndex) => {
|
|
277
|
+
result.tryAddChild(LineSegment3d.create(pointA, pointB));
|
|
278
|
+
};
|
|
279
|
+
PolyfaceQuery.announceBoundaryEdges(source, announceEdge, includeDanglers, includeMismatch, includeNull);
|
|
280
|
+
if (result.children.length === 0)
|
|
281
|
+
return undefined;
|
|
282
|
+
return result;
|
|
283
|
+
}
|
|
284
|
+
/**
|
|
285
|
+
* Test if the facets in `source` occur in perfectly mated pairs, as is required for a closed manifold volume.
|
|
286
|
+
* If not, extract the boundary edges as lines.
|
|
287
|
+
* @param source polyface or visitor
|
|
288
|
+
* @param announceEdge function to be called with each boundary edge. The announcement is start and end points, start and end indices, and facet index.
|
|
289
|
+
* @param includeDanglers true to in include typical boundary edges with a single incident facet
|
|
290
|
+
* @param includeMismatch true to include edges with more than 2 incident facets
|
|
291
|
+
* @param includeNull true to include edges with identical start and end vertex indices.
|
|
292
|
+
*/
|
|
293
|
+
static announceBoundaryEdges(source, announceEdge, includeDanglers = true, includeMismatch = true, includeNull = true) {
|
|
264
294
|
if (source === undefined)
|
|
265
295
|
return undefined;
|
|
266
296
|
const edges = new IndexedEdgeMatcher();
|
|
267
297
|
const visitor = source instanceof Polyface ? source.createVisitor(1) : source;
|
|
298
|
+
visitor.setNumWrap(1);
|
|
268
299
|
visitor.reset();
|
|
269
300
|
while (visitor.moveToNextFacet()) {
|
|
270
301
|
const numEdges = visitor.pointCount - 1;
|
|
@@ -286,7 +317,6 @@ export class PolyfaceQuery {
|
|
|
286
317
|
if (badList.length === 0)
|
|
287
318
|
return undefined;
|
|
288
319
|
const sourcePolyface = visitor.clientPolyface();
|
|
289
|
-
const result = new BagOfCurves();
|
|
290
320
|
for (const list of badList) {
|
|
291
321
|
for (const e of list) {
|
|
292
322
|
const e1 = e instanceof SortableEdge ? e : e[0];
|
|
@@ -295,10 +325,9 @@ export class PolyfaceQuery {
|
|
|
295
325
|
const pointA = sourcePolyface.data.getPoint(indexA);
|
|
296
326
|
const pointB = sourcePolyface.data.getPoint(indexB);
|
|
297
327
|
if (pointA && pointB)
|
|
298
|
-
|
|
328
|
+
announceEdge(pointA, pointB, indexA, indexB, visitor.currentReadIndex());
|
|
299
329
|
}
|
|
300
330
|
}
|
|
301
|
-
return result;
|
|
302
331
|
}
|
|
303
332
|
/** Find segments (within the linestring) which project to facets.
|
|
304
333
|
* * Announce each pair of linestring segment and on-facet segment through a callback.
|
|
@@ -441,9 +470,124 @@ export class PolyfaceQuery {
|
|
|
441
470
|
const visitor = IndexedPolyfaceSubsetVisitor.createSubsetVisitor(polyface, partitionedIndices[visibilitySelect], 1);
|
|
442
471
|
return this.boundaryEdges(visitor, true, false, false);
|
|
443
472
|
}
|
|
444
|
-
/**
|
|
445
|
-
*
|
|
473
|
+
/**
|
|
474
|
+
* Search for edges with only 1 incident facet.
|
|
475
|
+
* * chain them into loops
|
|
476
|
+
* * emit the loops to the announceLoop function
|
|
477
|
+
* @param mesh
|
|
478
|
+
*/
|
|
479
|
+
static announceBoundaryChainsAsLineString3d(mesh, announceLoop) {
|
|
480
|
+
const collector = new MultiChainCollector(Geometry.smallMetricDistance, 1000);
|
|
481
|
+
PolyfaceQuery.announceBoundaryEdges(mesh, (pointA, pointB, _indexA, _indexB) => collector.captureCurve(LineSegment3d.create(pointA, pointB)), true, false, false);
|
|
482
|
+
collector.announceChainsAsLineString3d(announceLoop);
|
|
483
|
+
}
|
|
484
|
+
/**
|
|
485
|
+
* Return a mesh with
|
|
486
|
+
* * clusters of adjacent, coplanar facets merged into larger facets.
|
|
487
|
+
* * other facets included unchanged.
|
|
488
|
+
* @param mesh existing mesh
|
|
489
|
+
* @returns
|
|
490
|
+
*/
|
|
491
|
+
static cloneWithMaximalPlanarFacets(mesh) {
|
|
492
|
+
PolyfaceQuery.markPairedEdgesInvisible(mesh, Angle.createRadians(Geometry.smallAngleRadians));
|
|
493
|
+
const partitions = PolyfaceQuery.partitionFacetIndicesByEdgeConnectedComponent(mesh, true);
|
|
494
|
+
const builder = PolyfaceBuilder.create();
|
|
495
|
+
const visitor = mesh.createVisitor(0);
|
|
496
|
+
const planarPartitions = [];
|
|
497
|
+
for (const partition of partitions) {
|
|
498
|
+
if (partition.length === 1) {
|
|
499
|
+
if (visitor.moveToReadIndex(partition[0]))
|
|
500
|
+
builder.addFacetFromVisitor(visitor);
|
|
501
|
+
}
|
|
502
|
+
else {
|
|
503
|
+
// This is a non-trivial set of contiguous coplanar facets
|
|
504
|
+
planarPartitions.push(partition);
|
|
505
|
+
}
|
|
506
|
+
}
|
|
507
|
+
const fragmentPolyfaces = PolyfaceQuery.clonePartitions(mesh, planarPartitions);
|
|
508
|
+
const gapTolerance = 1.0e-4;
|
|
509
|
+
const planarityTolerance = 1.0e-4;
|
|
510
|
+
for (const fragment of fragmentPolyfaces) {
|
|
511
|
+
const edges = [];
|
|
512
|
+
const edgeStrings = [];
|
|
513
|
+
PolyfaceQuery.announceBoundaryEdges(fragment, (pointA, pointB, _indexA, _indexB) => {
|
|
514
|
+
edges.push(LineSegment3d.create(pointA, pointB));
|
|
515
|
+
edgeStrings.push([pointA.clone(), pointB.clone()]);
|
|
516
|
+
});
|
|
517
|
+
const chains = OffsetHelpers.collectChains(edges, gapTolerance, planarityTolerance);
|
|
518
|
+
if (chains) {
|
|
519
|
+
const frameBuilder = new FrameBuilder();
|
|
520
|
+
frameBuilder.announce(chains);
|
|
521
|
+
const frame = frameBuilder.getValidatedFrame(false);
|
|
522
|
+
if (frame !== undefined) {
|
|
523
|
+
const inverseFrame = frame.inverse();
|
|
524
|
+
if (inverseFrame !== undefined) {
|
|
525
|
+
inverseFrame.multiplyPoint3dArrayArrayInPlace(edgeStrings);
|
|
526
|
+
const graph = HalfEdgeGraphMerge.formGraphFromChains(edgeStrings, true, HalfEdgeMask.BOUNDARY_EDGE);
|
|
527
|
+
if (graph) {
|
|
528
|
+
HalfEdgeGraphSearch.collectConnectedComponentsWithExteriorParityMasks(graph, new HalfEdgeMaskTester(HalfEdgeMask.BOUNDARY_EDGE), HalfEdgeMask.EXTERIOR);
|
|
529
|
+
// this.purgeNullFaces(HalfEdgeMask.EXTERIOR);
|
|
530
|
+
const polyface1 = PolyfaceBuilder.graphToPolyface(graph);
|
|
531
|
+
builder.addIndexedPolyface(polyface1, false, frame);
|
|
532
|
+
}
|
|
533
|
+
}
|
|
534
|
+
}
|
|
535
|
+
}
|
|
536
|
+
}
|
|
537
|
+
return builder.claimPolyface(true);
|
|
538
|
+
}
|
|
539
|
+
/**
|
|
540
|
+
* Return a mesh with "some" holes filled in with new facets.
|
|
541
|
+
* * The candidates to be filled are all loops returned by boundaryChainsAsLineString3d
|
|
542
|
+
* * unclosed chains are rejected.
|
|
543
|
+
* * optionally also copy the original mesh, so the composite is a clone with holes filled.
|
|
544
|
+
* * The options structure enforces restrictions on how complicated the hole filling can be:
|
|
545
|
+
* * maxEdgesAroundHole -- holes with more edges are skipped
|
|
546
|
+
* * maxPerimeter -- holes with larger summed edge lengths are skipped.
|
|
547
|
+
* * upVector -- holes that do not have positive area along this view are skipped.
|
|
548
|
+
* * includeOriginalMesh -- includes the original mesh in the output mesh.
|
|
549
|
+
* @param mesh existing mesh
|
|
550
|
+
* @param options options controlling the hole fill.
|
|
551
|
+
* @param unfilledChains optional array to receive the points around holes that were not filled.
|
|
552
|
+
* @returns
|
|
446
553
|
*/
|
|
554
|
+
static fillSimpleHoles(mesh, options, unfilledChains) {
|
|
555
|
+
if (mesh instanceof IndexedPolyface)
|
|
556
|
+
return this.fillSimpleHoles(mesh.createVisitor(0), options, unfilledChains);
|
|
557
|
+
const builder = PolyfaceBuilder.create();
|
|
558
|
+
const chains = [];
|
|
559
|
+
PolyfaceQuery.announceBoundaryChainsAsLineString3d(mesh, (ls) => { ls.reverseInPlace(); chains.push(ls); });
|
|
560
|
+
for (const c of chains) {
|
|
561
|
+
const points = c.points;
|
|
562
|
+
let rejected = false;
|
|
563
|
+
if (!c.isPhysicallyClosed)
|
|
564
|
+
rejected = true;
|
|
565
|
+
else if (options.maxEdgesAroundHole !== undefined && points.length > options.maxEdgesAroundHole)
|
|
566
|
+
rejected = true;
|
|
567
|
+
else if (options.maxPerimeter !== undefined && Point3dArray.sumEdgeLengths(points, false) > options.maxPerimeter)
|
|
568
|
+
rejected = true;
|
|
569
|
+
else if (options.upVector !== undefined && PolygonOps.sumTriangleAreasPerpendicularToUpVector(points, options.upVector) <= 0.0)
|
|
570
|
+
rejected = true;
|
|
571
|
+
if (!rejected && SpacePolygonTriangulation.triangulateSimplestSpaceLoop(points, (_loop, triangles) => {
|
|
572
|
+
for (const t of triangles)
|
|
573
|
+
builder.addPolygon(t);
|
|
574
|
+
})) {
|
|
575
|
+
}
|
|
576
|
+
else {
|
|
577
|
+
rejected = true;
|
|
578
|
+
}
|
|
579
|
+
if (rejected && unfilledChains !== undefined)
|
|
580
|
+
unfilledChains.push(c); // yes, capture it -- this scope owns the chains and has no further use for it.
|
|
581
|
+
}
|
|
582
|
+
if (options.includeOriginalMesh !== undefined && options.includeOriginalMesh) {
|
|
583
|
+
for (mesh.reset(); mesh.moveToNextFacet();)
|
|
584
|
+
builder.addFacetFromVisitor(mesh);
|
|
585
|
+
}
|
|
586
|
+
return builder.claimPolyface(true);
|
|
587
|
+
}
|
|
588
|
+
/** Clone the facets in each partition to a separate polyface.
|
|
589
|
+
*
|
|
590
|
+
*/
|
|
447
591
|
static clonePartitions(polyface, partitions) {
|
|
448
592
|
if (polyface instanceof Polyface) {
|
|
449
593
|
return this.clonePartitions(polyface.createVisitor(0), partitions);
|
|
@@ -505,9 +649,9 @@ export class PolyfaceQuery {
|
|
|
505
649
|
/** Search the facets for facet subsets that are connected with at least edge contact.
|
|
506
650
|
* * Return array of arrays of facet indices.
|
|
507
651
|
*/
|
|
508
|
-
static partitionFacetIndicesByEdgeConnectedComponent(polyface) {
|
|
652
|
+
static partitionFacetIndicesByEdgeConnectedComponent(polyface, stopAtVisibleEdges = false) {
|
|
509
653
|
if (polyface instanceof Polyface) {
|
|
510
|
-
return this.partitionFacetIndicesByEdgeConnectedComponent(polyface.createVisitor(0));
|
|
654
|
+
return this.partitionFacetIndicesByEdgeConnectedComponent(polyface.createVisitor(0), stopAtVisibleEdges);
|
|
511
655
|
}
|
|
512
656
|
polyface.setNumWrap(1);
|
|
513
657
|
const matcher = new IndexedEdgeMatcher();
|
|
@@ -517,7 +661,11 @@ export class PolyfaceQuery {
|
|
|
517
661
|
const numEdges = polyface.pointCount - 1;
|
|
518
662
|
numFacets++;
|
|
519
663
|
for (let i = 0; i < numEdges; i++) {
|
|
520
|
-
|
|
664
|
+
if (stopAtVisibleEdges && polyface.edgeVisible[i]) {
|
|
665
|
+
}
|
|
666
|
+
else {
|
|
667
|
+
matcher.addEdge(polyface.clientPointIndex(i), polyface.clientPointIndex(i + 1), polyface.currentReadIndex());
|
|
668
|
+
}
|
|
521
669
|
}
|
|
522
670
|
}
|
|
523
671
|
const allEdges = [];
|
|
@@ -661,7 +809,7 @@ export class PolyfaceQuery {
|
|
|
661
809
|
}
|
|
662
810
|
}
|
|
663
811
|
}
|
|
664
|
-
builder.addFacetFromGrowableArrays(newFacetVisitor.point, newFacetVisitor.normal, newFacetVisitor.param, newFacetVisitor.color);
|
|
812
|
+
builder.addFacetFromGrowableArrays(newFacetVisitor.point, newFacetVisitor.normal, newFacetVisitor.param, newFacetVisitor.color, newFacetVisitor.edgeVisible);
|
|
665
813
|
}
|
|
666
814
|
return builder.claimPolyface();
|
|
667
815
|
}
|
|
@@ -816,7 +964,7 @@ export class PolyfaceQuery {
|
|
|
816
964
|
}
|
|
817
965
|
}
|
|
818
966
|
if (newFacetVisitor.point.length > 2)
|
|
819
|
-
builder.addFacetFromGrowableArrays(newFacetVisitor.point, newFacetVisitor.normal, newFacetVisitor.param, newFacetVisitor.color);
|
|
967
|
+
builder.addFacetFromGrowableArrays(newFacetVisitor.point, newFacetVisitor.normal, newFacetVisitor.param, newFacetVisitor.color, newFacetVisitor.edgeVisible);
|
|
820
968
|
}
|
|
821
969
|
return builder.claimPolyface();
|
|
822
970
|
}
|
|
@@ -871,7 +1019,7 @@ export class PolyfaceQuery {
|
|
|
871
1019
|
/**
|
|
872
1020
|
* * Find mated pairs among facet edges.
|
|
873
1021
|
* * Mated pairs have the same vertex indices appearing in opposite order.
|
|
874
|
-
* * Mark all non-mated pairs
|
|
1022
|
+
* * Mark all non-mated pairs visible.
|
|
875
1023
|
* * At mated pairs
|
|
876
1024
|
* * if angle across the edge is larger than `sharpEdgeAngle`, mark visible
|
|
877
1025
|
* * otherwise mark invisible.
|