forgecad 0.9.7 → 0.9.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (47) hide show
  1. package/README.md +1 -0
  2. package/dist/assets/{AdminPage-DX0mpSZT.js → AdminPage-CXaVLMiV.js} +1 -1
  3. package/dist/assets/{BlogPage-CI_P0_Pf.js → BlogPage-Crpr3JjH.js} +1 -1
  4. package/dist/assets/{DocsPage-DLhIIZyJ.js → DocsPage-CNBKuitP.js} +2 -2
  5. package/dist/assets/{EditorApp-DfFT2Dn8.css → EditorApp-D11wL4Qn.css} +51 -0
  6. package/dist/assets/{EditorApp-BujZvuwX.js → EditorApp-DVMnXOmO.js} +151 -9
  7. package/dist/assets/{EmbedViewer-0S0qXKog.js → EmbedViewer-KXFLSnpo.js} +2 -2
  8. package/dist/assets/{LandingPageProofDriven-O_yMtAri.js → LandingPageProofDriven-2q2sn7aW.js} +1 -1
  9. package/dist/assets/{PricingPage-DGkX3Ahr.js → PricingPage-CVvgdv0i.js} +1 -1
  10. package/dist/assets/{SettingsPage-DBsqTB_y.js → SettingsPage-BVj1FtEv.js} +1 -1
  11. package/dist/assets/__vite-browser-external-Dhvy_jtL.js +4 -0
  12. package/dist/assets/{app-BE2nD6Yz.js → app-Dn4EwHhN.js} +707 -458
  13. package/dist/assets/cli/{render-iP9qh475.js → render-BI3gLMXz.js} +1011 -145
  14. package/dist/assets/constructionHistoryWorker-z9_LGiRd.js +42984 -0
  15. package/dist/assets/{evalWorker-Ds5U4xtN.js → evalWorker-CtO7GsJR.js} +42 -9
  16. package/dist/assets/{inspectWorker-Dll4eVyD.js → inspectWorker-BZ2CkQZr.js} +785 -111
  17. package/dist/assets/{manifold-sJ-axdXM.js → manifold-BVi4_OeB.js} +1 -1
  18. package/dist/assets/{manifold-DjYsd7A_.js → manifold-C6-sZYQN.js} +2 -2
  19. package/dist/assets/manifold-Cp_dCC7i.js +3018 -0
  20. package/dist/assets/{manifold-Bk26ViCr.js → manifold-DAzn2Fsa.js} +1 -1
  21. package/dist/assets/{renderSceneState-Bngp5MrQ.js → renderSceneState-BIvOkPK3.js} +1 -1
  22. package/dist/assets/{reportWorker-CU8RZ4O0.js → reportWorker-Bz9tGiHb.js} +42 -9
  23. package/dist/assets/{sectionPlaneMath-BdTjyVfs.js → scalar-sampling-budget-iBAeF8RM.js} +483 -71
  24. package/dist/cli/render.html +1 -1
  25. package/dist/docs/index.html +1 -1
  26. package/dist/docs-raw/CLI.md +10 -10
  27. package/dist/docs-raw/coding-best-practices.md +1 -1
  28. package/dist/docs-raw/guides/inspection-bundles.md +77 -19
  29. package/dist/docs-raw/guides/skill-maintenance.md +1 -1
  30. package/dist/docs-raw/runbook.md +2 -2
  31. package/dist/docs-raw/skills/forgecad-make-a-model.md +11 -0
  32. package/dist/docs-raw/skills/forgecad-render-inspect.md +12 -6
  33. package/dist/docs-raw/skills/index.md +1 -1
  34. package/dist/index.html +1 -1
  35. package/dist/sitemap.xml +6 -6
  36. package/dist-cli/forgecad.js +596 -354
  37. package/dist-cli/forgecad.js.map +1 -1
  38. package/dist-skill/CONTEXT.md +77 -19
  39. package/dist-skill/docs/CLI.md +10 -10
  40. package/dist-skill/docs/guides/inspection-bundles.md +77 -19
  41. package/dist-skill/docs-dev/CLI.md +10 -10
  42. package/dist-skill/docs-dev/coding-best-practices.md +1 -1
  43. package/dist-skill/docs-dev/guides/inspection-bundles.md +77 -19
  44. package/dist-skill/docs-dev/guides/skill-maintenance.md +1 -1
  45. package/dist-skill/library/forgecad-make-a-model/SKILL.md +11 -0
  46. package/dist-skill/library/forgecad-render-inspect/SKILL.md +12 -6
  47. package/package.json +6 -3
@@ -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-DjYsd7A_.js");
10608
+ const { default: __vite_default__ } = await import("./manifold-C6-sZYQN.js");
10609
10609
  return { default: __vite_default__ };
10610
10610
  }, true ? [] : void 0)).default;
10611
10611
  performance.mark("manifold:imported");
@@ -94501,6 +94501,19 @@ const Viewport = {
94501
94501
  collectRenderLabel(text, at, options);
94502
94502
  }
94503
94503
  };
94504
+ const NO_SURFACE_FIELD = {
94505
+ enabled: false,
94506
+ kind: "precision",
94507
+ baseColor: "#000000",
94508
+ darkColor: "#000000",
94509
+ lineColor: "#000000",
94510
+ nodeColor: "#000000",
94511
+ accentColor: "#000000",
94512
+ spacing: 1,
94513
+ lineWidth: 0.01,
94514
+ glow: 0,
94515
+ objectColorMix: 0
94516
+ };
94504
94517
  const DEFAULT_RENDER_STYLE = "classic";
