forgecad 0.9.8 → 0.9.9
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/dist/assets/{AdminPage-CXaVLMiV.js → AdminPage-CNEvQM7c.js} +1 -1
- package/dist/assets/{BlogPage-Crpr3JjH.js → BlogPage-Cc41PP4d.js} +1 -1
- package/dist/assets/{DocsPage-CNBKuitP.js → DocsPage-9U1hGjrg.js} +1 -1
- package/dist/assets/{EditorApp-DVMnXOmO.js → EditorApp-DnddQvBt.js} +5 -5
- package/dist/assets/{EmbedViewer-KXFLSnpo.js → EmbedViewer-B2lhWTcd.js} +2 -2
- package/dist/assets/{LandingPageProofDriven-2q2sn7aW.js → LandingPageProofDriven-CFet-l3o.js} +1 -1
- package/dist/assets/{PricingPage-CVvgdv0i.js → PricingPage-CPm8mQx3.js} +1 -1
- package/dist/assets/{SettingsPage-BVj1FtEv.js → SettingsPage-BarZonVZ.js} +1 -1
- package/dist/assets/{app-Dn4EwHhN.js → app-BjSEB4sY.js} +309 -78
- package/dist/assets/cli/{render-BI3gLMXz.js → render-CXVrHY8q.js} +5 -705
- package/dist/assets/{manifold-C6-sZYQN.js → manifold-BRdhoQy5.js} +2 -2
- package/dist/assets/{renderSceneState-BIvOkPK3.js → renderSceneState-CWO8rHlt.js} +1 -1
- package/dist/assets/{scalar-sampling-budget-iBAeF8RM.js → scalar-sampling-budget-Bmewod18.js} +910 -198
- package/dist/cli/render.html +1 -1
- package/dist/index.html +1 -1
- package/package.json +1 -1
package/dist/assets/{scalar-sampling-budget-iBAeF8RM.js → scalar-sampling-budget-Bmewod18.js}
RENAMED
|
@@ -806,11 +806,11 @@ function isFinitePositive$3(value) {
|
|
|
806
806
|
function isFiniteNonNegative(value) {
|
|
807
807
|
return Number.isFinite(value) && value >= 0;
|
|
808
808
|
}
|
|
809
|
-
function cloneVec3$
|
|
809
|
+
function cloneVec3$6(vec2) {
|
|
810
810
|
return [vec2[0], vec2[1], vec2[2]];
|
|
811
811
|
}
|
|
812
812
|
function cloneFaceAxis(vec2) {
|
|
813
|
-
return vec2 ? cloneVec3$
|
|
813
|
+
return vec2 ? cloneVec3$6(vec2) : void 0;
|
|
814
814
|
}
|
|
815
815
|
function cloneSheetMetalModel(model) {
|
|
816
816
|
if (!model) return null;
|
|
@@ -1120,8 +1120,8 @@ function lowerSheetMetalBasePlan(model, output) {
|
|
|
1120
1120
|
function descriptor(name, center, normal, planar, uAxis, vAxis, semantic = "face", memberNames = [name], coplanar = planar) {
|
|
1121
1121
|
return {
|
|
1122
1122
|
name,
|
|
1123
|
-
center: cloneVec3$
|
|
1124
|
-
normal: cloneVec3$
|
|
1123
|
+
center: cloneVec3$6(center),
|
|
1124
|
+
normal: cloneVec3$6(normal),
|
|
1125
1125
|
planar,
|
|
1126
1126
|
uAxis: cloneFaceAxis(uAxis),
|
|
1127
1127
|
vAxis: cloneFaceAxis(vAxis),
|
|
@@ -1374,10 +1374,10 @@ function describeSheetMetalPlanarRegionFrames(model, output) {
|
|
|
1374
1374
|
const size = sheetMetalPlanarRegionSize(derived, face.name);
|
|
1375
1375
|
return {
|
|
1376
1376
|
name: face.name,
|
|
1377
|
-
center: cloneVec3$
|
|
1378
|
-
normal: cloneVec3$
|
|
1379
|
-
uAxis: cloneVec3$
|
|
1380
|
-
vAxis: cloneVec3$
|
|
1377
|
+
center: cloneVec3$6(face.center),
|
|
1378
|
+
normal: cloneVec3$6(face.normal),
|
|
1379
|
+
uAxis: cloneVec3$6(face.uAxis),
|
|
1380
|
+
vAxis: cloneVec3$6(face.vAxis),
|
|
1381
1381
|
width: size.width,
|
|
1382
1382
|
height: size.height,
|
|
1383
1383
|
thickness: derived.thickness
|
|
@@ -8367,7 +8367,7 @@ function sub$7(a2, b) {
|
|
|
8367
8367
|
function cross$8(a2, b) {
|
|
8368
8368
|
return [a2[1] * b[2] - a2[2] * b[1], a2[2] * b[0] - a2[0] * b[2], a2[0] * b[1] - a2[1] * b[0]];
|
|
8369
8369
|
}
|
|
8370
|
-
function makeEdge(name, start, end, faceName, curve) {
|
|
8370
|
+
function makeEdge$1(name, start, end, faceName, curve) {
|
|
8371
8371
|
return {
|
|
8372
8372
|
name,
|
|
8373
8373
|
start,
|
|
@@ -8411,10 +8411,10 @@ function buildSurfaceSheetTopology(boundaries, options = {}) {
|
|
|
8411
8411
|
surface: options.surface
|
|
8412
8412
|
});
|
|
8413
8413
|
const edges = /* @__PURE__ */ new Map();
|
|
8414
|
-
edges.set("u0", makeEdge("u0", u0Start, u0End, faceName, (_a3 = options.edgeCurves) == null ? void 0 : _a3.u0));
|
|
8415
|
-
edges.set("u1", makeEdge("u1", u1Start, u1End, faceName, (_b3 = options.edgeCurves) == null ? void 0 : _b3.u1));
|
|
8416
|
-
edges.set("v0", makeEdge("v0", v0Start, v0End, faceName, (_c2 = options.edgeCurves) == null ? void 0 : _c2.v0));
|
|
8417
|
-
edges.set("v1", makeEdge("v1", v1Start, v1End, faceName, (_d2 = options.edgeCurves) == null ? void 0 : _d2.v1));
|
|
8414
|
+
edges.set("u0", makeEdge$1("u0", u0Start, u0End, faceName, (_a3 = options.edgeCurves) == null ? void 0 : _a3.u0));
|
|
8415
|
+
edges.set("u1", makeEdge$1("u1", u1Start, u1End, faceName, (_b3 = options.edgeCurves) == null ? void 0 : _b3.u1));
|
|
8416
|
+
edges.set("v0", makeEdge$1("v0", v0Start, v0End, faceName, (_c2 = options.edgeCurves) == null ? void 0 : _c2.v0));
|
|
8417
|
+
edges.set("v1", makeEdge$1("v1", v1Start, v1End, faceName, (_d2 = options.edgeCurves) == null ? void 0 : _d2.v1));
|
|
8418
8418
|
return { faces, edges };
|
|
8419
8419
|
}
|
|
8420
8420
|
function attachSurfaceSheetTopology(shape, boundaries, options = {}) {
|
|
@@ -8432,7 +8432,7 @@ function attachSurfaceSheetTopology(shape, boundaries, options = {}) {
|
|
|
8432
8432
|
});
|
|
8433
8433
|
return shape;
|
|
8434
8434
|
}
|
|
8435
|
-
function cloneVec3$
|
|
8435
|
+
function cloneVec3$5(value) {
|
|
8436
8436
|
return [value[0], value[1], value[2]];
|
|
8437
8437
|
}
|
|
8438
8438
|
function cloneNurbsFaceTrimLoop(loop) {
|
|
@@ -8454,38 +8454,38 @@ function cloneFaceSurface(surface) {
|
|
|
8454
8454
|
if (!surface) return void 0;
|
|
8455
8455
|
switch (surface.kind) {
|
|
8456
8456
|
case "plane":
|
|
8457
|
-
return { kind: "plane", normal: cloneVec3$
|
|
8457
|
+
return { kind: "plane", normal: cloneVec3$5(surface.normal) };
|
|
8458
8458
|
case "cylinder":
|
|
8459
8459
|
return {
|
|
8460
8460
|
kind: "cylinder",
|
|
8461
|
-
origin: cloneVec3$
|
|
8462
|
-
axis: cloneVec3$
|
|
8461
|
+
origin: cloneVec3$5(surface.origin),
|
|
8462
|
+
axis: cloneVec3$5(surface.axis),
|
|
8463
8463
|
radius: surface.radius,
|
|
8464
8464
|
height: surface.height
|
|
8465
8465
|
};
|
|
8466
8466
|
case "cone":
|
|
8467
8467
|
return {
|
|
8468
8468
|
kind: "cone",
|
|
8469
|
-
origin: cloneVec3$
|
|
8470
|
-
axis: cloneVec3$
|
|
8469
|
+
origin: cloneVec3$5(surface.origin),
|
|
8470
|
+
axis: cloneVec3$5(surface.axis),
|
|
8471
8471
|
radiusBottom: surface.radiusBottom,
|
|
8472
8472
|
radiusTop: surface.radiusTop,
|
|
8473
8473
|
height: surface.height
|
|
8474
8474
|
};
|
|
8475
8475
|
case "sphere":
|
|
8476
|
-
return { kind: "sphere", center: cloneVec3$
|
|
8476
|
+
return { kind: "sphere", center: cloneVec3$5(surface.center), radius: surface.radius };
|
|
8477
8477
|
case "torus":
|
|
8478
8478
|
return {
|
|
8479
8479
|
kind: "torus",
|
|
8480
|
-
center: cloneVec3$
|
|
8481
|
-
axis: cloneVec3$
|
|
8480
|
+
center: cloneVec3$5(surface.center),
|
|
8481
|
+
axis: cloneVec3$5(surface.axis),
|
|
8482
8482
|
majorRadius: surface.majorRadius,
|
|
8483
8483
|
minorRadius: surface.minorRadius
|
|
8484
8484
|
};
|
|
8485
8485
|
case "ruled":
|
|
8486
8486
|
return {
|
|
8487
8487
|
kind: "ruled",
|
|
8488
|
-
rails: surface.rails.map((rail2) => rail2.map(cloneVec3$
|
|
8488
|
+
rails: surface.rails.map((rail2) => rail2.map(cloneVec3$5))
|
|
8489
8489
|
};
|
|
8490
8490
|
case "nurbs":
|
|
8491
8491
|
return {
|
|
@@ -8498,9 +8498,9 @@ function cloneEdgeCurve(curve) {
|
|
|
8498
8498
|
if (!curve) return void 0;
|
|
8499
8499
|
switch (curve.kind) {
|
|
8500
8500
|
case "line":
|
|
8501
|
-
return { ...curve, start: cloneVec3$
|
|
8501
|
+
return { ...curve, start: cloneVec3$5(curve.start), end: cloneVec3$5(curve.end) };
|
|
8502
8502
|
case "circle":
|
|
8503
|
-
return { ...curve, center: cloneVec3$
|
|
8503
|
+
return { ...curve, center: cloneVec3$5(curve.center), axis: cloneVec3$5(curve.axis) };
|
|
8504
8504
|
case "surfaceIso":
|
|
8505
8505
|
return { ...curve, parameterRange: [curve.parameterRange[0], curve.parameterRange[1]] };
|
|
8506
8506
|
case "nurbsUv":
|
|
@@ -8518,7 +8518,7 @@ function cloneEdgeCurve(curve) {
|
|
|
8518
8518
|
}
|
|
8519
8519
|
}
|
|
8520
8520
|
function makeLineEdgeCurve(start, end, faceName) {
|
|
8521
|
-
return faceName ? { kind: "line", start: cloneVec3$
|
|
8521
|
+
return faceName ? { kind: "line", start: cloneVec3$5(start), end: cloneVec3$5(end), faceName } : { kind: "line", start: cloneVec3$5(start), end: cloneVec3$5(end) };
|
|
8522
8522
|
}
|
|
8523
8523
|
function edgeCurveFaceName(curve) {
|
|
8524
8524
|
switch (curve.kind) {
|
|
@@ -10605,7 +10605,7 @@ async function initManifoldWasm() {
|
|
|
10605
10605
|
if (_wasm$1) return _wasm$1;
|
|
10606
10606
|
performance.mark("manifold:start");
|
|
10607
10607
|
const Module = (await __vitePreload(async () => {
|
|
10608
|
-
const { default: __vite_default__ } = await import("./manifold-
|
|
10608
|
+
const { default: __vite_default__ } = await import("./manifold-BRdhoQy5.js");
|
|
10609
10609
|
return { default: __vite_default__ };
|
|
10610
10610
|
}, true ? [] : void 0)).default;
|
|
10611
10611
|
performance.mark("manifold:imported");
|
|
@@ -22489,7 +22489,7 @@ function marchingTetrahedra(sdfFn, bounds, edgeLength2) {
|
|
|
22489
22489
|
};
|
|
22490
22490
|
}
|
|
22491
22491
|
const EPS$8 = 1e-9;
|
|
22492
|
-
function finitePositive(value) {
|
|
22492
|
+
function finitePositive$1(value) {
|
|
22493
22493
|
return Number.isFinite(value) && value > EPS$8;
|
|
22494
22494
|
}
|
|
22495
22495
|
function clampNonNegative(value) {
|
|
@@ -22508,7 +22508,7 @@ function distancePreservingMatrixScale(matrix) {
|
|
|
22508
22508
|
const sx = length4(col0);
|
|
22509
22509
|
const sy = length4(col1);
|
|
22510
22510
|
const sz = length4(col2);
|
|
22511
|
-
if (!finitePositive(sx) || !finitePositive(sy) || !finitePositive(sz)) return null;
|
|
22511
|
+
if (!finitePositive$1(sx) || !finitePositive$1(sy) || !finitePositive$1(sz)) return null;
|
|
22512
22512
|
if (Math.abs(sx - sy) > EPS$8 || Math.abs(sx - sz) > EPS$8) return null;
|
|
22513
22513
|
if (Math.abs(dot2(col0, col1)) > EPS$8 || Math.abs(dot2(col0, col2)) > EPS$8 || Math.abs(dot2(col1, col2)) > EPS$8) return null;
|
|
22514
22514
|
return sx;
|
|
@@ -22525,7 +22525,7 @@ function transformStepDistanceScale(step) {
|
|
|
22525
22525
|
const sx = Math.abs(step.x);
|
|
22526
22526
|
const sy = Math.abs(step.y);
|
|
22527
22527
|
const sz = Math.abs(step.z);
|
|
22528
|
-
if (!finitePositive(sx) || !finitePositive(sy) || !finitePositive(sz)) return null;
|
|
22528
|
+
if (!finitePositive$1(sx) || !finitePositive$1(sy) || !finitePositive$1(sz)) return null;
|
|
22529
22529
|
return Math.abs(sx - sy) <= EPS$8 && Math.abs(sx - sz) <= EPS$8 ? sx : null;
|
|
22530
22530
|
}
|
|
22531
22531
|
}
|
|
@@ -22565,7 +22565,7 @@ function translatedPlan(base, z2) {
|
|
|
22565
22565
|
};
|
|
22566
22566
|
}
|
|
22567
22567
|
function offsetCylinderDimensions(plan, thickness) {
|
|
22568
|
-
if (!finitePositive(plan.height)) return null;
|
|
22568
|
+
if (!finitePositive$1(plan.height)) return null;
|
|
22569
22569
|
const radiusTop = plan.radiusTop ?? plan.radius;
|
|
22570
22570
|
const slope = (radiusTop - plan.radius) / plan.height;
|
|
22571
22571
|
const normalScale = Math.hypot(1, slope);
|
|
@@ -22574,7 +22574,7 @@ function offsetCylinderDimensions(plan, thickness) {
|
|
|
22574
22574
|
const height = zMax - zMin;
|
|
22575
22575
|
const radiusBottom = plan.radius + thickness * (normalScale - slope);
|
|
22576
22576
|
const offsetRadiusTop = radiusTop + thickness * (normalScale + slope);
|
|
22577
|
-
if (!finitePositive(height) || radiusBottom < -EPS$8 || offsetRadiusTop < -EPS$8) return null;
|
|
22577
|
+
if (!finitePositive$1(height) || radiusBottom < -EPS$8 || offsetRadiusTop < -EPS$8) return null;
|
|
22578
22578
|
return {
|
|
22579
22579
|
zMin,
|
|
22580
22580
|
height,
|
|
@@ -22632,7 +22632,7 @@ function rectangleCandidatePointsFromProfile(plan) {
|
|
|
22632
22632
|
case "rect": {
|
|
22633
22633
|
const width = Math.abs(plan.width);
|
|
22634
22634
|
const height = Math.abs(plan.height);
|
|
22635
|
-
if (!finitePositive(width) || !finitePositive(height)) return null;
|
|
22635
|
+
if (!finitePositive$1(width) || !finitePositive$1(height)) return null;
|
|
22636
22636
|
const halfWidth = width / 2;
|
|
22637
22637
|
const halfHeight = height / 2;
|
|
22638
22638
|
const points = [
|
|
@@ -22666,7 +22666,7 @@ function rectangleFootprintFromProfile(plan) {
|
|
|
22666
22666
|
const [xMin, xMax] = xs;
|
|
22667
22667
|
const [zMin, zMax] = zs;
|
|
22668
22668
|
if (xMin == null || xMax == null || zMin == null || zMax == null) return null;
|
|
22669
|
-
if (xMin < -EPS$8 || !finitePositive(xMax) || !finitePositive(zMax - zMin)) return null;
|
|
22669
|
+
if (xMin < -EPS$8 || !finitePositive$1(xMax) || !finitePositive$1(zMax - zMin)) return null;
|
|
22670
22670
|
const hasCorner = (x2, z2) => points.some(([px2, pz2]) => sameScalar$1(px2, x2) && sameScalar$1(pz2, z2));
|
|
22671
22671
|
if (!hasCorner(xMin, zMin) || !hasCorner(xMax, zMin) || !hasCorner(xMax, zMax) || !hasCorner(xMin, zMax)) return null;
|
|
22672
22672
|
return {
|
|
@@ -22679,7 +22679,7 @@ function rectangleFootprintFromProfile(plan) {
|
|
|
22679
22679
|
function circleFootprintFromProfile(plan) {
|
|
22680
22680
|
if (plan.kind !== "circle") return null;
|
|
22681
22681
|
const radius = Math.abs(plan.radius);
|
|
22682
|
-
if (!finitePositive(radius)) return null;
|
|
22682
|
+
if (!finitePositive$1(radius)) return null;
|
|
22683
22683
|
const center = transformProfilePointThrough$1([0, 0], plan.transforms);
|
|
22684
22684
|
const xPoint = transformProfilePointThrough$1([1, 0], plan.transforms);
|
|
22685
22685
|
const yPoint = transformProfilePointThrough$1([0, 1], plan.transforms);
|
|
@@ -22688,7 +22688,7 @@ function circleFootprintFromProfile(plan) {
|
|
|
22688
22688
|
const xScale = Math.hypot(xAxis[0], xAxis[1]);
|
|
22689
22689
|
const yScale = Math.hypot(yAxis[0], yAxis[1]);
|
|
22690
22690
|
const dot2 = xAxis[0] * yAxis[0] + xAxis[1] * yAxis[1];
|
|
22691
|
-
if (!finitePositive(xScale) || !finitePositive(yScale)) return null;
|
|
22691
|
+
if (!finitePositive$1(xScale) || !finitePositive$1(yScale)) return null;
|
|
22692
22692
|
if (Math.abs(xScale - yScale) > EPS$8 || Math.abs(dot2) > EPS$8 * xScale * yScale) return null;
|
|
22693
22693
|
return {
|
|
22694
22694
|
center,
|
|
@@ -22701,7 +22701,7 @@ function fullCircleRevolveTorusPlan(plan, minorRadiusOffset = 0) {
|
|
|
22701
22701
|
const circle2 = circleFootprintFromProfile(plan.profile);
|
|
22702
22702
|
if (!circle2 || circle2.center[0] <= EPS$8) return null;
|
|
22703
22703
|
const minorRadius = circle2.radius + minorRadiusOffset;
|
|
22704
|
-
if (!finitePositive(minorRadius) || minorRadius >= circle2.center[0] - EPS$8) return null;
|
|
22704
|
+
if (!finitePositive$1(minorRadius) || minorRadius >= circle2.center[0] - EPS$8) return null;
|
|
22705
22705
|
return translatedPlan(
|
|
22706
22706
|
{
|
|
22707
22707
|
kind: "torus",
|
|
@@ -22748,7 +22748,7 @@ function offsetFullRectRevolvePlan(plan, thickness) {
|
|
|
22748
22748
|
const innerRadius = rectangle.innerRadius - thickness;
|
|
22749
22749
|
const outerRadius = rectangle.outerRadius + thickness;
|
|
22750
22750
|
const height = rectangle.zMax - rectangle.zMin + 2 * thickness;
|
|
22751
|
-
if (innerRadius < -EPS$8 || !finitePositive(outerRadius) || !finitePositive(height) || outerRadius <= innerRadius + EPS$8) return null;
|
|
22751
|
+
if (innerRadius < -EPS$8 || !finitePositive$1(outerRadius) || !finitePositive$1(height) || outerRadius <= innerRadius + EPS$8) return null;
|
|
22752
22752
|
const zCenter = (rectangle.zMin + rectangle.zMax) / 2;
|
|
22753
22753
|
if (innerRadius <= EPS$8) {
|
|
22754
22754
|
return translatedPlan(
|
|
@@ -22789,11 +22789,11 @@ function offsetSolidAnalyticPrimitivePlan(base, thickness) {
|
|
|
22789
22789
|
};
|
|
22790
22790
|
}
|
|
22791
22791
|
case "box": {
|
|
22792
|
-
if (!finitePositive(base.z)) return null;
|
|
22792
|
+
if (!finitePositive$1(base.z)) return null;
|
|
22793
22793
|
const x2 = Math.abs(base.x) + 2 * thickness;
|
|
22794
22794
|
const y2 = Math.abs(base.y) + 2 * thickness;
|
|
22795
22795
|
const z2 = base.z + 2 * thickness;
|
|
22796
|
-
if (!finitePositive(x2) || !finitePositive(y2) || !finitePositive(z2)) return null;
|
|
22796
|
+
if (!finitePositive$1(x2) || !finitePositive$1(y2) || !finitePositive$1(z2)) return null;
|
|
22797
22797
|
return translatedPlan(
|
|
22798
22798
|
{
|
|
22799
22799
|
kind: "box",
|
|
@@ -22820,7 +22820,7 @@ function offsetSolidAnalyticPrimitivePlan(base, thickness) {
|
|
|
22820
22820
|
}
|
|
22821
22821
|
case "sphere": {
|
|
22822
22822
|
const radius = base.radius + thickness;
|
|
22823
|
-
if (!finitePositive(radius)) return null;
|
|
22823
|
+
if (!finitePositive$1(radius)) return null;
|
|
22824
22824
|
return {
|
|
22825
22825
|
kind: "sphere",
|
|
22826
22826
|
radius,
|
|
@@ -22829,7 +22829,7 @@ function offsetSolidAnalyticPrimitivePlan(base, thickness) {
|
|
|
22829
22829
|
}
|
|
22830
22830
|
case "torus": {
|
|
22831
22831
|
const minorRadius = base.minorRadius + thickness;
|
|
22832
|
-
if (!finitePositive(minorRadius) || minorRadius >= base.majorRadius - EPS$8) return null;
|
|
22832
|
+
if (!finitePositive$1(minorRadius) || minorRadius >= base.majorRadius - EPS$8) return null;
|
|
22833
22833
|
return {
|
|
22834
22834
|
kind: "torus",
|
|
22835
22835
|
majorRadius: base.majorRadius,
|
|
@@ -30683,17 +30683,17 @@ function emptyFaceTable() {
|
|
|
30683
30683
|
blockedQueries: []
|
|
30684
30684
|
};
|
|
30685
30685
|
}
|
|
30686
|
-
function cloneVec3$
|
|
30686
|
+
function cloneVec3$4(vec2) {
|
|
30687
30687
|
return [vec2[0], vec2[1], vec2[2]];
|
|
30688
30688
|
}
|
|
30689
30689
|
function cloneFaceRefValue(face) {
|
|
30690
30690
|
return {
|
|
30691
30691
|
...face,
|
|
30692
|
-
normal: cloneVec3$
|
|
30693
|
-
center: cloneVec3$
|
|
30692
|
+
normal: cloneVec3$4(face.normal),
|
|
30693
|
+
center: cloneVec3$4(face.center),
|
|
30694
30694
|
query: cloneFaceQueryRef(face.query),
|
|
30695
|
-
uAxis: face.uAxis ? cloneVec3$
|
|
30696
|
-
vAxis: face.vAxis ? cloneVec3$
|
|
30695
|
+
uAxis: face.uAxis ? cloneVec3$4(face.uAxis) : void 0,
|
|
30696
|
+
vAxis: face.vAxis ? cloneVec3$4(face.vAxis) : void 0,
|
|
30697
30697
|
surface: cloneFaceSurface(face.surface),
|
|
30698
30698
|
descendant: face.descendant ? cloneFaceDescendantMetadata(face.descendant) : void 0
|
|
30699
30699
|
};
|
|
@@ -31548,11 +31548,11 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31548
31548
|
for (const descriptor2 of describeSheetMetalFaces(plan.model, plan.output)) {
|
|
31549
31549
|
registerFace(table2, {
|
|
31550
31550
|
name: descriptor2.name,
|
|
31551
|
-
normal: cloneVec3$
|
|
31552
|
-
center: cloneVec3$
|
|
31551
|
+
normal: cloneVec3$4(descriptor2.normal),
|
|
31552
|
+
center: cloneVec3$4(descriptor2.center),
|
|
31553
31553
|
planar: descriptor2.planar,
|
|
31554
|
-
uAxis: descriptor2.uAxis ? cloneVec3$
|
|
31555
|
-
vAxis: descriptor2.vAxis ? cloneVec3$
|
|
31554
|
+
uAxis: descriptor2.uAxis ? cloneVec3$4(descriptor2.uAxis) : void 0,
|
|
31555
|
+
vAxis: descriptor2.vAxis ? cloneVec3$4(descriptor2.vAxis) : void 0,
|
|
31556
31556
|
query: createTrackedFaceQuery(descriptor2.name, owner),
|
|
31557
31557
|
descendant: createFaceDescendantMetadata(descriptor2.semantic, descriptor2.memberNames, descriptor2.coplanar)
|
|
31558
31558
|
});
|
|
@@ -31579,7 +31579,7 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31579
31579
|
baseFace.center[2] - baseFace.normal[2] * plan.thickness
|
|
31580
31580
|
],
|
|
31581
31581
|
normal: [-baseFace.normal[0], -baseFace.normal[1], -baseFace.normal[2]],
|
|
31582
|
-
uAxis: baseFace.uAxis ? cloneVec3$
|
|
31582
|
+
uAxis: baseFace.uAxis ? cloneVec3$4(baseFace.uAxis) : void 0,
|
|
31583
31583
|
vAxis: baseFace.vAxis ? [-baseFace.vAxis[0], -baseFace.vAxis[1], -baseFace.vAxis[2]] : void 0,
|
|
31584
31584
|
query: createdQuery
|
|
31585
31585
|
});
|
|
@@ -31645,15 +31645,15 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31645
31645
|
if (counterboreFloorQuery && plan.hole.counterbore) {
|
|
31646
31646
|
registerFace(table2, {
|
|
31647
31647
|
name: "counterbore-floor",
|
|
31648
|
-
normal: cloneVec3$
|
|
31648
|
+
normal: cloneVec3$4(workplane.normal),
|
|
31649
31649
|
center: [
|
|
31650
31650
|
origin[0] + inward[0] * plan.hole.counterbore.depth,
|
|
31651
31651
|
origin[1] + inward[1] * plan.hole.counterbore.depth,
|
|
31652
31652
|
origin[2] + inward[2] * plan.hole.counterbore.depth
|
|
31653
31653
|
],
|
|
31654
31654
|
planar: true,
|
|
31655
|
-
uAxis: cloneVec3$
|
|
31656
|
-
vAxis: cloneVec3$
|
|
31655
|
+
uAxis: cloneVec3$4(workplane.u),
|
|
31656
|
+
vAxis: cloneVec3$4(workplane.v),
|
|
31657
31657
|
query: counterboreFloorQuery
|
|
31658
31658
|
});
|
|
31659
31659
|
}
|
|
@@ -31677,11 +31677,11 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31677
31677
|
if (floorQuery) {
|
|
31678
31678
|
registerFace(table2, {
|
|
31679
31679
|
name: "floor",
|
|
31680
|
-
normal: cloneVec3$
|
|
31680
|
+
normal: cloneVec3$4(workplane.normal),
|
|
31681
31681
|
center: [origin[0] + inward[0] * forward.depth, origin[1] + inward[1] * forward.depth, origin[2] + inward[2] * forward.depth],
|
|
31682
31682
|
planar: true,
|
|
31683
|
-
uAxis: cloneVec3$
|
|
31684
|
-
vAxis: cloneVec3$
|
|
31683
|
+
uAxis: cloneVec3$4(workplane.u),
|
|
31684
|
+
vAxis: cloneVec3$4(workplane.v),
|
|
31685
31685
|
query: floorQuery
|
|
31686
31686
|
});
|
|
31687
31687
|
}
|
|
@@ -31692,7 +31692,7 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31692
31692
|
normal: [-workplane.normal[0], -workplane.normal[1], -workplane.normal[2]],
|
|
31693
31693
|
center: [origin[0] - inward[0] * reverse.depth, origin[1] - inward[1] * reverse.depth, origin[2] - inward[2] * reverse.depth],
|
|
31694
31694
|
planar: true,
|
|
31695
|
-
uAxis: cloneVec3$
|
|
31695
|
+
uAxis: cloneVec3$4(workplane.u),
|
|
31696
31696
|
vAxis: [-workplane.v[0], -workplane.v[1], -workplane.v[2]],
|
|
31697
31697
|
query: capQuery
|
|
31698
31698
|
});
|
|
@@ -31871,11 +31871,11 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31871
31871
|
})();
|
|
31872
31872
|
registerFace(table2, {
|
|
31873
31873
|
name: "floor",
|
|
31874
|
-
normal: cloneVec3$
|
|
31874
|
+
normal: cloneVec3$4(placement.workplane.normal),
|
|
31875
31875
|
center: floorCenter,
|
|
31876
31876
|
planar: true,
|
|
31877
|
-
uAxis: cloneVec3$
|
|
31878
|
-
vAxis: cloneVec3$
|
|
31877
|
+
uAxis: cloneVec3$4(placement.workplane.u),
|
|
31878
|
+
vAxis: cloneVec3$4(placement.workplane.v),
|
|
31879
31879
|
query: floorQuery
|
|
31880
31880
|
});
|
|
31881
31881
|
}
|
|
@@ -31890,7 +31890,7 @@ function resolveShapeFaceTableInternal(plan, owner) {
|
|
|
31890
31890
|
origin[2] - depthDir[2] * reverse.depth
|
|
31891
31891
|
],
|
|
31892
31892
|
planar: true,
|
|
31893
|
-
uAxis: cloneVec3$
|
|
31893
|
+
uAxis: cloneVec3$4(placement.workplane.u),
|
|
31894
31894
|
vAxis: [-placement.workplane.v[0], -placement.workplane.v[1], -placement.workplane.v[2]],
|
|
31895
31895
|
query: capQuery
|
|
31896
31896
|
});
|
|
@@ -32076,7 +32076,7 @@ function preservedShapeFaceQueries(basePlan) {
|
|
|
32076
32076
|
return listShapeFaceQueries(basePlan);
|
|
32077
32077
|
}
|
|
32078
32078
|
const PLACEMENT_REFERENCE_KINDS = ["points", "edges", "surfaces", "objects"];
|
|
32079
|
-
function cloneVec3$
|
|
32079
|
+
function cloneVec3$3(value, label) {
|
|
32080
32080
|
if (!Array.isArray(value) || value.length < 3) {
|
|
32081
32081
|
throw new Error(`${label} must be a [x, y, z] tuple`);
|
|
32082
32082
|
}
|
|
@@ -32102,23 +32102,23 @@ function isBoundsObject(value) {
|
|
|
32102
32102
|
function toObjectBounds(value, label) {
|
|
32103
32103
|
if (isBoundsObject(value)) {
|
|
32104
32104
|
return {
|
|
32105
|
-
min: cloneVec3$
|
|
32106
|
-
max: cloneVec3$
|
|
32105
|
+
min: cloneVec3$3(value.min, `${label}.min`),
|
|
32106
|
+
max: cloneVec3$3(value.max, `${label}.max`)
|
|
32107
32107
|
};
|
|
32108
32108
|
}
|
|
32109
32109
|
if (typeof value === "object" && value != null) {
|
|
32110
32110
|
if ("boundingBox" in value && typeof value.boundingBox === "function") {
|
|
32111
32111
|
const bounds = value.boundingBox();
|
|
32112
32112
|
return {
|
|
32113
|
-
min: cloneVec3$
|
|
32114
|
-
max: cloneVec3$
|
|
32113
|
+
min: cloneVec3$3(bounds.min, `${label}.min`),
|
|
32114
|
+
max: cloneVec3$3(bounds.max, `${label}.max`)
|
|
32115
32115
|
};
|
|
32116
32116
|
}
|
|
32117
32117
|
if ("_bbox" in value && typeof value._bbox === "function") {
|
|
32118
32118
|
const bounds = value._bbox();
|
|
32119
32119
|
return {
|
|
32120
|
-
min: cloneVec3$
|
|
32121
|
-
max: cloneVec3$
|
|
32120
|
+
min: cloneVec3$3(bounds.min, `${label}.min`),
|
|
32121
|
+
max: cloneVec3$3(bounds.max, `${label}.max`)
|
|
32122
32122
|
};
|
|
32123
32123
|
}
|
|
32124
32124
|
}
|
|
@@ -32162,24 +32162,24 @@ function createPlacementReferences() {
|
|
|
32162
32162
|
function clonePlacementReferences(refs) {
|
|
32163
32163
|
const out = createPlacementReferences();
|
|
32164
32164
|
for (const [name, point2] of Object.entries(refs.points)) {
|
|
32165
|
-
out.points[name] = cloneVec3$
|
|
32165
|
+
out.points[name] = cloneVec3$3(point2, `points.${name}`);
|
|
32166
32166
|
}
|
|
32167
32167
|
for (const [name, edge] of Object.entries(refs.edges)) {
|
|
32168
32168
|
out.edges[name] = {
|
|
32169
|
-
start: cloneVec3$
|
|
32170
|
-
end: cloneVec3$
|
|
32169
|
+
start: cloneVec3$3(edge.start, `edges.${name}.start`),
|
|
32170
|
+
end: cloneVec3$3(edge.end, `edges.${name}.end`)
|
|
32171
32171
|
};
|
|
32172
32172
|
}
|
|
32173
32173
|
for (const [name, surface] of Object.entries(refs.surfaces)) {
|
|
32174
32174
|
out.surfaces[name] = {
|
|
32175
|
-
center: cloneVec3$
|
|
32176
|
-
normal: cloneVec3$
|
|
32175
|
+
center: cloneVec3$3(surface.center, `surfaces.${name}.center`),
|
|
32176
|
+
normal: cloneVec3$3(surface.normal, `surfaces.${name}.normal`)
|
|
32177
32177
|
};
|
|
32178
32178
|
}
|
|
32179
32179
|
for (const [name, objectRef] of Object.entries(refs.objects)) {
|
|
32180
32180
|
out.objects[name] = {
|
|
32181
|
-
min: cloneVec3$
|
|
32182
|
-
max: cloneVec3$
|
|
32181
|
+
min: cloneVec3$3(objectRef.min, `objects.${name}.min`),
|
|
32182
|
+
max: cloneVec3$3(objectRef.max, `objects.${name}.max`)
|
|
32183
32183
|
};
|
|
32184
32184
|
}
|
|
32185
32185
|
return out;
|
|
@@ -32187,18 +32187,18 @@ function clonePlacementReferences(refs) {
|
|
|
32187
32187
|
function normalizePlacementReferenceInput(input = {}) {
|
|
32188
32188
|
const out = createPlacementReferences();
|
|
32189
32189
|
for (const [name, point2] of Object.entries(input.points ?? {})) {
|
|
32190
|
-
out.points[name] = cloneVec3$
|
|
32190
|
+
out.points[name] = cloneVec3$3(point2, `points.${name}`);
|
|
32191
32191
|
}
|
|
32192
32192
|
for (const [name, edge] of Object.entries(input.edges ?? {})) {
|
|
32193
32193
|
out.edges[name] = {
|
|
32194
|
-
start: cloneVec3$
|
|
32195
|
-
end: cloneVec3$
|
|
32194
|
+
start: cloneVec3$3(edge.start, `edges.${name}.start`),
|
|
32195
|
+
end: cloneVec3$3(edge.end, `edges.${name}.end`)
|
|
32196
32196
|
};
|
|
32197
32197
|
}
|
|
32198
32198
|
for (const [name, surface] of Object.entries(input.surfaces ?? {})) {
|
|
32199
32199
|
out.surfaces[name] = {
|
|
32200
|
-
center: cloneVec3$
|
|
32201
|
-
normal: normalizeVector$1(cloneVec3$
|
|
32200
|
+
center: cloneVec3$3(surface.center, `surfaces.${name}.center`),
|
|
32201
|
+
normal: normalizeVector$1(cloneVec3$3(surface.normal, `surfaces.${name}.normal`))
|
|
32202
32202
|
};
|
|
32203
32203
|
}
|
|
32204
32204
|
for (const [name, objectRef] of Object.entries(input.objects ?? {})) {
|
|
@@ -32209,23 +32209,23 @@ function normalizePlacementReferenceInput(input = {}) {
|
|
|
32209
32209
|
function mergePlacementReferences(...refsList) {
|
|
32210
32210
|
const out = createPlacementReferences();
|
|
32211
32211
|
for (const refs of refsList) {
|
|
32212
|
-
for (const [name, point2] of Object.entries(refs.points)) out.points[name] = cloneVec3$
|
|
32212
|
+
for (const [name, point2] of Object.entries(refs.points)) out.points[name] = cloneVec3$3(point2, `points.${name}`);
|
|
32213
32213
|
for (const [name, edge] of Object.entries(refs.edges)) {
|
|
32214
32214
|
out.edges[name] = {
|
|
32215
|
-
start: cloneVec3$
|
|
32216
|
-
end: cloneVec3$
|
|
32215
|
+
start: cloneVec3$3(edge.start, `edges.${name}.start`),
|
|
32216
|
+
end: cloneVec3$3(edge.end, `edges.${name}.end`)
|
|
32217
32217
|
};
|
|
32218
32218
|
}
|
|
32219
32219
|
for (const [name, surface] of Object.entries(refs.surfaces)) {
|
|
32220
32220
|
out.surfaces[name] = {
|
|
32221
|
-
center: cloneVec3$
|
|
32222
|
-
normal: cloneVec3$
|
|
32221
|
+
center: cloneVec3$3(surface.center, `surfaces.${name}.center`),
|
|
32222
|
+
normal: cloneVec3$3(surface.normal, `surfaces.${name}.normal`)
|
|
32223
32223
|
};
|
|
32224
32224
|
}
|
|
32225
32225
|
for (const [name, objectRef] of Object.entries(refs.objects)) {
|
|
32226
32226
|
out.objects[name] = {
|
|
32227
|
-
min: cloneVec3$
|
|
32228
|
-
max: cloneVec3$
|
|
32227
|
+
min: cloneVec3$3(objectRef.min, `objects.${name}.min`),
|
|
32228
|
+
max: cloneVec3$3(objectRef.max, `objects.${name}.max`)
|
|
32229
32229
|
};
|
|
32230
32230
|
}
|
|
32231
32231
|
}
|
|
@@ -32269,7 +32269,7 @@ function resolvePointFromKind(refs, kind, name, selector, originalRef) {
|
|
|
32269
32269
|
const point2 = refs.points[name];
|
|
32270
32270
|
if (!point2) return null;
|
|
32271
32271
|
if (selector != null) placementRefSelectorError(originalRef, "does not support selectors");
|
|
32272
|
-
return cloneVec3$
|
|
32272
|
+
return cloneVec3$3(point2, `points.${name}`);
|
|
32273
32273
|
}
|
|
32274
32274
|
case "edges": {
|
|
32275
32275
|
const edge = refs.edges[name];
|
|
@@ -32277,8 +32277,8 @@ function resolvePointFromKind(refs, kind, name, selector, originalRef) {
|
|
|
32277
32277
|
if (selector == null || selector === "midpoint" || selector === "center") {
|
|
32278
32278
|
return midpoint$2(edge.start, edge.end);
|
|
32279
32279
|
}
|
|
32280
|
-
if (selector === "start") return cloneVec3$
|
|
32281
|
-
if (selector === "end") return cloneVec3$
|
|
32280
|
+
if (selector === "start") return cloneVec3$3(edge.start, `edges.${name}.start`);
|
|
32281
|
+
if (selector === "end") return cloneVec3$3(edge.end, `edges.${name}.end`);
|
|
32282
32282
|
placementRefSelectorError(originalRef, "supports only .start, .end, or .midpoint");
|
|
32283
32283
|
}
|
|
32284
32284
|
case "surfaces": {
|
|
@@ -32287,7 +32287,7 @@ function resolvePointFromKind(refs, kind, name, selector, originalRef) {
|
|
|
32287
32287
|
if (selector != null && selector !== "center") {
|
|
32288
32288
|
placementRefSelectorError(originalRef, "supports only .center");
|
|
32289
32289
|
}
|
|
32290
|
-
return cloneVec3$
|
|
32290
|
+
return cloneVec3$3(surface.center, `surfaces.${name}.center`);
|
|
32291
32291
|
}
|
|
32292
32292
|
case "objects": {
|
|
32293
32293
|
const objectRef = refs.objects[name];
|
|
@@ -35372,7 +35372,7 @@ function attachTopologyRewritePropagation(plan, propagation) {
|
|
|
35372
35372
|
}
|
|
35373
35373
|
const DEFAULT_TOLERANCE$2 = 1;
|
|
35374
35374
|
const DEFAULT_ANGLE_TOLERANCE = 10;
|
|
35375
|
-
function distSq(a2, b) {
|
|
35375
|
+
function distSq$1(a2, b) {
|
|
35376
35376
|
const dx = a2[0] - b[0], dy = a2[1] - b[1], dz = a2[2] - b[2];
|
|
35377
35377
|
return dx * dx + dy * dy + dz * dz;
|
|
35378
35378
|
}
|
|
@@ -35464,7 +35464,7 @@ function applyFilters(edges, query) {
|
|
|
35464
35464
|
}
|
|
35465
35465
|
if (query.near) {
|
|
35466
35466
|
const pt = query.near;
|
|
35467
|
-
result = result.slice().sort((a2, b) => distSq(a2.midpoint, pt) - distSq(b.midpoint, pt));
|
|
35467
|
+
result = result.slice().sort((a2, b) => distSq$1(a2.midpoint, pt) - distSq$1(b.midpoint, pt));
|
|
35468
35468
|
}
|
|
35469
35469
|
return result;
|
|
35470
35470
|
}
|
|
@@ -35528,10 +35528,10 @@ function coalesceEdges(segments, tolerance = 0.01) {
|
|
|
35528
35528
|
}
|
|
35529
35529
|
function minEndpointGap(a2, b) {
|
|
35530
35530
|
return Math.min(
|
|
35531
|
-
Math.sqrt(distSq(a2.start, b.start)),
|
|
35532
|
-
Math.sqrt(distSq(a2.start, b.end)),
|
|
35533
|
-
Math.sqrt(distSq(a2.end, b.start)),
|
|
35534
|
-
Math.sqrt(distSq(a2.end, b.end))
|
|
35531
|
+
Math.sqrt(distSq$1(a2.start, b.start)),
|
|
35532
|
+
Math.sqrt(distSq$1(a2.start, b.end)),
|
|
35533
|
+
Math.sqrt(distSq$1(a2.end, b.start)),
|
|
35534
|
+
Math.sqrt(distSq$1(a2.end, b.end))
|
|
35535
35535
|
);
|
|
35536
35536
|
}
|
|
35537
35537
|
function mergeCollinearGroup(group2, index2) {
|
|
@@ -53237,11 +53237,11 @@ function inverseLerp(x2, y2, value) {
|
|
|
53237
53237
|
return 0;
|
|
53238
53238
|
}
|
|
53239
53239
|
}
|
|
53240
|
-
function lerp$
|
|
53240
|
+
function lerp$6(x2, y2, t) {
|
|
53241
53241
|
return (1 - t) * x2 + t * y2;
|
|
53242
53242
|
}
|
|
53243
53243
|
function damp(x2, y2, lambda, dt) {
|
|
53244
|
-
return lerp$
|
|
53244
|
+
return lerp$6(x2, y2, 1 - Math.exp(-lambda * dt));
|
|
53245
53245
|
}
|
|
53246
53246
|
function pingpong(x2, length4 = 1) {
|
|
53247
53247
|
return length4 - Math.abs(euclideanModulo(x2, length4 * 2) - length4);
|
|
@@ -53434,7 +53434,7 @@ const MathUtils = {
|
|
|
53434
53434
|
* @param {number} t - The interpolation factor in the closed interval `[0, 1]`.
|
|
53435
53435
|
* @return {number} The interpolated value.
|
|
53436
53436
|
*/
|
|
53437
|
-
lerp: lerp$
|
|
53437
|
+
lerp: lerp$6,
|
|
53438
53438
|
/**
|
|
53439
53439
|
* Smoothly interpolate a number from `x` to `y` in a spring-like manner using a delta
|
|
53440
53440
|
* time to maintain frame rate independent movement. For details, see
|
|
@@ -62388,9 +62388,9 @@ class Color {
|
|
|
62388
62388
|
lerpHSL(color, alpha) {
|
|
62389
62389
|
this.getHSL(_hslA);
|
|
62390
62390
|
color.getHSL(_hslB);
|
|
62391
|
-
const h = lerp$
|
|
62392
|
-
const s = lerp$
|
|
62393
|
-
const l = lerp$
|
|
62391
|
+
const h = lerp$6(_hslA.h, _hslB.h, alpha);
|
|
62392
|
+
const s = lerp$6(_hslA.s, _hslB.s, alpha);
|
|
62393
|
+
const l = lerp$6(_hslA.l, _hslB.l, alpha);
|
|
62394
62394
|
this.setHSL(h, s, l);
|
|
62395
62395
|
return this;
|
|
62396
62396
|
}
|
|
@@ -96725,7 +96725,7 @@ function scale$1(v, s) {
|
|
|
96725
96725
|
function dot$2(a2, b) {
|
|
96726
96726
|
return a2[0] * b[0] + a2[1] * b[1] + a2[2] * b[2];
|
|
96727
96727
|
}
|
|
96728
|
-
function lerp$
|
|
96728
|
+
function lerp$5(a2, b, t) {
|
|
96729
96729
|
return a2 + (b - a2) * t;
|
|
96730
96730
|
}
|
|
96731
96731
|
function frameMatrix$1(x2, y2, z2, p2) {
|
|
@@ -96801,9 +96801,9 @@ function interpolateQuery(a2, b, t) {
|
|
|
96801
96801
|
}
|
|
96802
96802
|
return {
|
|
96803
96803
|
side: sideA,
|
|
96804
|
-
u: lerp$
|
|
96805
|
-
v: lerp$
|
|
96806
|
-
offset: lerp$
|
|
96804
|
+
u: lerp$5(a2.u ?? 0.5, b.u ?? 0.5, t),
|
|
96805
|
+
v: lerp$5(a2.v ?? 0.5, b.v ?? 0.5, t),
|
|
96806
|
+
offset: lerp$5(a2.offset ?? 0, b.offset ?? 0, t)
|
|
96807
96807
|
};
|
|
96808
96808
|
}
|
|
96809
96809
|
function resolvePathQueries(points) {
|
|
@@ -96928,7 +96928,7 @@ class ProductSkin {
|
|
|
96928
96928
|
}
|
|
96929
96929
|
/** Interpolate center, width, and depth at a normalized v or absolute axis value. */
|
|
96930
96930
|
stationAt(vOrAxis) {
|
|
96931
|
-
const axisValue = vOrAxis >= 0 && vOrAxis <= 1 ? lerp$
|
|
96931
|
+
const axisValue = vOrAxis >= 0 && vOrAxis <= 1 ? lerp$5(this.axisMin, this.axisMax, vOrAxis) : clamp$5(vOrAxis, this.axisMin, this.axisMax);
|
|
96932
96932
|
const sorted = this.stations;
|
|
96933
96933
|
for (let index2 = 0; index2 < sorted.length - 1; index2 += 1) {
|
|
96934
96934
|
const a2 = sorted[index2];
|
|
@@ -96940,12 +96940,12 @@ class ProductSkin {
|
|
|
96940
96940
|
const t = clamp$5((axisValue - aAxis) / span, 0, 1);
|
|
96941
96941
|
return {
|
|
96942
96942
|
axisValue,
|
|
96943
|
-
center: [lerp$
|
|
96944
|
-
width: lerp$
|
|
96945
|
-
depth: lerp$
|
|
96943
|
+
center: [lerp$5(a2.center[0], b.center[0], t), lerp$5(a2.center[1], b.center[1], t), lerp$5(a2.center[2], b.center[2], t)],
|
|
96944
|
+
width: lerp$5(a2.profile.width, b.profile.width, t),
|
|
96945
|
+
depth: lerp$5(a2.profile.depth, b.profile.depth, t),
|
|
96946
96946
|
dWidth: (b.profile.width - a2.profile.width) / span,
|
|
96947
96947
|
dDepth: (b.profile.depth - a2.profile.depth) / span,
|
|
96948
|
-
exponent: lerp$
|
|
96948
|
+
exponent: lerp$5(profileExponent(a2), profileExponent(b), t),
|
|
96949
96949
|
kind: a2.profile.kind === b.profile.kind ? a2.profile.kind : "custom"
|
|
96950
96950
|
};
|
|
96951
96951
|
}
|
|
@@ -97778,7 +97778,7 @@ function requirePositive$3(value, label) {
|
|
|
97778
97778
|
function clamp$4(value, min2, max2) {
|
|
97779
97779
|
return Math.max(min2, Math.min(max2, value));
|
|
97780
97780
|
}
|
|
97781
|
-
function lerp$
|
|
97781
|
+
function lerp$4(a2, b, t) {
|
|
97782
97782
|
return a2 + (b - a2) * t;
|
|
97783
97783
|
}
|
|
97784
97784
|
function add(a2, b) {
|
|
@@ -97828,19 +97828,19 @@ function transformLocal(point2, tangentAcross, normal, tangentAlong, x2, y2, z2
|
|
|
97828
97828
|
function interpolateCylinder(a2, b, t, mode) {
|
|
97829
97829
|
let delta = b.angle - a2.angle;
|
|
97830
97830
|
if (mode === "shortest" && Math.abs(delta) > 180) delta -= Math.sign(delta) * 360;
|
|
97831
|
-
return { kind: "cylinder", angle: a2.angle + delta * t, z: lerp$
|
|
97831
|
+
return { kind: "cylinder", angle: a2.angle + delta * t, z: lerp$4(a2.z, b.z, t), offset: lerp$4(a2.offset ?? 0, b.offset ?? 0, t) };
|
|
97832
97832
|
}
|
|
97833
97833
|
function interpolatePlane(a2, b, t) {
|
|
97834
|
-
return { kind: "plane", x: lerp$
|
|
97834
|
+
return { kind: "plane", x: lerp$4(a2.x, b.x, t), y: lerp$4(a2.y, b.y, t), offset: lerp$4(a2.offset ?? 0, b.offset ?? 0, t) };
|
|
97835
97835
|
}
|
|
97836
97836
|
function interpolateProductSkin(a2, b, t) {
|
|
97837
97837
|
if ((a2.side ?? b.side) !== (b.side ?? a2.side)) throw new Error("SurfacePath on ProductSkin currently supports one side per path; split side transitions into separate members.");
|
|
97838
97838
|
return {
|
|
97839
97839
|
kind: "productSkin",
|
|
97840
97840
|
side: a2.side ?? b.side,
|
|
97841
|
-
u: lerp$
|
|
97842
|
-
v: lerp$
|
|
97843
|
-
offset: lerp$
|
|
97841
|
+
u: lerp$4(a2.u ?? 0.5, b.u ?? 0.5, t),
|
|
97842
|
+
v: lerp$4(a2.v ?? 0.5, b.v ?? 0.5, t),
|
|
97843
|
+
offset: lerp$4(a2.offset ?? 0, b.offset ?? 0, t)
|
|
97844
97844
|
};
|
|
97845
97845
|
}
|
|
97846
97846
|
class SurfacePath {
|
|
@@ -98938,7 +98938,7 @@ function counterboresForPlate(spec2, width, height, thickness, diagnostics) {
|
|
|
98938
98938
|
function minWidthAcrossAlongRange(widthAtT, length4, minAlong, maxAlong) {
|
|
98939
98939
|
let minWidth = Number.POSITIVE_INFINITY;
|
|
98940
98940
|
for (let index2 = 0; index2 <= 8; index2 += 1) {
|
|
98941
|
-
const along = lerp$
|
|
98941
|
+
const along = lerp$4(minAlong, maxAlong, index2 / 8);
|
|
98942
98942
|
const t = Math.max(0, Math.min(1, (along + length4 / 2) / Math.max(length4, 1e-8)));
|
|
98943
98943
|
minWidth = Math.min(minWidth, widthAtT(t));
|
|
98944
98944
|
}
|
|
@@ -99238,7 +99238,7 @@ function pathParameterAtDistance(samples, distance2) {
|
|
|
99238
99238
|
const segmentLength = Math.hypot(b.point[0] - a2.point[0], b.point[1] - a2.point[1], b.point[2] - a2.point[2]);
|
|
99239
99239
|
if (traveled + segmentLength >= distance2) {
|
|
99240
99240
|
const localT = segmentLength <= 1e-8 ? 0 : (distance2 - traveled) / segmentLength;
|
|
99241
|
-
return lerp$
|
|
99241
|
+
return lerp$4(a2.t, b.t, localT);
|
|
99242
99242
|
}
|
|
99243
99243
|
traveled += segmentLength;
|
|
99244
99244
|
}
|
|
@@ -99291,7 +99291,7 @@ function compileBandFootprintMesh(path2, input) {
|
|
|
99291
99291
|
const width = input.widthAt(t);
|
|
99292
99292
|
const along = distance2 - length4 / 2;
|
|
99293
99293
|
for (let acrossIndex = 0; acrossIndex <= acrossSegments; acrossIndex += 1) {
|
|
99294
|
-
const across = lerp$
|
|
99294
|
+
const across = lerp$4(-width / 2, width / 2, acrossIndex / acrossSegments);
|
|
99295
99295
|
mesh.vertices.push(pointAtProfile([across, along], false));
|
|
99296
99296
|
}
|
|
99297
99297
|
}
|
|
@@ -99301,7 +99301,7 @@ function compileBandFootprintMesh(path2, input) {
|
|
|
99301
99301
|
const width = input.widthAt(t);
|
|
99302
99302
|
const along = distance2 - length4 / 2;
|
|
99303
99303
|
for (let acrossIndex = 0; acrossIndex <= acrossSegments; acrossIndex += 1) {
|
|
99304
|
-
const across = lerp$
|
|
99304
|
+
const across = lerp$4(-width / 2, width / 2, acrossIndex / acrossSegments);
|
|
99305
99305
|
mesh.vertices.push(pointAtProfile([across, along], true));
|
|
99306
99306
|
}
|
|
99307
99307
|
}
|
|
@@ -99313,7 +99313,7 @@ function compileBandFootprintMesh(path2, input) {
|
|
|
99313
99313
|
const width = input.widthAt(t);
|
|
99314
99314
|
const along = distance2 - length4 / 2;
|
|
99315
99315
|
for (let acrossIndex = 0; acrossIndex < acrossSegments; acrossIndex += 1) {
|
|
99316
|
-
const across = lerp$
|
|
99316
|
+
const across = lerp$4(-width / 2, width / 2, (acrossIndex + 0.5) / acrossSegments);
|
|
99317
99317
|
filled[alongIndex][acrossIndex] = !holes.some((hole2) => pointInProfileLoop([across, along], hole2));
|
|
99318
99318
|
}
|
|
99319
99319
|
}
|
|
@@ -101513,7 +101513,7 @@ function midpoint$1(a2, b) {
|
|
|
101513
101513
|
requireVec3$1(b, "b");
|
|
101514
101514
|
return [(a2[0] + b[0]) / 2, (a2[1] + b[1]) / 2, (a2[2] + b[2]) / 2];
|
|
101515
101515
|
}
|
|
101516
|
-
function lerp$
|
|
101516
|
+
function lerp$3(a2, b, t) {
|
|
101517
101517
|
requireVec3$1(a2, "a");
|
|
101518
101518
|
requireVec3$1(b, "b");
|
|
101519
101519
|
requireFiniteNumber(t, "t");
|
|
@@ -101543,7 +101543,7 @@ const Points2 = {
|
|
|
101543
101543
|
/** Center point between two 3D points. */
|
|
101544
101544
|
midpoint: midpoint$1,
|
|
101545
101545
|
/** Linearly interpolate between two 3D points. t=0 returns a, t=1 returns b. */
|
|
101546
|
-
lerp: lerp$
|
|
101546
|
+
lerp: lerp$3,
|
|
101547
101547
|
/** Unit direction vector from a to b. Throws if a and b are the same point. */
|
|
101548
101548
|
direction,
|
|
101549
101549
|
/** Move a point along a direction vector by a given amount. */
|
|
@@ -122079,7 +122079,7 @@ function railCrossAt(rail2, position) {
|
|
|
122079
122079
|
const b = points[index2 + 1];
|
|
122080
122080
|
if (position >= a2.position - LOFT_GUIDE_EPS && position <= b.position + LOFT_GUIDE_EPS) {
|
|
122081
122081
|
const t = (position - a2.position) / (b.position - a2.position);
|
|
122082
|
-
return [lerp$
|
|
122082
|
+
return [lerp$2(a2.cross[0], b.cross[0], t), lerp$2(a2.cross[1], b.cross[1], t)];
|
|
122083
122083
|
}
|
|
122084
122084
|
}
|
|
122085
122085
|
throw new Error("Loft guide rail does not cover requested station position");
|
|
@@ -122117,7 +122117,7 @@ function crossPointForAxis(axis, point2) {
|
|
|
122117
122117
|
if (axis === "Y") return [point2[0], -point2[2]];
|
|
122118
122118
|
return [point2[0], point2[1]];
|
|
122119
122119
|
}
|
|
122120
|
-
function lerp$
|
|
122120
|
+
function lerp$2(a2, b, t) {
|
|
122121
122121
|
return a2 + (b - a2) * t;
|
|
122122
122122
|
}
|
|
122123
122123
|
function loftWithGuideRails(stations, rails, options = {}) {
|
|
@@ -122241,13 +122241,13 @@ function sketchBounds(profile) {
|
|
|
122241
122241
|
}
|
|
122242
122242
|
function lerpBounds(a2, b, t) {
|
|
122243
122243
|
return {
|
|
122244
|
-
minX: lerp(a2.minX, b.minX, t),
|
|
122245
|
-
maxX: lerp(a2.maxX, b.maxX, t),
|
|
122246
|
-
minY: lerp(a2.minY, b.minY, t),
|
|
122247
|
-
maxY: lerp(a2.maxY, b.maxY, t)
|
|
122244
|
+
minX: lerp$1(a2.minX, b.minX, t),
|
|
122245
|
+
maxX: lerp$1(a2.maxX, b.maxX, t),
|
|
122246
|
+
minY: lerp$1(a2.minY, b.minY, t),
|
|
122247
|
+
maxY: lerp$1(a2.maxY, b.maxY, t)
|
|
122248
122248
|
};
|
|
122249
122249
|
}
|
|
122250
|
-
function lerp(a2, b, t) {
|
|
122250
|
+
function lerp$1(a2, b, t) {
|
|
122251
122251
|
return a2 + (b - a2) * t;
|
|
122252
122252
|
}
|
|
122253
122253
|
function mapLoftPath2D(path2, label, mapper) {
|
|
@@ -341732,7 +341732,7 @@ function runScript(code, fileName = "main.forge.js", allFiles = {}, options = {}
|
|
|
341732
341732
|
}
|
|
341733
341733
|
}
|
|
341734
341734
|
const DEFAULT_LEAF_SIZE = 8;
|
|
341735
|
-
function cloneVec3$
|
|
341735
|
+
function cloneVec3$2(value) {
|
|
341736
341736
|
return [value[0], value[1], value[2]];
|
|
341737
341737
|
}
|
|
341738
341738
|
function emptyBounds() {
|
|
@@ -341800,14 +341800,14 @@ class AabbSpatialIndex {
|
|
|
341800
341800
|
nodeCount += 1;
|
|
341801
341801
|
const bounds = boundsFor(entries, indexes);
|
|
341802
341802
|
if (indexes.length <= this.leafSize) {
|
|
341803
|
-
return { min: cloneVec3$
|
|
341803
|
+
return { min: cloneVec3$2(bounds.min), max: cloneVec3$2(bounds.max), left: null, right: null, indexes };
|
|
341804
341804
|
}
|
|
341805
341805
|
const axis = longestAxis(bounds);
|
|
341806
341806
|
indexes.sort((a2, b) => centerOnAxis(entries[a2], axis) - centerOnAxis(entries[b], axis) || a2 - b);
|
|
341807
341807
|
const mid = Math.max(1, Math.floor(indexes.length / 2));
|
|
341808
341808
|
return {
|
|
341809
|
-
min: cloneVec3$
|
|
341810
|
-
max: cloneVec3$
|
|
341809
|
+
min: cloneVec3$2(bounds.min),
|
|
341810
|
+
max: cloneVec3$2(bounds.max),
|
|
341811
341811
|
left: build(indexes.slice(0, mid)),
|
|
341812
341812
|
right: build(indexes.slice(mid)),
|
|
341813
341813
|
indexes: null
|
|
@@ -341873,7 +341873,7 @@ class AabbSpatialIndex {
|
|
|
341873
341873
|
const DEFAULT_COLLISION_INSPECTION_OPTIONS = {
|
|
341874
341874
|
minOverlapVolume: 0.1
|
|
341875
341875
|
};
|
|
341876
|
-
function cloneVec3(value) {
|
|
341876
|
+
function cloneVec3$1(value) {
|
|
341877
341877
|
return [value[0], value[1], value[2]];
|
|
341878
341878
|
}
|
|
341879
341879
|
function isIdentityTransform(matrix) {
|
|
@@ -341915,8 +341915,8 @@ function prepareEntry(entry) {
|
|
|
341915
341915
|
if (isIdentityTransform(entry.transform)) {
|
|
341916
341916
|
return {
|
|
341917
341917
|
...entry,
|
|
341918
|
-
min: cloneVec3(entry.min),
|
|
341919
|
-
max: cloneVec3(entry.max)
|
|
341918
|
+
min: cloneVec3$1(entry.min),
|
|
341919
|
+
max: cloneVec3$1(entry.max)
|
|
341920
341920
|
};
|
|
341921
341921
|
}
|
|
341922
341922
|
const bbox = transformBBox(entry.min, entry.max, entry.transform);
|
|
@@ -341935,7 +341935,7 @@ function shouldSkipPair(a2, b, options) {
|
|
|
341935
341935
|
if (options.skipMockPairs && a2.mock && b.mock) return true;
|
|
341936
341936
|
return false;
|
|
341937
341937
|
}
|
|
341938
|
-
function collectCandidatePairs(entries, options) {
|
|
341938
|
+
function collectCandidatePairs$1(entries, options) {
|
|
341939
341939
|
const index2 = new AabbSpatialIndex(entries, 1);
|
|
341940
341940
|
const result = index2.overlapPairs({
|
|
341941
341941
|
padding: options.bboxPadding,
|
|
@@ -341976,7 +341976,7 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
|
|
|
341976
341976
|
const warnings = [];
|
|
341977
341977
|
const collisions = [];
|
|
341978
341978
|
const preparedEntries = entries.map((entry) => prepareEntry(entry));
|
|
341979
|
-
const { pairs: candidatePairs, bboxPairChecks } = collectCandidatePairs(preparedEntries, options);
|
|
341979
|
+
const { pairs: candidatePairs, bboxPairChecks } = collectCandidatePairs$1(preparedEntries, options);
|
|
341980
341980
|
const exactCandidatePairs = candidatePairs.filter((pair) => pair.bboxOverlapVolume > options.minOverlapVolume);
|
|
341981
341981
|
const bboxVolumePrunedPairCount = candidatePairs.length - exactCandidatePairs.length;
|
|
341982
341982
|
const limitedCandidatePairs = options.maxCandidatePairs === null ? exactCandidatePairs : exactCandidatePairs.slice(0, options.maxCandidatePairs);
|
|
@@ -342062,8 +342062,8 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
|
|
|
342062
342062
|
treePath: entry.treePath,
|
|
342063
342063
|
mock: entry.mock === true,
|
|
342064
342064
|
bbox: {
|
|
342065
|
-
min: cloneVec3(entry.min),
|
|
342066
|
-
max: cloneVec3(entry.max)
|
|
342065
|
+
min: cloneVec3$1(entry.min),
|
|
342066
|
+
max: cloneVec3$1(entry.max)
|
|
342067
342067
|
}
|
|
342068
342068
|
}));
|
|
342069
342069
|
return {
|
|
@@ -342277,6 +342277,706 @@ function geometryWithVisibleVertexColors(geometry, colors) {
|
|
|
342277
342277
|
out.setAttribute("color", colorAttribute);
|
|
342278
342278
|
return out;
|
|
342279
342279
|
}
|
|
342280
|
+
const DEFAULT_ROUGHNESS_INSPECTION_OPTIONS = {
|
|
342281
|
+
smoothAngleDeg: 5,
|
|
342282
|
+
sharpAngleDeg: 30,
|
|
342283
|
+
harshAngleDeg: 90,
|
|
342284
|
+
maxSamplesPerObject: 5e3
|
|
342285
|
+
};
|
|
342286
|
+
const ROUGHNESS_COLORS = {
|
|
342287
|
+
smooth: [62, 72, 84],
|
|
342288
|
+
moderate: [255, 214, 0],
|
|
342289
|
+
sharp: [255, 124, 34],
|
|
342290
|
+
harsh: [255, 42, 96]
|
|
342291
|
+
};
|
|
342292
|
+
function resolveRoughnessInspectionOptions(raw = {}) {
|
|
342293
|
+
const options = {
|
|
342294
|
+
smoothAngleDeg: raw.smoothAngleDeg ?? DEFAULT_ROUGHNESS_INSPECTION_OPTIONS.smoothAngleDeg,
|
|
342295
|
+
sharpAngleDeg: raw.sharpAngleDeg ?? DEFAULT_ROUGHNESS_INSPECTION_OPTIONS.sharpAngleDeg,
|
|
342296
|
+
harshAngleDeg: raw.harshAngleDeg ?? DEFAULT_ROUGHNESS_INSPECTION_OPTIONS.harshAngleDeg,
|
|
342297
|
+
maxSamplesPerObject: raw.maxSamplesPerObject ?? DEFAULT_ROUGHNESS_INSPECTION_OPTIONS.maxSamplesPerObject
|
|
342298
|
+
};
|
|
342299
|
+
if (!Number.isFinite(options.smoothAngleDeg) || options.smoothAngleDeg < 0) {
|
|
342300
|
+
throw new Error(`smoothAngleDeg must be a finite non-negative angle (got ${options.smoothAngleDeg}).`);
|
|
342301
|
+
}
|
|
342302
|
+
if (!Number.isFinite(options.sharpAngleDeg) || options.sharpAngleDeg <= options.smoothAngleDeg) {
|
|
342303
|
+
throw new Error(`sharpAngleDeg must be greater than smoothAngleDeg (got ${options.sharpAngleDeg}).`);
|
|
342304
|
+
}
|
|
342305
|
+
if (!Number.isFinite(options.harshAngleDeg) || options.harshAngleDeg <= options.sharpAngleDeg || options.harshAngleDeg > 180) {
|
|
342306
|
+
throw new Error(`harshAngleDeg must be greater than sharpAngleDeg and <= 180 (got ${options.harshAngleDeg}).`);
|
|
342307
|
+
}
|
|
342308
|
+
if (!Number.isFinite(options.maxSamplesPerObject) || options.maxSamplesPerObject <= 0) {
|
|
342309
|
+
throw new Error(`maxSamplesPerObject must be a positive finite number (got ${options.maxSamplesPerObject}).`);
|
|
342310
|
+
}
|
|
342311
|
+
return {
|
|
342312
|
+
...options,
|
|
342313
|
+
maxSamplesPerObject: Math.max(1, Math.floor(options.maxSamplesPerObject))
|
|
342314
|
+
};
|
|
342315
|
+
}
|
|
342316
|
+
function roughnessClassForAngle(angleDeg, options) {
|
|
342317
|
+
if (angleDeg >= options.harshAngleDeg) return "harsh";
|
|
342318
|
+
if (angleDeg >= options.sharpAngleDeg) return "sharp";
|
|
342319
|
+
if (angleDeg >= options.smoothAngleDeg) return "moderate";
|
|
342320
|
+
return "smooth";
|
|
342321
|
+
}
|
|
342322
|
+
function roughnessScoreForAngle(angleDeg, options) {
|
|
342323
|
+
if (angleDeg < options.sharpAngleDeg) return 0;
|
|
342324
|
+
if (angleDeg < options.harshAngleDeg) {
|
|
342325
|
+
return MathUtils.lerp(0.48, 0.82, (angleDeg - options.sharpAngleDeg) / (options.harshAngleDeg - options.sharpAngleDeg));
|
|
342326
|
+
}
|
|
342327
|
+
return 1;
|
|
342328
|
+
}
|
|
342329
|
+
function roughnessColorForAngle(angleDeg, options) {
|
|
342330
|
+
const cls = roughnessClassForAngle(angleDeg, options);
|
|
342331
|
+
if (cls === "smooth" || cls === "harsh") return ROUGHNESS_COLORS[cls];
|
|
342332
|
+
if (cls === "moderate") {
|
|
342333
|
+
return lerpRgb(
|
|
342334
|
+
ROUGHNESS_COLORS.moderate,
|
|
342335
|
+
ROUGHNESS_COLORS.sharp,
|
|
342336
|
+
(angleDeg - options.smoothAngleDeg) / (options.sharpAngleDeg - options.smoothAngleDeg)
|
|
342337
|
+
);
|
|
342338
|
+
}
|
|
342339
|
+
return lerpRgb(
|
|
342340
|
+
ROUGHNESS_COLORS.sharp,
|
|
342341
|
+
ROUGHNESS_COLORS.harsh,
|
|
342342
|
+
(angleDeg - options.sharpAngleDeg) / (options.harshAngleDeg - options.sharpAngleDeg)
|
|
342343
|
+
);
|
|
342344
|
+
}
|
|
342345
|
+
function lerpRgb(a2, b, t) {
|
|
342346
|
+
const clamped = MathUtils.clamp(t, 0, 1);
|
|
342347
|
+
return [
|
|
342348
|
+
Math.round(MathUtils.lerp(a2[0], b[0], clamped)),
|
|
342349
|
+
Math.round(MathUtils.lerp(a2[1], b[1], clamped)),
|
|
342350
|
+
Math.round(MathUtils.lerp(a2[2], b[2], clamped))
|
|
342351
|
+
];
|
|
342352
|
+
}
|
|
342353
|
+
const AXIS_NAMES = ["x", "y", "z"];
|
|
342354
|
+
function nearestBoundaryGap(a2, b, axis) {
|
|
342355
|
+
return Math.min(Math.abs(a2.max[axis] - b.min[axis]), Math.abs(b.max[axis] - a2.min[axis]));
|
|
342356
|
+
}
|
|
342357
|
+
function hasPositiveGap(gaps) {
|
|
342358
|
+
return gaps[0] > 0 || gaps[1] > 0 || gaps[2] > 0;
|
|
342359
|
+
}
|
|
342360
|
+
function contactFromBBoxes(a2, b, tolerance) {
|
|
342361
|
+
const gaps = aabbGaps(a2, b);
|
|
342362
|
+
const largestGap = Math.max(gaps[0], gaps[1], gaps[2]);
|
|
342363
|
+
if (largestGap > tolerance) return { touching: false, gap: largestGap };
|
|
342364
|
+
const separatedAxes = gaps.map((gap, axis) => ({ gap, axis })).filter((entry) => entry.gap > 0);
|
|
342365
|
+
if (separatedAxes.length > 0) {
|
|
342366
|
+
const nearest2 = separatedAxes.reduce((best, entry) => entry.gap > best.gap ? entry : best, separatedAxes[0]);
|
|
342367
|
+
return { touching: true, gap: nearest2.gap, axis: AXIS_NAMES[nearest2.axis] };
|
|
342368
|
+
}
|
|
342369
|
+
const boundaryAxes = AXIS_NAMES.map((axisName, axis) => ({
|
|
342370
|
+
axis,
|
|
342371
|
+
axisName,
|
|
342372
|
+
gap: nearestBoundaryGap(a2, b, axis)
|
|
342373
|
+
})).filter((entry) => entry.gap <= tolerance);
|
|
342374
|
+
if (boundaryAxes.length === 0) return { touching: false, gap: 0 };
|
|
342375
|
+
const nearest = boundaryAxes.reduce((best, entry) => entry.gap < best.gap ? entry : best, boundaryAxes[0]);
|
|
342376
|
+
return { touching: true, gap: nearest.gap, axis: nearest.axisName };
|
|
342377
|
+
}
|
|
342378
|
+
function isFiniteTriangle(positions, offset2) {
|
|
342379
|
+
for (let index2 = 0; index2 < 9; index2 += 1) {
|
|
342380
|
+
if (!Number.isFinite(positions[offset2 + index2])) return false;
|
|
342381
|
+
}
|
|
342382
|
+
return true;
|
|
342383
|
+
}
|
|
342384
|
+
function triangleRef(positions, offset2) {
|
|
342385
|
+
if (!isFiniteTriangle(positions, offset2)) return null;
|
|
342386
|
+
const ax = positions[offset2];
|
|
342387
|
+
const ay = positions[offset2 + 1];
|
|
342388
|
+
const az = positions[offset2 + 2];
|
|
342389
|
+
const bx = positions[offset2 + 3];
|
|
342390
|
+
const by = positions[offset2 + 4];
|
|
342391
|
+
const bz = positions[offset2 + 5];
|
|
342392
|
+
const cx = positions[offset2 + 6];
|
|
342393
|
+
const cy = positions[offset2 + 7];
|
|
342394
|
+
const cz = positions[offset2 + 8];
|
|
342395
|
+
return {
|
|
342396
|
+
offset: offset2,
|
|
342397
|
+
min: [Math.min(ax, bx, cx), Math.min(ay, by, cy), Math.min(az, bz, cz)],
|
|
342398
|
+
max: [Math.max(ax, bx, cx), Math.max(ay, by, cy), Math.max(az, bz, cz)]
|
|
342399
|
+
};
|
|
342400
|
+
}
|
|
342401
|
+
function meshContactDataFor(entry) {
|
|
342402
|
+
const positions = entry.positions;
|
|
342403
|
+
if (!positions || positions.length < 9) return null;
|
|
342404
|
+
const triangleCount = Math.floor(positions.length / 9);
|
|
342405
|
+
const triangles = [];
|
|
342406
|
+
for (let triangleIndex = 0; triangleIndex < triangleCount; triangleIndex += 1) {
|
|
342407
|
+
const triangle = triangleRef(positions, triangleIndex * 9);
|
|
342408
|
+
if (triangle) triangles.push(triangle);
|
|
342409
|
+
}
|
|
342410
|
+
if (triangles.length === 0) return null;
|
|
342411
|
+
return {
|
|
342412
|
+
positions,
|
|
342413
|
+
vertexCount: triangleCount * 3,
|
|
342414
|
+
triangles
|
|
342415
|
+
};
|
|
342416
|
+
}
|
|
342417
|
+
function distSq(px2, py2, pz2, qx, qy, qz) {
|
|
342418
|
+
const dx = px2 - qx;
|
|
342419
|
+
const dy = py2 - qy;
|
|
342420
|
+
const dz = pz2 - qz;
|
|
342421
|
+
return dx * dx + dy * dy + dz * dz;
|
|
342422
|
+
}
|
|
342423
|
+
function pointSegmentDistanceSq(point2, start, end) {
|
|
342424
|
+
const dx = end[0] - start[0];
|
|
342425
|
+
const dy = end[1] - start[1];
|
|
342426
|
+
const dz = end[2] - start[2];
|
|
342427
|
+
const lengthSq = dx * dx + dy * dy + dz * dz;
|
|
342428
|
+
if (lengthSq <= 1e-20) return distSq(point2[0], point2[1], point2[2], start[0], start[1], start[2]);
|
|
342429
|
+
const t = Math.max(0, Math.min(1, ((point2[0] - start[0]) * dx + (point2[1] - start[1]) * dy + (point2[2] - start[2]) * dz) / lengthSq));
|
|
342430
|
+
return distSq(point2[0], point2[1], point2[2], start[0] + t * dx, start[1] + t * dy, start[2] + t * dz);
|
|
342431
|
+
}
|
|
342432
|
+
function pointTriangleDistanceSq(px2, py2, pz2, ax, ay, az, bx, by, bz, cx, cy, cz) {
|
|
342433
|
+
const abx = bx - ax;
|
|
342434
|
+
const aby = by - ay;
|
|
342435
|
+
const abz = bz - az;
|
|
342436
|
+
const acx = cx - ax;
|
|
342437
|
+
const acy = cy - ay;
|
|
342438
|
+
const acz = cz - az;
|
|
342439
|
+
const apx = px2 - ax;
|
|
342440
|
+
const apy = py2 - ay;
|
|
342441
|
+
const apz = pz2 - az;
|
|
342442
|
+
const d1 = abx * apx + aby * apy + abz * apz;
|
|
342443
|
+
const d2 = acx * apx + acy * apy + acz * apz;
|
|
342444
|
+
if (d1 <= 0 && d2 <= 0) return distSq(px2, py2, pz2, ax, ay, az);
|
|
342445
|
+
const bpx = px2 - bx;
|
|
342446
|
+
const bpy = py2 - by;
|
|
342447
|
+
const bpz = pz2 - bz;
|
|
342448
|
+
const d3 = abx * bpx + aby * bpy + abz * bpz;
|
|
342449
|
+
const d4 = acx * bpx + acy * bpy + acz * bpz;
|
|
342450
|
+
if (d3 >= 0 && d4 <= d3) return distSq(px2, py2, pz2, bx, by, bz);
|
|
342451
|
+
const vc = d1 * d4 - d3 * d2;
|
|
342452
|
+
if (vc <= 0 && d1 >= 0 && d3 <= 0) {
|
|
342453
|
+
const v22 = d1 / (d1 - d3);
|
|
342454
|
+
return distSq(px2, py2, pz2, ax + v22 * abx, ay + v22 * aby, az + v22 * abz);
|
|
342455
|
+
}
|
|
342456
|
+
const cpx = px2 - cx;
|
|
342457
|
+
const cpy = py2 - cy;
|
|
342458
|
+
const cpz = pz2 - cz;
|
|
342459
|
+
const d5 = abx * cpx + aby * cpy + abz * cpz;
|
|
342460
|
+
const d6 = acx * cpx + acy * cpy + acz * cpz;
|
|
342461
|
+
if (d6 >= 0 && d5 <= d6) return distSq(px2, py2, pz2, cx, cy, cz);
|
|
342462
|
+
const vb = d5 * d2 - d1 * d6;
|
|
342463
|
+
if (vb <= 0 && d2 >= 0 && d6 <= 0) {
|
|
342464
|
+
const w22 = d2 / (d2 - d6);
|
|
342465
|
+
return distSq(px2, py2, pz2, ax + w22 * acx, ay + w22 * acy, az + w22 * acz);
|
|
342466
|
+
}
|
|
342467
|
+
const va = d3 * d6 - d5 * d4;
|
|
342468
|
+
if (va <= 0 && d4 - d3 >= 0 && d5 - d6 >= 0) {
|
|
342469
|
+
const bcx = cx - bx;
|
|
342470
|
+
const bcy = cy - by;
|
|
342471
|
+
const bcz = cz - bz;
|
|
342472
|
+
const w22 = (d4 - d3) / (d4 - d3 + d5 - d6);
|
|
342473
|
+
return distSq(px2, py2, pz2, bx + w22 * bcx, by + w22 * bcy, bz + w22 * bcz);
|
|
342474
|
+
}
|
|
342475
|
+
const barycentricTotal = va + vb + vc;
|
|
342476
|
+
if (!Number.isFinite(barycentricTotal) || Math.abs(barycentricTotal) < 1e-20) {
|
|
342477
|
+
return Math.min(distSq(px2, py2, pz2, ax, ay, az), distSq(px2, py2, pz2, bx, by, bz), distSq(px2, py2, pz2, cx, cy, cz));
|
|
342478
|
+
}
|
|
342479
|
+
const denom = 1 / barycentricTotal;
|
|
342480
|
+
const v = vb * denom;
|
|
342481
|
+
const w2 = vc * denom;
|
|
342482
|
+
return distSq(px2, py2, pz2, ax + abx * v + acx * w2, ay + aby * v + acy * w2, az + abz * v + acz * w2);
|
|
342483
|
+
}
|
|
342484
|
+
function segmentSegmentDistanceSq(a0, a1, b0, b1) {
|
|
342485
|
+
const ux = a1[0] - a0[0];
|
|
342486
|
+
const uy = a1[1] - a0[1];
|
|
342487
|
+
const uz = a1[2] - a0[2];
|
|
342488
|
+
const vx = b1[0] - b0[0];
|
|
342489
|
+
const vy = b1[1] - b0[1];
|
|
342490
|
+
const vz = b1[2] - b0[2];
|
|
342491
|
+
const wx = a0[0] - b0[0];
|
|
342492
|
+
const wy = a0[1] - b0[1];
|
|
342493
|
+
const wz = a0[2] - b0[2];
|
|
342494
|
+
const a2 = ux * ux + uy * uy + uz * uz;
|
|
342495
|
+
const b = ux * vx + uy * vy + uz * vz;
|
|
342496
|
+
const c2 = vx * vx + vy * vy + vz * vz;
|
|
342497
|
+
const d2 = ux * wx + uy * wy + uz * wz;
|
|
342498
|
+
const e = vx * wx + vy * wy + vz * wz;
|
|
342499
|
+
const denom = a2 * c2 - b * b;
|
|
342500
|
+
let sNumerator = denom;
|
|
342501
|
+
let sDenominator = denom;
|
|
342502
|
+
let tNumerator = denom;
|
|
342503
|
+
let tDenominator = denom;
|
|
342504
|
+
if (a2 <= 1e-20) return pointSegmentDistanceSq(a0, b0, b1);
|
|
342505
|
+
if (c2 <= 1e-20) return pointSegmentDistanceSq(b0, a0, a1);
|
|
342506
|
+
if (denom < 1e-20) {
|
|
342507
|
+
sNumerator = 0;
|
|
342508
|
+
sDenominator = 1;
|
|
342509
|
+
tNumerator = e;
|
|
342510
|
+
tDenominator = c2;
|
|
342511
|
+
} else {
|
|
342512
|
+
sNumerator = b * e - c2 * d2;
|
|
342513
|
+
tNumerator = a2 * e - b * d2;
|
|
342514
|
+
if (sNumerator < 0) {
|
|
342515
|
+
sNumerator = 0;
|
|
342516
|
+
tNumerator = e;
|
|
342517
|
+
tDenominator = c2;
|
|
342518
|
+
} else if (sNumerator > sDenominator) {
|
|
342519
|
+
sNumerator = sDenominator;
|
|
342520
|
+
tNumerator = e + b;
|
|
342521
|
+
tDenominator = c2;
|
|
342522
|
+
}
|
|
342523
|
+
}
|
|
342524
|
+
if (tNumerator < 0) {
|
|
342525
|
+
tNumerator = 0;
|
|
342526
|
+
if (-d2 < 0) {
|
|
342527
|
+
sNumerator = 0;
|
|
342528
|
+
} else if (-d2 > a2) {
|
|
342529
|
+
sNumerator = sDenominator;
|
|
342530
|
+
} else {
|
|
342531
|
+
sNumerator = -d2;
|
|
342532
|
+
sDenominator = a2;
|
|
342533
|
+
}
|
|
342534
|
+
} else if (tNumerator > tDenominator) {
|
|
342535
|
+
tNumerator = tDenominator;
|
|
342536
|
+
if (-d2 + b < 0) {
|
|
342537
|
+
sNumerator = 0;
|
|
342538
|
+
} else if (-d2 + b > a2) {
|
|
342539
|
+
sNumerator = sDenominator;
|
|
342540
|
+
} else {
|
|
342541
|
+
sNumerator = -d2 + b;
|
|
342542
|
+
sDenominator = a2;
|
|
342543
|
+
}
|
|
342544
|
+
}
|
|
342545
|
+
const s = Math.abs(sNumerator) < 1e-20 ? 0 : sNumerator / sDenominator;
|
|
342546
|
+
const t = Math.abs(tNumerator) < 1e-20 ? 0 : tNumerator / tDenominator;
|
|
342547
|
+
const dx = wx + s * ux - t * vx;
|
|
342548
|
+
const dy = wy + s * uy - t * vy;
|
|
342549
|
+
const dz = wz + s * uz - t * vz;
|
|
342550
|
+
return dx * dx + dy * dy + dz * dz;
|
|
342551
|
+
}
|
|
342552
|
+
function trianglePoint(positions, triangle, corner) {
|
|
342553
|
+
const offset2 = triangle.offset + corner * 3;
|
|
342554
|
+
return [positions[offset2], positions[offset2 + 1], positions[offset2 + 2]];
|
|
342555
|
+
}
|
|
342556
|
+
function bboxDistanceSq(a2, b) {
|
|
342557
|
+
let total = 0;
|
|
342558
|
+
for (let axis = 0; axis < 3; axis += 1) {
|
|
342559
|
+
const gap = Math.max(0, a2.min[axis] - b.max[axis], b.min[axis] - a2.max[axis]);
|
|
342560
|
+
total += gap * gap;
|
|
342561
|
+
}
|
|
342562
|
+
return total;
|
|
342563
|
+
}
|
|
342564
|
+
function triangleDistanceSq(aPositions, a2, bPositions, b) {
|
|
342565
|
+
const a0 = trianglePoint(aPositions, a2, 0);
|
|
342566
|
+
const a1 = trianglePoint(aPositions, a2, 1);
|
|
342567
|
+
const a22 = trianglePoint(aPositions, a2, 2);
|
|
342568
|
+
const b0 = trianglePoint(bPositions, b, 0);
|
|
342569
|
+
const b1 = trianglePoint(bPositions, b, 1);
|
|
342570
|
+
const b22 = trianglePoint(bPositions, b, 2);
|
|
342571
|
+
return Math.min(
|
|
342572
|
+
pointTriangleDistanceSq(a0[0], a0[1], a0[2], b0[0], b0[1], b0[2], b1[0], b1[1], b1[2], b22[0], b22[1], b22[2]),
|
|
342573
|
+
pointTriangleDistanceSq(a1[0], a1[1], a1[2], b0[0], b0[1], b0[2], b1[0], b1[1], b1[2], b22[0], b22[1], b22[2]),
|
|
342574
|
+
pointTriangleDistanceSq(a22[0], a22[1], a22[2], b0[0], b0[1], b0[2], b1[0], b1[1], b1[2], b22[0], b22[1], b22[2]),
|
|
342575
|
+
pointTriangleDistanceSq(b0[0], b0[1], b0[2], a0[0], a0[1], a0[2], a1[0], a1[1], a1[2], a22[0], a22[1], a22[2]),
|
|
342576
|
+
pointTriangleDistanceSq(b1[0], b1[1], b1[2], a0[0], a0[1], a0[2], a1[0], a1[1], a1[2], a22[0], a22[1], a22[2]),
|
|
342577
|
+
pointTriangleDistanceSq(b22[0], b22[1], b22[2], a0[0], a0[1], a0[2], a1[0], a1[1], a1[2], a22[0], a22[1], a22[2]),
|
|
342578
|
+
segmentSegmentDistanceSq(a0, a1, b0, b1),
|
|
342579
|
+
segmentSegmentDistanceSq(a0, a1, b1, b22),
|
|
342580
|
+
segmentSegmentDistanceSq(a0, a1, b22, b0),
|
|
342581
|
+
segmentSegmentDistanceSq(a1, a22, b0, b1),
|
|
342582
|
+
segmentSegmentDistanceSq(a1, a22, b1, b22),
|
|
342583
|
+
segmentSegmentDistanceSq(a1, a22, b22, b0),
|
|
342584
|
+
segmentSegmentDistanceSq(a22, a0, b0, b1),
|
|
342585
|
+
segmentSegmentDistanceSq(a22, a0, b1, b22),
|
|
342586
|
+
segmentSegmentDistanceSq(a22, a0, b22, b0)
|
|
342587
|
+
);
|
|
342588
|
+
}
|
|
342589
|
+
function meshEntriesContactDistance(a2, b, tolerance) {
|
|
342590
|
+
const toleranceSq = tolerance * tolerance;
|
|
342591
|
+
let bestDistanceSq = Infinity;
|
|
342592
|
+
for (const aTriangle of a2.triangles) {
|
|
342593
|
+
for (const bTriangle of b.triangles) {
|
|
342594
|
+
if (bboxDistanceSq(aTriangle, bTriangle) > toleranceSq) continue;
|
|
342595
|
+
const distanceSq = triangleDistanceSq(a2.positions, aTriangle, b.positions, bTriangle);
|
|
342596
|
+
if (distanceSq > toleranceSq) continue;
|
|
342597
|
+
if (distanceSq <= 1e-20) return 0;
|
|
342598
|
+
bestDistanceSq = Math.min(bestDistanceSq, distanceSq);
|
|
342599
|
+
}
|
|
342600
|
+
}
|
|
342601
|
+
return Number.isFinite(bestDistanceSq) ? Math.sqrt(bestDistanceSq) : null;
|
|
342602
|
+
}
|
|
342603
|
+
function intersectionVolume(a2, b) {
|
|
342604
|
+
try {
|
|
342605
|
+
const hit = a2.shape.intersect(b.shape);
|
|
342606
|
+
if (hit.isEmpty()) return { volume: 0 };
|
|
342607
|
+
const volume = hit.volume();
|
|
342608
|
+
return { volume: Number.isFinite(volume) ? volume : 0 };
|
|
342609
|
+
} catch (err2) {
|
|
342610
|
+
const message = err2 instanceof Error ? err2.message : String(err2);
|
|
342611
|
+
return { volume: null, warning: `Could not boolean-test ${a2.name} against ${b.name}: ${message}` };
|
|
342612
|
+
}
|
|
342613
|
+
}
|
|
342614
|
+
function detectPhysicalContact(a2, b, options, meshCache = {}) {
|
|
342615
|
+
const gaps = aabbGaps(a2, b);
|
|
342616
|
+
const largestGap = Math.max(gaps[0], gaps[1], gaps[2]);
|
|
342617
|
+
if (largestGap > options.contactTolerance) return { contact: null };
|
|
342618
|
+
const sourceMesh = meshCache.sourceMesh !== void 0 ? meshCache.sourceMesh : meshContactDataFor(a2);
|
|
342619
|
+
const targetMesh = meshCache.targetMesh !== void 0 ? meshCache.targetMesh : meshContactDataFor(b);
|
|
342620
|
+
if (sourceMesh && targetMesh) {
|
|
342621
|
+
const distance2 = meshEntriesContactDistance(sourceMesh, targetMesh, options.contactTolerance);
|
|
342622
|
+
if (distance2 != null) {
|
|
342623
|
+
return {
|
|
342624
|
+
contact: {
|
|
342625
|
+
kind: "touching",
|
|
342626
|
+
method: "mesh-surface-distance",
|
|
342627
|
+
gap: distance2
|
|
342628
|
+
}
|
|
342629
|
+
};
|
|
342630
|
+
}
|
|
342631
|
+
}
|
|
342632
|
+
const bboxOverlaps = !hasPositiveGap(gaps) && aabbInteriorOverlaps(a2, b);
|
|
342633
|
+
if (options.exactGeometry && bboxOverlaps) {
|
|
342634
|
+
if (aabbOverlapVolume(a2, b) <= options.minOverlapVolume) return { contact: null };
|
|
342635
|
+
const overlap = intersectionVolume(a2, b);
|
|
342636
|
+
if (overlap.volume != null && overlap.volume > options.minOverlapVolume) {
|
|
342637
|
+
return {
|
|
342638
|
+
contact: {
|
|
342639
|
+
kind: "overlap",
|
|
342640
|
+
method: "boolean-intersection",
|
|
342641
|
+
gap: 0,
|
|
342642
|
+
overlapVolume: overlap.volume
|
|
342643
|
+
},
|
|
342644
|
+
warning: overlap.warning
|
|
342645
|
+
};
|
|
342646
|
+
}
|
|
342647
|
+
return { contact: null, warning: overlap.warning };
|
|
342648
|
+
}
|
|
342649
|
+
if (bboxOverlaps && options.mergeOverlappingBBoxes) {
|
|
342650
|
+
return {
|
|
342651
|
+
contact: {
|
|
342652
|
+
kind: "overlap",
|
|
342653
|
+
method: "bbox-overlap",
|
|
342654
|
+
gap: 0,
|
|
342655
|
+
overlapVolume: aabbOverlapVolume(a2, b)
|
|
342656
|
+
}
|
|
342657
|
+
};
|
|
342658
|
+
}
|
|
342659
|
+
if (options.mergeTouchingBBoxes) {
|
|
342660
|
+
const contact = contactFromBBoxes(a2, b, options.contactTolerance);
|
|
342661
|
+
if (contact.touching) {
|
|
342662
|
+
return {
|
|
342663
|
+
contact: {
|
|
342664
|
+
kind: "touching",
|
|
342665
|
+
method: "bbox-contact",
|
|
342666
|
+
gap: contact.gap,
|
|
342667
|
+
axis: contact.axis
|
|
342668
|
+
}
|
|
342669
|
+
};
|
|
342670
|
+
}
|
|
342671
|
+
}
|
|
342672
|
+
return { contact: null };
|
|
342673
|
+
}
|
|
342674
|
+
const DEFAULT_PHYSICAL_CONNECTIVITY_OPTIONS = {
|
|
342675
|
+
contactTolerance: 0.05,
|
|
342676
|
+
minOverlapVolume: 0.1,
|
|
342677
|
+
exactGeometry: true
|
|
342678
|
+
};
|
|
342679
|
+
class UnionFind {
|
|
342680
|
+
constructor(size) {
|
|
342681
|
+
__publicField(this, "parent");
|
|
342682
|
+
__publicField(this, "rank");
|
|
342683
|
+
this.parent = Array.from({ length: size }, (_2, index2) => index2);
|
|
342684
|
+
this.rank = Array.from({ length: size }, () => 0);
|
|
342685
|
+
}
|
|
342686
|
+
find(value) {
|
|
342687
|
+
const parent = this.parent[value];
|
|
342688
|
+
if (parent === value) return value;
|
|
342689
|
+
const root = this.find(parent);
|
|
342690
|
+
this.parent[value] = root;
|
|
342691
|
+
return root;
|
|
342692
|
+
}
|
|
342693
|
+
union(a2, b) {
|
|
342694
|
+
const rootA = this.find(a2);
|
|
342695
|
+
const rootB = this.find(b);
|
|
342696
|
+
if (rootA === rootB) return;
|
|
342697
|
+
if (this.rank[rootA] < this.rank[rootB]) {
|
|
342698
|
+
this.parent[rootA] = rootB;
|
|
342699
|
+
return;
|
|
342700
|
+
}
|
|
342701
|
+
if (this.rank[rootA] > this.rank[rootB]) {
|
|
342702
|
+
this.parent[rootB] = rootA;
|
|
342703
|
+
return;
|
|
342704
|
+
}
|
|
342705
|
+
this.parent[rootB] = rootA;
|
|
342706
|
+
this.rank[rootA] += 1;
|
|
342707
|
+
}
|
|
342708
|
+
}
|
|
342709
|
+
function cloneVec3(value) {
|
|
342710
|
+
return [value[0], value[1], value[2]];
|
|
342711
|
+
}
|
|
342712
|
+
function emptyBBox() {
|
|
342713
|
+
return {
|
|
342714
|
+
min: [Infinity, Infinity, Infinity],
|
|
342715
|
+
max: [-Infinity, -Infinity, -Infinity]
|
|
342716
|
+
};
|
|
342717
|
+
}
|
|
342718
|
+
function expandBBox(target, min2, max2) {
|
|
342719
|
+
for (let axis = 0; axis < 3; axis += 1) {
|
|
342720
|
+
target.min[axis] = Math.min(target.min[axis], min2[axis]);
|
|
342721
|
+
target.max[axis] = Math.max(target.max[axis], max2[axis]);
|
|
342722
|
+
}
|
|
342723
|
+
}
|
|
342724
|
+
function collectCandidatePairs(entries, tolerance) {
|
|
342725
|
+
if (entries.length < 2) return [];
|
|
342726
|
+
const index2 = new AabbSpatialIndex(entries);
|
|
342727
|
+
const pairs = index2.overlapPairs({ padding: tolerance }).pairs.map((pair) => ({
|
|
342728
|
+
sourceIndex: pair.sourceIndex,
|
|
342729
|
+
targetIndex: pair.targetIndex,
|
|
342730
|
+
gaps: aabbGaps(entries[pair.sourceIndex], entries[pair.targetIndex])
|
|
342731
|
+
})).filter((pair) => Math.max(pair.gaps[0], pair.gaps[1], pair.gaps[2]) <= tolerance);
|
|
342732
|
+
pairs.sort((a2, b) => a2.sourceIndex - b.sourceIndex || a2.targetIndex - b.targetIndex);
|
|
342733
|
+
return pairs;
|
|
342734
|
+
}
|
|
342735
|
+
function bodyCountForEntry(entry) {
|
|
342736
|
+
if (typeof entry.bodyCount === "number" && Number.isFinite(entry.bodyCount)) {
|
|
342737
|
+
return Math.max(0, Math.round(entry.bodyCount));
|
|
342738
|
+
}
|
|
342739
|
+
return 1;
|
|
342740
|
+
}
|
|
342741
|
+
function makeEdge(entries, sourceIndex, targetIndex, edge) {
|
|
342742
|
+
const source = entries[sourceIndex];
|
|
342743
|
+
const target = entries[targetIndex];
|
|
342744
|
+
return {
|
|
342745
|
+
sourceIndex,
|
|
342746
|
+
targetIndex,
|
|
342747
|
+
sourceId: source.id,
|
|
342748
|
+
targetId: target.id,
|
|
342749
|
+
sourceName: source.name,
|
|
342750
|
+
targetName: target.name,
|
|
342751
|
+
...edge
|
|
342752
|
+
};
|
|
342753
|
+
}
|
|
342754
|
+
function analyzePhysicalConnectivity(entries, rawOptions = {}) {
|
|
342755
|
+
const exactGeometry = rawOptions.exactGeometry ?? DEFAULT_PHYSICAL_CONNECTIVITY_OPTIONS.exactGeometry;
|
|
342756
|
+
const options = {
|
|
342757
|
+
contactTolerance: rawOptions.contactTolerance ?? DEFAULT_PHYSICAL_CONNECTIVITY_OPTIONS.contactTolerance,
|
|
342758
|
+
minOverlapVolume: rawOptions.minOverlapVolume ?? DEFAULT_PHYSICAL_CONNECTIVITY_OPTIONS.minOverlapVolume,
|
|
342759
|
+
exactGeometry,
|
|
342760
|
+
mergeOverlappingBBoxes: rawOptions.mergeOverlappingBBoxes ?? !exactGeometry,
|
|
342761
|
+
mergeTouchingBBoxes: rawOptions.mergeTouchingBBoxes ?? !exactGeometry
|
|
342762
|
+
};
|
|
342763
|
+
const warnings = [];
|
|
342764
|
+
const edges = [];
|
|
342765
|
+
const unionFind = new UnionFind(entries.length);
|
|
342766
|
+
const meshDataByIndex = /* @__PURE__ */ new Map();
|
|
342767
|
+
entries.forEach((entry, index2) => {
|
|
342768
|
+
const meshData = meshContactDataFor(entry);
|
|
342769
|
+
if (meshData) meshDataByIndex.set(index2, meshData);
|
|
342770
|
+
});
|
|
342771
|
+
for (const pair of collectCandidatePairs(entries, options.contactTolerance)) {
|
|
342772
|
+
const i = pair.sourceIndex;
|
|
342773
|
+
const j = pair.targetIndex;
|
|
342774
|
+
const detection = detectPhysicalContact(entries[i], entries[j], options, {
|
|
342775
|
+
sourceMesh: meshDataByIndex.get(i) ?? null,
|
|
342776
|
+
targetMesh: meshDataByIndex.get(j) ?? null
|
|
342777
|
+
});
|
|
342778
|
+
if (detection.warning) warnings.push(detection.warning);
|
|
342779
|
+
if (!detection.contact) continue;
|
|
342780
|
+
unionFind.union(i, j);
|
|
342781
|
+
edges.push(makeEdge(entries, i, j, detection.contact));
|
|
342782
|
+
}
|
|
342783
|
+
const objects = entries.map((entry, index2) => ({
|
|
342784
|
+
index: index2,
|
|
342785
|
+
id: entry.id,
|
|
342786
|
+
name: entry.name,
|
|
342787
|
+
groupName: entry.groupName,
|
|
342788
|
+
treePath: entry.treePath,
|
|
342789
|
+
mock: entry.mock === true,
|
|
342790
|
+
bodyCount: bodyCountForEntry(entry),
|
|
342791
|
+
bbox: {
|
|
342792
|
+
min: cloneVec3(entry.min),
|
|
342793
|
+
max: cloneVec3(entry.max)
|
|
342794
|
+
},
|
|
342795
|
+
componentIndex: 0
|
|
342796
|
+
}));
|
|
342797
|
+
const componentByRoot = /* @__PURE__ */ new Map();
|
|
342798
|
+
const rootToComponentIndex = /* @__PURE__ */ new Map();
|
|
342799
|
+
for (let objectIndex = 0; objectIndex < objects.length; objectIndex += 1) {
|
|
342800
|
+
const root = unionFind.find(objectIndex);
|
|
342801
|
+
let component = componentByRoot.get(root);
|
|
342802
|
+
if (!component) {
|
|
342803
|
+
component = {
|
|
342804
|
+
index: componentByRoot.size + 1,
|
|
342805
|
+
objectIndexes: [],
|
|
342806
|
+
objectIds: [],
|
|
342807
|
+
objectNames: [],
|
|
342808
|
+
objectCount: 0,
|
|
342809
|
+
bodyCount: 0,
|
|
342810
|
+
bbox: emptyBBox()
|
|
342811
|
+
};
|
|
342812
|
+
componentByRoot.set(root, component);
|
|
342813
|
+
rootToComponentIndex.set(root, component.index);
|
|
342814
|
+
}
|
|
342815
|
+
const object = objects[objectIndex];
|
|
342816
|
+
object.componentIndex = rootToComponentIndex.get(root) ?? component.index;
|
|
342817
|
+
component.objectIndexes.push(object.index);
|
|
342818
|
+
component.objectIds.push(object.id);
|
|
342819
|
+
component.objectNames.push(object.name);
|
|
342820
|
+
component.objectCount += 1;
|
|
342821
|
+
component.bodyCount += object.bodyCount;
|
|
342822
|
+
expandBBox(component.bbox, object.bbox.min, object.bbox.max);
|
|
342823
|
+
}
|
|
342824
|
+
const components = [...componentByRoot.values()];
|
|
342825
|
+
return {
|
|
342826
|
+
method: options.exactGeometry ? "mesh-contact-plus-boolean-overlap" : "bbox-neighborhood",
|
|
342827
|
+
options,
|
|
342828
|
+
objectCount: objects.length,
|
|
342829
|
+
componentCount: components.length,
|
|
342830
|
+
objects,
|
|
342831
|
+
components,
|
|
342832
|
+
edges,
|
|
342833
|
+
warnings
|
|
342834
|
+
};
|
|
342835
|
+
}
|
|
342836
|
+
const DEFAULT_THICKNESS_INSPECTION_OPTIONS = {
|
|
342837
|
+
minThickness: 1.2,
|
|
342838
|
+
warnThickness: 2,
|
|
342839
|
+
maxThickness: 6,
|
|
342840
|
+
maxSamplesPerObject: 5e3,
|
|
342841
|
+
contactTolerance: DEFAULT_PHYSICAL_CONNECTIVITY_OPTIONS.contactTolerance
|
|
342842
|
+
};
|
|
342843
|
+
const THICKNESS_COLORS = {
|
|
342844
|
+
critical: [255, 28, 28],
|
|
342845
|
+
warning: [255, 150, 0],
|
|
342846
|
+
ok: [60, 220, 90],
|
|
342847
|
+
thick: [70, 145, 255],
|
|
342848
|
+
unknown: [90, 90, 90]
|
|
342849
|
+
};
|
|
342850
|
+
function finitePositive(value, fallback, label) {
|
|
342851
|
+
if (value === void 0) return fallback;
|
|
342852
|
+
if (!Number.isFinite(value) || value <= 0) {
|
|
342853
|
+
throw new Error(`${label} must be a positive finite number.`);
|
|
342854
|
+
}
|
|
342855
|
+
return value;
|
|
342856
|
+
}
|
|
342857
|
+
function finiteNonNegative(value, fallback, label) {
|
|
342858
|
+
if (value === void 0) return fallback;
|
|
342859
|
+
if (!Number.isFinite(value) || value < 0) {
|
|
342860
|
+
throw new Error(`${label} must be a non-negative finite number.`);
|
|
342861
|
+
}
|
|
342862
|
+
return value;
|
|
342863
|
+
}
|
|
342864
|
+
function resolveThicknessInspectionOptions(raw = {}) {
|
|
342865
|
+
const minThickness = finitePositive(raw.minThickness, DEFAULT_THICKNESS_INSPECTION_OPTIONS.minThickness, "minThickness");
|
|
342866
|
+
const warnThickness = finitePositive(raw.warnThickness, DEFAULT_THICKNESS_INSPECTION_OPTIONS.warnThickness, "warnThickness");
|
|
342867
|
+
const maxThickness = finitePositive(raw.maxThickness, DEFAULT_THICKNESS_INSPECTION_OPTIONS.maxThickness, "maxThickness");
|
|
342868
|
+
const maxSamplesPerObject = finitePositive(
|
|
342869
|
+
raw.maxSamplesPerObject,
|
|
342870
|
+
DEFAULT_THICKNESS_INSPECTION_OPTIONS.maxSamplesPerObject,
|
|
342871
|
+
"maxSamplesPerObject"
|
|
342872
|
+
);
|
|
342873
|
+
const contactTolerance = finiteNonNegative(
|
|
342874
|
+
raw.contactTolerance,
|
|
342875
|
+
DEFAULT_THICKNESS_INSPECTION_OPTIONS.contactTolerance,
|
|
342876
|
+
"contactTolerance"
|
|
342877
|
+
);
|
|
342878
|
+
if (minThickness > warnThickness) {
|
|
342879
|
+
throw new Error("minThickness must be less than or equal to warnThickness.");
|
|
342880
|
+
}
|
|
342881
|
+
if (warnThickness > maxThickness) {
|
|
342882
|
+
throw new Error("warnThickness must be less than or equal to maxThickness.");
|
|
342883
|
+
}
|
|
342884
|
+
return {
|
|
342885
|
+
minThickness,
|
|
342886
|
+
warnThickness,
|
|
342887
|
+
maxThickness,
|
|
342888
|
+
maxSamplesPerObject: Math.max(1, Math.floor(maxSamplesPerObject)),
|
|
342889
|
+
contactTolerance
|
|
342890
|
+
};
|
|
342891
|
+
}
|
|
342892
|
+
function lerp(a2, b, t) {
|
|
342893
|
+
return a2 + (b - a2) * Math.max(0, Math.min(1, t));
|
|
342894
|
+
}
|
|
342895
|
+
function lerpColor(a2, b, t) {
|
|
342896
|
+
return [Math.round(lerp(a2[0], b[0], t)), Math.round(lerp(a2[1], b[1], t)), Math.round(lerp(a2[2], b[2], t))];
|
|
342897
|
+
}
|
|
342898
|
+
function thicknessClass(thickness, options) {
|
|
342899
|
+
if (thickness == null || !Number.isFinite(thickness) || thickness <= 0) return "unknown";
|
|
342900
|
+
if (thickness <= options.minThickness) return "critical";
|
|
342901
|
+
if (thickness <= options.warnThickness) return "warning";
|
|
342902
|
+
if (thickness <= options.maxThickness) return "ok";
|
|
342903
|
+
return "thick";
|
|
342904
|
+
}
|
|
342905
|
+
function thicknessColor(thickness, options) {
|
|
342906
|
+
const cls = thicknessClass(thickness, options);
|
|
342907
|
+
if (cls === "unknown") return THICKNESS_COLORS.unknown;
|
|
342908
|
+
if (cls === "critical") return THICKNESS_COLORS.critical;
|
|
342909
|
+
if (cls === "warning") {
|
|
342910
|
+
const span = Math.max(1e-9, options.warnThickness - options.minThickness);
|
|
342911
|
+
return lerpColor(THICKNESS_COLORS.critical, THICKNESS_COLORS.warning, ((thickness ?? 0) - options.minThickness) / span);
|
|
342912
|
+
}
|
|
342913
|
+
if (cls === "ok") {
|
|
342914
|
+
const span = Math.max(1e-9, options.maxThickness - options.warnThickness);
|
|
342915
|
+
return lerpColor(THICKNESS_COLORS.ok, THICKNESS_COLORS.thick, ((thickness ?? 0) - options.warnThickness) / span);
|
|
342916
|
+
}
|
|
342917
|
+
return THICKNESS_COLORS.thick;
|
|
342918
|
+
}
|
|
342919
|
+
function sampleArea(sample) {
|
|
342920
|
+
const area2 = sample.area ?? 1;
|
|
342921
|
+
return Number.isFinite(area2) && area2 > 0 ? area2 : 1;
|
|
342922
|
+
}
|
|
342923
|
+
function weightedQuantile(samples, q) {
|
|
342924
|
+
if (samples.length === 0) return null;
|
|
342925
|
+
const sorted = [...samples].sort((a2, b) => a2.thickness - b.thickness);
|
|
342926
|
+
const totalArea = sorted.reduce((sum2, sample) => sum2 + sample.area, 0);
|
|
342927
|
+
const target = totalArea * Math.max(0, Math.min(1, q));
|
|
342928
|
+
let cumulative = 0;
|
|
342929
|
+
for (const sample of sorted) {
|
|
342930
|
+
cumulative += sample.area;
|
|
342931
|
+
if (cumulative >= target) return sample.thickness;
|
|
342932
|
+
}
|
|
342933
|
+
return sorted[sorted.length - 1].thickness;
|
|
342934
|
+
}
|
|
342935
|
+
function percent(part, total) {
|
|
342936
|
+
if (total <= 0) return 0;
|
|
342937
|
+
return part / total * 100;
|
|
342938
|
+
}
|
|
342939
|
+
function summarizeThicknessSamples(samples, options) {
|
|
342940
|
+
const resolved = [];
|
|
342941
|
+
let totalArea = 0;
|
|
342942
|
+
let resolvedArea = 0;
|
|
342943
|
+
let unresolvedArea = 0;
|
|
342944
|
+
let criticalArea = 0;
|
|
342945
|
+
let warningArea = 0;
|
|
342946
|
+
let weightedSum = 0;
|
|
342947
|
+
for (const sample of samples) {
|
|
342948
|
+
const area2 = sampleArea(sample);
|
|
342949
|
+
totalArea += area2;
|
|
342950
|
+
const value = sample.thickness;
|
|
342951
|
+
if (value == null || !Number.isFinite(value) || value <= 0) {
|
|
342952
|
+
unresolvedArea += area2;
|
|
342953
|
+
continue;
|
|
342954
|
+
}
|
|
342955
|
+
resolved.push({ thickness: value, area: area2 });
|
|
342956
|
+
resolvedArea += area2;
|
|
342957
|
+
weightedSum += value * area2;
|
|
342958
|
+
if (value <= options.minThickness) {
|
|
342959
|
+
criticalArea += area2;
|
|
342960
|
+
} else if (value <= options.warnThickness) {
|
|
342961
|
+
warningArea += area2;
|
|
342962
|
+
}
|
|
342963
|
+
}
|
|
342964
|
+
const values = resolved.map((sample) => sample.thickness);
|
|
342965
|
+
return {
|
|
342966
|
+
sampleCount: samples.length,
|
|
342967
|
+
resolvedCount: resolved.length,
|
|
342968
|
+
unresolvedCount: samples.length - resolved.length,
|
|
342969
|
+
minThickness: values.length > 0 ? Math.min(...values) : null,
|
|
342970
|
+
p05Thickness: weightedQuantile(resolved, 0.05),
|
|
342971
|
+
medianThickness: weightedQuantile(resolved, 0.5),
|
|
342972
|
+
meanThickness: resolvedArea > 0 ? weightedSum / resolvedArea : null,
|
|
342973
|
+
maxThickness: values.length > 0 ? Math.max(...values) : null,
|
|
342974
|
+
criticalAreaPercent: percent(criticalArea, resolvedArea),
|
|
342975
|
+
warningAreaPercent: percent(warningArea, resolvedArea),
|
|
342976
|
+
belowWarnAreaPercent: percent(criticalArea + warningArea, resolvedArea),
|
|
342977
|
+
unresolvedAreaPercent: percent(unresolvedArea, totalArea)
|
|
342978
|
+
};
|
|
342979
|
+
}
|
|
342280
342980
|
const VECTOR_KEYS = /* @__PURE__ */ new Set(["pos", "position", "target", "lookat", "aim", "up"]);
|
|
342281
342981
|
const roundNumber = (value, digits) => {
|
|
342282
342982
|
const scale2 = 10 ** digits;
|
|
@@ -342565,7 +343265,7 @@ export {
|
|
|
342565
343265
|
DEFAULT_ACTIVE_BACKEND as ay,
|
|
342566
343266
|
isConstraintSketch as az,
|
|
342567
343267
|
PCFShadowMap as b,
|
|
342568
|
-
|
|
343268
|
+
analyzePhysicalConnectivity as b$,
|
|
342569
343269
|
PointLight as b0,
|
|
342570
343270
|
DirectionalLight as b1,
|
|
342571
343271
|
analyzeCollisionIntersections as b2,
|
|
@@ -342576,33 +343276,33 @@ export {
|
|
|
342576
343276
|
runScript as b7,
|
|
342577
343277
|
MeshPhysicalMaterial as b8,
|
|
342578
343278
|
LineSegments as b9,
|
|
342579
|
-
|
|
342580
|
-
|
|
342581
|
-
|
|
342582
|
-
|
|
342583
|
-
|
|
342584
|
-
|
|
342585
|
-
|
|
342586
|
-
|
|
342587
|
-
|
|
342588
|
-
|
|
342589
|
-
|
|
342590
|
-
|
|
342591
|
-
|
|
342592
|
-
|
|
342593
|
-
|
|
342594
|
-
|
|
342595
|
-
|
|
342596
|
-
|
|
342597
|
-
|
|
342598
|
-
|
|
342599
|
-
|
|
342600
|
-
|
|
342601
|
-
|
|
342602
|
-
|
|
342603
|
-
|
|
342604
|
-
|
|
342605
|
-
|
|
343279
|
+
parseViewportCameraState as bA,
|
|
343280
|
+
createResolvedExplodeConfig as bB,
|
|
343281
|
+
explodeBoundsCenter as bC,
|
|
343282
|
+
explodeMergeBounds as bD,
|
|
343283
|
+
resolveExplodeDirective as bE,
|
|
343284
|
+
computeExplodeMotion as bF,
|
|
343285
|
+
getSketchWorldMatrix as bG,
|
|
343286
|
+
explodeAdd as bH,
|
|
343287
|
+
hasExplodeOverride as bI,
|
|
343288
|
+
resolveExplodeLocalFanDirection as bJ,
|
|
343289
|
+
explodeMul as bK,
|
|
343290
|
+
explodeLeafFanStage as bL,
|
|
343291
|
+
normalizeCutPlane as bM,
|
|
343292
|
+
toClippingPlane as bN,
|
|
343293
|
+
findJointAnimationClip as bO,
|
|
343294
|
+
resolveJointAnimation as bP,
|
|
343295
|
+
resolveJointViewValues as bQ,
|
|
343296
|
+
getShapePorts as bR,
|
|
343297
|
+
getShapeUsedPorts as bS,
|
|
343298
|
+
DEFAULT_VIEW_CONFIG as bT,
|
|
343299
|
+
getKernelFaceNameForTriangle as bU,
|
|
343300
|
+
resolveScalarSceneSampleBudget as bV,
|
|
343301
|
+
initKernel as bW,
|
|
343302
|
+
initSolverWasm as bX,
|
|
343303
|
+
BoxGeometry as bY,
|
|
343304
|
+
localAabbPlaneRelation as bZ,
|
|
343305
|
+
ShapeUtils as b_,
|
|
342606
343306
|
geometryWithVisibleVertexColors as ba,
|
|
342607
343307
|
getRenderStylePreset as bb,
|
|
342608
343308
|
AdditiveBlending as bc,
|
|
@@ -342617,32 +343317,44 @@ export {
|
|
|
342617
343317
|
SURFACE_FIELD_VERTEX_SHADER as bl,
|
|
342618
343318
|
CatmullRomCurve3 as bm,
|
|
342619
343319
|
TubeGeometry as bn,
|
|
342620
|
-
|
|
342621
|
-
|
|
342622
|
-
|
|
342623
|
-
|
|
342624
|
-
|
|
342625
|
-
|
|
342626
|
-
|
|
342627
|
-
|
|
342628
|
-
|
|
342629
|
-
|
|
342630
|
-
|
|
342631
|
-
|
|
343320
|
+
ROUGHNESS_COLORS as bo,
|
|
343321
|
+
DEFAULT_ROUGHNESS_INSPECTION_OPTIONS as bp,
|
|
343322
|
+
DEFAULT_THICKNESS_INSPECTION_OPTIONS as bq,
|
|
343323
|
+
THICKNESS_COLORS as br,
|
|
343324
|
+
MeshStandardMaterial as bs,
|
|
343325
|
+
compileSdfNode3 as bt,
|
|
343326
|
+
buildSdfRaymarchFragmentShader as bu,
|
|
343327
|
+
SDF_RAYMARCH_PROXY_VERTEX_SHADER as bv,
|
|
343328
|
+
Shape2 as bw,
|
|
343329
|
+
ShapeGeometry as bx,
|
|
343330
|
+
ShaderLib as by,
|
|
343331
|
+
CylinderGeometry as bz,
|
|
342632
343332
|
SRGBColorSpace as c,
|
|
342633
|
-
|
|
342634
|
-
|
|
342635
|
-
|
|
342636
|
-
|
|
342637
|
-
|
|
342638
|
-
|
|
342639
|
-
|
|
342640
|
-
|
|
342641
|
-
|
|
342642
|
-
|
|
342643
|
-
|
|
342644
|
-
|
|
342645
|
-
|
|
343333
|
+
meshContactDataFor as c0,
|
|
343334
|
+
AabbSpatialIndex as c1,
|
|
343335
|
+
detectPhysicalContact as c2,
|
|
343336
|
+
resolveThicknessInspectionOptions as c3,
|
|
343337
|
+
thicknessColor as c4,
|
|
343338
|
+
thicknessClass as c5,
|
|
343339
|
+
roughnessClassForAngle as c6,
|
|
343340
|
+
resolveRoughnessInspectionOptions as c7,
|
|
343341
|
+
roughnessColorForAngle as c8,
|
|
343342
|
+
roughnessScoreForAngle as c9,
|
|
343343
|
+
Group as ca,
|
|
343344
|
+
intersectWithPlane as cb,
|
|
343345
|
+
setActiveBackend as cc,
|
|
343346
|
+
parseCameraCliSpec as cd,
|
|
343347
|
+
PMREMGenerator as ce,
|
|
343348
|
+
PointsMaterial as cf,
|
|
343349
|
+
Points$1 as cg,
|
|
343350
|
+
serializeCollisionFinding as ch,
|
|
343351
|
+
summarizeThicknessSamples as ci,
|
|
343352
|
+
worldAuthorPlaneToLocal as cj,
|
|
343353
|
+
generateCuttingLayoutPdf as ck,
|
|
343354
|
+
getCameraForwardVector as cl,
|
|
343355
|
+
RENDER_STYLE_OPTIONS as cm,
|
|
343356
|
+
initKernelManifoldOnly as cn,
|
|
343357
|
+
__viteBrowserExternal$1 as co,
|
|
342646
343358
|
Layers as d,
|
|
342647
343359
|
Color as e,
|
|
342648
343360
|
RGBAFormat as f,
|