@luma.gl/webgl 9.0.0-alpha.26 → 9.0.0-alpha.29

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 (56) hide show
  1. package/dist/adapter/helpers/get-shader-layout.d.ts +8 -5
  2. package/dist/adapter/helpers/get-shader-layout.d.ts.map +1 -1
  3. package/dist/adapter/helpers/get-shader-layout.js +59 -16
  4. package/dist/adapter/helpers/get-shader-layout.js.map +1 -1
  5. package/dist/adapter/helpers/get-vertex-buffer-layout.d.ts +12 -0
  6. package/dist/adapter/helpers/get-vertex-buffer-layout.d.ts.map +1 -0
  7. package/dist/adapter/helpers/get-vertex-buffer-layout.js +84 -0
  8. package/dist/adapter/helpers/get-vertex-buffer-layout.js.map +1 -0
  9. package/dist/adapter/objects/webgl-vertex-array-object.d.ts +35 -8
  10. package/dist/adapter/objects/webgl-vertex-array-object.d.ts.map +1 -1
  11. package/dist/adapter/objects/webgl-vertex-array-object.js +116 -16
  12. package/dist/adapter/objects/webgl-vertex-array-object.js.map +1 -1
  13. package/dist/adapter/resources/webgl-buffer.d.ts +13 -4
  14. package/dist/adapter/resources/webgl-buffer.d.ts.map +1 -1
  15. package/dist/adapter/resources/webgl-buffer.js +23 -21
  16. package/dist/adapter/resources/webgl-buffer.js.map +1 -1
  17. package/dist/adapter/resources/webgl-external-texture.js.map +1 -1
  18. package/dist/adapter/resources/webgl-render-pipeline.d.ts +38 -5
  19. package/dist/adapter/resources/webgl-render-pipeline.d.ts.map +1 -1
  20. package/dist/adapter/resources/webgl-render-pipeline.js +35 -7
  21. package/dist/adapter/resources/webgl-render-pipeline.js.map +1 -1
  22. package/dist/adapter/webgl-device.d.ts.map +1 -1
  23. package/dist/adapter/webgl-device.js +5 -2
  24. package/dist/adapter/webgl-device.js.map +1 -1
  25. package/dist/classic/buffer-with-accessor.d.ts +5 -15
  26. package/dist/classic/buffer-with-accessor.d.ts.map +1 -1
  27. package/dist/classic/buffer-with-accessor.js +25 -30
  28. package/dist/classic/buffer-with-accessor.js.map +1 -1
  29. package/dist/classic/copy-and-blit.d.ts.map +1 -1
  30. package/dist/classic/copy-and-blit.js +2 -2
  31. package/dist/classic/copy-and-blit.js.map +1 -1
  32. package/dist/context/debug/webgl-developer-tools.d.ts.map +1 -1
  33. package/dist/context/debug/webgl-developer-tools.js +2 -1
  34. package/dist/context/debug/webgl-developer-tools.js.map +1 -1
  35. package/dist/context/parameters/webgl-parameter-tables.js +2 -2
  36. package/dist/context/parameters/webgl-parameter-tables.js.map +1 -1
  37. package/dist/dist.dev.js +350 -99
  38. package/dist/index.cjs +343 -157
  39. package/dist/index.d.ts +1 -1
  40. package/dist/index.d.ts.map +1 -1
  41. package/dist/index.js +1 -1
  42. package/dist/index.js.map +1 -1
  43. package/dist.min.js +22 -22
  44. package/package.json +5 -5
  45. package/src/adapter/helpers/get-shader-layout.ts +93 -33
  46. package/src/adapter/helpers/get-vertex-buffer-layout.ts +123 -0
  47. package/src/adapter/objects/webgl-vertex-array-object.ts +192 -28
  48. package/src/adapter/resources/webgl-buffer.ts +40 -41
  49. package/src/adapter/resources/webgl-external-texture.ts +1 -1
  50. package/src/adapter/resources/webgl-render-pipeline.ts +73 -36
  51. package/src/adapter/webgl-device.ts +4 -2
  52. package/src/classic/buffer-with-accessor.ts +42 -43
  53. package/src/classic/copy-and-blit.ts +2 -3
  54. package/src/context/debug/webgl-developer-tools.ts +8 -2
  55. package/src/context/parameters/webgl-parameter-tables.ts +2 -2
  56. package/src/index.ts +1 -1