94505
94518
  const RENDER_STYLE_OPTIONS = [
94506
94519
  {
@@ -94522,6 +94535,16 @@ const RENDER_STYLE_OPTIONS = [
94522
94535
  id: "glass",
94523
94536
  label: "Glass",
94524
94537
  description: "Showcase lighting for authored transparent materials."
94538
+ },
94539
+ {
94540
+ id: "precision",
94541
+ label: "Precision",
94542
+ description: "Dense, thin surface-field contours for technical inspection."
94543
+ },
94544
+ {
94545
+ id: "hybrid",
94546
+ label: "Hybrid",
94547
+ description: "Topo-led surface contours with a quiet orthogonal field."
94525
94548
  }
94526
94549
  ];
94527
94550
  const RENDER_STYLE_IDS = new Set(RENDER_STYLE_OPTIONS.map((option) => option.id));
@@ -94577,7 +94600,8 @@ const PRESETS = {
94577
94600
  color: "#ffffff",
94578
94601
  opacity: 0,
94579
94602
  scale: 1
94580
- }
94603
+ },
94604
+ surfaceField: NO_SURFACE_FIELD
94581
94605
  },
94582
94606
  studio: {
94583
94607
  id: "studio",
@@ -94630,7 +94654,8 @@ const PRESETS = {
94630
94654
  color: "#f7fffb",
94631
94655
  opacity: 0.055,
94632
94656
  scale: 1.006
94633
- }
94657
+ },
94658
+ surfaceField: NO_SURFACE_FIELD
94634
94659
  },
94635
94660
  fast: {
94636
94661
  id: "fast",
@@ -94683,7 +94708,8 @@ const PRESETS = {
94683
94708
  color: "#fff6df",
94684
94709
  opacity: 0,
94685
94710
  scale: 1
94686
- }
94711
+ },
94712
+ surfaceField: NO_SURFACE_FIELD
94687
94713
  },
94688
94714
  glass: {
94689
94715
  id: "glass",
@@ -94736,6 +94762,139 @@ const PRESETS = {
94736
94762
  color: "#e8fff8",
94737
94763
  opacity: 0.13,
94738
94764
  scale: 1.012
94765
+ },
94766
+ surfaceField: NO_SURFACE_FIELD
94767
+ },
94768
+ precision: {
94769
+ id: "precision",
94770
+ label: "Precision",
94771
+ background: "#0c1011",
94772
+ toneMappingExposure: 1.06,
94773
+ environmentIntensity: 0.35,
94774
+ canvasDpr: { live: 1, idleMax: 1.45 },
94775
+ lights: {
94776
+ ambientIntensity: 0.36,
94777
+ keyIntensity: 1.25,
94778
+ keyColor: "#f2fff9",
94779
+ keyPosition: [95, -120, 145],
94780
+ fillIntensity: 0.32,
94781
+ fillColor: "#cbeee8",
94782
+ fillPosition: [-80, 70, 80],
94783
+ rimIntensity: 0.28,
94784
+ rimColor: "#d1fff7",
94785
+ rimPosition: [-105, -75, 120],
94786
+ hemisphereSky: "#d1fff7",
94787
+ hemisphereGround: "#111616",
94788
+ hemisphereIntensity: 0.3
94789
+ },
94790
+ material: {
94791
+ metalness: 0,
94792
+ roughness: 0.68,
94793
+ clearcoat: 0,
94794
+ clearcoatRoughness: 0.6,
94795
+ reflectivity: 0.18,
94796
+ specularIntensity: 0.62,
94797
+ opacity: 1,
94798
+ transmission: 0,
94799
+ thickness: 0,
94800
+ authoredTransparent: {
94801
+ roughness: 0.42,
94802
+ clearcoat: 0.08,
94803
+ clearcoatRoughness: 0.46,
94804
+ reflectivity: 0.24,
94805
+ specularIntensity: 0.72,
94806
+ transmission: 0,
94807
+ thickness: 0.2
94808
+ }
94809
+ },
94810
+ edge: {
94811
+ color: "#d1fff7",
94812
+ opacity: 0.26
94813
+ },
94814
+ glassShell: {
94815
+ enabled: false,
94816
+ color: "#d1fff7",
94817
+ opacity: 0,
94818
+ scale: 1
94819
+ },
94820
+ surfaceField: {
94821
+ enabled: true,
94822
+ kind: "precision",
94823
+ baseColor: "#3d5659",
94824
+ darkColor: "#070b0c",
94825
+ lineColor: "#d1fff7",
94826
+ nodeColor: "#fff4bc",
94827
+ accentColor: "#ffb66f",
94828
+ spacing: 0.22,
94829
+ lineWidth: 36e-4,
94830
+ glow: 0.2,
94831
+ objectColorMix: 0.35
94832
+ }
94833
+ },
94834
+ hybrid: {
94835
+ id: "hybrid",
94836
+ label: "Hybrid",
94837
+ background: "#0b1312",
94838
+ toneMappingExposure: 1.08,
94839
+ environmentIntensity: 0.42,
94840
+ canvasDpr: { live: 1, idleMax: 1.45 },
94841
+ lights: {
94842
+ ambientIntensity: 0.38,
94843
+ keyIntensity: 1.32,
94844
+ keyColor: "#f2fff9",
94845
+ keyPosition: [100, -125, 145],
94846
+ fillIntensity: 0.34,
94847
+ fillColor: "#c9fff2",
94848
+ fillPosition: [-80, 78, 85],
94849
+ rimIntensity: 0.34,
94850
+ rimColor: "#d7ff86",
94851
+ rimPosition: [-105, -80, 125],
94852
+ hemisphereSky: "#bfffee",
94853
+ hemisphereGround: "#101810",
94854
+ hemisphereIntensity: 0.32
94855
+ },
94856
+ material: {
94857
+ metalness: 0,
94858
+ roughness: 0.66,
94859
+ clearcoat: 0,
94860
+ clearcoatRoughness: 0.6,
94861
+ reflectivity: 0.2,
94862
+ specularIntensity: 0.66,
94863
+ opacity: 1,
94864
+ transmission: 0,
94865
+ thickness: 0,
94866
+ authoredTransparent: {
94867
+ roughness: 0.4,
94868
+ clearcoat: 0.08,
94869
+ clearcoatRoughness: 0.46,
94870
+ reflectivity: 0.24,
94871
+ specularIntensity: 0.74,
94872
+ transmission: 0,
94873
+ thickness: 0.2
94874
+ }
94875
+ },
94876
+ edge: {
94877
+ color: "#defdf7",
94878
+ opacity: 0.28
94879
+ },
94880
+ glassShell: {
94881
+ enabled: false,
94882
+ color: "#defdf7",
94883
+ opacity: 0,
94884
+ scale: 1
94885
+ },
94886
+ surfaceField: {
94887
+ enabled: true,
94888
+ kind: "hybrid",
94889
+ baseColor: "#32645e",
94890
+ darkColor: "#07100f",
94891
+ lineColor: "#95fff0",
94892
+ nodeColor: "#ffe098",
94893
+ accentColor: "#d7ff86",
94894
+ spacing: 0.3,
94895
+ lineWidth: 5e-3,
94896
+ glow: 0.4,
94897
+ objectColorMix: 0.28
94739
94898
  }
94740
94899
  }
