@xeokit/xeokit-sdk 2.6.108 → 2.6.109

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.
@@ -1,11 +1,11 @@
1
1
  /**
2
- * xeokit-sdk v2.6.108
3
- * Commit: a2bfb2cb967c8a3925c74e4039bfc60f136128c2
4
- * Built: 2026-04-03T14:14:43.600Z
2
+ * xeokit-sdk v2.6.109
3
+ * Commit: 3796b67f0bbcca7382160e5030522506fb49a54e
4
+ * Built: 2026-05-08T06:25:43.604Z
5
5
  */
6
6
 
7
7
  if (typeof window !== 'undefined') {
8
- window.__XEOKIT__ = { version: '2.6.108', commit: 'a2bfb2cb967c8a3925c74e4039bfc60f136128c2', built: '2026-04-03T14:14:43.600Z' };
8
+ window.__XEOKIT__ = { version: '2.6.109', commit: '3796b67f0bbcca7382160e5030522506fb49a54e', built: '2026-05-08T06:25:43.604Z' };
9
9
  }
10
10
 
11
11
  'use strict';
@@ -20737,7 +20737,7 @@ const tempVec3a$f = math.vec3();
20737
20737
  const tempVec4$3 = math.vec4();
20738
20738
  const TEXTURE_DECODE_FUNCS = { [sRGBEncoding]: "sRGBToLinear" };
20739
20739
 