package/dist/index.cjs CHANGED
@@ -80,11 +80,11 @@ __export(src_exports, {
80
80
  convertGLToTextureFormat: () => convertGLToTextureFormat,
81
81
  copyToTexture: () => copyToTexture,
82
82
  getParameters: () => getParameters,
83
- getProgramBindings: () => getProgramBindings,
84
83
  getShaderLayout: () => getShaderLayout,
85
84
  getWebGL2Context: () => getWebGL2Context,
86
85
  isWebGL: () => isWebGL,
87
86
  isWebGL2: () => isWebGL2,
87
+ mergeShaderLayout: () => mergeShaderLayout,
88
88
  polyfillContext: () => polyfillContext,
89
89
  popContextState: () => popContextState,
90
90
  pushContextState: () => pushContextState,
@@ -133,8 +133,8 @@ function createHeadlessContext(options) {
133
133
  }
134
134
 
135
135
  // src/adapter/webgl-device.ts
136
- var import_api26 = require("@luma.gl/api");
137
- var import_env2 = require("@probe.gl/env");
136
+ var import_api27 = require("@luma.gl/api");
137
+ var import_env3 = require("@probe.gl/env");
138
138
 
139
139
  // src/context/polyfill/polyfill-context.ts
140
140
  var import_api3 = require("@luma.gl/api");
@@ -880,8 +880,8 @@ var bindBuffer = (gl2, value, key) => {
880
880
  [import_constants3.GL.PIXEL_PACK_BUFFER_BINDING]: import_constants3.GL.PIXEL_PACK_BUFFER,
881
881
  [import_constants3.GL.PIXEL_UNPACK_BUFFER_BINDING]: import_constants3.GL.PIXEL_UNPACK_BUFFER
882
882
  };
883
- const target = bindingMap[key];
884
- gl2.bindBuffer(target, value);
883
+ const glTarget = bindingMap[key];
884
+ gl2.bindBuffer(glTarget, value);
885
885
  };
886
886
  function isArray(array) {
887
887
  return Array.isArray(array) || ArrayBuffer.isView(array) && !(array instanceof DataView);
@@ -1358,7 +1358,7 @@ var GLState = class {
1358
1358
  constructor(gl2, {
1359
1359
  copyState = false,
1360
1360
  // Copy cache from params (slow) or initialize from WebGL defaults (fast)
1361
- log: log9 = () => {
1361
+ log: log10 = () => {
1362
1362
  }
1363
1363
  // Logging function, called when gl parameter change calls are actually issued
1364
1364
  } = {}) {
@@ -1367,7 +1367,7 @@ var GLState = class {
1367
1367
  this.enable = true;
1368
1368
  this.gl = gl2;
1369
1369
  this.cache = copyState ? getParameters(gl2) : Object.assign({}, GL_PARAMETER_DEFAULTS);
1370
- this.log = log9;
1370
+ this.log = log10;
1371
1371
  this._updateCache = this._updateCache.bind(this);
1372
1372
  Object.seal(this);
1373
1373
  }
@@ -2521,9 +2521,11 @@ var import_api7 = require("@luma.gl/api");
2521
2521
  var import_constants9 = require("@luma.gl/constants");
2522
2522
  var DEBUG_DATA_LENGTH = 10;
2523
2523
  var WEBGLBuffer = class extends import_api7.Buffer {
2524
- // accessor: {};
2525
2524
  constructor(device, props = {}) {
2526
2525
  super(device, props);
2526
+ /** Index type is needed when issuing draw calls, so we pre-compute it */
2527
+ this.glIndexType = import_constants9.GL.UNSIGNED_SHORT;
2528
+ /** A partial CPU-side copy of the data in this buffer, for debugging purposes */
2527
2529
  this.debugData = null;
2528
2530
  this.device = device;
2529
2531
  this.gl = this.device.gl;
@@ -2531,8 +2533,9 @@ var WEBGLBuffer = class extends import_api7.Buffer {
2531
2533
  const handle = typeof props === "object" ? props.handle : void 0;
2532
2534
  this.handle = handle || this.gl.createBuffer();
2533
2535
  device.setSpectorMetadata(this.handle, __spreadProps(__spreadValues({}, this.props), { data: typeof this.props.data }));
2534
- this.target = this.props.target || getWebGLTarget(this.props.usage);
2535
- this.webglUsage = this.props.webglUsage || getWebGLUsage(this.props.usage);
2536
+ this.glTarget = getWebGLTarget(this.props.usage);
2537
+ this.glUsage = getWebGLUsage(this.props.usage);
2538
+ this.glIndexType = this.props.indexType === "uint32" ? import_constants9.GL.UNSIGNED_INT : import_constants9.GL.UNSIGNED_SHORT;
2536
2539
  this.debugData = null;
2537
2540
  if (props.data) {
2538
2541
  this._initWithData(props.data, props.byteOffset, props.byteLength);
@@ -2541,14 +2544,14 @@ var WEBGLBuffer = class extends import_api7.Buffer {
2541
2544
  }
2542
2545
  }
2543
2546
  // PRIVATE METHODS
2544
- // Allocate a new buffer and initialize to contents of typed array
2547
+ /** Allocate a new buffer and initialize to contents of typed array */
2545
2548
  _initWithData(data, byteOffset = 0, byteLength = data.byteLength + byteOffset) {
2546
2549
  (0, import_api7.assert)(ArrayBuffer.isView(data));
2547
- const target = this._getWriteTarget();
2548
- this.gl.bindBuffer(target, this.handle);
2549
- this.gl.bufferData(target, byteLength, this.webglUsage);
2550
- this.gl.bufferSubData(target, byteOffset, data);
2551
- this.gl.bindBuffer(target, null);
2550
+ const glTarget = this._getWriteTarget();
2551
+ this.gl.bindBuffer(glTarget, this.handle);
2552
+ this.gl.bufferData(glTarget, byteLength, this.glUsage);
2553
+ this.gl.bufferSubData(glTarget, byteOffset, data);
2554
+ this.gl.bindBuffer(glTarget, null);
2552
2555
  this.debugData = data.slice(0, DEBUG_DATA_LENGTH);
2553
2556
  this.bytesUsed = byteLength;
2554
2557
  this.byteLength = byteLength;
@@ -2562,10 +2565,10 @@ var WEBGLBuffer = class extends import_api7.Buffer {
2562
2565
  if (byteLength === 0) {
2563
2566
  data = new Float32Array(0);
2564
2567
  }
2565
- const target = this._getWriteTarget();
2566
- this.gl.bindBuffer(target, this.handle);
2567
- this.gl.bufferData(target, data, this.webglUsage);
2568
- this.gl.bindBuffer(target, null);
2568
+ const glTarget = this._getWriteTarget();
2569
+ this.gl.bindBuffer(glTarget, this.handle);
2570
+ this.gl.bufferData(glTarget, data, this.glUsage);
2571
+ this.gl.bindBuffer(glTarget, null);
2569
2572
  this.debugData = null;
2570
2573
  this.bytesUsed = byteLength;
2571
2574
  this.byteLength = byteLength;
@@ -2583,15 +2586,15 @@ var WEBGLBuffer = class extends import_api7.Buffer {
2583
2586
  write(data, byteOffset = 0) {
2584
2587
  const srcOffset = 0;
2585
2588
  const byteLength = void 0;
2586
- const target = this.device.isWebGL2 ? import_constants9.GL.COPY_WRITE_BUFFER : this.target;
2587
- this.gl.bindBuffer(target, this.handle);
2589
+ const glTarget = this.device.isWebGL2 ? import_constants9.GL.COPY_WRITE_BUFFER : this.glTarget;
2590
+ this.gl.bindBuffer(glTarget, this.handle);
2588
2591
  if (srcOffset !== 0 || byteLength !== void 0) {
2589
2592
  this.device.assertWebGL2();
2590
- this.gl2.bufferSubData(target, byteOffset, data, srcOffset, byteLength);
2593
+ this.gl2.bufferSubData(glTarget, byteOffset, data, srcOffset, byteLength);
2591
2594
  } else {
2592
- this.gl.bufferSubData(target, byteOffset, data);
2595
+ this.gl.bufferSubData(glTarget, byteOffset, data);
2593
2596
  }
2594
- this.gl.bindBuffer(target, null);
2597
+ this.gl.bindBuffer(glTarget, null);
2595
2598
  }
2596
2599
  /** Read data from the buffer */
2597
2600
  readAsync(byteOffset = 0, byteLength) {
@@ -2610,10 +2613,10 @@ var WEBGLBuffer = class extends import_api7.Buffer {
2610
2613
  this.debugData = null;
2611
2614
  }
2612
2615
  _getWriteTarget() {
2613
- return this.target;
2616
+ return this.glTarget;
2614
2617
  }
2615
2618
  _getReadTarget() {
2616
- return this.target;
2619
+ return this.glTarget;
2617
2620
  }
2618
2621
  };
2619
2622
  function getWebGLTarget(usage) {
@@ -2638,7 +2641,7 @@ function getWebGLUsage(usage) {
2638
2641
  if (usage & import_api7.Buffer.UNIFORM) {
2639
2642
  return import_constants9.GL.DYNAMIC_DRAW;
2640
2643
  }
2641
- return import_constants9.GL.DYNAMIC_DRAW;
2644
+ return import_constants9.GL.STATIC_DRAW;
2642
2645
  }
2643
2646
 
2644
2647
  // src/adapter/resources/webgl-sampler.ts
@@ -3973,6 +3976,7 @@ function initializeSpectorJS(props) {
3973
3976
  // src/context/debug/webgl-developer-tools.ts
3974
3977
  var import_api17 = require("@luma.gl/api");
3975
3978
  var import_constants14 = require("@luma.gl/constants");
3979
+ var import_env = require("@probe.gl/env");
3976
3980
  var WEBGL_DEBUG_CDN_URL = "https://unpkg.com/webgl-debug@2.0.1/index.js";
3977
3981
  function getContextData2(gl2) {
3978
3982
  gl2.luma = gl2.luma || {};
@@ -3980,7 +3984,7 @@ function getContextData2(gl2) {
3980
3984
  }
3981
3985
  function loadWebGLDeveloperTools() {
3982
3986
  return __async(this, null, function* () {
3983
- if (!globalThis.WebGLDebugUtils) {
3987
+ if ((0, import_env.isBrowser)() && !globalThis.WebGLDebugUtils) {
3984
3988
  globalThis.global = globalThis.global || globalThis;
3985
3989
  globalThis.global.module = {};
3986
3990
  yield (0, import_api17.loadScript)(WEBGL_DEBUG_CDN_URL);
@@ -4280,9 +4284,6 @@ function getWEBGLBufferProps(props) {
4280
4284
  }
4281
4285
  props = (0, import_api19.checkProps)("Buffer", props, PROP_CHECKS_INITIALIZE);
4282
4286
  const bufferProps = __spreadValues({}, props);
4283
- if (bufferProps.offset) {
4284
- bufferProps.byteOffset = bufferProps.offset;
4285
- }
4286
4287
  return bufferProps;
4287
4288
  }
4288
4289
  var BufferWithAccessor = class extends WEBGLBuffer {
@@ -4319,11 +4320,11 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4319
4320
  props = { byteLength: props };
4320
4321
  }
4321
4322
  props = (0, import_api19.checkProps)("Buffer", props, PROP_CHECKS_INITIALIZE);
4322
- this.webglUsage = props.webglUsage || import_constants17.GL.STATIC_DRAW;
4323
+ this.glUsage = props.glUsage || import_constants17.GL.STATIC_DRAW;
4323
4324
  this.debugData = null;
4324
4325
  this.setAccessor(Object.assign({}, props, props.accessor));
4325
4326
  if (props.data) {
4326
- this._setData(props.data, props.offset, props.byteLength);
4327
+ this._setData(props.data, props.byteOffset, props.byteLength);
4327
4328
  } else {
4328
4329
  this._setByteLength(props.byteLength || 0);
4329
4330
  }
@@ -4373,15 +4374,15 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4373
4374
  const { data, offset = 0, srcOffset = 0 } = options;
4374
4375
  const byteLength = options.byteLength || options.length;
4375
4376
  (0, import_api19.assert)(data);
4376
- const target = this.gl.webgl2 ? import_constants17.GL.COPY_WRITE_BUFFER : this.target;
4377
- this.gl.bindBuffer(target, this.handle);
4377
+ const glTarget = this.gl.webgl2 ? import_constants17.GL.COPY_WRITE_BUFFER : this.glTarget;
4378
+ this.gl.bindBuffer(glTarget, this.handle);
4378
4379
  if (srcOffset !== 0 || byteLength !== void 0) {
4379
4380
  assertWebGL2Context(this.gl);
4380
- this.gl.bufferSubData(this.target, offset, data, srcOffset, byteLength);
4381
+ this.gl.bufferSubData(this.glTarget, offset, data, srcOffset, byteLength);
4381
4382
  } else {
4382
- this.gl.bufferSubData(target, offset, data);
4383
+ this.gl.bufferSubData(glTarget, offset, data);
4383
4384
  }
4384
- this.gl.bindBuffer(target, null);
4385
+ this.gl.bindBuffer(glTarget, null);
4385
4386
  this.debugData = null;
4386
4387
  this._inferType(data);
4387
4388
  return this;
@@ -4445,33 +4446,33 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4445
4446
  bind(options) {
4446
4447
  var _a, _b;
4447
4448
  const {
4448
- target = this.target,
4449
+ glTarget = this.glTarget,
4449
4450
  // target for the bind operation
4450
4451
  index = this.accessor && this.accessor.index,
4451
4452
  // index = index of target (indexed bind point)
4452
4453
  offset = 0,
4453
4454
  size
4454
4455
  } = options || {};
4455
- if (target === import_constants17.GL.UNIFORM_BUFFER || target === import_constants17.GL.TRANSFORM_FEEDBACK_BUFFER) {
4456
+ if (glTarget === import_constants17.GL.UNIFORM_BUFFER || glTarget === import_constants17.GL.TRANSFORM_FEEDBACK_BUFFER) {
4456
4457
  if (size !== void 0) {
4457
- (_a = this.gl2) == null ? void 0 : _a.bindBufferRange(target, index, this.handle, offset, size);
4458
+ (_a = this.gl2) == null ? void 0 : _a.bindBufferRange(glTarget, index, this.handle, offset, size);
4458
4459
  } else {
4459
4460
  (0, import_api19.assert)(offset === 0);
4460
- (_b = this.gl2) == null ? void 0 : _b.bindBufferBase(target, index, this.handle);
4461
+ (_b = this.gl2) == null ? void 0 : _b.bindBufferBase(glTarget, index, this.handle);
4461
4462
  }
4462
4463
  } else {
4463
- this.gl.bindBuffer(target, this.handle);
4464
+ this.gl.bindBuffer(glTarget, this.handle);
4464
4465
  }
4465
4466
  return this;
4466
4467
  }
4467
4468
  unbind(options) {
4468
4469
  var _a;
4469
- const { target = this.target, index = this.accessor && this.accessor.index } = options || {};
4470
- const isIndexedBuffer = target === import_constants17.GL.UNIFORM_BUFFER || target === import_constants17.GL.TRANSFORM_FEEDBACK_BUFFER;
4470
+ const { glTarget = this.glTarget, index = this.accessor && this.accessor.index } = options || {};
4471
+ const isIndexedBuffer = glTarget === import_constants17.GL.UNIFORM_BUFFER || glTarget === import_constants17.GL.TRANSFORM_FEEDBACK_BUFFER;
4471
4472
  if (isIndexedBuffer) {
4472
- (_a = this.gl2) == null ? void 0 : _a.bindBufferBase(target, index, null);
4473
+ (_a = this.gl2) == null ? void 0 : _a.bindBufferBase(glTarget, index, null);
4473
4474
  } else {
4474
- this.gl.bindBuffer(target, null);
4475
+ this.gl.bindBuffer(glTarget, null);
4475
4476
  }
4476
4477
  return this;
4477
4478
  }
@@ -4494,7 +4495,7 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4494
4495
  this.trackDeallocatedMemory();
4495
4496
  const target = this._getTarget();
4496
4497
  this.gl.bindBuffer(target, this.handle);
4497
- this.gl.bufferData(target, byteLength, this.webglUsage);
4498
+ this.gl.bufferData(target, byteLength, this.glUsage);
4498
4499
  this.gl.bufferSubData(target, offset, data);
4499
4500
  this.gl.bindBuffer(target, null);
4500
4501
  this.debugData = data.slice(0, DEBUG_DATA_LENGTH2);
@@ -4507,18 +4508,17 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4507
4508
  return this;
4508
4509
  }
4509
4510
  // Allocate a GPU buffer of specified size.
4510
- _setByteLength(byteLength, webglUsage = this.webglUsage) {
4511
+ _setByteLength(byteLength) {
4511
4512
  (0, import_api19.assert)(byteLength >= 0);
4512
4513
  this.trackDeallocatedMemory();
4513
4514
  let data = byteLength;
4514
4515
  if (byteLength === 0) {
4515
4516
  data = new Float32Array(0);
4516
4517
  }
4517
- const target = this._getTarget();
4518
- this.gl.bindBuffer(target, this.handle);
4519
- this.gl.bufferData(target, data, webglUsage);
4520
- this.gl.bindBuffer(target, null);
4521
- this.webglUsage = webglUsage;
4518
+ const glTarget = this._getTarget();
4519
+ this.gl.bindBuffer(glTarget, this.handle);
4520
+ this.gl.bufferData(glTarget, data, this.glUsage);
4521
+ this.gl.bindBuffer(glTarget, null);
4522
4522
  this.debugData = null;
4523
4523
  this.bytesUsed = byteLength;
4524
4524
  this.byteLength = byteLength;
@@ -4528,7 +4528,7 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4528
4528
  // Binding a buffer for the first time locks the type
4529
4529
  // In WebGL2, use GL.COPY_WRITE_BUFFER to avoid locking the type
4530
4530
  _getTarget() {
4531
- return this.gl.webgl2 ? import_constants17.GL.COPY_WRITE_BUFFER : this.target;
4531
+ return this.gl.webgl2 ? import_constants17.GL.COPY_WRITE_BUFFER : this.glTarget;
4532
4532
  }
4533
4533
  _getAvailableElementCount(srcByteOffset) {
4534
4534
  const ArrayType = getTypedArrayFromGLType(this.accessor.type || import_constants17.GL.FLOAT, { clamped: false });
@@ -4544,9 +4544,9 @@ var BufferWithAccessor = class extends WEBGLBuffer {
4544
4544
  }
4545
4545
  // RESOURCE METHODS
4546
4546
  getParameter(pname) {
4547
- this.gl.bindBuffer(this.target, this.handle);
4548
- const value = this.gl.getBufferParameter(this.target, pname);
4549
- this.gl.bindBuffer(this.target, null);
4547
+ this.gl.bindBuffer(this.glTarget, this.handle);
4548
+ const value = this.gl.getBufferParameter(this.glTarget, pname);
4549
+ this.gl.bindBuffer(this.glTarget, null);
4550
4550
  return value;
4551
4551
  }
4552
4552
  // DEPRECATIONS - v7.0
@@ -4643,8 +4643,8 @@ var WEBGLShader = class extends import_api20.Shader {
4643
4643
  }
4644
4644
  compilationInfo() {
4645
4645
  return __async(this, null, function* () {
4646
- const log9 = this.device.gl.getShaderInfoLog(this.handle);
4647
- return log9 ? parseShaderCompilerLog(log9) : [];
4646
+ const log10 = this.device.gl.getShaderInfoLog(this.handle);
4647
+ return log10 ? parseShaderCompilerLog(log10) : [];
4648
4648
  });
4649
4649
  }
4650
4650
  // PRIVATE METHODS
@@ -4794,10 +4794,11 @@ var WEBGLRenderPass = class extends import_api21.RenderPass {
4794
4794
  };
4795
4795
 
4796
4796
  // src/adapter/resources/webgl-render-pipeline.ts
4797
- var import_api23 = require("@luma.gl/api");
4797
+ var import_api24 = require("@luma.gl/api");
4798
4798
  var import_constants25 = require("@luma.gl/constants");
4799
4799
 
4800
4800
  // src/adapter/helpers/get-shader-layout.ts
4801
+ var import_api22 = require("@luma.gl/api");
4801
4802
  var import_constants22 = require("@luma.gl/constants");
4802
4803
 
4803
4804
  // src/adapter/helpers/uniforms.ts
@@ -4907,13 +4908,12 @@ function getDataFormat(type) {
4907
4908
 
4908
4909
  // src/adapter/helpers/get-shader-layout.ts
4909
4910
  function getShaderLayout(gl2, program) {
4910
- var _a, _b;
4911
- const programBindings = getProgramBindings(gl2, program);
4912
4911
  const shaderLayout = {
4913
4912
  attributes: [],
4914
4913
  bindings: []
4915
4914
  };
4916
- for (const attribute of programBindings.attributes) {
4915
+ const attributes = readAttributeBindings(gl2, program);
4916
+ for (const attribute of attributes) {
4917
4917
  const size = Math.min(attribute.accessor.size, 4);
4918
4918
  const format = (
4919
4919
  // attribute.accessor.format ||
@@ -4926,7 +4926,8 @@ function getShaderLayout(gl2, program) {
4926
4926
  stepMode: attribute.accessor.divisor === 1 ? "instance" : "vertex"
4927
4927
  });
4928
4928
  }
4929
- for (const uniformBlock of programBindings.uniformBlocks) {
4929
+ const uniformBlocks = readUniformBlocks(gl2, program);
4930
+ for (const uniformBlock of uniformBlocks) {
4930
4931
  const uniforms2 = uniformBlock.uniforms.map((uniform) => ({
4931
4932
  name: uniform.name,
4932
4933
  format: uniform.format,
@@ -4943,8 +4944,9 @@ function getShaderLayout(gl2, program) {
4943
4944
  uniforms: uniforms2
4944
4945
  });
4945
4946
  }
4947
+ const uniforms = readUniformBindings(gl2, program);
4946
4948
  let textureUnit = 0;
4947
- for (const uniform of programBindings.uniforms) {
4949
+ for (const uniform of uniforms) {
4948
4950
  if (isSamplerUniform(uniform.type)) {
4949
4951
  const { viewDimension, sampleType } = getSamplerInfo(uniform.type);
4950
4952
  shaderLayout.bindings.push({
@@ -4958,24 +4960,59 @@ function getShaderLayout(gl2, program) {
4958
4960
  textureUnit += 1;
4959
4961
  }
4960
4962
  }
4961
- const uniforms = ((_a = programBindings.uniforms) == null ? void 0 : _a.filter((uniform) => uniform.location !== null)) || [];
4962
4963
  if (uniforms.length) {
4963
4964
  shaderLayout.uniforms = uniforms;
4964
4965
  }
4965
- if ((_b = programBindings.varyings) == null ? void 0 : _b.length) {
4966
- shaderLayout.varyings = programBindings.varyings;
4966
+ const varyings = readVaryings(gl2, program);
4967
+ if (varyings == null ? void 0 : varyings.length) {
4968
+ shaderLayout.varyings = varyings;
4967
4969
  }
4968
4970
  return shaderLayout;
4969
4971
  }
4970
- function getProgramBindings(gl2, program) {
4971
- const config = {
4972
- attributes: readAttributeBindings(gl2, program),
4973
- uniforms: readUniformBindings(gl2, program),
4974
- uniformBlocks: readUniformBlocks(gl2, program),
4975
- varyings: readVaryings(gl2, program)
4976
- };
4977
- Object.seal(config);
4978
- return config;
4972
+ function mergeShaderLayout(baseLayout, overrideLayout) {
4973
+ const mergedLayout = __spreadProps(__spreadValues({}, baseLayout), {
4974
+ attributes: baseLayout.attributes.map((attribute) => __spreadValues({}, attribute))
4975
+ });
4976
+ for (const attribute of (overrideLayout == null ? void 0 : overrideLayout.attributes) || []) {
4977
+ const baseAttribute = mergedLayout.attributes.find((attr) => attr.name === attribute.name);
4978
+ if (!baseAttribute) {
4979
+ import_api22.log.warn(`shader layout attribute ${attribute.name} not present in shader`);
4980
+ } else {
4981
+ baseAttribute.format = attribute.format || baseAttribute.format;
4982
+ baseAttribute.stepMode = attribute.stepMode || baseAttribute.stepMode;
4983
+ }
4984
+ }
4985
+ return mergedLayout;
4986
+ }
4987
+ function mergeBufferMap(baseLayout, bufferMap) {
4988
+ const mergedLayout = __spreadProps(__spreadValues({}, baseLayout), {
4989
+ attributes: baseLayout.attributes.map((attribute) => __spreadValues({}, attribute))
4990
+ });
4991
+ for (const bufferMapping of bufferMap) {
4992
+ switch (bufferMapping.type) {
4993
+ case "interleave":
4994
+ for (const attributeOverride of bufferMapping.attributes) {
4995
+ overrideShaderLayoutAttribute(mergedLayout, attributeOverride);
4996
+ }
4997
+ break;
4998
+ default:
4999
+ overrideShaderLayoutAttribute(mergedLayout, bufferMapping);
5000
+ }
5001
+ }
5002
+ return mergedLayout;
5003
+ }
5004
+ function overrideShaderLayoutAttribute(layout, attributeOverride) {
5005
+ const attribute = getAttributeFromLayout(layout, attributeOverride.name);
5006
+ if (attribute && attributeOverride.format) {
5007
+ attribute.format = attributeOverride.format;
5008
+ }
5009
+ }
5010
+ function getAttributeFromLayout(shaderLayout, name) {
5011
+ const attribute = shaderLayout.attributes.find((attr) => attr.name === name);
5012
+ if (!attribute) {
5013
+ import_api22.log.warn(`shader layout attribute "${name}" not present in shader`);
5014
+ }
5015
+ return attribute || null;
4979
5016
  }
4980
5017
  function readAttributeBindings(gl2, program) {
4981
5018
  const attributes = [];
@@ -5231,16 +5268,31 @@ function setUniform(gl2, location, type, value) {
5231
5268
  }
5232
5269
 
5233
5270
  // src/adapter/objects/webgl-vertex-array-object.ts
5234
- var import_api22 = require("@luma.gl/api");
5271
+ var import_api23 = require("@luma.gl/api");
5235
5272
  var import_constants24 = require("@luma.gl/constants");
5236
- var import_env = require("@probe.gl/env");
5273
+ var import_env2 = require("@probe.gl/env");
5237
5274
  var ERR_ELEMENTS = "elements must be GL.ELEMENT_ARRAY_BUFFER";
5238
5275
  var WEBGLVertexArrayObject = class extends WebGLResource {
5276
+ // Create a VertexArray
5277
+ constructor(device, props) {
5278
+ super(device, props, __spreadProps(__spreadValues({}, import_api23.Resource.defaultProps), { constantAttributeZero: false }));
5279
+ /** Buffer constant */
5280
+ this.buffer = null;
5281
+ this.bufferValue = null;
5282
+ Object.seal(this);
5283
+ }
5239
5284
  get [Symbol.toStringTag]() {
5240
5285
  return "BaseVertexArrayObject";
5241
5286
  }
5242
- constructor(device, props) {
5243
- super(device, props, {});
5287
+ static isConstantAttributeZeroSupported(device) {
5288
+ return device.info.type === "webgl2" || (0, import_env2.getBrowser)() === "Chrome";
5289
+ }
5290
+ destroy() {
5291
+ var _a;
5292
+ super.destroy();
5293
+ if (this.buffer) {
5294
+ (_a = this.buffer) == null ? void 0 : _a.destroy();
5295
+ }
5244
5296
  }
5245
5297
  _createHandle() {
5246
5298
  return this.gl2.createVertexArray();
@@ -5252,19 +5304,35 @@ var WEBGLVertexArrayObject = class extends WebGLResource {
5252
5304
  _bindHandle(handle) {
5253
5305
  this.gl2.bindVertexArray(handle);
5254
5306
  }
5307
+ /**
5308
+ * Enabling an attribute location makes it reference the currently bound buffer
5309
+ * Disabling an attribute location makes it reference the global constant value
5310
+ * TODO - handle single values for size 1 attributes?
5311
+ * TODO - convert classic arrays based on known type?
5312
+ */
5313
+ enable(location, enable2 = true) {
5314
+ const canDisableAttributeZero = this.device.isWebGL2 || (0, import_env2.getBrowser)() === "Chrome";
5315
+ const canDisableAttribute = canDisableAttributeZero || location !== 0;
5316
+ if (enable2 || canDisableAttribute) {
5317
+ location = Number(location);
5318
+ this.bind(
5319
+ () => enable2 ? this.gl.enableVertexAttribArray(location) : this.gl.disableVertexAttribArray(location)
5320
+ );
5321
+ }
5322
+ }
5255
5323
  // Set (bind) an elements buffer, for indexed rendering.
5256
5324
  // Must be a Buffer bound to GL.ELEMENT_ARRAY_BUFFER. Constants not supported
5257
5325
  setElementBuffer(elementBuffer = null, opts = {}) {
5258
- (0, import_api22.assert)(!elementBuffer || elementBuffer.target === import_constants24.GL.ELEMENT_ARRAY_BUFFER, ERR_ELEMENTS);
5326
+ (0, import_api23.assert)(!elementBuffer || elementBuffer.glTarget === import_constants24.GL.ELEMENT_ARRAY_BUFFER, ERR_ELEMENTS);
5259
5327
  this.bind(() => {
5260
5328
  this.gl.bindBuffer(import_constants24.GL.ELEMENT_ARRAY_BUFFER, elementBuffer ? elementBuffer.handle : null);
5261
5329
  });
5262
- return this;
5263
5330
  }
5264
5331
  /** Set a location in vertex attributes array to a buffer, enables the location, sets divisor */
5265
5332
  setBuffer(location, buffer, accessor) {
5266
- if (buffer.target === import_constants24.GL.ELEMENT_ARRAY_BUFFER) {
5267
- return this.setElementBuffer(buffer, accessor);
5333
+ if (buffer.glTarget === import_constants24.GL.ELEMENT_ARRAY_BUFFER) {
5334
+ this.setElementBuffer(buffer, accessor);
5335
+ return;
5268
5336
  }
5269
5337
  const { size, type, stride, offset, normalized, integer, divisor } = accessor;
5270
5338
  const { gl: gl2, gl2: gl22 } = this;
@@ -5280,39 +5348,117 @@ var WEBGLVertexArrayObject = class extends WebGLResource {
5280
5348
  gl2.enableVertexAttribArray(location);
5281
5349
  gl22.vertexAttribDivisor(location, divisor || 0);
5282
5350
  });
5283
- return this;
5284
5351
  }
5285
5352
  /**
5286
- * Enabling an attribute location makes it reference the currently bound buffer
5287
- * Disabling an attribute location makes it reference the global constant value
5288
- * TODO - handle single values for size 1 attributes?
5289
- * TODO - convert classic arrays based on known type?
5353
+ * Set an attribute to a constant value
5354
+ * @param device
5355
+ * @param location
5356
+ * @param array
5357
+ *
5358
+ * @note Constants are stored globally on the WebGL context, not the VAO
5359
+ * so they need to be updated before every render
5360
+ * @todo - use known type (in configuration or passed in) to allow non-typed arrays?
5361
+ * @todo - remember/cache values to avoid setting them unnecessarily?
5290
5362
  */
5291
- enable(location, enable2 = true) {
5292
- const canDisableAttributeZero = this.device.isWebGL2 || (0, import_env.getBrowser)() === "Chrome";
5293
- const canDisableAttribute = canDisableAttributeZero || location !== 0;
5294
- if (enable2 || canDisableAttribute) {
5295
- location = Number(location);
5296
- this.bind(
5297
- () => enable2 ? this.gl.enableVertexAttribArray(location) : this.gl.disableVertexAttribArray(location)
5298
- );
5363
+ setConstant(location, array) {
5364
+ switch (array.constructor) {
5365
+ case Float32Array:
5366
+ setConstantFloatArray(this.device, location, array);
5367
+ break;
5368
+ case Int32Array:
5369
+ setConstantIntArray(this.device, location, array);
5370
+ break;
5371
+ case Uint32Array:
5372
+ setConstantUintArray(this.device, location, array);
5373
+ break;
5374
+ default:
5375
+ (0, import_api23.assert)(false);
5299
5376
  }
5300
- return this;
5377
+ }
5378
+ /**
5379
+ * Provide a means to create a buffer that is equivalent to a constant.
5380
+ * NOTE: Desktop OpenGL cannot disable attribute 0.
5381
+ * https://stackoverflow.com/questions/20305231/webgl-warning-attribute-0-is-disabled-
5382
+ * this-has-significant-performance-penalty
5383
+ */
5384
+ getConstantBuffer(elementCount, value) {
5385
+ const constantValue = normalizeConstantArrayValue(value);
5386
+ const byteLength = constantValue.byteLength * elementCount;
5387
+ const length = constantValue.length * elementCount;
5388
+ let updateNeeded = !this.buffer;
5389
+ this.buffer = this.buffer || this.device.createBuffer({ byteLength });
5390
+ updateNeeded = updateNeeded || this.buffer.reallocate(byteLength);
5391
+ updateNeeded = updateNeeded || !compareConstantArrayValues(constantValue, this.bufferValue);
5392
+ if (updateNeeded) {
5393
+ const typedArray = (0, import_api23.getScratchArray)(value.constructor, length);
5394
+ (0, import_api23.fillArray)({ target: typedArray, source: constantValue, start: 0, count: length });
5395
+ this.buffer.subData(typedArray);
5396
+ this.bufferValue = value;
5397
+ }
5398
+ return this.buffer;
5301
5399
  }
5302
5400
  };
5401
+ function setConstantFloatArray(device, location, array) {
5402
+ switch (array.length) {
5403
+ case 1:
5404
+ device.gl.vertexAttrib1fv(location, array);
5405
+ break;
5406
+ case 2:
5407
+ device.gl.vertexAttrib2fv(location, array);
5408
+ break;
5409
+ case 3:
5410
+ device.gl.vertexAttrib3fv(location, array);
5411
+ break;
5412
+ case 4:
5413
+ device.gl.vertexAttrib4fv(location, array);
5414
+ break;
5415
+ default:
5416
+ (0, import_api23.assert)(false);
5417
+ }
5418
+ }
5419
+ function setConstantIntArray(device, location, array) {
5420
+ var _a;
5421
+ device.assertWebGL2();
5422
+ (_a = device.gl2) == null ? void 0 : _a.vertexAttribI4iv(location, array);
5423
+ }
5424
+ function setConstantUintArray(device, location, array) {
5425
+ var _a;
5426
+ device.assertWebGL2();
5427
+ (_a = device.gl2) == null ? void 0 : _a.vertexAttribI4uiv(location, array);
5428
+ }
5429
+ function normalizeConstantArrayValue(arrayValue) {
5430
+ if (Array.isArray(arrayValue)) {
5431
+ return new Float32Array(arrayValue);
5432
+ }
5433
+ return arrayValue;
5434
+ }
5435
+ function compareConstantArrayValues(v1, v2) {
5436
+ if (!v1 || !v2 || v1.length !== v2.length || v1.constructor !== v2.constructor) {
5437
+ return false;
5438
+ }
5439
+ for (let i = 0; i < v1.length; ++i) {
5440
+ if (v1[i] !== v2[i]) {
5441
+ return false;
5442
+ }
5443
+ }
5444
+ return true;
5445
+ }
5303
5446
 
5304
5447
  // src/adapter/resources/webgl-render-pipeline.ts
5305
5448
  var LOG_PROGRAM_PERF_PRIORITY = 4;
5306
- var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5449
+ var WEBGLRenderPipeline = class extends import_api24.RenderPipeline {
5307
5450
  // TODO are these used?
5308
5451
  constructor(device, props) {
5309
5452
  var _a;
5310
5453
  super(device, props);
5311
- // configuration: ProgramConfiguration;
5312
- // Experimental flag to avoid deleting Program object while it is cached
5313
- this.varyings = null;
5454
+ /** Uniforms set on this model */
5314
5455
  this.uniforms = {};
5456
+ /** Bindings set on this model */
5315
5457
  this.bindings = {};
5458
+ /** Any constant attributes */
5459
+ this.constantAttributes = {};
5460
+ /** WebGL varyings */
5461
+ this.varyings = null;
5316
5462
  this._textureUniforms = {};
5317
5463
  this._textureIndexCounter = 0;
5318
5464
  this._uniformCount = 0;
@@ -5320,8 +5466,8 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5320
5466
  this.device = device;
5321
5467
  this.handle = this.props.handle || this.device.gl.createProgram();
5322
5468
  this.device.setSpectorMetadata(this.handle, { id: this.props.id });
5323
- this.vs = (0, import_api23.cast)(props.vs);
5324
- this.fs = (0, import_api23.cast)(props.fs);
5469
+ this.vs = (0, import_api24.cast)(props.vs);
5470
+ this.fs = (0, import_api24.cast)(props.fs);
5325
5471
  const { varyings, bufferMode = import_constants25.GL.SEPARATE_ATTRIBS } = props;
5326
5472
  if (varyings && varyings.length > 0) {
5327
5473
  this.device.assertWebGL2();
@@ -5329,7 +5475,10 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5329
5475
  (_a = this.device.gl2) == null ? void 0 : _a.transformFeedbackVaryings(this.handle, varyings, bufferMode);
5330
5476
  }
5331
5477
  this._compileAndLink();
5332
- this.layout = props.layout || getShaderLayout(this.device.gl, this.handle);
5478
+ this.introspectedLayout = getShaderLayout(this.device.gl, this.handle);
5479
+ this.layout = mergeShaderLayout(this.introspectedLayout, props.layout);
5480
+ this.bufferMap = props.bufferMap || [];
5481
+ this.layout = mergeBufferMap(this.layout, this.bufferMap);
5333
5482
  this.vertexArrayObject = new WEBGLVertexArrayObject(this.device);
5334
5483
  }
5335
5484
  destroy() {
@@ -5339,20 +5488,20 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5339
5488
  }
5340
5489
  }
5341
5490
  setIndexBuffer(indexBuffer) {
5342
- const webglBuffer = (0, import_api23.cast)(indexBuffer);
5491
+ const webglBuffer = (0, import_api24.cast)(indexBuffer);
5343
5492
  this.vertexArrayObject.setElementBuffer(webglBuffer);
5344
- this._indexBuffer = indexBuffer;
5493
+ this._indexBuffer = webglBuffer;
5345
5494
  }
5346
5495
  /** @todo needed for portable model */
5347
5496
  setAttributes(attributes) {
5348
5497
  for (const [name, buffer] of Object.entries(attributes)) {
5349
- const webglBuffer = (0, import_api23.cast)(buffer);
5498
+ const webglBuffer = (0, import_api24.cast)(buffer);
5350
5499
  const attribute = getAttributeLayout(this.layout, name);
5351
5500
  if (!attribute) {
5352
- import_api23.log.warn(`Ignoring buffer supplied for unknown attribute "${name}" in pipeline "${this.id}" (buffer "${buffer.id}")`)();
5501
+ import_api24.log.warn(`Ignoring buffer supplied for unknown attribute "${name}" in pipeline "${this.id}" (buffer "${buffer.id}")`)();
5353
5502
  continue;
5354
5503
  }
5355
- const decoded = (0, import_api23.decodeVertexFormat)(attribute.format);
5504
+ const decoded = (0, import_api24.decodeVertexFormat)(attribute.format);
5356
5505
  const { type: typeString, components: size, byteLength: stride, normalized, integer } = decoded;
5357
5506
  const divisor = attribute.stepMode === "instance" ? 1 : 0;
5358
5507
  const type = getWebGLDataType(typeString);
@@ -5367,16 +5516,36 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5367
5516
  });
5368
5517
  }
5369
5518
  }
5370
- /** @todo needed for portable model */
5519
+ /**
5520
+ * Constant attributes are only supported in WebGL, not in WebGPU
5521
+ * Any attribute that is disabled in the current vertex array object
5522
+ * is read from the context's global constant value for that attribute location.
5523
+ * @param attributes
5524
+ */
5525
+ setConstantAttributes(attributes) {
5526
+ for (const [name, value] of Object.entries(attributes)) {
5527
+ const attribute = getAttributeLayout(this.layout, name);
5528
+ if (!attribute) {
5529
+ import_api24.log.warn(`Ignoring constant value supplied for unknown attribute "${name}" in pipeline "${this.id}"`)();
5530
+ continue;
5531
+ }
5532
+ this.vertexArrayObject.setConstant(attribute.location, value);
5533
+ }
5534
+ Object.assign(this.constantAttributes, attributes);
5535
+ }
5536
+ /**
5537
+ * Bindings include: textures, samplers and uniform buffers
5538
+ * @todo needed for portable model
5539
+ */
5371
5540
  setBindings(bindings) {
5372
5541
  for (const [name, value] of Object.entries(bindings)) {
5373
5542
  const binding = this.layout.bindings.find((binding2) => binding2.name === name);
5374
5543
  if (!binding) {
5375
- import_api23.log.warn(`Unknown binding ${name} in render pipeline ${this.id}`)();
5544
+ import_api24.log.warn(`Unknown binding ${name} in render pipeline ${this.id}`)();
5376
5545
  continue;
5377
5546
  }
5378
5547
  if (!value) {
5379
- import_api23.log.warn(`Unsetting binding ${name} in render pipeline ${this.id}`)();
5548
+ import_api24.log.warn(`Unsetting binding ${name} in render pipeline ${this.id}`)();
5380
5549
  }
5381
5550
  switch (binding.type) {
5382
5551
  case "uniform":
@@ -5390,7 +5559,7 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5390
5559
  }
5391
5560
  break;
5392
5561
  case "sampler":
5393
- import_api23.log.warn(`Ignoring sampler ${name}`)();
5562
+ import_api24.log.warn(`Ignoring sampler ${name}`)();
5394
5563
  break;
5395
5564
  default:
5396
5565
  throw new Error(binding.type);
@@ -5419,7 +5588,7 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5419
5588
  } = options;
5420
5589
  const drawMode = getDrawMode(this.props.topology);
5421
5590
  const isIndexed = Boolean(this._indexBuffer);
5422
- const indexType = ((_a = this._indexBuffer) == null ? void 0 : _a.props.indexType) === "uint16" ? import_constants25.GL.UNSIGNED_SHORT : import_constants25.GL.UNSIGNED_INT;
5591
+ const indexType = (_a = this._indexBuffer) == null ? void 0 : _a.glIndexType;
5423
5592
  const isInstanced = Number(options.instanceCount) > 0;
5424
5593
  if (!this._areTexturesRenderable() || options.vertexCount === 0) {
5425
5594
  return false;
@@ -5433,6 +5602,7 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5433
5602
  }
5434
5603
  this._applyBindings();
5435
5604
  this._applyUniforms();
5605
+ this._applyConstantAttributes();
5436
5606
  const webglRenderPass = renderPass;
5437
5607
  withDeviceParameters(this.device, this.props.parameters, () => {
5438
5608
  withGLParameters(this.device, webglRenderPass.glParameters, () => {
@@ -5467,10 +5637,10 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5467
5637
  const { gl: gl2 } = this.device;
5468
5638
  gl2.attachShader(this.handle, this.vs.handle);
5469
5639
  gl2.attachShader(this.handle, this.fs.handle);
5470
- import_api23.log.time(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
5640
+ import_api24.log.time(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
5471
5641
  gl2.linkProgram(this.handle);
5472
- import_api23.log.timeEnd(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
5473
- if (gl2.debug || import_api23.log.level > 0) {
5642
+ import_api24.log.timeEnd(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
5643
+ if (gl2.debug || import_api24.log.level > 0) {
5474
5644
  const linked = gl2.getProgramParameter(this.handle, gl2.LINK_STATUS);
5475
5645
  if (!linked) {
5476
5646
  throw new Error(`Error linking: ${gl2.getProgramInfoLog(this.handle)}`);
@@ -5563,6 +5733,21 @@ var WEBGLRenderPipeline = class extends import_api23.RenderPipeline {
5563
5733
  }
5564
5734
  }
5565
5735
  }
5736
+ /**
5737
+ * Constant attributes are only supported in WebGL, not in WebGPU
5738
+ * Any attribute that is disabled in the current vertex array object
5739
+ * is read from the context's global constant value for that attribute location.
5740
+ */
5741
+ _applyConstantAttributes() {
5742
+ for (const [name, value] of Object.entries(this.constantAttributes)) {
5743
+ const attribute = getAttributeLayout(this.layout, name);
5744
+ if (!attribute) {
5745
+ import_api24.log.warn(`Ignoring constant value supplied for unknown attribute "${name}" in pipeline "${this.id}"`)();
5746
+ continue;
5747
+ }
5748
+ this.vertexArrayObject.setConstant(attribute.location, value);
5749
+ }
5750
+ }
5566
5751
  };
5567
5752
  function getDrawMode(topology) {
5568
5753
  switch (topology) {
@@ -5609,15 +5794,15 @@ function getAttributeLayout(layout, name) {
5609
5794
  }
5610
5795
 
5611
5796
  // src/adapter/resources/webgl-command-encoder.ts
5612
- var import_api25 = require("@luma.gl/api");
5797
+ var import_api26 = require("@luma.gl/api");
5613
5798
 
5614
5799
  // src/adapter/resources/webgl-command-buffer.ts
5615
- var import_api24 = require("@luma.gl/api");
5800
+ var import_api25 = require("@luma.gl/api");
5616
5801
  var import_constants26 = require("@luma.gl/constants");
5617
5802
  function cast3(value) {
5618
5803
  return value;
5619
5804
  }
5620
- var WEBGLCommandBuffer = class extends import_api24.CommandBuffer {
5805
+ var WEBGLCommandBuffer = class extends import_api25.CommandBuffer {
5621
5806
  constructor(device) {
5622
5807
  super({});
5623
5808
  this.commands = [];
@@ -5795,7 +5980,7 @@ function _copyTextureToTexture(device, options) {
5795
5980
  return texture;
5796
5981
  }
5797
5982
  function getFramebuffer(source) {
5798
- if (source instanceof import_api24.Texture) {
5983
+ if (source instanceof import_api25.Texture) {
5799
5984
  const { width, height, id } = source;
5800
5985
  const framebuffer = source.device.createFramebuffer({
5801
5986
  id: `framebuffer-for-${id}`,
@@ -5809,7 +5994,7 @@ function getFramebuffer(source) {
5809
5994
  }
5810
5995
 
5811
5996
  // src/adapter/resources/webgl-command-encoder.ts
5812
- var WEBGLCommandEncoder = class extends import_api25.CommandEncoder {
5997
+ var WEBGLCommandEncoder = class extends import_api26.CommandEncoder {
5813
5998
  constructor(device, props) {
5814
5999
  super(props);
5815
6000
  this.device = device;
@@ -5853,13 +6038,13 @@ var WEBGLCommandEncoder = class extends import_api25.CommandEncoder {
5853
6038
 
5854
6039
  // src/adapter/webgl-device.ts
5855
6040
  var LOG_LEVEL2 = 1;
5856
- var _WebGLDevice = class extends import_api26.Device {
6041
+ var _WebGLDevice = class extends import_api27.Device {
5857
6042
  //
5858
6043
  // Public API
5859
6044
  //
5860
6045
  constructor(props) {
5861
6046
  var _a;
5862
- super(__spreadProps(__spreadValues({}, props), { id: props.id || (0, import_api26.uid)("webgl-device") }));
6047
+ super(__spreadProps(__spreadValues({}, props), { id: props.id || (0, import_api27.uid)("webgl-device") }));
5863
6048
  this.renderPass = null;
5864
6049
  /** WebGL2 typed context. Need to check isWebGL2 or isWebGL1 before using. */
5865
6050
  this.gl2 = null;
@@ -5885,8 +6070,8 @@ var _WebGLDevice = class extends import_api26.Device {
5885
6070
  });
5886
6071
  };
5887
6072
  let gl2 = props.gl || null;
5888
- gl2 = gl2 || ((0, import_env2.isBrowser)() ? createBrowserContext(this.canvasContext.canvas, __spreadProps(__spreadValues({}, props), { onContextLost })) : null);
5889
- gl2 = gl2 || (!(0, import_env2.isBrowser)() ? createHeadlessContext(__spreadProps(__spreadValues({}, props), { onContextLost })) : null);
6073
+ gl2 = gl2 || ((0, import_env3.isBrowser)() ? createBrowserContext(this.canvasContext.canvas, __spreadProps(__spreadValues({}, props), { onContextLost })) : null);
6074
+ gl2 = gl2 || (!(0, import_env3.isBrowser)() ? createHeadlessContext(__spreadProps(__spreadValues({}, props), { onContextLost })) : null);
5890
6075
  if (!gl2) {
5891
6076
  throw new Error("WebGL context creation failed");
5892
6077
  }
@@ -5903,22 +6088,22 @@ var _WebGLDevice = class extends import_api26.Device {
5903
6088
  trackContextState(this.gl, {
5904
6089
  enable: enable2,
5905
6090
  copyState,
5906
- log: (...args) => import_api26.log.log(1, ...args)()
6091
+ log: (...args) => import_api27.log.log(1, ...args)()
5907
6092
  });
5908
- if ((0, import_env2.isBrowser)() && props.debug) {
6093
+ if ((0, import_env3.isBrowser)() && props.debug) {
5909
6094
  this.gl = makeDebugContext(this.gl, __spreadProps(__spreadValues({}, props), { webgl2: this.isWebGL2, throwOnError: true }));
5910
6095
  this.gl2 = this.gl;
5911
6096
  this.debug = true;
5912
- import_api26.log.level = Math.max(import_api26.log.level, 1);
5913
- import_api26.log.warn("WebGL debug mode activated. Performance reduced.")();
6097
+ import_api27.log.level = Math.max(import_api27.log.level, 1);
6098
+ import_api27.log.warn("WebGL debug mode activated. Performance reduced.")();
5914
6099
  }
5915
- if ((0, import_env2.isBrowser)() && props.spector) {
6100
+ if ((0, import_env3.isBrowser)() && props.spector) {
5916
6101
  const canvas = this.handle.canvas || props.canvas;
5917
6102
  this.spector = initializeSpectorJS(__spreadProps(__spreadValues({}, this.props), { canvas }));
5918
6103
  }
5919
6104
  const message2 = `Created ${this.info.type}${this.debug ? " debug" : ""} context: ${this.info.vendor}, ${this.info.renderer} for canvas: ${this.canvasContext.id}`;
5920
- import_api26.log.probe(LOG_LEVEL2, message2)();
5921
- import_api26.log.groupEnd(LOG_LEVEL2)();
6105
+ import_api27.log.probe(LOG_LEVEL2, message2)();
6106
+ import_api27.log.groupEnd(LOG_LEVEL2)();
5922
6107
  }
5923
6108
  static isSupported() {
5924
6109
  return typeof WebGLRenderingContext !== "undefined" || isHeadlessGLRegistered();
@@ -5944,7 +6129,7 @@ var _WebGLDevice = class extends import_api26.Device {
5944
6129
  if (gl2 instanceof _WebGLDevice) {
5945
6130
  return gl2;
5946
6131
  }
5947
- if ((gl2 == null ? void 0 : gl2.device) instanceof import_api26.Device) {
6132
+ if ((gl2 == null ? void 0 : gl2.device) instanceof import_api27.Device) {
5948
6133
  return gl2.device;
5949
6134
  }
5950
6135
  if (!isWebGL3(gl2)) {
@@ -5954,17 +6139,18 @@ var _WebGLDevice = class extends import_api26.Device {
5954
6139
  }
5955
6140
  static create() {
5956
6141
  return __async(this, arguments, function* (props = {}) {
5957
- import_api26.log.groupCollapsed(LOG_LEVEL2, "WebGLDevice created");
6142
+ import_api27.log.groupCollapsed(LOG_LEVEL2, "WebGLDevice created");
5958
6143
  if (typeof props.canvas === "string") {
5959
- yield import_api26.CanvasContext.pageLoaded;
6144
+ yield import_api27.CanvasContext.pageLoaded;
5960
6145
  }
5961
- if (props.debug) {
6146
+ if (import_api27.log.get("debug") || props.debug) {
5962
6147
  yield loadWebGLDeveloperTools();
5963
6148
  }
5964
- if (props.spector) {
6149
+ const { spector: spector2 } = props;
6150
+ if (import_api27.log.get("spector") || spector2) {
5965
6151
  yield loadSpectorJS();
5966
6152
  }
5967
- import_api26.log.probe(LOG_LEVEL2 + 1, "DOM is loaded")();
6153
+ import_api27.log.probe(LOG_LEVEL2 + 1, "DOM is loaded")();
5968
6154
  if (props.gl && props.gl.device) {
5969
6155
  return _WebGLDevice.attach(props.gl);
5970
6156
  }
@@ -6134,7 +6320,7 @@ function isWebGL22(gl2) {
6134
6320
  }
6135
6321
 
6136
6322
  // src/classic/clear.ts
6137
- var import_api27 = require("@luma.gl/api");
6323
+ var import_api28 = require("@luma.gl/api");
6138
6324
  var GL_DEPTH_BUFFER_BIT2 = 256;
6139
6325
  var GL_STENCIL_BUFFER_BIT2 = 1024;
6140
6326
  var GL_COLOR_BUFFER_BIT2 = 16384;
@@ -6165,18 +6351,18 @@ function clear(gl2, options) {
6165
6351
  parameters.clearStencil = depth;
6166
6352
  }
6167
6353
  }
6168
- (0, import_api27.assert)(clearFlags !== 0, ERR_ARGUMENTS);
6354
+ (0, import_api28.assert)(clearFlags !== 0, ERR_ARGUMENTS);
6169
6355
  withParameters(device.gl, parameters, () => {
6170
6356
  device.gl.clear(clearFlags);
6171
6357
  });
6172
6358
  }
6173
6359
 
6174
6360
  // src/classic/copy-and-blit.ts
6175
- var import_api29 = require("@luma.gl/api");
6361
+ var import_api30 = require("@luma.gl/api");
6176
6362
  var import_constants28 = require("@luma.gl/constants");
6177
6363
 
6178
6364
  // src/classic/format-utils.ts
6179
- var import_api28 = require("@luma.gl/api");
6365
+ var import_api29 = require("@luma.gl/api");
6180
6366
  var import_constants27 = require("@luma.gl/constants");
6181
6367
  function glFormatToComponents(format) {
6182
6368
  switch (format) {
@@ -6194,7 +6380,7 @@ function glFormatToComponents(format) {
6194
6380
  case import_constants27.GL.RGBA32F:
6195
6381
  return 4;
6196
6382
  default:
6197
- (0, import_api28.assert)(false);
6383
+ (0, import_api29.assert)(false);
6198
6384
  return 0;
6199
6385
  }
6200
6386
  }
@@ -6209,7 +6395,7 @@ function glTypeToBytes(type) {
6209
6395
  case import_constants27.GL.FLOAT:
6210
6396
  return 4;
6211
6397
  default:
6212
- (0, import_api28.assert)(false);
6398
+ (0, import_api29.assert)(false);
6213
6399
  return 0;
6214
6400
  }
6215
6401
  }
@@ -6227,7 +6413,7 @@ function readPixelsToArray(source, options) {
6227
6413
  sourceType
6228
6414
  } = options || {};
6229
6415
  const { framebuffer, deleteFramebuffer } = getFramebuffer2(source);
6230
- (0, import_api29.assert)(framebuffer);
6416
+ (0, import_api30.assert)(framebuffer);
6231
6417
  const { gl: gl2, handle } = framebuffer;
6232
6418
  sourceWidth = sourceWidth || framebuffer.width;
6233
6419
  sourceHeight = sourceHeight || framebuffer.height;
@@ -6250,7 +6436,7 @@ function readPixelsToBuffer(source, options) {
6250
6436
  const { sourceX = 0, sourceY = 0, sourceFormat = import_constants28.GL.RGBA, targetByteOffset = 0 } = options || {};
6251
6437
  let { target, sourceWidth, sourceHeight, sourceType } = options || {};
6252
6438
  const { framebuffer, deleteFramebuffer } = getFramebuffer2(source);
6253
- (0, import_api29.assert)(framebuffer);
6439
+ (0, import_api30.assert)(framebuffer);
6254
6440
  sourceWidth = sourceWidth || framebuffer.width;
6255
6441
  sourceHeight = sourceHeight || framebuffer.height;
6256
6442
  const webglFramebuffer = framebuffer;
@@ -6262,7 +6448,7 @@ function readPixelsToBuffer(source, options) {
6262
6448
  const byteLength = targetByteOffset + sourceWidth * sourceHeight * components * byteCount;
6263
6449
  target = new BufferWithAccessor(gl2, { byteLength, accessor: { type: sourceType, size: components } });
6264
6450
  }
6265
- target.bind({ target: import_constants28.GL.PIXEL_PACK_BUFFER });
6451
+ target.bind({ glTarget: import_constants28.GL.PIXEL_PACK_BUFFER });
6266
6452
  withParameters(gl2, { framebuffer }, () => {
6267
6453
  gl2.readPixels(
6268
6454
  sourceX,
@@ -6274,7 +6460,7 @@ function readPixelsToBuffer(source, options) {
6274
6460
  targetByteOffset
6275
6461
  );
6276
6462
  });
6277
- target.unbind({ target: import_constants28.GL.PIXEL_PACK_BUFFER });
6463
+ target.unbind({ glTarget: import_constants28.GL.PIXEL_PACK_BUFFER });
6278
6464
  if (deleteFramebuffer) {
6279
6465
  framebuffer.destroy();
6280
6466
  }
@@ -6298,7 +6484,7 @@ function copyToTexture(source, target, options) {
6298
6484
  // defaults to target height
6299
6485
  } = options || {};
6300
6486
  const { framebuffer, deleteFramebuffer } = getFramebuffer2(source);
6301
- (0, import_api29.assert)(framebuffer);
6487
+ (0, import_api30.assert)(framebuffer);
6302
6488
  const webglFramebuffer = framebuffer;
6303
6489
  const { device, handle } = webglFramebuffer;
6304
6490
  const isSubCopy = typeof targetX !== "undefined" || typeof targetY !== "undefined" || typeof targetZ !== "undefined";
@@ -6306,10 +6492,10 @@ function copyToTexture(source, target, options) {
6306
6492
  targetY = targetY || 0;
6307
6493
  targetZ = targetZ || 0;
6308
6494
  const prevHandle2 = device.gl.bindFramebuffer(import_constants28.GL.FRAMEBUFFER, handle);
6309
- (0, import_api29.assert)(target);
6495
+ (0, import_api30.assert)(target);
6310
6496
  let texture = null;
6311
6497
  let textureTarget;
6312
- if (target instanceof import_api29.Texture) {
6498
+ if (target instanceof import_api30.Texture) {
6313
6499
  texture = target;
6314
6500
  width = Number.isFinite(width) ? width : texture.width;
6315
6501
  height = Number.isFinite(height) ? height : texture.height;
@@ -6373,7 +6559,7 @@ function copyToTexture(source, target, options) {
6373
6559
  return texture;
6374
6560
  }
6375
6561
  function getFramebuffer2(source) {
6376
- if (!(source instanceof import_api29.Framebuffer)) {
6562
+ if (!(source instanceof import_api30.Framebuffer)) {
6377
6563
  return { framebuffer: toFramebuffer(source), deleteFramebuffer: true };
6378
6564
  }
6379
6565
  return { framebuffer: source, deleteFramebuffer: false };