94741
94900
  };
@@ -339496,6 +339655,14 @@ function createForgeRuntimeModule(bindings) {
339496
339655
  runtime.default = runtime;
339497
339656
  return runtime;
339498
339657
  }
339658
+ function finalizeForgeJsImport(moduleExports, importedDims) {
339659
+ if (moduleExports instanceof Assembly) {
339660
+ return new ImportedAssembly(moduleExports, moduleExports.getReferences());
339661
+ }
339662
+ if (!(moduleExports instanceof Shape$1)) return moduleExports;
339663
+ if (importedDims.length === 0) return moduleExports;
339664
+ return setShapeDimensions(moduleExports, [...getShapeDimensions(moduleExports), ...importedDims]);
339665
+ }
339499
339666
  const DEFAULT_RAYMARCH_STEPS = 360;
339500
339667
  const MIN_RAYMARCH_STEP = 0.012;
339501
339668
  function classifySdfPreviewNode(node) {
@@ -340417,7 +340584,7 @@ function isRenderableEntryResult(value) {
340417
340584
  return containsRenderableLeaf(value, /* @__PURE__ */ new WeakSet());
340418
340585
  }
340419
340586
  function containsRenderableLeaf(value, seen2) {
340420
- if (value instanceof Shape$1 || value instanceof Sketch || value instanceof SdfShape || value instanceof ShapeGroup || value instanceof GCodeBuilder || value instanceof Assembly || value instanceof SolvedAssembly) {
340587
+ if (value instanceof Shape$1 || value instanceof Sketch || value instanceof SdfShape || value instanceof ShapeGroup || value instanceof GCodeBuilder || value instanceof Assembly || value instanceof ImportedAssembly || value instanceof SolvedAssembly) {
340421
340588
  return true;
340422
340589
  }
340423
340590
  if (!value || typeof value !== "object") return false;
@@ -340439,11 +340606,6 @@ function hasExplicitModuleExports(exportsValue, initialExportsRef) {
340439
340606
  const keys = Object.keys(exportsValue);
340440
340607
  return keys.some((key) => key !== "__esModule");
340441
340608
  }
340442
- function finalizeForgeJsImport(moduleExports, importedDims) {
340443
- if (!(moduleExports instanceof Shape$1)) return moduleExports;
340444
- if (importedDims.length === 0) return moduleExports;
340445
- return setShapeDimensions(moduleExports, [...getShapeDimensions(moduleExports), ...importedDims]);
340446
- }
340447
340609
  function mapScriptResultToScene(args) {
340448
340610
  var _a3;
340449
340611
  const objects = [];
@@ -340571,6 +340733,19 @@ function mapScriptResultToScene(args) {
340571
340733
  value.solve().toSceneObjects().forEach((item, index2) => processNamedItem(item, `${name}.${index2 + 1}`, `${index2 + 1}`, name, treePath, inheritedTags));
340572
340734
  return;
340573
340735
  }
340736
+ if (value instanceof ImportedAssembly) {
340737
+ const group2 = value.toGroup();
340738
+ group2.children.forEach((child, index2) => {
340739
+ flattenGroupChild(
340740
+ child,
340741
+ groupChildLabel(group2, name, index2),
340742
+ name,
340743
+ [...treePath, shapeGroupChildSegment(group2, index2)],
340744
+ mergeSceneTags(inheritedTags, group2.tagsForChild(index2))
340745
+ );
340746
+ });
340747
+ return;
340748
+ }
340574
340749
  if (value instanceof SolvedAssembly) {
340575
340750
  value.toSceneObjects().forEach((item, index2) => processNamedItem(item, `${name}.${index2 + 1}`, `${index2 + 1}`, name, treePath, inheritedTags));
340576
340751
  return;
@@ -340726,6 +340901,12 @@ function mapScriptResultToScene(args) {
340726
340901
  const label = `Object ${index2 + 1}`;
340727
340902
  processNamedItem(item, label, label);
340728
340903
  });
340904
+ } else if (result instanceof ImportedAssembly) {
340905
+ const group2 = result.toGroup();
340906
+ group2.children.forEach((child, index2) => {
340907
+ const label = rootGroupChildLabel(group2, index2);
340908
+ flattenGroupChild(child, label, void 0, [label], group2.tagsForChild(index2));
340909
+ });
340729
340910
  } else if (result instanceof ShapeGroup) {
340730
340911
  result.children.forEach((child, i) => {
340731
340912
  const label = rootGroupChildLabel(result, i);
@@ -340764,7 +340945,7 @@ function mapScriptResultToScene(args) {
340764
340945
  }
340765
340946
  processRenderableTree(item, label, label);
340766
340947
  });
340767
- } else if (result !== null && typeof result === "object" && !Array.isArray(result) && !(result instanceof Shape$1) && !(result instanceof Sketch) && !(result instanceof SdfShape) && !(result instanceof ShapeGroup) && !(result instanceof GCodeBuilder) && !(result instanceof Assembly) && !(result instanceof SolvedAssembly)) {
340948
+ } else if (result !== null && typeof result === "object" && !Array.isArray(result) && !(result instanceof Shape$1) && !(result instanceof Sketch) && !(result instanceof SdfShape) && !(result instanceof ShapeGroup) && !(result instanceof GCodeBuilder) && !(result instanceof Assembly) && !(result instanceof ImportedAssembly) && !(result instanceof SolvedAssembly)) {
340768
340949
  const obj = result;
340769
340950
  const defaultValue = obj.default;
340770
340951
  if (defaultValue && isRenderableEntryResult(defaultValue)) {
@@ -340852,7 +341033,7 @@ Fix one:
340852
341033
  sketch: objects.length === 1 ? objects[0].sketch : null,
340853
341034
  objects,
340854
341035
  extraDimensions: shapeDimensions,
340855
- error: objects.length > 0 || args.allowEmptyResult ? null : "No renderable objects found. Return a Shape, Sketch, SdfShape, array, or object tree containing renderable values."
341036
+ error: objects.length > 0 || args.allowEmptyResult ? null : "No renderable objects found. Return a Shape, Sketch, SdfShape, Assembly, ImportedAssembly, array, or object tree containing renderable values."
340856
341037
  };
340857
341038
  }
340858
341039
  const FORGE_RUNTIME_MODULE_SPECIFIERS = /* @__PURE__ */ new Set(["forgecad", "@forge/runtime", "@forgecad/runtime"]);
@@ -341149,6 +341330,7 @@ function executeFile(code, fileName, allFiles, visited, scope = {}, options, exe
341149
341330
  composeChain,
341150
341331
  assembly,
341151
341332
  Assembly,
341333
+ ImportedAssembly,
341152
341334
  port: () => {
341153
341335
  throw new Error("port() has been renamed to connector(). Update your script.");
341154
341336
  },
@@ -341795,10 +341977,16 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
341795
341977
  const collisions = [];
341796
341978
  const preparedEntries = entries.map((entry) => prepareEntry(entry));
341797
341979
  const { pairs: candidatePairs, bboxPairChecks } = collectCandidatePairs(preparedEntries, options);
341798
- const limitedCandidatePairs = options.maxCandidatePairs === null ? candidatePairs : candidatePairs.slice(0, options.maxCandidatePairs);
341799
- const pairLimitSkippedPairCount = candidatePairs.length - limitedCandidatePairs.length;
341980
+ const exactCandidatePairs = candidatePairs.filter((pair) => pair.bboxOverlapVolume > options.minOverlapVolume);
341981
+ const bboxVolumePrunedPairCount = candidatePairs.length - exactCandidatePairs.length;
341982
+ const limitedCandidatePairs = options.maxCandidatePairs === null ? exactCandidatePairs : exactCandidatePairs.slice(0, options.maxCandidatePairs);
341983
+ const pairLimitSkippedPairCount = exactCandidatePairs.length - limitedCandidatePairs.length;
341800
341984
  let testedPairCount = 0;
341801
341985
  let timeBudgetStopped = false;
341986
+ const exactCheckedKeys = /* @__PURE__ */ new Set();
341987
+ const pairKey = (pair) => `${pair.sourceIndex}:${pair.targetIndex}`;
341988
+ const exactCandidateKeys = new Set(exactCandidatePairs.map(pairKey));
341989
+ const limitedCandidateKeys = new Set(limitedCandidatePairs.map(pairKey));
341802
341990
  const exactStarted = performance.now();
341803
341991
  for (const pair of limitedCandidatePairs) {
341804
341992
  if (options.maxElapsedMs !== null && (options.maxElapsedMs <= 0 || performance.now() - exactStarted >= options.maxElapsedMs)) {
@@ -341806,6 +341994,7 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
341806
341994
  break;
341807
341995
  }
341808
341996
  testedPairCount += 1;
341997
+ exactCheckedKeys.add(pairKey(pair));
341809
341998
  const a2 = preparedEntries[pair.sourceIndex];
341810
341999
  const b = preparedEntries[pair.targetIndex];
341811
342000
  try {
@@ -341836,10 +342025,11 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
341836
342025
  const bboxCandidates = options.includeBBoxCandidates ? candidatePairs.map((pair, index2) => {
341837
342026
  const source = preparedEntries[pair.sourceIndex];
341838
342027
  const target = preparedEntries[pair.targetIndex];
341839
- const exactChecked = index2 < testedPairCount;
342028
+ const exactChecked = exactCheckedKeys.has(pairKey(pair));
341840
342029
  let skippedBy;
341841
342030
  if (!exactChecked) {
341842
- skippedBy = index2 >= limitedCandidatePairs.length ? "pair-limit" : "time-budget";
342031
+ const key = pairKey(pair);
342032
+ skippedBy = !exactCandidateKeys.has(key) ? "bbox-volume-threshold" : limitedCandidateKeys.has(key) ? "time-budget" : "pair-limit";
341843
342033
  }
341844
342034
  return {
341845
342035
  index: index2 + 1,
@@ -341883,10 +342073,12 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
341883
342073
  method: "aabb-bvh",
341884
342074
  allPairCount: preparedEntries.length * (preparedEntries.length - 1) / 2,
341885
342075
  bboxPairChecks,
342076
+ bboxVolumePrunedPairCount,
341886
342077
  booleanPairChecks: testedPairCount
341887
342078
  },
341888
342079
  objectCount: objects.length,
341889
342080
  candidatePairCount: candidatePairs.length,
342081
+ bboxVolumePrunedPairCount,
341890
342082
  testedPairCount,
341891
342083
  skippedPairCount,
341892
342084
  pairLimitSkippedPairCount,
@@ -341899,6 +342091,192 @@ function analyzeCollisionIntersections(entries, rawOptions = {}) {
341899
342091
  warnings
341900
342092
  };
341901
342093
  }
342094
+ const SURFACE_FIELD_VERTEX_SHADER = `
342095
+ varying vec3 vWorldPos;
342096
+ varying vec3 vNormalW;
342097
+
342098
+ void main() {
342099
+ vec4 world = modelMatrix * vec4(position, 1.0);
342100
+ vWorldPos = world.xyz;
342101
+ vNormalW = normalize(mat3(modelMatrix) * normal);
342102
+ gl_Position = projectionMatrix * viewMatrix * world;
342103
+ }
342104
+ `;
342105
+ const SURFACE_FIELD_FRAGMENT_SHADER = `
342106
+ uniform float uGlow;
342107
+ uniform float uLineWidth;
342108
+ uniform float uObjectColorMix;
342109
+ uniform float uFieldScale;
342110
+ uniform float uSpacing;
342111
+ uniform int uFieldKind;
342112
+ uniform vec3 uAccentColor;
342113
+ uniform vec3 uBaseColor;
342114
+ uniform vec3 uDarkColor;
342115
+ uniform vec3 uLineColor;
342116
+ uniform vec3 uNodeColor;
342117
+ uniform vec3 uObjectColor;
342118
+
342119
+ varying vec3 vNormalW;
342120
+ varying vec3 vWorldPos;
342121
+
342122
+ float gridLine(float coord, float spacing, float width) {
342123
+ float distanceToLine = abs(fract(coord / spacing + 0.5) - 0.5) * spacing;
342124
+ return 1.0 - smoothstep(width, width * 2.7, distanceToLine);
342125
+ }
342126
+
342127
+ float intersectionFade(float axisNormal) {
342128
+ return 1.0 - smoothstep(0.72, 0.98, abs(axisNormal));
342129
+ }
342130
+
342131
+ void main() {
342132
+ vec3 normalW = normalize(vNormalW);
342133
+ vec3 viewDir = normalize(cameraPosition - vWorldPos);
342134
+ vec3 lightDir = normalize(vec3(-0.38, 0.72, 0.58));
342135
+ float lit = max(dot(normalW, lightDir), 0.0);
342136
+ float rim = pow(1.0 - max(dot(normalW, viewDir), 0.0), 2.35);
342137
+ vec3 fieldPos = vWorldPos / uFieldScale;
342138
+
342139
+ float xFade = intersectionFade(normalW.x);
342140
+ float yFade = intersectionFade(normalW.y);
342141
+ float zFade = intersectionFade(normalW.z);
342142
+
342143
+ float lx = gridLine(fieldPos.x, uSpacing, uLineWidth) * xFade;
342144
+ float ly = gridLine(fieldPos.y, uSpacing, uLineWidth) * yFade;
342145
+ float lz = gridLine(fieldPos.z, uSpacing, uLineWidth) * zFade;
342146
+ float mx = gridLine(fieldPos.x, uSpacing * 0.5, uLineWidth * 0.52) * xFade * 0.34;
342147
+ float my = gridLine(fieldPos.y, uSpacing * 0.5, uLineWidth * 0.52) * yFade * 0.34;
342148
+ float mz = gridLine(fieldPos.z, uSpacing * 0.5, uLineWidth * 0.52) * zFade * 0.34;
342149
+ float majorX = gridLine(fieldPos.x, uSpacing * 4.0, uLineWidth * 1.25) * xFade;
342150
+ float majorY = gridLine(fieldPos.y, uSpacing * 4.0, uLineWidth * 1.25) * yFade;
342151
+ float majorZ = gridLine(fieldPos.z, uSpacing * 4.0, uLineWidth * 1.25) * zFade;
342152
+
342153
+ float contour = max(max(lx, ly), lz);
342154
+ float minorContour = max(max(mx, my), mz);
342155
+ float majorContour = max(max(majorX, majorY), majorZ);
342156
+ float pairNode = max(max(min(lx, ly), min(lx, lz)), min(ly, lz));
342157
+ float topoScale = max(max(lz, mz), majorZ);
342158
+ float lineMask = max(max(contour * 0.74, minorContour), majorContour * 0.54);
342159
+ float nodeMask = pairNode * 0.035;
342160
+
342161
+ if (uFieldKind == 1) {
342162
+ lineMask = max(topoScale, max(mx, my) * 0.42);
342163
+ nodeMask = pairNode * 0.06;
342164
+ }
342165
+
342166
+ vec3 body = mix(uBaseColor, uObjectColor, uObjectColorMix);
342167
+ vec3 base = mix(uDarkColor, body, 0.34 + lit * 0.66) + rim * uAccentColor * 0.14;
342168
+ vec3 color = mix(base, uLineColor, clamp(lineMask * 0.58, 0.0, 1.0));
342169
+ color += uLineColor * lineMask * uGlow * 0.22;
342170
+ color += uNodeColor * nodeMask * uGlow * 0.28;
342171
+ color += sin(gl_FragCoord.y * 3.14159) * 0.008;
342172
+
342173
+ gl_FragColor = vec4(color, 1.0);
342174
+ }
342175
+ `;
342176
+ const ZEBRA_STRIPE_SCALE = 18;
342177
+ const ZEBRA_STRIPE_SOFTNESS = 0.16;
342178
+ const ZEBRA_DARK_COLOR = "#05070a";
342179
+ const ZEBRA_LIGHT_COLOR = "#f2f4ec";
342180
+ const ZEBRA_ACCENT_COLOR = "#3bd6ff";
342181
+ const ZEBRA_STRIPE_VERTEX_SHADER = `
342182
+ varying vec3 vViewNormal;
342183
+ varying vec3 vViewPosition;
342184
+
342185
+ void main() {
342186
+ vec4 viewPosition = modelViewMatrix * vec4(position, 1.0);
342187
+ vViewPosition = viewPosition.xyz;
342188
+ vViewNormal = normalize(normalMatrix * normal);
342189
+ gl_Position = projectionMatrix * viewPosition;
342190
+ }
342191
+ `;
342192
+ const ZEBRA_STRIPE_FRAGMENT_SHADER = `
342193
+ precision highp float;
342194
+
342195
+ uniform vec3 uAccentColor;
342196
+ uniform vec3 uDarkColor;
342197
+ uniform vec3 uLightColor;
342198
+ uniform float uStripeScale;
342199
+ uniform float uStripeSoftness;
342200
+
342201
+ varying vec3 vViewNormal;
342202
+ varying vec3 vViewPosition;
342203
+
342204
+ void main() {
342205
+ vec3 normal = normalize(vViewNormal);
342206
+ if (!gl_FrontFacing) {
342207
+ normal = -normal;
342208
+ }
342209
+
342210
+ vec3 eyeDirection = normalize(-vViewPosition);
342211
+ vec3 reflection = normalize(reflect(-eyeDirection, normal));
342212
+ float stripePhase = reflection.x * 0.92 + reflection.y * 0.28 + reflection.z * 0.18;
342213
+ float stripeWave = sin(stripePhase * uStripeScale);
342214
+ float stripeMask = smoothstep(-uStripeSoftness, uStripeSoftness, stripeWave);
342215
+
342216
+ float grazing = pow(1.0 - clamp(dot(normal, eyeDirection), 0.0, 1.0), 1.8);
342217
+ float secondaryWave = sin((reflection.y - reflection.z * 0.45) * uStripeScale * 0.45);
342218
+ float secondary = smoothstep(0.72, 1.0, secondaryWave) * 0.12;
342219
+
342220
+ vec3 bands = mix(uDarkColor, uLightColor, stripeMask);
342221
+ vec3 color = mix(bands, uAccentColor, grazing * 0.18);
342222
+ color += uLightColor * secondary * (0.35 + grazing * 0.4);
342223
+
342224
+ gl_FragColor = vec4(color, 1.0);
342225
+ }
342226
+ `;
342227
+ function isVisibleColor(colors, vertexIndex) {
342228
+ const offset2 = vertexIndex * 3;
342229
+ return colors[offset2] > 1e-6 || colors[offset2 + 1] > 1e-6 || colors[offset2 + 2] > 1e-6;
342230
+ }
342231
+ function copyAttribute(attribute, vertexIndexes) {
342232
+ const itemSize = attribute.itemSize;
342233
+ const source = attribute.array;
342234
+ const out = new Float32Array(vertexIndexes.length * itemSize);
342235
+ vertexIndexes.forEach((vertexIndex, outIndex) => {
342236
+ const sourceOffset = vertexIndex * itemSize;
342237
+ const outOffset = outIndex * itemSize;
342238
+ for (let component = 0; component < itemSize; component += 1) {
342239
+ out[outOffset + component] = source[sourceOffset + component];
342240
+ }
342241
+ });
342242
+ return new BufferAttribute(out, itemSize, attribute.normalized);
342243
+ }
342244
+ function selectedTriangleVertexIndexes(geometry, colors) {
342245
+ const position = geometry.getAttribute("position");
342246
+ if (!position || colors.length !== position.count * 3) return [];
342247
+ const selected = [];
342248
+ const index2 = geometry.getIndex();
342249
+ if (index2) {
342250
+ const values = index2.array;
342251
+ for (let triangle = 0; triangle + 2 < index2.count; triangle += 3) {
342252
+ const a2 = values[triangle];
342253
+ const b = values[triangle + 1];
342254
+ const c2 = values[triangle + 2];
342255
+ if (isVisibleColor(colors, a2) || isVisibleColor(colors, b) || isVisibleColor(colors, c2)) {
342256
+ selected.push(a2, b, c2);
342257
+ }
342258
+ }
342259
+ return selected;
342260
+ }
342261
+ for (let vertex2 = 0; vertex2 + 2 < position.count; vertex2 += 3) {
342262
+ if (isVisibleColor(colors, vertex2) || isVisibleColor(colors, vertex2 + 1) || isVisibleColor(colors, vertex2 + 2)) {
342263
+ selected.push(vertex2, vertex2 + 1, vertex2 + 2);
342264
+ }
342265
+ }
342266
+ return selected;
342267
+ }
342268
+ function geometryWithVisibleVertexColors(geometry, colors) {
342269
+ const vertexIndexes = selectedTriangleVertexIndexes(geometry, colors);
342270
+ if (vertexIndexes.length === 0) return null;
342271
+ const out = new BufferGeometry();
342272
+ for (const name of ["position", "normal"]) {
342273
+ const attribute = geometry.getAttribute(name);
342274
+ if (attribute) out.setAttribute(name, copyAttribute(attribute, vertexIndexes));
342275
+ }
342276
+ const colorAttribute = copyAttribute(new BufferAttribute(colors, 3), vertexIndexes);
342277
+ out.setAttribute("color", colorAttribute);
342278
+ return out;
342279
+ }
341902
342280
  const VECTOR_KEYS = /* @__PURE__ */ new Set(["pos", "position", "target", "lookat", "aim", "up"]);
341903
342281
  const roundNumber = (value, digits) => {
341904
342282
  const scale2 = 10 ** digits;
@@ -342070,6 +342448,28 @@ function localAabbPlaneRelation(min2, max2, plane, eps = 1e-7) {
342070
342448
  if (minDistance > -eps) return "positive";
342071
342449
  return "crossing";
342072
342450
  }
342451
+ const DEFAULT_SCALAR_SCENE_BUDGET_OBJECTS = 15;
342452
+ const DEFAULT_SCALAR_SCENE_MIN_SAMPLES_PER_OBJECT = 100;
342453
+ function resolveScalarSceneSampleBudget(args) {
342454
+ const objectCount = Math.max(0, Math.floor(args.objectCount));
342455
+ const requestedMaxSamplesPerObject = Math.max(1, Math.floor(args.maxSamplesPerObject));
342456
+ const sceneBudgetObjectCount = Math.max(1, Math.floor(args.sceneBudgetObjectCount ?? DEFAULT_SCALAR_SCENE_BUDGET_OBJECTS));
342457
+ const minSamplesPerObject = Math.max(1, Math.floor(args.minSamplesPerObject ?? DEFAULT_SCALAR_SCENE_MIN_SAMPLES_PER_OBJECT));
342458
+ const explicitMaxSamplesPerObject = args.explicitMaxSamplesPerObject === true;
342459
+ const sceneMaxSamples = requestedMaxSamplesPerObject * sceneBudgetObjectCount;
342460
+ const budgeted = objectCount <= 0 || objectCount <= sceneBudgetObjectCount || explicitMaxSamplesPerObject ? requestedMaxSamplesPerObject : Math.max(minSamplesPerObject, Math.floor(sceneMaxSamples / objectCount));
342461
+ const effectiveMaxSamplesPerObject = Math.min(requestedMaxSamplesPerObject, budgeted);
342462
+ return {
342463
+ objectCount,
342464
+ requestedMaxSamplesPerObject,
342465
+ effectiveMaxSamplesPerObject,
342466
+ sceneBudgetObjectCount,
342467
+ sceneMaxSamples,
342468
+ minSamplesPerObject,
342469
+ explicitMaxSamplesPerObject,
342470
+ capped: effectiveMaxSamplesPerObject < requestedMaxSamplesPerObject
342471
+ };
342472
+ }
342073
342473
  export {
342074
342474
  Matrix4 as $,
342075
342475
  ACESFilmicToneMapping as A,
@@ -342165,7 +342565,7 @@ export {
342165
342565
  DEFAULT_ACTIVE_BACKEND as ay,
342166
342566
  isConstraintSketch as az,
342167
342567
  PCFShadowMap as b,
342168
- initKernelManifoldOnly as b$,
342568
+ Group as b$,
342169
342569
  PointLight as b0,
342170
342570
  DirectionalLight as b1,
342171
342571
  analyzeCollisionIntersections as b2,
@@ -342176,61 +342576,73 @@ export {
342176
342576
  runScript as b7,
342177
342577
  MeshPhysicalMaterial as b8,
342178
342578
  LineSegments as b9,
342179
- findJointAnimationClip as bA,
342180
- resolveJointAnimation as bB,
342181
- resolveJointViewValues as bC,
342182
- getShapePorts as bD,
342183
- getShapeUsedPorts as bE,
342184
- DEFAULT_VIEW_CONFIG as bF,
342185
- getKernelFaceNameForTriangle as bG,
342186
- initKernel as bH,
342187
- initSolverWasm as bI,
342188
- BoxGeometry as bJ,
342189
- localAabbPlaneRelation as bK,
342190
- ShapeUtils as bL,
342191
- aabbInteriorOverlaps as bM,
342192
- aabbOverlapVolume as bN,
342193
- AabbSpatialIndex as bO,
342194
- aabbGaps as bP,
342195
- Group as bQ,
342196
- intersectWithPlane as bR,
342197
- parseCameraCliSpec as bS,
342198
- PMREMGenerator as bT,
342199
- PointsMaterial as bU,
342200
- Points$1 as bV,
342201
- serializeCollisionFinding as bW,
342202
- worldAuthorPlaneToLocal as bX,
342203
- generateCuttingLayoutPdf as bY,
342204
- getCameraForwardVector as bZ,
342205
- RENDER_STYLE_OPTIONS as b_,
342206
- getRenderStylePreset as ba,
342207
- AdditiveBlending as bb,
342208
- CatmullRomCurve3 as bc,
342209
- TubeGeometry as bd,
342210
- MeshStandardMaterial as be,
342211
- compileSdfNode3 as bf,
342212
- buildSdfRaymarchFragmentShader as bg,
342213
- SDF_RAYMARCH_PROXY_VERTEX_SHADER as bh,
342214
- Shape2 as bi,
342215
- ShapeGeometry as bj,
342216
- ShaderLib as bk,
342217
- CylinderGeometry as bl,
342218
- parseViewportCameraState as bm,
342219
- createResolvedExplodeConfig as bn,
342220
- explodeBoundsCenter as bo,
342221
- explodeMergeBounds as bp,
342222
- resolveExplodeDirective as bq,
342223
- computeExplodeMotion as br,
342224
- getSketchWorldMatrix as bs,
342225
- explodeAdd as bt,
342226
- hasExplodeOverride as bu,
342227
- resolveExplodeLocalFanDirection as bv,
342228
- explodeMul as bw,
342229
- explodeLeafFanStage as bx,
342230
- normalizeCutPlane as by,
342231
- toClippingPlane as bz,
342579
+ resolveExplodeDirective as bA,
342580
+ computeExplodeMotion as bB,
342581
+ getSketchWorldMatrix as bC,
342582
+ explodeAdd as bD,
342583
+ hasExplodeOverride as bE,
342584
+ resolveExplodeLocalFanDirection as bF,
342585
+ explodeMul as bG,
342586
+ explodeLeafFanStage as bH,
342587
+ normalizeCutPlane as bI,
342588
+ toClippingPlane as bJ,
342589
+ findJointAnimationClip as bK,
342590
+ resolveJointAnimation as bL,
342591
+ resolveJointViewValues as bM,
342592
+ getShapePorts as bN,
342593
+ getShapeUsedPorts as bO,
342594
+ DEFAULT_VIEW_CONFIG as bP,
342595
+ getKernelFaceNameForTriangle as bQ,
342596
+ resolveScalarSceneSampleBudget as bR,
342597
+ initKernel as bS,
342598
+ initSolverWasm as bT,
342599
+ BoxGeometry as bU,
342600
+ localAabbPlaneRelation as bV,
342601
+ ShapeUtils as bW,
342602
+ aabbGaps as bX,
342603
+ aabbInteriorOverlaps as bY,
342604
+ aabbOverlapVolume as bZ,
342605
+ AabbSpatialIndex as b_,
342606
+ geometryWithVisibleVertexColors as ba,
342607
+ getRenderStylePreset as bb,
342608
+ AdditiveBlending as bc,
342609
+ ZEBRA_STRIPE_SOFTNESS as bd,
342610
+ ZEBRA_STRIPE_SCALE as be,
342611
+ ZEBRA_LIGHT_COLOR as bf,
342612
+ ZEBRA_DARK_COLOR as bg,
342613
+ ZEBRA_ACCENT_COLOR as bh,
342614
+ ZEBRA_STRIPE_FRAGMENT_SHADER as bi,
342615
+ ZEBRA_STRIPE_VERTEX_SHADER as bj,
342616
+ SURFACE_FIELD_FRAGMENT_SHADER as bk,
342617
+ SURFACE_FIELD_VERTEX_SHADER as bl,
342618
+ CatmullRomCurve3 as bm,
342619
+ TubeGeometry as bn,
342620
+ MeshStandardMaterial as bo,
342621
+ compileSdfNode3 as bp,
342622
+ buildSdfRaymarchFragmentShader as bq,
342623
+ SDF_RAYMARCH_PROXY_VERTEX_SHADER as br,
342624
+ Shape2 as bs,
342625
+ ShapeGeometry as bt,
342626
+ ShaderLib as bu,
342627
+ CylinderGeometry as bv,
342628
+ parseViewportCameraState as bw,
342629
+ createResolvedExplodeConfig as bx,
342630
+ explodeBoundsCenter as by,
342631
+ explodeMergeBounds as bz,
342232
342632
  SRGBColorSpace as c,
342233
- __viteBrowserExternal$1 as c0,
342633
+ intersectWithPlane as c0,
342634
+ setActiveBackend as c1,
342635
+ parseCameraCliSpec as c2,
342636
+ PMREMGenerator as c3,
342637
+ PointsMaterial as c4,
342638
+ Points$1 as c5,
342639
+ serializeCollisionFinding as c6,
342640
+ worldAuthorPlaneToLocal as c7,
342641
+ generateCuttingLayoutPdf as c8,
342642
+ getCameraForwardVector as c9,
342643
+ RENDER_STYLE_OPTIONS as ca,
342644
+ initKernelManifoldOnly as cb,
342645
+ __viteBrowserExternal$1 as cc,
342234
342646
  Layers as d,
342235
342647
  Color as e,
342236
342648
  RGBAFormat as f,