20740
- const iota$3 = function(n) {
20740
+ const iota$4 = function(n) {
20741
20741
  const ret = [ ];
20742
20742
  for (let i = 0; i < n; ++i) ret.push(i);
20743
20743
  return ret;
@@ -20936,7 +20936,7 @@ const createProgramVariablesState = function() {
20936
20936
 
20937
20937
  const sectionPlanesState = cfg.sectionPlanesState;
20938
20938
  const getClippingDistance = sectionPlanesState && (function() {
20939
- const allocatedUniforms = iota$3(sectionPlanesState.getNumAllocatedSectionPlanes()).map(i => {
20939
+ const allocatedUniforms = iota$4(sectionPlanesState.getNumAllocatedSectionPlanes()).map(i => {
20940
20940
  const sectionPlaneUniform = (type, postfix, getValue) => {
20941
20941
  return programVariables.createUniform(type, `sectionPlane${postfix}${i}`, (set, state) => {
20942
20942
  const sectionPlanes = sectionPlanesState.sectionPlanes;
@@ -32539,9 +32539,7 @@ class Layer {
32539
32539
  }
32540
32540
 
32541
32541
  drawEdgesColorOpaque(renderFlags, frameCtx) {
32542
- if (this._compiledPortions.edgesColorOpaqueAllowed()) {
32543
- this.__drawVertexEdges(renderFlags, frameCtx, RENDER_PASSES.EDGES_COLOR_OPAQUE);
32544
- }
32542
+ this.__drawVertexEdges(renderFlags, frameCtx, RENDER_PASSES.EDGES_COLOR_OPAQUE);
32545
32543
  }
32546
32544
 
32547
32545
  drawEdgesColorTransparent(renderFlags, frameCtx) {
@@ -32832,7 +32830,7 @@ class Configs {
32832
32830
  }
32833
32831
  }
32834
32832
 
32835
- const iota$2 = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
32833
+ const iota$3 = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
32836
32834
 
32837
32835
  const dataTextureRamStats = {
32838
32836
  sizeDataColorsAndFlags: 0,
@@ -33414,17 +33412,6 @@ class DTXLayer extends Layer {
33414
33412
  };
33415
33413
 
33416
33414
  return {
33417
- edgesColorOpaqueAllowed: () => {
33418
- if (scene.logarithmicDepthBufferEnabled) {
33419
- if (!scene._loggedWarning) {
33420
- console.log("Edge enhancement for SceneModel data texture layers currently disabled with logarithmic depth buffer");
33421
- scene._loggedWarning = true;
33422
- }
33423
- return false;
33424
- } else {
33425
- return true;
33426
- }
33427
- },
33428
33415
  sortId: sortId,
33429
33416
  setClippableFlags: setFlags2,
33430
33417
  setFlags: (portionId, flags, transparent, deferred = false) => {
@@ -33661,7 +33648,7 @@ const makeDTXRenderingAttributes = function(programVariables, isTriangle) {
33661
33648
  geometryParameters: {
33662
33649
  attributes: {
33663
33650
  color: colorA,
33664
- flags: iota$2(4).map(i => `int(flags[${i}])`),
33651
+ flags: iota$3(4).map(i => `int(flags[${i}])`),
33665
33652
  metallicRoughness: null,
33666
33653
  normal: {
33667
33654
  view: viewNormal,
@@ -33953,7 +33940,7 @@ const tempVec3g = math.vec3();
33953
33940
  const tempUint8Array4 = new Uint8Array(4);
33954
33941
  const matricesUniformBlockBufferData = new Float32Array(4 * 4 * 6); // there is 6 mat4
33955
33942
 
33956
- const iota$1 = function(n) {
33943
+ const iota$2 = function(n) {
33957
33944
  const ret = [ ];
33958
33945
  for (let i = 0; i < n; ++i) ret.push(i);
33959
33946
  return ret;
@@ -34500,7 +34487,6 @@ class VBOLayer extends Layer {
34500
34487
 
34501
34488
  const solid = (primitive === "solid");
34502
34489
  return {
34503
- edgesColorOpaqueAllowed: () => true,
34504
34490
  solid: solid,
34505
34491
  sortId: (((primitive === "points") ? "Points" : ((primitive === "lines") ? "Lines" : "Triangles"))
34506
34492
  + (instancing ? "Instancing" : "Batching") + "Layer" +
@@ -34881,8 +34867,8 @@ const makeVBORenderingAttributes = function(programVariables, instancing, entity
34881
34867
  metallicRoughness: createAttribute("vec2", "metallicRoughness"),
34882
34868
  flags: createAttribute("float", "flagsA"),
34883
34869
  offset: entityOffsetsEnabled && createAttribute("vec3", "offset"),
34884
- modelMatrixCol: instancing && iota$1(3).map(i => createAttribute("vec4", "modelMatrixCol" + i)),
34885
- modelNormalMatrixCol: instancing && instancing.hasModelNormalMat && iota$1(3).map(i => createAttribute("vec4", "modelNormalMatrixCol" + i))
34870
+ modelMatrixCol: instancing && iota$2(3).map(i => createAttribute("vec4", "modelMatrixCol" + i)),
34871
+ modelNormalMatrixCol: instancing && instancing.hasModelNormalMat && iota$2(3).map(i => createAttribute("vec4", "modelNormalMatrixCol" + i))
34886
34872
  };
34887
34873
 
34888
34874
  const uvA = lazyShaderVariable("aUv");
@@ -34913,7 +34899,7 @@ const makeVBORenderingAttributes = function(programVariables, instancing, entity
34913
34899
  geometryParameters: {
34914
34900
  attributes: {
34915
34901
  color: attributes.color,
34916
- flags: iota$1(4).map(i => ({ toString: () => `(int(${attributes.flags}) >> ${i * 4} & 0xF)` })),
34902
+ flags: iota$2(4).map(i => ({ toString: () => `(int(${attributes.flags}) >> ${i * 4} & 0xF)` })),
34917
34903
  metallicRoughness: attributes.metallicRoughness,
34918
34904
  normal: {
34919
34905
  view: viewNormal,
@@ -40724,7 +40710,7 @@ class SceneModel extends Component {
40724
40710
  const positionsDecodeHash = posDecode ? this._createHashStringFromMatrix(posDecode) : "-";
40725
40711
  const textureSetId = cfg.textureSetId || "-";
40726
40712
  const geometryId = instancing ? cfg.geometryId : "-";
40727
- const layerId = (instancing ? "instancing" : "batching") + `.${Math.round(origin[0])}.${Math.round(origin[1])}.${Math.round(origin[2])}.${primitive}.${positionsDecodeHash}.${textureSetId}.${geometryId}`;
40713
+ const layerId = (instancing ? "instancing" : "batching") + `.${Math.round(origin[0])}.${Math.round(origin[1])}.${Math.round(origin[2])}.${primitive}.${positionsDecodeHash}.${textureSetId}.${geometryId}.${((cfg.normalsCompressed || cfg.normals || [ ]).length > 0) ? "n" : "-"}`;
40728
40714
 
40729
40715
  if ((! instancing) && (layerId in this._vboLayers)) {
40730
40716
  const layer = this._vboLayers[layerId];
@@ -47135,9 +47121,9 @@ class OcclusionTester {
47135
47121
 
47136
47122
  const vec3_0 = math.vec3([0,0,0]);
47137
47123
 
47138
- const iota = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
47124
+ const iota$1 = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
47139
47125
 
47140
- const tempPlanes = iota(6).map(() => math.vec4());
47126
+ const tempPlanes = iota$1(6).map(() => math.vec4());
47141
47127
  const tempVec4 = math.vec4();
47142
47128
 
47143
47129
  const bitShiftScreenZ = math.vec4([1.0 / (256.0 * 256.0 * 256.0 * 256.0), 1.0 / (256.0 * 256.0 * 256.0), 1.0 / (256.0 * 256.0), 1.0 / 256.0]);
@@ -47468,7 +47454,7 @@ const Renderer$1 = function (scene, options) {
47468
47454
  const sampleOffsetsHor = createSampleOffsets([1, 0]);
47469
47455
 
47470
47456
  const gaussian = (i, stdDev) => Math.exp(-(i * i) / (2.0 * (stdDev * stdDev))) / (Math.sqrt(2.0 * Math.PI) * stdDev);
47471
- const sampleWeights = new Float32Array(iota(KERNEL_RADIUS + 1).map(i => gaussian(i, blurStdDev))); // TODO: Optimize
47457
+ const sampleWeights = new Float32Array(iota$1(KERNEL_RADIUS + 1).map(i => gaussian(i, blurStdDev))); // TODO: Optimize
47472
47458
 
47473
47459
  const programVariablesState = createProgramVariablesState();
47474
47460
 
@@ -104795,7 +104781,7 @@ class AngleMeasurementsPlugin extends Plugin {
104795
104781
  * @param {Viewer} viewer The Viewer.
104796
104782
  * @param {Object} [cfg] Plugin configuration.
104797
104783
  * @param {String} [cfg.id="AngleMeasurements"] Optional ID for this plugin, so that we can find it within {@link Viewer#plugins}.
104798
- * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````.
104784
+ * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````, but different element should be specified to capture it with {@link Viewer.getSnapshotWithPlugins}.
104799
104785
  * @param {string} [cfg.defaultColor=null] The default color of the dots, wire and label.
104800
104786
  * @param {boolean} [cfg.defaultLabelsVisible=true] The default value of {@link AngleMeasurement.labelsVisible}.
104801
104787
  * @param {number} [cfg.zIndex] If set, the wires, dots and labels will have this zIndex (+1 for dots and +2 for labels).
@@ -106838,7 +106824,7 @@ class AnnotationsPlugin extends Plugin {
106838
106824
  * @param {String} [cfg.id="Annotations"] Optional ID for this plugin, so that we can find it within {@link Viewer#plugins}.
106839
106825
  * @param {String} [cfg.markerHTML] HTML text template for Annotation markers. Defaults to ````<div></div>````. Ignored on {@link Annotation}s configured with a ````markerElementId````.
106840
106826
  * @param {String} [cfg.labelHTML] HTML text template for Annotation labels. Defaults to ````<div></div>````. Ignored on {@link Annotation}s configured with a ````labelElementId````.
106841
- * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````.
106827
+ * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````, but different element should be specified to capture it with {@link Viewer.getSnapshotWithPlugins}.
106842
106828
  * @param {{String:(String|Number)}} [cfg.values={}] Map of default values to insert into the HTML templates for the marker and label.
106843
106829
  * @param {Number} [cfg.surfaceOffset=0.3] The amount by which each {@link Annotation} is offset from the surface of
106844
106830
  * its {@link Entity} when we create the Annotation by supplying a {@link PickResult} to {@link AnnotationsPlugin#createAnnotation}.
@@ -109782,7 +109768,7 @@ class DistanceMeasurementsPlugin extends Plugin {
109782
109768
  * @param {Object} [cfg] Plugin configuration.
109783
109769
  * @param {String} [cfg.id="DistanceMeasurements"] Optional ID for this plugin, so that we can find it within {@link Viewer#plugins}.
109784
109770
  * @param {Number} [cfg.labelMinAxisLength=25] The minimum length, in pixels, of an axis wire beyond which its label is shown.
109785
- * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````.
109771
+ * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````, but different element should be specified to capture it with {@link Viewer.getSnapshotWithPlugins}.
109786
109772
  * @param {boolean} [cfg.defaultVisible=true] The default value of the DistanceMeasurements `visible` property.
109787
109773
  * @param {boolean} [cfg.defaultOriginVisible=true] The default value of the DistanceMeasurements `originVisible` property.
109788
109774
  * @param {boolean} [cfg.defaultTargetVisible=true] The default value of the DistanceMeasurements `targetVisible` property.
@@ -111524,6 +111510,13 @@ function getBasePath$1(src) {
111524
111510
  return (i !== 0) ? src.substring(0, i + 1) : "";
111525
111511
  }
111526
111512
 
111513
+ const iota = n => {
111514
+ const ret = [ ];
111515
+ for (let i = 0; i < n; ++i)
111516
+ ret.push(i);
111517
+ return ret;
111518
+ };
111519
+
111527
111520
  /**
111528
111521
  * @private
111529
111522
  */
@@ -112087,6 +112080,51 @@ function parseNodeMesh(node, ctx, matrix, meshIds) {
112087
112080
  meshCfg.color = new Float32Array([1.0, 1.0, 1.0]);
112088
112081
  meshCfg.opacity = 1.0;
112089
112082
  }
112083
+ const POSITION = primitive.attributes.POSITION;
112084
+ if (!POSITION) {
112085
+ continue;
112086
+ }
112087
+ meshCfg.localPositions = POSITION.value;
112088
+ meshCfg.positions = new Float64Array(meshCfg.localPositions.length);
112089
+ if (primitive.attributes.NORMAL) {
112090
+ meshCfg.normals = primitive.attributes.NORMAL.value;
112091
+ }
112092
+ if (primitive.attributes.TEXCOORD_0) {
112093
+ meshCfg.uv = primitive.attributes.TEXCOORD_0.value;
112094
+ }
112095
+ if (primitive.indices) {
112096
+ meshCfg.indices = primitive.indices.value;
112097
+ }
112098
+ if (matrix) {
112099
+ math.transformPositions3(matrix, meshCfg.localPositions, meshCfg.positions);
112100
+ } else { // eqiv to math.transformPositions3(math.identityMat4(), meshCfg.localPositions, meshCfg.positions);
112101
+ meshCfg.positions.set(meshCfg.localPositions);
112102
+ }
112103
+ const linearize = closeLoop => {
112104
+ const indices = meshCfg.indices || iota(meshCfg.localPositions.length / 3);
112105
+ const len = indices.length;
112106
+ const cnt = closeLoop ? len : (len - 1);
112107
+ const linesIndices = new Uint32Array(cnt * 2);
112108
+ for (let i = 0; i < cnt; ++i) {
112109
+ const idx = i * 2;
112110
+ linesIndices[idx] = indices[i];
112111
+ linesIndices[idx+1] = indices[(i+1) % len];
112112
+ }
112113
+ meshCfg.indices = linesIndices;
112114
+ };
112115
+ const triangularize = getFirstPoint => {
112116
+ const indices = meshCfg.indices || iota(meshCfg.localPositions.length / 3);
112117
+ const len = indices.length;
112118
+ const cnt = len - 2;
112119
+ const trianglesIndices = new Uint32Array(cnt * 3);
112120
+ for (let i = 0; i < cnt; ++i) {
112121
+ const idx = i * 3;
112122
+ trianglesIndices[idx] = getFirstPoint(indices, i);
112123
+ trianglesIndices[idx+1] = indices[(i+1) % len];
112124
+ trianglesIndices[idx+2] = indices[(i+2) % len];
112125
+ }
112126
+ meshCfg.indices = trianglesIndices;
112127
+ };
112090
112128
  const backfaces = ((ctx.backfaces !== false) || (material && material.doubleSided !== false));
112091
112129
  switch (primitive.mode) {
112092
112130
  case 0: // POINTS
@@ -112097,42 +112135,26 @@ function parseNodeMesh(node, ctx, matrix, meshIds) {
112097
112135
  break;
112098
112136
  case 2: // LINE_LOOP
112099
112137
  meshCfg.primitive = "lines";
112138
+ linearize(true);
112100
112139
  break;
112101
112140
  case 3: // LINE_STRIP
112102
112141
  meshCfg.primitive = "lines";
112142
+ linearize(false);
112103
112143
  break;
112104
112144
  case 4: // TRIANGLES
112105
112145
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112106
112146
  break;
112107
112147
  case 5: // TRIANGLE_STRIP
112108
112148
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112149
+ triangularize((indices, i) => indices[i]);
112109
112150
  break;
112110
112151
  case 6: // TRIANGLE_FAN
112111
112152
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112153
+ triangularize((indices, i) => indices[0]);
112112
112154
  break;
112113
112155
  default:
112114
112156
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112115
112157
  }
112116
- const POSITION = primitive.attributes.POSITION;
112117
- if (!POSITION) {
112118
- continue;
112119
- }
112120
- meshCfg.localPositions = POSITION.value;
112121
- meshCfg.positions = new Float64Array(meshCfg.localPositions.length);
112122
- if (primitive.attributes.NORMAL) {
112123
- meshCfg.normals = primitive.attributes.NORMAL.value;
112124
- }
112125
- if (primitive.attributes.TEXCOORD_0) {
112126
- meshCfg.uv = primitive.attributes.TEXCOORD_0.value;
112127
- }
112128
- if (primitive.indices) {
112129
- meshCfg.indices = primitive.indices.value;
112130
- }
112131
- if (matrix) {
112132
- math.transformPositions3(matrix, meshCfg.localPositions, meshCfg.positions);
112133
- } else { // eqiv to math.transformPositions3(math.identityMat4(), meshCfg.localPositions, meshCfg.positions);
112134
- meshCfg.positions.set(meshCfg.localPositions);
112135
- }
112136
112158
  const origin = math.vec3();
112137
112159
  const rtcNeeded = worldToRTCPositions(meshCfg.positions, meshCfg.positions, origin); // Small cellsize guarantees better accuracy
112138
112160
  if (rtcNeeded) {
@@ -1,11 +1,11 @@
1
1
  /**
2
- * xeokit-sdk v2.6.108
3
- * Commit: a2bfb2cb967c8a3925c74e4039bfc60f136128c2
4
- * Built: 2026-04-03T14:14:43.600Z
2
+ * xeokit-sdk v2.6.109
3
+ * Commit: 3796b67f0bbcca7382160e5030522506fb49a54e
4
+ * Built: 2026-05-08T06:25:43.604Z
5
5
  */
6
6
 
7
7
  if (typeof window !== 'undefined') {
8
- window.__XEOKIT__ = { version: '2.6.108', commit: 'a2bfb2cb967c8a3925c74e4039bfc60f136128c2', built: '2026-04-03T14:14:43.600Z' };
8
+ window.__XEOKIT__ = { version: '2.6.109', commit: '3796b67f0bbcca7382160e5030522506fb49a54e', built: '2026-05-08T06:25:43.604Z' };
9
9
  }
10
10
 
11
11
  /** @private */
@@ -20733,7 +20733,7 @@ const tempVec3a$f = math.vec3();
20733
20733
  const tempVec4$3 = math.vec4();
20734
20734
  const TEXTURE_DECODE_FUNCS = { [sRGBEncoding]: "sRGBToLinear" };
20735
20735
 
20736
- const iota$3 = function(n) {
20736
+ const iota$4 = function(n) {
20737
20737
  const ret = [ ];
20738
20738
  for (let i = 0; i < n; ++i) ret.push(i);
20739
20739
  return ret;
@@ -20932,7 +20932,7 @@ const createProgramVariablesState = function() {
20932
20932
 
20933
20933
  const sectionPlanesState = cfg.sectionPlanesState;
20934
20934
  const getClippingDistance = sectionPlanesState && (function() {
20935
- const allocatedUniforms = iota$3(sectionPlanesState.getNumAllocatedSectionPlanes()).map(i => {
20935
+ const allocatedUniforms = iota$4(sectionPlanesState.getNumAllocatedSectionPlanes()).map(i => {
20936
20936
  const sectionPlaneUniform = (type, postfix, getValue) => {
20937
20937
  return programVariables.createUniform(type, `sectionPlane${postfix}${i}`, (set, state) => {
20938
20938
  const sectionPlanes = sectionPlanesState.sectionPlanes;
@@ -32535,9 +32535,7 @@ class Layer {
32535
32535
  }
32536
32536
 
32537
32537
  drawEdgesColorOpaque(renderFlags, frameCtx) {
32538
- if (this._compiledPortions.edgesColorOpaqueAllowed()) {
32539
- this.__drawVertexEdges(renderFlags, frameCtx, RENDER_PASSES.EDGES_COLOR_OPAQUE);
32540
- }
32538
+ this.__drawVertexEdges(renderFlags, frameCtx, RENDER_PASSES.EDGES_COLOR_OPAQUE);
32541
32539
  }
32542
32540
 
32543
32541
  drawEdgesColorTransparent(renderFlags, frameCtx) {
@@ -32828,7 +32826,7 @@ class Configs {
32828
32826
  }
32829
32827
  }
32830
32828
 
32831
- const iota$2 = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
32829
+ const iota$3 = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
32832
32830
 
32833
32831
  const dataTextureRamStats = {
32834
32832
  sizeDataColorsAndFlags: 0,
@@ -33410,17 +33408,6 @@ class DTXLayer extends Layer {
33410
33408
  };
33411
33409
 
33412
33410
  return {
33413
- edgesColorOpaqueAllowed: () => {
33414
- if (scene.logarithmicDepthBufferEnabled) {
33415
- if (!scene._loggedWarning) {
33416
- console.log("Edge enhancement for SceneModel data texture layers currently disabled with logarithmic depth buffer");
33417
- scene._loggedWarning = true;
33418
- }
33419
- return false;
33420
- } else {
33421
- return true;
33422
- }
33423
- },
33424
33411
  sortId: sortId,
33425
33412
  setClippableFlags: setFlags2,
33426
33413
  setFlags: (portionId, flags, transparent, deferred = false) => {
@@ -33657,7 +33644,7 @@ const makeDTXRenderingAttributes = function(programVariables, isTriangle) {
33657
33644
  geometryParameters: {
33658
33645
  attributes: {
33659
33646
  color: colorA,
33660
- flags: iota$2(4).map(i => `int(flags[${i}])`),
33647
+ flags: iota$3(4).map(i => `int(flags[${i}])`),
33661
33648
  metallicRoughness: null,
33662
33649
  normal: {
33663
33650
  view: viewNormal,
@@ -33949,7 +33936,7 @@ const tempVec3g = math.vec3();
33949
33936
  const tempUint8Array4 = new Uint8Array(4);
33950
33937
  const matricesUniformBlockBufferData = new Float32Array(4 * 4 * 6); // there is 6 mat4
33951
33938
 
33952
- const iota$1 = function(n) {
33939
+ const iota$2 = function(n) {
33953
33940
  const ret = [ ];
33954
33941
  for (let i = 0; i < n; ++i) ret.push(i);
33955
33942
  return ret;
@@ -34496,7 +34483,6 @@ class VBOLayer extends Layer {
34496
34483
 
34497
34484
  const solid = (primitive === "solid");
34498
34485
  return {
34499
- edgesColorOpaqueAllowed: () => true,
34500
34486
  solid: solid,
34501
34487
  sortId: (((primitive === "points") ? "Points" : ((primitive === "lines") ? "Lines" : "Triangles"))
34502
34488
  + (instancing ? "Instancing" : "Batching") + "Layer" +
@@ -34877,8 +34863,8 @@ const makeVBORenderingAttributes = function(programVariables, instancing, entity
34877
34863
  metallicRoughness: createAttribute("vec2", "metallicRoughness"),
34878
34864
  flags: createAttribute("float", "flagsA"),
34879
34865
  offset: entityOffsetsEnabled && createAttribute("vec3", "offset"),
34880
- modelMatrixCol: instancing && iota$1(3).map(i => createAttribute("vec4", "modelMatrixCol" + i)),
34881
- modelNormalMatrixCol: instancing && instancing.hasModelNormalMat && iota$1(3).map(i => createAttribute("vec4", "modelNormalMatrixCol" + i))
34866
+ modelMatrixCol: instancing && iota$2(3).map(i => createAttribute("vec4", "modelMatrixCol" + i)),
34867
+ modelNormalMatrixCol: instancing && instancing.hasModelNormalMat && iota$2(3).map(i => createAttribute("vec4", "modelNormalMatrixCol" + i))
34882
34868
  };
34883
34869
 
34884
34870
  const uvA = lazyShaderVariable("aUv");
@@ -34909,7 +34895,7 @@ const makeVBORenderingAttributes = function(programVariables, instancing, entity
34909
34895
  geometryParameters: {
34910
34896
  attributes: {
34911
34897
  color: attributes.color,
34912
- flags: iota$1(4).map(i => ({ toString: () => `(int(${attributes.flags}) >> ${i * 4} & 0xF)` })),
34898
+ flags: iota$2(4).map(i => ({ toString: () => `(int(${attributes.flags}) >> ${i * 4} & 0xF)` })),
34913
34899
  metallicRoughness: attributes.metallicRoughness,
34914
34900
  normal: {
34915
34901
  view: viewNormal,
@@ -40720,7 +40706,7 @@ class SceneModel extends Component {
40720
40706
  const positionsDecodeHash = posDecode ? this._createHashStringFromMatrix(posDecode) : "-";
40721
40707
  const textureSetId = cfg.textureSetId || "-";
40722
40708
  const geometryId = instancing ? cfg.geometryId : "-";
40723
- const layerId = (instancing ? "instancing" : "batching") + `.${Math.round(origin[0])}.${Math.round(origin[1])}.${Math.round(origin[2])}.${primitive}.${positionsDecodeHash}.${textureSetId}.${geometryId}`;
40709
+ const layerId = (instancing ? "instancing" : "batching") + `.${Math.round(origin[0])}.${Math.round(origin[1])}.${Math.round(origin[2])}.${primitive}.${positionsDecodeHash}.${textureSetId}.${geometryId}.${((cfg.normalsCompressed || cfg.normals || [ ]).length > 0) ? "n" : "-"}`;
40724
40710
 
40725
40711
  if ((! instancing) && (layerId in this._vboLayers)) {
40726
40712
  const layer = this._vboLayers[layerId];
@@ -47131,9 +47117,9 @@ class OcclusionTester {
47131
47117
 
47132
47118
  const vec3_0 = math.vec3([0,0,0]);
47133
47119
 
47134
- const iota = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
47120
+ const iota$1 = (n) => { const ret = [ ]; for (let i = 0; i < n; ++i) ret.push(i); return ret; };
47135
47121
 
47136
- const tempPlanes = iota(6).map(() => math.vec4());
47122
+ const tempPlanes = iota$1(6).map(() => math.vec4());
47137
47123
  const tempVec4 = math.vec4();
47138
47124
 
47139
47125
  const bitShiftScreenZ = math.vec4([1.0 / (256.0 * 256.0 * 256.0 * 256.0), 1.0 / (256.0 * 256.0 * 256.0), 1.0 / (256.0 * 256.0), 1.0 / 256.0]);
@@ -47464,7 +47450,7 @@ const Renderer$1 = function (scene, options) {
47464
47450
  const sampleOffsetsHor = createSampleOffsets([1, 0]);
47465
47451
 
47466
47452
  const gaussian = (i, stdDev) => Math.exp(-(i * i) / (2.0 * (stdDev * stdDev))) / (Math.sqrt(2.0 * Math.PI) * stdDev);
47467
- const sampleWeights = new Float32Array(iota(KERNEL_RADIUS + 1).map(i => gaussian(i, blurStdDev))); // TODO: Optimize
47453
+ const sampleWeights = new Float32Array(iota$1(KERNEL_RADIUS + 1).map(i => gaussian(i, blurStdDev))); // TODO: Optimize
47468
47454
 
47469
47455
  const programVariablesState = createProgramVariablesState();
47470
47456
 
@@ -104791,7 +104777,7 @@ class AngleMeasurementsPlugin extends Plugin {
104791
104777
  * @param {Viewer} viewer The Viewer.
104792
104778
  * @param {Object} [cfg] Plugin configuration.
104793
104779
  * @param {String} [cfg.id="AngleMeasurements"] Optional ID for this plugin, so that we can find it within {@link Viewer#plugins}.
104794
- * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````.
104780
+ * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````, but different element should be specified to capture it with {@link Viewer.getSnapshotWithPlugins}.
104795
104781
  * @param {string} [cfg.defaultColor=null] The default color of the dots, wire and label.
104796
104782
  * @param {boolean} [cfg.defaultLabelsVisible=true] The default value of {@link AngleMeasurement.labelsVisible}.
104797
104783
  * @param {number} [cfg.zIndex] If set, the wires, dots and labels will have this zIndex (+1 for dots and +2 for labels).
@@ -106834,7 +106820,7 @@ class AnnotationsPlugin extends Plugin {
106834
106820
  * @param {String} [cfg.id="Annotations"] Optional ID for this plugin, so that we can find it within {@link Viewer#plugins}.
106835
106821
  * @param {String} [cfg.markerHTML] HTML text template for Annotation markers. Defaults to ````<div></div>````. Ignored on {@link Annotation}s configured with a ````markerElementId````.
106836
106822
  * @param {String} [cfg.labelHTML] HTML text template for Annotation labels. Defaults to ````<div></div>````. Ignored on {@link Annotation}s configured with a ````labelElementId````.
106837
- * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````.
106823
+ * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````, but different element should be specified to capture it with {@link Viewer.getSnapshotWithPlugins}.
106838
106824
  * @param {{String:(String|Number)}} [cfg.values={}] Map of default values to insert into the HTML templates for the marker and label.
106839
106825
  * @param {Number} [cfg.surfaceOffset=0.3] The amount by which each {@link Annotation} is offset from the surface of
106840
106826
  * its {@link Entity} when we create the Annotation by supplying a {@link PickResult} to {@link AnnotationsPlugin#createAnnotation}.
@@ -109778,7 +109764,7 @@ class DistanceMeasurementsPlugin extends Plugin {
109778
109764
  * @param {Object} [cfg] Plugin configuration.
109779
109765
  * @param {String} [cfg.id="DistanceMeasurements"] Optional ID for this plugin, so that we can find it within {@link Viewer#plugins}.
109780
109766
  * @param {Number} [cfg.labelMinAxisLength=25] The minimum length, in pixels, of an axis wire beyond which its label is shown.
109781
- * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````.
109767
+ * @param {HTMLElement} [cfg.container] Container DOM element for markers and labels. Defaults to ````document.body````, but different element should be specified to capture it with {@link Viewer.getSnapshotWithPlugins}.
109782
109768
  * @param {boolean} [cfg.defaultVisible=true] The default value of the DistanceMeasurements `visible` property.
109783
109769
  * @param {boolean} [cfg.defaultOriginVisible=true] The default value of the DistanceMeasurements `originVisible` property.
109784
109770
  * @param {boolean} [cfg.defaultTargetVisible=true] The default value of the DistanceMeasurements `targetVisible` property.
@@ -111520,6 +111506,13 @@ function getBasePath$1(src) {
111520
111506
  return (i !== 0) ? src.substring(0, i + 1) : "";
111521
111507
  }
111522
111508
 
111509
+ const iota = n => {
111510
+ const ret = [ ];
111511
+ for (let i = 0; i < n; ++i)
111512
+ ret.push(i);
111513
+ return ret;
111514
+ };
111515
+
111523
111516
  /**
111524
111517
  * @private
111525
111518
  */
@@ -112083,6 +112076,51 @@ function parseNodeMesh(node, ctx, matrix, meshIds) {
112083
112076
  meshCfg.color = new Float32Array([1.0, 1.0, 1.0]);
112084
112077
  meshCfg.opacity = 1.0;
112085
112078
  }
112079
+ const POSITION = primitive.attributes.POSITION;
112080
+ if (!POSITION) {
112081
+ continue;
112082
+ }
112083
+ meshCfg.localPositions = POSITION.value;
112084
+ meshCfg.positions = new Float64Array(meshCfg.localPositions.length);
112085
+ if (primitive.attributes.NORMAL) {
112086
+ meshCfg.normals = primitive.attributes.NORMAL.value;
112087
+ }
112088
+ if (primitive.attributes.TEXCOORD_0) {
112089
+ meshCfg.uv = primitive.attributes.TEXCOORD_0.value;
112090
+ }
112091
+ if (primitive.indices) {
112092
+ meshCfg.indices = primitive.indices.value;
112093
+ }
112094
+ if (matrix) {
112095
+ math.transformPositions3(matrix, meshCfg.localPositions, meshCfg.positions);
112096
+ } else { // eqiv to math.transformPositions3(math.identityMat4(), meshCfg.localPositions, meshCfg.positions);
112097
+ meshCfg.positions.set(meshCfg.localPositions);
112098
+ }
112099
+ const linearize = closeLoop => {
112100
+ const indices = meshCfg.indices || iota(meshCfg.localPositions.length / 3);
112101
+ const len = indices.length;
112102
+ const cnt = closeLoop ? len : (len - 1);
112103
+ const linesIndices = new Uint32Array(cnt * 2);
112104
+ for (let i = 0; i < cnt; ++i) {
112105
+ const idx = i * 2;
112106
+ linesIndices[idx] = indices[i];
112107
+ linesIndices[idx+1] = indices[(i+1) % len];
112108
+ }
112109
+ meshCfg.indices = linesIndices;
112110
+ };
112111
+ const triangularize = getFirstPoint => {
112112
+ const indices = meshCfg.indices || iota(meshCfg.localPositions.length / 3);
112113
+ const len = indices.length;
112114
+ const cnt = len - 2;
112115
+ const trianglesIndices = new Uint32Array(cnt * 3);
112116
+ for (let i = 0; i < cnt; ++i) {
112117
+ const idx = i * 3;
112118
+ trianglesIndices[idx] = getFirstPoint(indices, i);
112119
+ trianglesIndices[idx+1] = indices[(i+1) % len];
112120
+ trianglesIndices[idx+2] = indices[(i+2) % len];
112121
+ }
112122
+ meshCfg.indices = trianglesIndices;
112123
+ };
112086
112124
  const backfaces = ((ctx.backfaces !== false) || (material && material.doubleSided !== false));
112087
112125
  switch (primitive.mode) {
112088
112126
  case 0: // POINTS
@@ -112093,42 +112131,26 @@ function parseNodeMesh(node, ctx, matrix, meshIds) {
112093
112131
  break;
112094
112132
  case 2: // LINE_LOOP
112095
112133
  meshCfg.primitive = "lines";
112134
+ linearize(true);
112096
112135
  break;
112097
112136
  case 3: // LINE_STRIP
112098
112137
  meshCfg.primitive = "lines";
112138
+ linearize(false);
112099
112139
  break;
112100
112140
  case 4: // TRIANGLES
112101
112141
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112102
112142
  break;
112103
112143
  case 5: // TRIANGLE_STRIP
112104
112144
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112145
+ triangularize((indices, i) => indices[i]);
112105
112146
  break;
112106
112147
  case 6: // TRIANGLE_FAN
112107
112148
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112149
+ triangularize((indices, i) => indices[0]);
112108
112150
  break;
112109
112151
  default:
112110
112152
  meshCfg.primitive = backfaces ? "triangles" : "solid";
112111
112153
  }
112112
- const POSITION = primitive.attributes.POSITION;
112113
- if (!POSITION) {
112114
- continue;
112115
- }
112116
- meshCfg.localPositions = POSITION.value;
112117
- meshCfg.positions = new Float64Array(meshCfg.localPositions.length);
112118
- if (primitive.attributes.NORMAL) {
112119
- meshCfg.normals = primitive.attributes.NORMAL.value;
112120
- }
112121
- if (primitive.attributes.TEXCOORD_0) {
112122
- meshCfg.uv = primitive.attributes.TEXCOORD_0.value;
112123
- }
112124
- if (primitive.indices) {
112125
- meshCfg.indices = primitive.indices.value;
112126
- }
112127
- if (matrix) {
112128
- math.transformPositions3(matrix, meshCfg.localPositions, meshCfg.positions);
112129
- } else { // eqiv to math.transformPositions3(math.identityMat4(), meshCfg.localPositions, meshCfg.positions);
112130
- meshCfg.positions.set(meshCfg.localPositions);
112131
- }
112132
112154
  const origin = math.vec3();
112133
112155
  const rtcNeeded = worldToRTCPositions(meshCfg.positions, meshCfg.positions, origin); // Small cellsize guarantees better accuracy
112134
112156
  if (rtcNeeded) {