@luma.gl/webgl 9.0.17 → 9.1.0-alpha.10

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 (144) hide show
  1. package/dist/adapter/converters/device-parameters.d.ts.map +1 -1
  2. package/dist/adapter/converters/device-parameters.js +30 -12
  3. package/dist/adapter/converters/texture-formats.d.ts +22 -16
  4. package/dist/adapter/converters/texture-formats.d.ts.map +1 -1
  5. package/dist/adapter/converters/texture-formats.js +39 -47
  6. package/dist/adapter/device-helpers/webgl-device-features.d.ts.map +1 -1
  7. package/dist/adapter/device-helpers/webgl-device-features.js +1 -2
  8. package/dist/adapter/device-helpers/webgl-device-limits.js +1 -1
  9. package/dist/adapter/helpers/webgl-texture-utils.d.ts +300 -0
  10. package/dist/adapter/helpers/webgl-texture-utils.d.ts.map +1 -0
  11. package/dist/adapter/helpers/webgl-texture-utils.js +370 -0
  12. package/dist/adapter/helpers/webgl-topology-utils.d.ts.map +1 -1
  13. package/dist/adapter/helpers/webgl-topology-utils.js +0 -4
  14. package/dist/adapter/resources/webgl-buffer.d.ts.map +1 -1
  15. package/dist/adapter/resources/webgl-buffer.js +2 -2
  16. package/dist/adapter/resources/webgl-command-buffer.d.ts.map +1 -1
  17. package/dist/adapter/resources/webgl-command-buffer.js +6 -9
  18. package/dist/adapter/resources/webgl-framebuffer.d.ts +32 -5
  19. package/dist/adapter/resources/webgl-framebuffer.d.ts.map +1 -1
  20. package/dist/adapter/resources/webgl-framebuffer.js +42 -60
  21. package/dist/adapter/resources/webgl-render-pass.d.ts +3 -2
  22. package/dist/adapter/resources/webgl-render-pass.d.ts.map +1 -1
  23. package/dist/adapter/resources/webgl-render-pass.js +18 -7
  24. package/dist/adapter/resources/webgl-render-pipeline.d.ts.map +1 -1
  25. package/dist/adapter/resources/webgl-render-pipeline.js +46 -21
  26. package/dist/adapter/resources/webgl-shader.d.ts.map +1 -1
  27. package/dist/adapter/resources/webgl-shader.js +3 -3
  28. package/dist/adapter/resources/webgl-texture-view.d.ts +1 -1
  29. package/dist/adapter/resources/webgl-texture-view.d.ts.map +1 -1
  30. package/dist/adapter/resources/webgl-texture-view.js +1 -1
  31. package/dist/adapter/resources/webgl-texture.d.ts +76 -172
  32. package/dist/adapter/resources/webgl-texture.d.ts.map +1 -1
  33. package/dist/adapter/resources/webgl-texture.js +397 -511
  34. package/dist/adapter/resources/webgl-vertex-array.d.ts +3 -2
  35. package/dist/adapter/resources/webgl-vertex-array.d.ts.map +1 -1
  36. package/dist/adapter/resources/webgl-vertex-array.js +2 -2
  37. package/dist/adapter/webgl-adapter.d.ts +21 -0
  38. package/dist/adapter/webgl-adapter.d.ts.map +1 -0
  39. package/dist/adapter/webgl-adapter.js +91 -0
  40. package/dist/adapter/webgl-canvas-context.d.ts +3 -1
  41. package/dist/adapter/webgl-canvas-context.d.ts.map +1 -1
  42. package/dist/adapter/webgl-canvas-context.js +2 -0
  43. package/dist/adapter/webgl-device.d.ts +19 -30
  44. package/dist/adapter/webgl-device.d.ts.map +1 -1
  45. package/dist/adapter/webgl-device.js +35 -114
  46. package/dist/classic/accessor.d.ts +22 -1
  47. package/dist/classic/accessor.d.ts.map +1 -1
  48. package/dist/classic/accessor.js +1 -9
  49. package/dist/classic/clear.d.ts.map +1 -1
  50. package/dist/classic/clear.js +2 -5
  51. package/dist/classic/copy-and-blit.d.ts +3 -1
  52. package/dist/classic/copy-and-blit.d.ts.map +1 -1
  53. package/dist/classic/copy-and-blit.js +21 -18
  54. package/dist/classic/format-utils.d.ts.map +1 -1
  55. package/dist/classic/format-utils.js +0 -3
  56. package/dist/classic/typed-array-utils.d.ts +1 -1
  57. package/dist/classic/typed-array-utils.d.ts.map +1 -1
  58. package/dist/context/debug/spector-types.d.ts +1108 -0
  59. package/dist/context/debug/spector-types.d.ts.map +1 -0
  60. package/dist/context/debug/spector-types.js +697 -0
  61. package/dist/context/debug/spector.d.ts +12 -8
  62. package/dist/context/debug/spector.d.ts.map +1 -1
  63. package/dist/context/debug/spector.js +25 -18
  64. package/dist/context/debug/webgl-developer-tools.d.ts +1 -1
  65. package/dist/context/debug/webgl-developer-tools.d.ts.map +1 -1
  66. package/dist/context/debug/webgl-developer-tools.js +2 -5
  67. package/dist/context/parameters/webgl-parameter-tables.js +1 -1
  68. package/dist/context/polyfills/polyfill-webgl1-extensions.d.ts +9 -0
  69. package/dist/context/polyfills/polyfill-webgl1-extensions.d.ts.map +1 -0
  70. package/dist/context/polyfills/polyfill-webgl1-extensions.js +181 -0
  71. package/dist/context/state-tracker/webgl-state-tracker.d.ts +43 -0
  72. package/dist/context/state-tracker/webgl-state-tracker.d.ts.map +1 -0
  73. package/dist/context/state-tracker/{track-context-state.js → webgl-state-tracker.js} +46 -77
  74. package/dist/context/state-tracker/with-parameters.d.ts.map +1 -1
  75. package/dist/context/state-tracker/with-parameters.js +5 -4
  76. package/dist/dist.dev.js +1112 -1380
  77. package/dist/dist.min.js +2 -2
  78. package/dist/index.cjs +1122 -1284
  79. package/dist/index.cjs.map +4 -4
  80. package/dist/index.d.ts +3 -5
  81. package/dist/index.d.ts.map +1 -1
  82. package/dist/index.js +3 -5
  83. package/dist/utils/fill-array.d.ts +8 -0
  84. package/dist/utils/fill-array.d.ts.map +1 -0
  85. package/dist/utils/fill-array.js +26 -0
  86. package/dist/utils/load-script.d.ts +8 -0
  87. package/dist/utils/load-script.d.ts.map +1 -0
  88. package/dist/utils/load-script.js +26 -0
  89. package/dist/utils/split-uniforms-and-bindings.d.ts +9 -0
  90. package/dist/utils/split-uniforms-and-bindings.d.ts.map +1 -0
  91. package/dist/utils/split-uniforms-and-bindings.js +20 -0
  92. package/dist/utils/uid.d.ts +7 -0
  93. package/dist/utils/uid.d.ts.map +1 -0
  94. package/dist/utils/uid.js +14 -0
  95. package/package.json +6 -5
  96. package/src/adapter/converters/device-parameters.ts +31 -13
  97. package/src/adapter/converters/texture-formats.ts +51 -56
  98. package/src/adapter/device-helpers/webgl-device-features.ts +1 -2
  99. package/src/adapter/device-helpers/webgl-device-limits.ts +1 -1
  100. package/src/adapter/helpers/webgl-texture-utils.ts +484 -0
  101. package/src/adapter/helpers/webgl-topology-utils.ts +0 -4
  102. package/src/adapter/resources/webgl-buffer.ts +2 -2
  103. package/src/adapter/resources/webgl-command-buffer.ts +8 -10
  104. package/src/adapter/resources/webgl-framebuffer.ts +22 -56
  105. package/src/adapter/resources/webgl-render-pass.ts +21 -9
  106. package/src/adapter/resources/webgl-render-pipeline.ts +50 -24
  107. package/src/adapter/resources/webgl-shader.ts +4 -4
  108. package/src/adapter/resources/webgl-texture-view.ts +1 -3
  109. package/src/adapter/resources/webgl-texture.ts +445 -784
  110. package/src/adapter/resources/webgl-vertex-array.ts +8 -7
  111. package/src/adapter/webgl-adapter.ts +113 -0
  112. package/src/adapter/webgl-canvas-context.ts +4 -1
  113. package/src/adapter/webgl-device.ts +40 -151
  114. package/src/classic/accessor.ts +31 -11
  115. package/src/classic/clear.ts +3 -6
  116. package/src/classic/copy-and-blit.ts +32 -27
  117. package/src/classic/format-utils.ts +0 -3
  118. package/src/classic/typed-array-utils.ts +1 -1
  119. package/src/context/debug/spector-types.ts +1154 -0
  120. package/src/context/debug/spector.ts +40 -30
  121. package/src/context/debug/webgl-developer-tools.ts +3 -7
  122. package/src/context/parameters/webgl-parameter-tables.ts +3 -3
  123. package/src/context/polyfills/polyfill-webgl1-extensions.ts +202 -0
  124. package/src/context/state-tracker/{track-context-state.ts → webgl-state-tracker.ts} +57 -97
  125. package/src/context/state-tracker/with-parameters.ts +5 -4
  126. package/src/index.ts +5 -13
  127. package/src/utils/fill-array.ts +35 -0
  128. package/src/utils/load-script.ts +30 -0
  129. package/src/utils/split-uniforms-and-bindings.ts +31 -0
  130. package/src/utils/uid.ts +16 -0
  131. package/dist/adapter/objects/constants-to-keys.d.ts +0 -3
  132. package/dist/adapter/objects/constants-to-keys.d.ts.map +0 -1
  133. package/dist/adapter/objects/constants-to-keys.js +0 -22
  134. package/dist/adapter/objects/webgl-renderbuffer.d.ts +0 -43
  135. package/dist/adapter/objects/webgl-renderbuffer.d.ts.map +0 -1
  136. package/dist/adapter/objects/webgl-renderbuffer.js +0 -95
  137. package/dist/adapter/objects/webgl-resource.d.ts +0 -32
  138. package/dist/adapter/objects/webgl-resource.d.ts.map +0 -1
  139. package/dist/adapter/objects/webgl-resource.js +0 -114
  140. package/dist/context/state-tracker/track-context-state.d.ts +0 -22
  141. package/dist/context/state-tracker/track-context-state.d.ts.map +0 -1
  142. package/src/adapter/objects/constants-to-keys.ts +0 -27
  143. package/src/adapter/objects/webgl-renderbuffer.ts +0 -132
  144. package/src/adapter/objects/webgl-resource.ts +0 -183
package/dist/dist.dev.js CHANGED
@@ -11,7 +11,6 @@ var __exports__ = (() => {
11
11
  var __getOwnPropNames = Object.getOwnPropertyNames;
12
12
  var __getProtoOf = Object.getPrototypeOf;
13
13
  var __hasOwnProp = Object.prototype.hasOwnProperty;
14
- var __defNormalProp = (obj, key, value) => key in obj ? __defProp(obj, key, { enumerable: true, configurable: true, writable: true, value }) : obj[key] = value;
15
14
  var __commonJS = (cb, mod) => function __require() {
16
15
  return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;
17
16
  };
@@ -37,10 +36,6 @@ var __exports__ = (() => {
37
36
  mod
38
37
  ));
39
38
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
40
- var __publicField = (obj, key, value) => {
41
- __defNormalProp(obj, typeof key !== "symbol" ? key + "" : key, value);
42
- return value;
43
- };
44
39
 
45
40
  // external-global-plugin:@luma.gl/core
46
41
  var require_core = __commonJS({
@@ -58,7 +53,6 @@ var __exports__ = (() => {
58
53
  WEBGLFramebuffer: () => WEBGLFramebuffer,
59
54
  WEBGLRenderPass: () => WEBGLRenderPass,
60
55
  WEBGLRenderPipeline: () => WEBGLRenderPipeline,
61
- WEBGLResource: () => WebGLResource,
62
56
  WEBGLSampler: () => WEBGLSampler,
63
57
  WEBGLShader: () => WEBGLShader,
64
58
  WEBGLTexture: () => WEBGLTexture,
@@ -66,28 +60,24 @@ var __exports__ = (() => {
66
60
  WEBGLVertexArray: () => WEBGLVertexArray,
67
61
  WebGLCanvasContext: () => WebGLCanvasContext,
68
62
  WebGLDevice: () => WebGLDevice,
69
- WebGLResource: () => WebGLResource,
63
+ WebGLStateTracker: () => WebGLStateTracker,
70
64
  _TEXTURE_FORMATS: () => TEXTURE_FORMATS,
71
- _WEBGLRenderbuffer: () => WEBGLRenderbuffer,
72
- convertGLToTextureFormat: () => convertGLToTextureFormat,
73
65
  getGLParameters: () => getGLParameters,
74
66
  getShaderLayout: () => getShaderLayout,
75
- popContextState: () => popContextState,
76
- pushContextState: () => pushContextState,
77
67
  resetGLParameters: () => resetGLParameters,
78
68
  setDeviceParameters: () => setDeviceParameters,
79
69
  setGLParameters: () => setGLParameters,
80
- trackContextState: () => trackContextState,
70
+ webgl2Adapter: () => webgl2Adapter,
81
71
  withDeviceParameters: () => withDeviceParameters,
82
72
  withGLParameters: () => withGLParameters
83
73
  });
84
74
  __reExport(bundle_exports, __toESM(require_core(), 1));
85
75
 
86
- // src/adapter/webgl-device.ts
87
- var import_core27 = __toESM(require_core(), 1);
76
+ // src/adapter/webgl-adapter.ts
77
+ var import_core23 = __toESM(require_core(), 1);
88
78
 
89
- // src/context/state-tracker/track-context-state.ts
90
- var import_core = __toESM(require_core(), 1);
79
+ // src/adapter/webgl-device.ts
80
+ var import_core22 = __toESM(require_core(), 1);
91
81
 
92
82
  // ../constants/src/webgl-constants.ts
93
83
  var GLEnum = /* @__PURE__ */ ((GLEnum2) => {
@@ -970,7 +960,7 @@ var __exports__ = (() => {
970
960
  lineWidth: (gl, value) => gl.lineWidth(value),
971
961
  polygonOffsetFill: (gl, value) => value ? gl.enable(32823 /* POLYGON_OFFSET_FILL */) : gl.disable(32823 /* POLYGON_OFFSET_FILL */),
972
962
  polygonOffset: (gl, value) => gl.polygonOffset(...value),
973
- sampleCoverage: (gl, value) => gl.sampleCoverage(...value),
963
+ sampleCoverage: (gl, value) => gl.sampleCoverage(value[0], value[1] || false),
974
964
  scissorTest: (gl, value) => value ? gl.enable(3089 /* SCISSOR_TEST */) : gl.disable(3089 /* SCISSOR_TEST */),
975
965
  scissor: (gl, value) => gl.scissor(...value),
976
966
  stencilTest: (gl, value) => value ? gl.enable(2960 /* STENCIL_TEST */) : gl.disable(2960 /* STENCIL_TEST */),
@@ -1316,24 +1306,22 @@ var __exports__ = (() => {
1316
1306
  return false;
1317
1307
  }
1318
1308
 
1319
- // src/context/state-tracker/track-context-state.ts
1320
- var GLState = class {
1309
+ // src/context/state-tracker/webgl-state-tracker.ts
1310
+ var WebGLStateTracker = class {
1311
+ static get(gl) {
1312
+ return gl.state;
1313
+ }
1321
1314
  gl;
1322
1315
  program = null;
1323
1316
  stateStack = [];
1324
1317
  enable = true;
1325
- cache;
1318
+ cache = null;
1326
1319
  log;
1327
- constructor(gl, {
1328
- copyState = false,
1329
- // Copy cache from params (slow) or initialize from WebGL defaults (fast)
1330
- log: log9 = () => {
1331
- }
1332
- // Logging function, called when gl parameter change calls are actually issued
1333
- } = {}) {
1320
+ initialized = false;
1321
+ constructor(gl, props) {
1334
1322
  this.gl = gl;
1335
- this.cache = copyState ? getGLParameters(gl) : Object.assign({}, GL_PARAMETER_DEFAULTS);
1336
- this.log = log9;
1323
+ this.log = props?.log || (() => {
1324
+ });
1337
1325
  this._updateCache = this._updateCache.bind(this);
1338
1326
  Object.seal(this);
1339
1327
  }
@@ -1341,11 +1329,33 @@ var __exports__ = (() => {
1341
1329
  this.stateStack.push({});
1342
1330
  }
1343
1331
  pop() {
1344
- (0, import_core.assert)(this.stateStack.length > 0);
1345
1332
  const oldValues = this.stateStack[this.stateStack.length - 1];
1346
1333
  setGLParameters(this.gl, oldValues);
1347
1334
  this.stateStack.pop();
1348
1335
  }
1336
+ /**
1337
+ * Initialize WebGL state caching on a context
1338
+ * can be called multiple times to enable/disable
1339
+ *
1340
+ * @note After calling this function, context state will be cached
1341
+ * .push() and .pop() will be available for saving,
1342
+ * temporarily modifying, and then restoring state.
1343
+ */
1344
+ trackState(gl, options) {
1345
+ this.cache = options.copyState ? getGLParameters(gl) : Object.assign({}, GL_PARAMETER_DEFAULTS);
1346
+ if (this.initialized) {
1347
+ throw new Error("WebGLStateTracker");
1348
+ }
1349
+ this.initialized = true;
1350
+ this.gl.state = this;
1351
+ installProgramSpy(gl);
1352
+ for (const key in GL_HOOKED_SETTERS) {
1353
+ const setter = GL_HOOKED_SETTERS[key];
1354
+ installSetterSpy(gl, key, setter);
1355
+ }
1356
+ installGetterOverride(gl, "getParameter");
1357
+ installGetterOverride(gl, "isEnabled");
1358
+ }
1349
1359
  /**
1350
1360
  // interceptor for context set functions - update our cache and our stack
1351
1361
  // values (Object) - the key values for this setter
@@ -1357,7 +1367,6 @@ var __exports__ = (() => {
1357
1367
  let oldValue;
1358
1368
  const oldValues = this.stateStack.length > 0 ? this.stateStack[this.stateStack.length - 1] : null;
1359
1369
  for (const key in values) {
1360
- (0, import_core.assert)(key !== void 0);
1361
1370
  const value = values[key];
1362
1371
  const cached = this.cache[key];
1363
1372
  if (!deepArrayEqual(value, cached)) {
@@ -1372,46 +1381,13 @@ var __exports__ = (() => {
1372
1381
  return { valueChanged, oldValue };
1373
1382
  }
1374
1383
  };
1375
- function getContextState(gl) {
1376
- return gl.state;
1377
- }
1378
- function trackContextState(gl, options) {
1379
- const { enable: enable2 = true, copyState } = options;
1380
- (0, import_core.assert)(copyState !== void 0);
1381
- if (!gl.state) {
1382
- gl.state = new GLState(gl, { copyState });
1383
- installProgramSpy(gl);
1384
- for (const key in GL_HOOKED_SETTERS) {
1385
- const setter = GL_HOOKED_SETTERS[key];
1386
- installSetterSpy(gl, key, setter);
1387
- }
1388
- installGetterOverride(gl, "getParameter");
1389
- installGetterOverride(gl, "isEnabled");
1390
- }
1391
- const glState = getContextState(gl);
1392
- glState.enable = enable2;
1393
- return gl;
1394
- }
1395
- function pushContextState(gl) {
1396
- let glState = getContextState(gl);
1397
- if (!glState) {
1398
- trackContextState(gl, { copyState: false });
1399
- glState = getContextState(gl);
1400
- }
1401
- glState.push();
1402
- }
1403
- function popContextState(gl) {
1404
- const glState = getContextState(gl);
1405
- (0, import_core.assert)(glState);
1406
- glState.pop();
1407
- }
1408
1384
  function installGetterOverride(gl, functionName) {
1409
1385
  const originalGetterFunc = gl[functionName].bind(gl);
1410
1386
  gl[functionName] = function get(pname) {
1411
1387
  if (pname === void 0 || NON_CACHE_PARAMETERS.has(pname)) {
1412
1388
  return originalGetterFunc(pname);
1413
1389
  }
1414
- const glState = getContextState(gl);
1390
+ const glState = WebGLStateTracker.get(gl);
1415
1391
  if (!(pname in glState.cache)) {
1416
1392
  glState.cache[pname] = originalGetterFunc(pname);
1417
1393
  }
@@ -1434,7 +1410,7 @@ var __exports__ = (() => {
1434
1410
  }
1435
1411
  const originalSetterFunc = gl[functionName].bind(gl);
1436
1412
  gl[functionName] = function set(...params) {
1437
- const glState = getContextState(gl);
1413
+ const glState = WebGLStateTracker.get(gl);
1438
1414
  const { valueChanged, oldValue } = setter(glState._updateCache, ...params);
1439
1415
  if (valueChanged) {
1440
1416
  originalSetterFunc(...params);
@@ -1449,7 +1425,7 @@ var __exports__ = (() => {
1449
1425
  function installProgramSpy(gl) {
1450
1426
  const originalUseProgram = gl.useProgram.bind(gl);
1451
1427
  gl.useProgram = function useProgramLuma(handle) {
1452
- const glState = getContextState(gl);
1428
+ const glState = WebGLStateTracker.get(gl);
1453
1429
  if (glState.program !== handle) {
1454
1430
  originalUseProgram(handle);
1455
1431
  glState.program = handle;
@@ -1573,10 +1549,10 @@ var __exports__ = (() => {
1573
1549
  }
1574
1550
 
1575
1551
  // src/adapter/device-helpers/webgl-device-features.ts
1576
- var import_core3 = __toESM(require_core(), 1);
1552
+ var import_core2 = __toESM(require_core(), 1);
1577
1553
 
1578
1554
  // src/adapter/converters/texture-formats.ts
1579
- var import_core2 = __toESM(require_core(), 1);
1555
+ var import_core = __toESM(require_core(), 1);
1580
1556
 
1581
1557
  // src/adapter/converters/vertex-formats.ts
1582
1558
  function getGLFromVertexType(dataType) {
@@ -1666,26 +1642,6 @@ var __exports__ = (() => {
1666
1642
  return textureExtensions.every((extension) => getWebGLExtension(gl, extension, extensions));
1667
1643
  }
1668
1644
  var TEXTURE_FORMATS = {
1669
- // Unsized formats that leave the precision up to the driver. TODO - Fix bpp constants
1670
- "rgb8unorm-unsized": {
1671
- gl: 6407 /* RGB */,
1672
- b: 4,
1673
- c: 2,
1674
- bpp: 4,
1675
- dataFormat: 6407 /* RGB */,
1676
- types: [5121 /* UNSIGNED_BYTE */, 33635 /* UNSIGNED_SHORT_5_6_5 */]
1677
- },
1678
- "rgba8unorm-unsized": {
1679
- gl: 6408 /* RGBA */,
1680
- b: 4,
1681
- c: 2,
1682
- bpp: 4,
1683
- dataFormat: 6408 /* RGBA */,
1684
- types: [5121 /* UNSIGNED_BYTE */, 32819 /* UNSIGNED_SHORT_4_4_4_4 */, 32820 /* UNSIGNED_SHORT_5_5_5_1 */]
1685
- },
1686
- // 'r8unorm-unsized': {gl: GL.LUMINANCE, b: 4, c: 2, bpp: 4},
1687
- // 'rgb8unorm-srgb-unsized': {gl: GL.SRGB_EXT, b: 4, c: 2, bpp: 4, gl1Ext: SRGB},
1688
- // 'rgba8unorm-srgb-unsized': {gl: GL.SRGB_ALPHA_EXT, b: 4, c: 2, bpp: 4, gl1Ext: SRGB},
1689
1645
  // 8-bit formats
1690
1646
  "r8unorm": { gl: 33321 /* R8 */, b: 1, c: 1, rb: true },
1691
1647
  "r8snorm": { gl: 36756 /* R8_SNORM */, b: 1, c: 1, render: snorm8_renderable },
@@ -1719,7 +1675,6 @@ var __exports__ = (() => {
1719
1675
  "bgra8unorm-srgb": { b: 4, c: 4 },
1720
1676
  "rg16uint": { gl: 33338 /* RG16UI */, b: 4, c: 1, bpp: 4 },
1721
1677
  "rg16sint": { gl: 33337 /* RG16I */, b: 4, c: 2, bpp: 4 },
1722
- // When using a WebGL 2 context and the EXT_color_buffer_float WebGL2 extension
1723
1678
  "rg16float": { gl: 33327 /* RG16F */, bpp: 4, b: 4, c: 2, render: float16_renderable, filter: float16_filterable, rb: true },
1724
1679
  "rg16unorm-webgl": { gl: 33324 /* RG16_EXT */, b: 2, c: 2, render: norm16_renderable },
1725
1680
  "rg16snorm-webgl": { gl: 36761 /* RG16_SNORM_EXT */, b: 2, c: 2, render: snorm16_renderable },
@@ -1801,17 +1756,6 @@ var __exports__ = (() => {
1801
1756
  dataFormat: 34041 /* DEPTH_STENCIL */,
1802
1757
  types: [34042 /* UNSIGNED_INT_24_8 */]
1803
1758
  },
1804
- // "depth24unorm-stencil8" feature
1805
- "depth24unorm-stencil8": {
1806
- gl: 35056 /* DEPTH24_STENCIL8 */,
1807
- b: 4,
1808
- c: 2,
1809
- p: 1,
1810
- attachment: 33306 /* DEPTH_STENCIL_ATTACHMENT */,
1811
- dataFormat: 34041 /* DEPTH_STENCIL */,
1812
- types: [34042 /* UNSIGNED_INT_24_8 */],
1813
- rb: true
1814
- },
1815
1759
  // "depth32float-stencil8" feature - TODO below is render buffer only?
1816
1760
  "depth32float-stencil8": {
1817
1761
  gl: 36013 /* DEPTH32F_STENCIL8 */,
@@ -1926,33 +1870,16 @@ var __exports__ = (() => {
1926
1870
  if (info.gl === void 0) {
1927
1871
  return false;
1928
1872
  }
1873
+ const feature = info.f;
1874
+ if (feature) {
1875
+ return checkTextureFeature(gl, feature, extensions);
1876
+ }
1929
1877
  const extension = info.x || info.gl2ext;
1930
1878
  if (extension) {
1931
1879
  return Boolean(getWebGLExtension(gl, extension, extensions));
1932
1880
  }
1933
1881
  return true;
1934
1882
  }
1935
- function isRenderbufferFormatSupported(gl, format, extensions) {
1936
- return isTextureFormatSupported(gl, format, extensions) && TEXTURE_FORMATS[format]?.rb;
1937
- }
1938
- function convertGLToTextureFormat(format) {
1939
- if (typeof format === "string") {
1940
- return format;
1941
- }
1942
- const entry = Object.entries(TEXTURE_FORMATS).find(([, entry2]) => entry2.gl === format);
1943
- if (!entry) {
1944
- throw new Error(`Unknown texture format ${format}`);
1945
- }
1946
- return entry[0];
1947
- }
1948
- function convertTextureFormatToGL(format) {
1949
- const formatInfo = TEXTURE_FORMATS[format];
1950
- const webglFormat = formatInfo?.gl;
1951
- if (webglFormat === void 0) {
1952
- throw new Error(`Unsupported texture format ${format}`);
1953
- }
1954
- return webglFormat;
1955
- }
1956
1883
  function isTextureFormatFilterable(gl, format, extensions) {
1957
1884
  if (!isTextureFormatSupported(gl, format, extensions)) {
1958
1885
  return false;
@@ -1961,7 +1888,7 @@ var __exports__ = (() => {
1961
1888
  return false;
1962
1889
  }
1963
1890
  try {
1964
- const decoded = (0, import_core2.decodeTextureFormat)(format);
1891
+ const decoded = (0, import_core.decodeTextureFormat)(format);
1965
1892
  if (decoded.signed) {
1966
1893
  return false;
1967
1894
  }
@@ -1985,17 +1912,16 @@ var __exports__ = (() => {
1985
1912
  }
1986
1913
  return true;
1987
1914
  }
1988
- function getWebGLTextureParameters(format) {
1915
+ function getTextureFormatWebGL(format) {
1989
1916
  const formatData = TEXTURE_FORMATS[format];
1990
1917
  const webglFormat = convertTextureFormatToGL(format);
1991
- const decoded = (0, import_core2.decodeTextureFormat)(format);
1918
+ const decoded = (0, import_core.decodeTextureFormat)(format);
1992
1919
  return {
1993
- format: webglFormat,
1994
- dataFormat: formatData?.dataFormat || getWebGLPixelDataFormat(decoded.format, decoded.integer, decoded.normalized, webglFormat),
1920
+ internalFormat: webglFormat,
1921
+ format: formatData?.dataFormat || getWebGLPixelDataFormat(decoded.channels, decoded.integer, decoded.normalized, webglFormat),
1995
1922
  // depth formats don't have a type
1996
1923
  type: decoded.dataType ? getGLFromVertexType(decoded.dataType) : formatData?.types?.[0] || 5121 /* UNSIGNED_BYTE */,
1997
- // @ts-expect-error
1998
- compressed: decoded.compressed
1924
+ compressed: decoded.compressed || false
1999
1925
  };
2000
1926
  }
2001
1927
  function getDepthStencilAttachmentWebGL(format) {
@@ -2005,17 +1931,11 @@ var __exports__ = (() => {
2005
1931
  }
2006
1932
  return info.attachment;
2007
1933
  }
2008
- function getTextureFormatBytesPerPixel(format) {
2009
- const params = getWebGLTextureParameters(format);
2010
- const channels = DATA_FORMAT_CHANNELS[params.dataFormat] || 4;
2011
- const channelSize = TYPE_SIZES[params.type] || 1;
2012
- return channels * channelSize;
2013
- }
2014
- function getWebGLPixelDataFormat(dataFormat, integer, normalized, format) {
1934
+ function getWebGLPixelDataFormat(channels, integer, normalized, format) {
2015
1935
  if (format === 6408 /* RGBA */ || format === 6407 /* RGB */) {
2016
1936
  return format;
2017
1937
  }
2018
- switch (dataFormat) {
1938
+ switch (channels) {
2019
1939
  case "r":
2020
1940
  return integer && !normalized ? 36244 /* RED_INTEGER */ : 6403 /* RED */;
2021
1941
  case "rg":
@@ -2024,10 +1944,20 @@ var __exports__ = (() => {
2024
1944
  return integer && !normalized ? 36248 /* RGB_INTEGER */ : 6407 /* RGB */;
2025
1945
  case "rgba":
2026
1946
  return integer && !normalized ? 36249 /* RGBA_INTEGER */ : 6408 /* RGBA */;
1947
+ case "bgra":
1948
+ throw new Error("bgra pixels not supported by WebGL");
2027
1949
  default:
2028
1950
  return 6408 /* RGBA */;
2029
1951
  }
2030
1952
  }
1953
+ function convertTextureFormatToGL(format) {
1954
+ const formatInfo = TEXTURE_FORMATS[format];
1955
+ const webglFormat = formatInfo?.gl;
1956
+ if (webglFormat === void 0) {
1957
+ throw new Error(`Unsupported texture format ${format}`);
1958
+ }
1959
+ return webglFormat;
1960
+ }
2031
1961
 
2032
1962
  // src/adapter/device-helpers/webgl-device-features.ts
2033
1963
  var WEBGL_FEATURES = {
@@ -2037,7 +1967,6 @@ var __exports__ = (() => {
2037
1967
  // 'timestamp-query' // GPUQueryType "timestamp-query"
2038
1968
  // "indirect-first-instance"
2039
1969
  // Textures are handled by getTextureFeatures()
2040
- // 'depth24unorm-stencil8' // GPUTextureFormat 'depth24unorm-stencil8'
2041
1970
  // 'depth32float-stencil8' // GPUTextureFormat 'depth32float-stencil8'
2042
1971
  // optional WebGL features
2043
1972
  "timer-query-webgl": "EXT_disjoint_timer_query_webgl2",
@@ -2049,7 +1978,7 @@ var __exports__ = (() => {
2049
1978
  "shader-conservative-depth-webgl": "EXT_conservative_depth"
2050
1979
  // Textures are handled by getTextureFeatures()
2051
1980
  };
2052
- var WebGLDeviceFeatures = class extends import_core3.DeviceFeatures {
1981
+ var WebGLDeviceFeatures = class extends import_core2.DeviceFeatures {
2053
1982
  gl;
2054
1983
  extensions;
2055
1984
  testedFeatures = /* @__PURE__ */ new Set();
@@ -2069,7 +1998,7 @@ var __exports__ = (() => {
2069
1998
  return [];
2070
1999
  }
2071
2000
  has(feature) {
2072
- if (this.disabledFeatures[feature]) {
2001
+ if (this.disabledFeatures?.[feature]) {
2073
2002
  return false;
2074
2003
  }
2075
2004
  if (!this.testedFeatures.has(feature)) {
@@ -2103,8 +2032,8 @@ var __exports__ = (() => {
2103
2032
  };
2104
2033
 
2105
2034
  // src/adapter/device-helpers/webgl-device-limits.ts
2106
- var import_core4 = __toESM(require_core(), 1);
2107
- var WebGLDeviceLimits = class extends import_core4.DeviceLimits {
2035
+ var import_core3 = __toESM(require_core(), 1);
2036
+ var WebGLDeviceLimits = class extends import_core3.DeviceLimits {
2108
2037
  get maxTextureDimension1D() {
2109
2038
  return 0;
2110
2039
  }
@@ -2208,18 +2137,18 @@ var __exports__ = (() => {
2208
2137
  if (this.limits[parameter] === void 0) {
2209
2138
  this.limits[parameter] = this.gl.getParameter(parameter);
2210
2139
  }
2211
- return this.limits[parameter];
2140
+ return this.limits[parameter] || 0;
2212
2141
  }
2213
2142
  };
2214
2143
 
2215
2144
  // src/adapter/webgl-canvas-context.ts
2216
- var import_core11 = __toESM(require_core(), 1);
2145
+ var import_core9 = __toESM(require_core(), 1);
2217
2146
 
2218
2147
  // src/adapter/resources/webgl-framebuffer.ts
2219
- var import_core10 = __toESM(require_core(), 1);
2148
+ var import_core8 = __toESM(require_core(), 1);
2220
2149
 
2221
2150
  // src/adapter/resources/webgl-texture.ts
2222
- var import_core9 = __toESM(require_core(), 1);
2151
+ var import_core7 = __toESM(require_core(), 1);
2223
2152
 
2224
2153
  // src/context/state-tracker/with-parameters.ts
2225
2154
  function withGLParameters(gl, parameters, func) {
@@ -2227,17 +2156,18 @@ var __exports__ = (() => {
2227
2156
  return func(gl);
2228
2157
  }
2229
2158
  const { nocatch = true } = parameters;
2230
- pushContextState(gl);
2159
+ const webglState = WebGLStateTracker.get(gl);
2160
+ webglState.push();
2231
2161
  setGLParameters(gl, parameters);
2232
2162
  let value;
2233
2163
  if (nocatch) {
2234
2164
  value = func(gl);
2235
- popContextState(gl);
2165
+ webglState.pop();
2236
2166
  } else {
2237
2167
  try {
2238
2168
  value = func(gl);
2239
2169
  } finally {
2240
- popContextState(gl);
2170
+ webglState.pop();
2241
2171
  }
2242
2172
  }
2243
2173
  return value;
@@ -2250,31 +2180,32 @@ var __exports__ = (() => {
2250
2180
  }
2251
2181
 
2252
2182
  // src/adapter/converters/device-parameters.ts
2253
- var import_core5 = __toESM(require_core(), 1);
2183
+ var import_core4 = __toESM(require_core(), 1);
2254
2184
  function withDeviceAndGLParameters(device, parameters, glParameters, func) {
2255
- if ((0, import_core5.isObjectEmpty)(parameters)) {
2185
+ if (isObjectEmpty3(parameters)) {
2256
2186
  return func(device);
2257
2187
  }
2258
2188
  const webglDevice = device;
2259
- pushContextState(webglDevice.gl);
2189
+ webglDevice.pushState();
2260
2190
  try {
2261
2191
  setDeviceParameters(device, parameters);
2262
2192
  setGLParameters(webglDevice.gl, glParameters);
2263
2193
  return func(device);
2264
2194
  } finally {
2265
- popContextState(webglDevice.gl);
2195
+ webglDevice.popState();
2266
2196
  }
2267
2197
  }
2268
2198
  function withDeviceParameters(device, parameters, func) {
2269
- if ((0, import_core5.isObjectEmpty)(parameters)) {
2199
+ if (isObjectEmpty3(parameters)) {
2270
2200
  return func(device);
2271
2201
  }
2272
- pushContextState(device.gl);
2202
+ const webglDevice = device;
2203
+ webglDevice.pushState();
2273
2204
  try {
2274
2205
  setDeviceParameters(device, parameters);
2275
2206
  return func(device);
2276
2207
  } finally {
2277
- popContextState(device.gl);
2208
+ webglDevice.popState();
2278
2209
  }
2279
2210
  }
2280
2211
  function setDeviceParameters(device, parameters) {
@@ -2383,7 +2314,7 @@ var __exports__ = (() => {
2383
2314
  gl.stencilMaskSeparate(1029 /* BACK */, mask);
2384
2315
  }
2385
2316
  if (parameters.stencilReadMask) {
2386
- import_core5.log.warn("stencilReadMask not supported under WebGL");
2317
+ import_core4.log.warn("stencilReadMask not supported under WebGL");
2387
2318
  }
2388
2319
  if (parameters.stencilCompare) {
2389
2320
  const mask = parameters.stencilReadMask || 4294967295;
@@ -2402,8 +2333,16 @@ var __exports__ = (() => {
2402
2333
  gl.stencilOpSeparate(1028 /* FRONT */, sfail, dpfail, dppass);
2403
2334
  gl.stencilOpSeparate(1029 /* BACK */, sfail, dpfail, dppass);
2404
2335
  }
2336
+ switch (parameters.blend) {
2337
+ case true:
2338
+ gl.enable(3042 /* BLEND */);
2339
+ break;
2340
+ case false:
2341
+ gl.disable(3042 /* BLEND */);
2342
+ break;
2343
+ default:
2344
+ }
2405
2345
  if (parameters.blendColorOperation || parameters.blendAlphaOperation) {
2406
- gl.enable(3042 /* BLEND */);
2407
2346
  const colorEquation = convertBlendOperationToEquation(
2408
2347
  "blendColorOperation",
2409
2348
  parameters.blendColorOperation || "add"
@@ -2496,6 +2435,14 @@ var __exports__ = (() => {
2496
2435
  function mapBoolean(parameter, value) {
2497
2436
  return value;
2498
2437
  }
2438
+ function isObjectEmpty3(obj) {
2439
+ let isEmpty = true;
2440
+ for (const key in obj) {
2441
+ isEmpty = false;
2442
+ break;
2443
+ }
2444
+ return isEmpty;
2445
+ }
2499
2446
 
2500
2447
  // src/adapter/converters/sampler-parameters.ts
2501
2448
  function convertSamplerParametersToWebGL(props) {
@@ -2565,134 +2512,9 @@ var __exports__ = (() => {
2565
2512
  }
2566
2513
  }
2567
2514
 
2568
- // src/adapter/resources/webgl-buffer.ts
2569
- var import_core6 = __toESM(require_core(), 1);
2570
- var WEBGLBuffer = class extends import_core6.Buffer {
2571
- device;
2572
- gl;
2573
- handle;
2574
- /** Target in OpenGL defines the type of buffer */
2575
- glTarget;
2576
- /** Usage is a hint on how frequently the buffer will be updates */
2577
- glUsage;
2578
- /** Index type is needed when issuing draw calls, so we pre-compute it */
2579
- glIndexType = 5123 /* UNSIGNED_SHORT */;
2580
- /** Number of bytes allocated on the GPU for this buffer */
2581
- byteLength;
2582
- /** Number of bytes used */
2583
- bytesUsed;
2584
- constructor(device, props = {}) {
2585
- super(device, props);
2586
- this.device = device;
2587
- this.gl = this.device.gl;
2588
- const handle = typeof props === "object" ? props.handle : void 0;
2589
- this.handle = handle || this.gl.createBuffer();
2590
- device.setSpectorMetadata(this.handle, { ...this.props, data: typeof this.props.data });
2591
- this.glTarget = getWebGLTarget(this.props.usage);
2592
- this.glUsage = getWebGLUsage(this.props.usage);
2593
- this.glIndexType = this.props.indexType === "uint32" ? 5125 /* UNSIGNED_INT */ : 5123 /* UNSIGNED_SHORT */;
2594
- if (props.data) {
2595
- this._initWithData(props.data, props.byteOffset, props.byteLength);
2596
- } else {
2597
- this._initWithByteLength(props.byteLength || 0);
2598
- }
2599
- }
2600
- // PRIVATE METHODS
2601
- /** Allocate a new buffer and initialize to contents of typed array */
2602
- _initWithData(data, byteOffset = 0, byteLength = data.byteLength + byteOffset) {
2603
- const glTarget = this.glTarget;
2604
- this.gl.bindBuffer(glTarget, this.handle);
2605
- this.gl.bufferData(glTarget, byteLength, this.glUsage);
2606
- this.gl.bufferSubData(glTarget, byteOffset, data);
2607
- this.gl.bindBuffer(glTarget, null);
2608
- this.bytesUsed = byteLength;
2609
- this.byteLength = byteLength;
2610
- this._setDebugData(data, byteOffset, byteLength);
2611
- this.trackAllocatedMemory(byteLength);
2612
- }
2613
- // Allocate a GPU buffer of specified size.
2614
- _initWithByteLength(byteLength) {
2615
- (0, import_core6.assert)(byteLength >= 0);
2616
- let data = byteLength;
2617
- if (byteLength === 0) {
2618
- data = new Float32Array(0);
2619
- }
2620
- const glTarget = this.glTarget;
2621
- this.gl.bindBuffer(glTarget, this.handle);
2622
- this.gl.bufferData(glTarget, data, this.glUsage);
2623
- this.gl.bindBuffer(glTarget, null);
2624
- this.bytesUsed = byteLength;
2625
- this.byteLength = byteLength;
2626
- this._setDebugData(null, 0, byteLength);
2627
- this.trackAllocatedMemory(byteLength);
2628
- return this;
2629
- }
2630
- destroy() {
2631
- if (!this.destroyed && this.handle) {
2632
- this.removeStats();
2633
- this.trackDeallocatedMemory();
2634
- this.gl.deleteBuffer(this.handle);
2635
- this.destroyed = true;
2636
- this.handle = null;
2637
- }
2638
- }
2639
- write(data, byteOffset = 0) {
2640
- const srcOffset = 0;
2641
- const byteLength = void 0;
2642
- const glTarget = 36663 /* COPY_WRITE_BUFFER */;
2643
- this.gl.bindBuffer(glTarget, this.handle);
2644
- if (srcOffset !== 0 || byteLength !== void 0) {
2645
- this.gl.bufferSubData(glTarget, byteOffset, data, srcOffset, byteLength);
2646
- } else {
2647
- this.gl.bufferSubData(glTarget, byteOffset, data);
2648
- }
2649
- this.gl.bindBuffer(glTarget, null);
2650
- this._setDebugData(data, byteOffset, data.byteLength);
2651
- }
2652
- /** Asynchronously read data from the buffer */
2653
- async readAsync(byteOffset = 0, byteLength) {
2654
- return this.readSyncWebGL(byteOffset, byteLength);
2655
- }
2656
- /** Synchronously read data from the buffer. WebGL only. */
2657
- readSyncWebGL(byteOffset = 0, byteLength) {
2658
- byteLength = byteLength ?? this.byteLength - byteOffset;
2659
- const data = new Uint8Array(byteLength);
2660
- const dstOffset = 0;
2661
- this.gl.bindBuffer(36662 /* COPY_READ_BUFFER */, this.handle);
2662
- this.gl.getBufferSubData(36662 /* COPY_READ_BUFFER */, byteOffset, data, dstOffset, byteLength);
2663
- this.gl.bindBuffer(36662 /* COPY_READ_BUFFER */, null);
2664
- this._setDebugData(data, byteOffset, byteLength);
2665
- return data;
2666
- }
2667
- };
2668
- function getWebGLTarget(usage) {
2669
- if (usage & import_core6.Buffer.INDEX) {
2670
- return 34963 /* ELEMENT_ARRAY_BUFFER */;
2671
- }
2672
- if (usage & import_core6.Buffer.VERTEX) {
2673
- return 34962 /* ARRAY_BUFFER */;
2674
- }
2675
- if (usage & import_core6.Buffer.UNIFORM) {
2676
- return 35345 /* UNIFORM_BUFFER */;
2677
- }
2678
- return 34962 /* ARRAY_BUFFER */;
2679
- }
2680
- function getWebGLUsage(usage) {
2681
- if (usage & import_core6.Buffer.INDEX) {
2682
- return 35044 /* STATIC_DRAW */;
2683
- }
2684
- if (usage & import_core6.Buffer.VERTEX) {
2685
- return 35044 /* STATIC_DRAW */;
2686
- }
2687
- if (usage & import_core6.Buffer.UNIFORM) {
2688
- return 35048 /* DYNAMIC_DRAW */;
2689
- }
2690
- return 35044 /* STATIC_DRAW */;
2691
- }
2692
-
2693
2515
  // src/adapter/resources/webgl-sampler.ts
2694
- var import_core7 = __toESM(require_core(), 1);
2695
- var WEBGLSampler = class extends import_core7.Sampler {
2516
+ var import_core5 = __toESM(require_core(), 1);
2517
+ var WEBGLSampler = class extends import_core5.Sampler {
2696
2518
  device;
2697
2519
  handle;
2698
2520
  parameters;
@@ -2730,14 +2552,15 @@ var __exports__ = (() => {
2730
2552
  };
2731
2553
 
2732
2554
  // src/adapter/resources/webgl-texture-view.ts
2733
- var import_core8 = __toESM(require_core(), 1);
2734
- var WEBGLTextureView = class extends import_core8.TextureView {
2555
+ var import_core6 = __toESM(require_core(), 1);
2556
+ var WEBGLTextureView = class extends import_core6.TextureView {
2735
2557
  device;
2736
2558
  gl;
2737
2559
  handle;
2560
+ // Does not have a WebGL representation
2738
2561
  texture;
2739
2562
  constructor(device, props) {
2740
- super(device, { ...import_core8.Texture.defaultProps, ...props });
2563
+ super(device, { ...import_core6.Texture.defaultProps, ...props });
2741
2564
  this.device = device;
2742
2565
  this.gl = this.device.gl;
2743
2566
  this.handle = null;
@@ -2745,167 +2568,252 @@ var __exports__ = (() => {
2745
2568
  }
2746
2569
  };
2747
2570
 
2748
- // src/adapter/resources/webgl-texture.ts
2749
- var DEFAULT_WEBGL_TEXTURE_PROPS = {
2750
- // deprecated
2751
- parameters: {},
2752
- pixelStore: {},
2753
- pixels: null,
2754
- border: 0,
2755
- dataFormat: void 0,
2756
- textureUnit: void 0,
2757
- target: void 0
2758
- };
2759
- var _WEBGLTexture = class extends import_core9.Texture {
2760
- MAX_ATTRIBUTES;
2761
- device;
2762
- gl;
2763
- handle;
2764
- // (TODO - currently unused in WebGL, but WebGL 2 does support sampler objects) */
2765
- sampler = void 0;
2766
- view = void 0;
2767
- // data;
2768
- glFormat = void 0;
2769
- type = void 0;
2770
- dataFormat = void 0;
2771
- mipmaps = void 0;
2772
- /**
2773
- * @note `target` cannot be modified by bind:
2774
- * textures are special because when you first bind them to a target,
2775
- * they get special information. When you first bind a texture as a
2776
- * GL_TEXTURE_2D, you are saying that this texture is a 2D texture.
2777
- * And it will always be a 2D texture; this state cannot be changed ever.
2778
- * A texture that was first bound as a GL_TEXTURE_2D, must always be bound as a GL_TEXTURE_2D;
2779
- * attempting to bind it as GL_TEXTURE_3D will give rise to a run-time error
2780
- * */
2781
- target;
2782
- textureUnit = void 0;
2783
- /**
2784
- * Program.draw() checks the loaded flag of all textures to avoid
2785
- * Textures that are still loading from promises
2786
- * Set to true as soon as texture has been initialized with valid data
2787
- */
2788
- loaded = false;
2789
- _video;
2790
- constructor(device, props) {
2791
- super(device, { ...DEFAULT_WEBGL_TEXTURE_PROPS, format: "rgba8unorm", ...props });
2792
- this.device = device;
2793
- this.gl = this.device.gl;
2794
- this.handle = this.props.handle || this.gl.createTexture();
2795
- this.device.setSpectorMetadata(this.handle, { ...this.props, data: typeof this.props.data });
2796
- this.glFormat = 6408 /* RGBA */;
2797
- this.target = getWebGLTextureTarget(this.props);
2798
- this.loaded = false;
2799
- if (typeof this.props?.data === "string") {
2800
- Object.assign(this.props, { data: (0, import_core9.loadImage)(this.props.data) });
2801
- }
2802
- this.initialize(this.props);
2803
- Object.seal(this);
2804
- }
2805
- destroy() {
2806
- if (this.handle) {
2807
- this.gl.deleteTexture(this.handle);
2808
- this.removeStats();
2809
- this.trackDeallocatedMemory("Texture");
2810
- this.destroyed = true;
2811
- }
2812
- }
2813
- toString() {
2814
- return `Texture(${this.id},${this.width}x${this.height})`;
2571
+ // src/adapter/helpers/webgl-texture-utils.ts
2572
+ function initializeTextureStorage(gl, levels, options) {
2573
+ const { dimension, width, height, depth = 0 } = options;
2574
+ const { glInternalFormat } = options;
2575
+ const glTarget = options.glTarget;
2576
+ switch (dimension) {
2577
+ case "2d-array":
2578
+ case "3d":
2579
+ gl.texStorage3D(glTarget, levels, glInternalFormat, width, height, depth);
2580
+ break;
2581
+ default:
2582
+ gl.texStorage2D(glTarget, levels, glInternalFormat, width, height);
2815
2583
  }
2816
- createView(props) {
2817
- return new WEBGLTextureView(this.device, { ...props, texture: this });
2584
+ }
2585
+ function copyCPUImageToMipLevel(gl, image, options) {
2586
+ const { dimension, width, height, depth = 0, level = 0 } = options;
2587
+ const { x = 0, y = 0, z = 0 } = options;
2588
+ const { glFormat, glType } = options;
2589
+ const glTarget = getWebGLCubeFaceTarget(options.glTarget, dimension, depth);
2590
+ switch (dimension) {
2591
+ case "2d-array":
2592
+ case "3d":
2593
+ gl.texSubImage3D(glTarget, level, x, y, z, width, height, depth, glFormat, glType, image);
2594
+ break;
2595
+ case "2d":
2596
+ case "cube":
2597
+ gl.texSubImage2D(glTarget, level, x, y, width, height, glFormat, glType, image);
2598
+ break;
2599
+ default:
2600
+ throw new Error(dimension);
2818
2601
  }
2819
- // eslint-disable-next-line max-statements
2820
- initialize(props = {}) {
2821
- if (this.props.dimension === "cube") {
2822
- return this.initializeCube(props);
2823
- }
2824
- let data = props.data;
2825
- if (data instanceof Promise) {
2826
- data.then(
2827
- (resolvedImageData) => this.initialize(
2828
- Object.assign({}, props, {
2829
- pixels: resolvedImageData,
2830
- data: resolvedImageData
2831
- })
2832
- )
2833
- );
2834
- return this;
2835
- }
2836
- const isVideo = typeof HTMLVideoElement !== "undefined" && data instanceof HTMLVideoElement;
2837
- if (isVideo && data.readyState < HTMLVideoElement.HAVE_METADATA) {
2602
+ }
2603
+ function copyCPUDataToMipLevel(gl, typedArray, options) {
2604
+ const { dimension, width, height, depth = 0, level = 0, byteOffset = 0 } = options;
2605
+ const { x = 0, y = 0, z = 0 } = options;
2606
+ const { glFormat, glType, compressed } = options;
2607
+ const glTarget = getWebGLCubeFaceTarget(options.glTarget, dimension, depth);
2608
+ switch (dimension) {
2609
+ case "2d-array":
2610
+ case "3d":
2611
+ if (compressed) {
2612
+ gl.compressedTexSubImage3D(glTarget, level, x, y, z, width, height, depth, glFormat, typedArray, byteOffset);
2613
+ } else {
2614
+ gl.texSubImage3D(glTarget, level, x, y, z, width, height, depth, glFormat, glType, typedArray, byteOffset);
2615
+ }
2616
+ break;
2617
+ case "2d":
2618
+ case "cube":
2619
+ if (compressed) {
2620
+ gl.compressedTexSubImage2D(glTarget, level, x, y, width, height, glFormat, typedArray, byteOffset);
2621
+ } else {
2622
+ gl.texSubImage2D(glTarget, level, x, y, width, height, glFormat, glType, typedArray, byteOffset);
2623
+ }
2624
+ break;
2625
+ default:
2626
+ throw new Error(dimension);
2627
+ }
2628
+ }
2629
+ function getWebGLTextureTarget(dimension) {
2630
+ switch (dimension) {
2631
+ case "1d":
2632
+ break;
2633
+ case "2d":
2634
+ return 3553 /* TEXTURE_2D */;
2635
+ case "3d":
2636
+ return 32879 /* TEXTURE_3D */;
2637
+ case "cube":
2638
+ return 34067 /* TEXTURE_CUBE_MAP */;
2639
+ case "2d-array":
2640
+ return 35866 /* TEXTURE_2D_ARRAY */;
2641
+ case "cube-array":
2642
+ break;
2643
+ }
2644
+ throw new Error(dimension);
2645
+ }
2646
+ function getWebGLCubeFaceTarget(glTarget, dimension, level) {
2647
+ return dimension === "cube" ? 34069 /* TEXTURE_CUBE_MAP_POSITIVE_X */ + level : glTarget;
2648
+ }
2649
+
2650
+ // src/adapter/resources/webgl-texture.ts
2651
+ function normalizeTextureData(data, options) {
2652
+ let lodArray;
2653
+ if (ArrayBuffer.isView(data)) {
2654
+ lodArray = [
2655
+ {
2656
+ // ts-expect-error does data really need to be Uint8ClampedArray?
2657
+ data,
2658
+ width: options.width,
2659
+ height: options.height
2660
+ // depth: options.depth
2661
+ }
2662
+ ];
2663
+ } else if (!Array.isArray(data)) {
2664
+ lodArray = [data];
2665
+ } else {
2666
+ lodArray = data;
2667
+ }
2668
+ return lodArray;
2669
+ }
2670
+ var WEBGLTexture = class extends import_core7.Texture {
2671
+ MAX_ATTRIBUTES;
2672
+ device;
2673
+ gl;
2674
+ handle;
2675
+ sampler = void 0;
2676
+ // TODO - currently unused in WebGL. Create dummy sampler?
2677
+ view = void 0;
2678
+ // TODO - currently unused in WebGL. Create dummy view?
2679
+ mipmaps = false;
2680
+ /**
2681
+ * @note `target` cannot be modified by bind:
2682
+ * textures are special because when you first bind them to a target,
2683
+ * When you first bind a texture as a GL_TEXTURE_2D, you are saying that this texture is a 2D texture.
2684
+ * And it will always be a 2D texture; this state cannot be changed ever.
2685
+ * A texture that was first bound as a GL_TEXTURE_2D, must always be bound as a GL_TEXTURE_2D;
2686
+ * attempting to bind it as GL_TEXTURE_3D will give rise to a run-time error
2687
+ */
2688
+ glTarget;
2689
+ // Texture type
2690
+ /** The WebGL format - essentially channel structure */
2691
+ glFormat;
2692
+ /** The WebGL data format - the type of each channel */
2693
+ glType;
2694
+ /** The WebGL constant corresponding to the WebGPU style constant in format */
2695
+ glInternalFormat;
2696
+ /** Whether the internal format is compressed */
2697
+ compressed;
2698
+ // data;
2699
+ // inherited props
2700
+ // dimension: ...
2701
+ // format: GLTextureTarget;
2702
+ // width: number = undefined;
2703
+ // height: number = undefined;
2704
+ // depth: number = undefined;
2705
+ // state
2706
+ /** Texture binding slot */
2707
+ textureUnit = 0;
2708
+ /** For automatically updating video */
2709
+ _video = null;
2710
+ constructor(device, props) {
2711
+ super(device, { ...import_core7.Texture.defaultProps, ...props, data: void 0 });
2712
+ this.device = device;
2713
+ this.gl = this.device.gl;
2714
+ this.glTarget = getWebGLTextureTarget(this.props.dimension);
2715
+ const format = getTextureFormatWebGL(this.props.format);
2716
+ this.glInternalFormat = format.internalFormat;
2717
+ this.glFormat = format.format;
2718
+ this.glType = format.type;
2719
+ this.compressed = format.compressed;
2720
+ if (typeof HTMLVideoElement !== "undefined" && props.data instanceof HTMLVideoElement && // @ts-expect-error
2721
+ props.data.readyState < HTMLVideoElement.HAVE_METADATA) {
2722
+ const video = props.data;
2838
2723
  this._video = null;
2839
- data.addEventListener("loadeddata", () => this.initialize(props));
2840
- return this;
2724
+ video.addEventListener("loadeddata", () => this.initialize(props));
2841
2725
  }
2842
- const { parameters = {} } = props;
2843
- const { pixels = null, pixelStore = {}, textureUnit = void 0, mipmaps = true } = props;
2844
- if (!data) {
2845
- data = pixels;
2726
+ this.initialize({ ...this.props, data: props.data });
2727
+ Object.seal(this);
2728
+ }
2729
+ /**
2730
+ * Initialize texture with supplied props
2731
+ */
2732
+ // eslint-disable-next-line max-statements
2733
+ initialize(props = {}) {
2734
+ this.handle = this.props.handle || this.gl.createTexture();
2735
+ this.device.setSpectorMetadata(this.handle, { ...this.props, data: typeof this.props.data });
2736
+ const data = props.data;
2737
+ let { width, height } = props;
2738
+ if (!width || !height) {
2739
+ const textureSize = import_core7.Texture.getTextureDataSize(data);
2740
+ width = textureSize?.width || 1;
2741
+ height = textureSize?.height || 1;
2846
2742
  }
2847
- let { width, height, dataFormat, type, compressed = false } = props;
2848
- const { depth = 0 } = props;
2849
- const glFormat = convertTextureFormatToGL(props.format);
2850
- ({ width, height, compressed, dataFormat, type } = this._deduceParameters({
2851
- format: props.format,
2852
- type,
2853
- dataFormat,
2854
- compressed,
2855
- data,
2856
- width,
2857
- height
2858
- }));
2859
2743
  this.width = width;
2860
2744
  this.height = height;
2861
- this.glFormat = glFormat;
2862
- this.type = type;
2863
- this.dataFormat = dataFormat;
2864
- this.textureUnit = textureUnit;
2865
- if (Number.isFinite(this.textureUnit)) {
2866
- this.gl.activeTexture(33984 /* TEXTURE0 */ + this.textureUnit);
2867
- this.gl.bindTexture(this.target, this.handle);
2868
- }
2869
- this.mipmaps = mipmaps;
2870
- this.setImageData({
2871
- data,
2872
- width,
2873
- height,
2874
- depth,
2875
- format: glFormat,
2876
- type,
2877
- dataFormat,
2878
- // @ts-expect-error
2879
- parameters: pixelStore,
2880
- compressed
2881
- });
2745
+ this.depth = props.depth;
2882
2746
  this.setSampler(props.sampler);
2883
- this._setSamplerParameters(parameters);
2884
- this.view = this.createView({ ...this.props, mipLevelCount: 1, arrayLayerCount: 1 });
2885
- if (mipmaps && this.device.isTextureFormatFilterable(props.format)) {
2747
+ this.view = new WEBGLTextureView(this.device, { ...this.props, texture: this });
2748
+ this.bind();
2749
+ if (!this.props.data) {
2750
+ initializeTextureStorage(this.gl, this.mipLevels, this);
2751
+ }
2752
+ if (props.data) {
2753
+ switch (props.dimension) {
2754
+ case "1d":
2755
+ this.setTexture1DData(props.data);
2756
+ break;
2757
+ case "2d":
2758
+ this.setTexture2DData(props.data);
2759
+ break;
2760
+ case "3d":
2761
+ this.setTexture3DData(props.data);
2762
+ break;
2763
+ case "cube":
2764
+ this.setTextureCubeData(props.data);
2765
+ break;
2766
+ case "2d-array":
2767
+ this.setTextureArrayData(props.data);
2768
+ break;
2769
+ case "cube-array":
2770
+ this.setTextureCubeArrayData(props.data);
2771
+ break;
2772
+ default:
2773
+ throw new Error(props.dimension);
2774
+ }
2775
+ }
2776
+ this.mipmaps = Boolean(props.mipmaps);
2777
+ if (this.mipmaps) {
2886
2778
  this.generateMipmap();
2887
2779
  }
2888
- if (isVideo) {
2889
- this._video = {
2890
- video: data,
2891
- parameters,
2892
- // @ts-expect-error
2893
- lastTime: data.readyState >= HTMLVideoElement.HAVE_CURRENT_DATA ? data.currentTime : -1
2894
- };
2780
+ }
2781
+ /*
2782
+ initializeCube(props?: TextureProps): void {
2783
+ const {mipmaps = true} = props; // , parameters = {} as Record<GL, any>} = props;
2784
+
2785
+ // Store props for accessors
2786
+ // this.props = props;
2787
+
2788
+ // @ts-expect-error
2789
+ this.setCubeMapData(props).then(() => {
2790
+ // TODO - should genMipmap() be called on the cubemap or on the faces?
2791
+ // TODO - without generateMipmap() cube textures do not work at all!!! Why?
2792
+ if (mipmaps) {
2793
+ this.generateMipmap(props);
2794
+ }
2795
+
2796
+ this.setSampler(props.sampler);
2797
+
2798
+ // v8 compatibility?
2799
+ // const {parameters = {} as Record<GL, any>} = props;
2800
+ // this._setSamplerParameters(parameters);
2801
+ });
2802
+ }
2803
+ */
2804
+ destroy() {
2805
+ if (this.handle) {
2806
+ this.gl.deleteTexture(this.handle);
2807
+ this.removeStats();
2808
+ this.trackDeallocatedMemory("Texture");
2809
+ this.destroyed = true;
2895
2810
  }
2896
- return this;
2897
2811
  }
2898
- initializeCube(props) {
2899
- const { mipmaps = true, parameters = {} } = props;
2900
- this.setCubeMapImageData(props).then(() => {
2901
- this.loaded = true;
2902
- if (mipmaps) {
2903
- this.generateMipmap(props);
2904
- }
2905
- this.setSampler(props.sampler);
2906
- this._setSamplerParameters(parameters);
2907
- });
2908
- return this;
2812
+ toString() {
2813
+ return `Texture(${this.id},${this.width}x${this.height})`;
2814
+ }
2815
+ createView(props) {
2816
+ return new WEBGLTextureView(this.device, { ...props, texture: this });
2909
2817
  }
2910
2818
  setSampler(sampler = {}) {
2911
2819
  let samplerProps;
@@ -2918,377 +2826,102 @@ var __exports__ = (() => {
2918
2826
  }
2919
2827
  const parameters = convertSamplerParametersToWebGL(samplerProps);
2920
2828
  this._setSamplerParameters(parameters);
2921
- return this;
2922
- }
2923
- /**
2924
- * If size has changed, reinitializes with current format
2925
- * @note note clears image and mipmaps
2926
- */
2927
- resize(options) {
2928
- const { height, width, mipmaps = false } = options;
2929
- if (width !== this.width || height !== this.height) {
2930
- return this.initialize({
2931
- width,
2932
- height,
2933
- format: this.format,
2934
- type: this.type,
2935
- dataFormat: this.dataFormat,
2936
- mipmaps
2937
- });
2938
- }
2939
- return this;
2940
2829
  }
2941
- /** Update external texture (video frame) */
2830
+ /** Update external texture (video frame or canvas) */
2942
2831
  update() {
2943
- if (this._video) {
2944
- const { video, parameters, lastTime } = this._video;
2945
- if (lastTime === video.currentTime || video.readyState < HTMLVideoElement.HAVE_CURRENT_DATA) {
2946
- return;
2947
- }
2948
- this.setSubImageData({
2949
- data: video,
2950
- parameters
2951
- });
2952
- if (this.mipmaps) {
2953
- this.generateMipmap();
2954
- }
2955
- this._video.lastTime = video.currentTime;
2956
- }
2832
+ import_core7.log.warn("Texture.update() not implemented");
2957
2833
  }
2958
2834
  // Call to regenerate mipmaps after modifying texture(s)
2959
2835
  generateMipmap(params = {}) {
2836
+ if (!this.props.data) {
2837
+ return;
2838
+ }
2960
2839
  this.mipmaps = true;
2961
- this.gl.bindTexture(this.target, this.handle);
2840
+ this.gl.bindTexture(this.glTarget, this.handle);
2962
2841
  withGLParameters(this.gl, params, () => {
2963
- this.gl.generateMipmap(this.target);
2842
+ this.gl.generateMipmap(this.glTarget);
2964
2843
  });
2965
- this.gl.bindTexture(this.target, null);
2966
- return this;
2844
+ this.gl.bindTexture(this.glTarget, null);
2967
2845
  }
2968
- /*
2969
- * Allocates storage
2970
- * @param {*} pixels -
2971
- * null - create empty texture of specified format
2972
- * Typed array - init from image data in typed array
2973
- * Buffer|WebGLBuffer - (WEBGL2) init from image data in WebGLBuffer
2974
- * HTMLImageElement|Image - Inits with content of image. Auto width/height
2975
- * HTMLCanvasElement - Inits with contents of canvas. Auto width/height
2976
- * HTMLVideoElement - Creates video texture. Auto width/height
2977
- *
2978
- * @param width -
2979
- * @param height -
2980
- * @param mipMapLevel -
2981
- * @param {GLenum} format - format of image data.
2982
- * @param {GLenum} type
2983
- * - format of array (autodetect from type) or
2984
- * - (WEBGL2) format of buffer
2985
- * @param {Number} offset - (WEBGL2) offset from start of buffer
2986
- * @parameters - temporary settings to be applied, can be used to supply pixel store settings.
2987
- */
2988
- // eslint-disable-next-line max-statements, complexity
2989
- setImageData(options) {
2990
- if (this.props.dimension === "3d" || this.props.dimension === "2d-array") {
2991
- return this.setImageData3D(options);
2846
+ // Image Data Setters
2847
+ copyExternalImage(options) {
2848
+ const size = import_core7.Texture.getExternalImageSize(options.image);
2849
+ const opts = { ...import_core7.Texture.defaultCopyExternalImageOptions, ...size, ...options };
2850
+ const { depth, mipLevel: lodLevel, image } = opts;
2851
+ this.bind();
2852
+ this._setMipLevel(depth, lodLevel, image);
2853
+ this.unbind();
2854
+ return { width: opts.width, height: opts.height };
2855
+ }
2856
+ setTexture1DData(data) {
2857
+ throw new Error("setTexture1DData not supported in WebGL.");
2858
+ }
2859
+ /** Set a simple texture */
2860
+ setTexture2DData(lodData, depth = 0) {
2861
+ this.bind();
2862
+ const lodArray = normalizeTextureData(lodData, this);
2863
+ if (lodArray.length > 1 && this.props.mipmaps !== false) {
2864
+ import_core7.log.warn(`Texture ${this.id} mipmap and multiple LODs.`)();
2992
2865
  }
2993
- this.trackDeallocatedMemory("Texture");
2994
- const {
2995
- target = this.target,
2996
- pixels = null,
2997
- level = 0,
2998
- glFormat = this.glFormat,
2999
- offset = 0,
3000
- parameters = {}
3001
- } = options;
3002
- let {
3003
- data = null,
3004
- type = this.type,
3005
- width = this.width,
3006
- height = this.height,
3007
- dataFormat = this.dataFormat,
3008
- compressed = false
3009
- } = options;
3010
- if (!data) {
3011
- data = pixels;
2866
+ for (let lodLevel = 0; lodLevel < lodArray.length; lodLevel++) {
2867
+ const imageData = lodArray[lodLevel];
2868
+ this._setMipLevel(depth, lodLevel, imageData);
3012
2869
  }
3013
- ({ type, dataFormat, compressed, width, height } = this._deduceParameters({
3014
- format: this.props.format,
3015
- type,
3016
- dataFormat,
3017
- compressed,
3018
- data,
3019
- width,
3020
- height
3021
- }));
3022
- const { gl } = this;
3023
- gl.bindTexture(this.target, this.handle);
3024
- let dataType = null;
3025
- ({ data, dataType } = this._getDataType({ data, compressed }));
3026
- withGLParameters(this.gl, parameters, () => {
3027
- switch (dataType) {
3028
- case "null":
3029
- gl.texImage2D(
3030
- target,
3031
- level,
3032
- glFormat,
3033
- width,
3034
- height,
3035
- 0,
3036
- dataFormat,
3037
- type,
3038
- data
3039
- );
3040
- break;
3041
- case "typed-array":
3042
- gl.texImage2D(
3043
- target,
3044
- level,
3045
- glFormat,
3046
- width,
3047
- height,
3048
- 0,
3049
- // border (must be 0)
3050
- dataFormat,
3051
- type,
3052
- data,
3053
- offset
3054
- );
3055
- break;
3056
- case "buffer":
3057
- this.device.gl.bindBuffer(35052 /* PIXEL_UNPACK_BUFFER */, data.handle || data);
3058
- this.device.gl.texImage2D(
3059
- target,
3060
- level,
3061
- glFormat,
3062
- width,
3063
- height,
3064
- 0,
3065
- dataFormat,
3066
- type,
3067
- offset
3068
- );
3069
- this.device.gl.bindBuffer(35052 /* PIXEL_UNPACK_BUFFER */, null);
3070
- break;
3071
- case "browser-object":
3072
- gl.texImage2D(
3073
- target,
3074
- level,
3075
- glFormat,
3076
- width,
3077
- height,
3078
- 0,
3079
- dataFormat,
3080
- type,
3081
- data
3082
- );
3083
- break;
3084
- case "compressed":
3085
- for (const [levelIndex, levelData] of data.entries()) {
3086
- gl.compressedTexImage2D(
3087
- target,
3088
- levelIndex,
3089
- levelData.format,
3090
- levelData.width,
3091
- levelData.height,
3092
- 0,
3093
- levelData.data
3094
- );
3095
- }
3096
- break;
3097
- default:
3098
- (0, import_core9.assert)(false, "Unknown image data type");
3099
- }
3100
- });
3101
- if (data && data.byteLength) {
3102
- this.trackAllocatedMemory(data.byteLength, "Texture");
3103
- } else {
3104
- const bytesPerPixel = getTextureFormatBytesPerPixel(this.props.format);
3105
- this.trackAllocatedMemory(this.width * this.height * bytesPerPixel, "Texture");
3106
- }
3107
- this.loaded = true;
3108
- return this;
2870
+ this.unbind();
3109
2871
  }
3110
2872
  /**
3111
- * Redefines an area of an existing texture
3112
- * Note: does not allocate storage
3113
- * Redefines an area of an existing texture
2873
+ * Sets a 3D texture
2874
+ * @param data
3114
2875
  */
3115
- setSubImageData({
3116
- target = this.target,
3117
- pixels = null,
3118
- data = null,
3119
- x = 0,
3120
- y = 0,
3121
- width = this.width,
3122
- height = this.height,
3123
- level = 0,
3124
- glFormat = this.glFormat,
3125
- type = this.type,
3126
- dataFormat = this.dataFormat,
3127
- compressed = false,
3128
- offset = 0,
3129
- parameters = {}
3130
- }) {
3131
- ({ type, dataFormat, compressed, width, height } = this._deduceParameters({
3132
- format: this.props.format,
3133
- type,
3134
- dataFormat,
3135
- compressed,
3136
- data,
3137
- width,
3138
- height
3139
- }));
3140
- (0, import_core9.assert)(this.depth === 1, "texSubImage not supported for 3D textures");
3141
- if (!data) {
3142
- data = pixels;
3143
- }
3144
- if (data && data.data) {
3145
- const ndarray = data;
3146
- data = ndarray.data;
3147
- width = ndarray.shape[0];
3148
- height = ndarray.shape[1];
2876
+ setTexture3DData(data) {
2877
+ if (this.props.dimension !== "3d") {
2878
+ throw new Error(this.id);
3149
2879
  }
3150
- if (data instanceof WEBGLBuffer) {
3151
- data = data.handle;
2880
+ if (ArrayBuffer.isView(data)) {
2881
+ this.bind();
2882
+ copyCPUDataToMipLevel(this.device.gl, data, this);
2883
+ this.unbind();
3152
2884
  }
3153
- this.gl.bindTexture(this.target, this.handle);
3154
- withGLParameters(this.gl, parameters, () => {
3155
- if (compressed) {
3156
- this.gl.compressedTexSubImage2D(target, level, x, y, width, height, glFormat, data);
3157
- } else if (data === null) {
3158
- this.gl.texSubImage2D(target, level, x, y, width, height, dataFormat, type, null);
3159
- } else if (ArrayBuffer.isView(data)) {
3160
- this.gl.texSubImage2D(target, level, x, y, width, height, dataFormat, type, data, offset);
3161
- } else if (typeof WebGLBuffer !== "undefined" && data instanceof WebGLBuffer) {
3162
- this.device.gl.bindBuffer(35052 /* PIXEL_UNPACK_BUFFER */, data);
3163
- this.device.gl.texSubImage2D(target, level, x, y, width, height, dataFormat, type, offset);
3164
- this.device.gl.bindBuffer(35052 /* PIXEL_UNPACK_BUFFER */, null);
3165
- } else {
3166
- this.device.gl.texSubImage2D(target, level, x, y, width, height, dataFormat, type, data);
3167
- }
3168
- });
3169
- this.gl.bindTexture(this.target, null);
3170
2885
  }
3171
2886
  /**
3172
- * Defines a two-dimensional texture image or cube-map texture image with
3173
- * pixels from the current framebuffer (rather than from client memory).
3174
- * (gl.copyTexImage2D wrapper)
3175
- *
3176
- * Note that binding a texture into a Framebuffer's color buffer and
3177
- * rendering can be faster.
2887
+ * Set a Texture Cube Data
2888
+ * @todo - could support TextureCubeArray with depth
2889
+ * @param data
2890
+ * @param index
3178
2891
  */
3179
- copyFramebuffer(opts = {}) {
3180
- import_core9.log.error(
3181
- "Texture.copyFramebuffer({...}) is no logner supported, use copyToTexture(source, target, opts})"
3182
- )();
3183
- return null;
3184
- }
3185
- getActiveUnit() {
3186
- return this.gl.getParameter(34016 /* ACTIVE_TEXTURE */) - 33984 /* TEXTURE0 */;
3187
- }
3188
- bind(textureUnit = this.textureUnit) {
3189
- const { gl } = this;
3190
- if (textureUnit !== void 0) {
3191
- this.textureUnit = textureUnit;
3192
- gl.activeTexture(gl.TEXTURE0 + textureUnit);
2892
+ setTextureCubeData(data, depth = 0) {
2893
+ if (this.props.dimension !== "cube") {
2894
+ throw new Error(this.id);
3193
2895
  }
3194
- gl.bindTexture(this.target, this.handle);
3195
- return textureUnit;
3196
- }
3197
- unbind(textureUnit = this.textureUnit) {
3198
- const { gl } = this;
3199
- if (textureUnit !== void 0) {
3200
- this.textureUnit = textureUnit;
3201
- gl.activeTexture(gl.TEXTURE0 + textureUnit);
2896
+ for (const face of import_core7.Texture.CubeFaces) {
2897
+ this.setTextureCubeFaceData(data[face], face);
3202
2898
  }
3203
- gl.bindTexture(this.target, null);
3204
- return textureUnit;
3205
2899
  }
3206
- // PRIVATE METHODS
3207
- _getDataType({ data, compressed = false }) {
3208
- if (compressed) {
3209
- return { data, dataType: "compressed" };
3210
- }
3211
- if (data === null) {
3212
- return { data, dataType: "null" };
3213
- }
3214
- if (ArrayBuffer.isView(data)) {
3215
- return { data, dataType: "typed-array" };
3216
- }
3217
- if (data instanceof WEBGLBuffer) {
3218
- return { data: data.handle, dataType: "buffer" };
3219
- }
3220
- if (typeof WebGLBuffer !== "undefined" && data instanceof WebGLBuffer) {
3221
- return { data, dataType: "buffer" };
3222
- }
3223
- return { data, dataType: "browser-object" };
3224
- }
3225
- // HELPER METHODS
3226
- _deduceParameters(opts) {
3227
- const { format, data } = opts;
3228
- let { width, height, dataFormat, type, compressed } = opts;
3229
- const parameters = getWebGLTextureParameters(format);
3230
- dataFormat = dataFormat || parameters.dataFormat;
3231
- type = type || parameters.type;
3232
- compressed = compressed || parameters.compressed;
3233
- ({ width, height } = this._deduceImageSize(data, width, height));
3234
- return { dataFormat, type, compressed, width, height, format, data };
3235
- }
3236
- // eslint-disable-next-line complexity
3237
- _deduceImageSize(data, width, height) {
3238
- let size;
3239
- if (typeof ImageData !== "undefined" && data instanceof ImageData) {
3240
- size = { width: data.width, height: data.height };
3241
- } else if (typeof HTMLImageElement !== "undefined" && data instanceof HTMLImageElement) {
3242
- size = { width: data.naturalWidth, height: data.naturalHeight };
3243
- } else if (typeof HTMLCanvasElement !== "undefined" && data instanceof HTMLCanvasElement) {
3244
- size = { width: data.width, height: data.height };
3245
- } else if (typeof ImageBitmap !== "undefined" && data instanceof ImageBitmap) {
3246
- size = { width: data.width, height: data.height };
3247
- } else if (typeof HTMLVideoElement !== "undefined" && data instanceof HTMLVideoElement) {
3248
- size = { width: data.videoWidth, height: data.videoHeight };
3249
- } else if (!data) {
3250
- size = { width: width >= 0 ? width : 1, height: height >= 0 ? height : 1 };
3251
- } else {
3252
- size = { width, height };
2900
+ /**
2901
+ * Sets an entire texture array
2902
+ * @param data
2903
+ */
2904
+ setTextureArrayData(data) {
2905
+ if (this.props.dimension !== "2d-array") {
2906
+ throw new Error(this.id);
3253
2907
  }
3254
- (0, import_core9.assert)(size, "Could not deduced texture size");
3255
- (0, import_core9.assert)(
3256
- width === void 0 || size.width === width,
3257
- "Deduced texture width does not match supplied width"
3258
- );
3259
- (0, import_core9.assert)(
3260
- height === void 0 || size.height === height,
3261
- "Deduced texture height does not match supplied height"
3262
- );
3263
- return size;
2908
+ throw new Error("setTextureArrayData not implemented.");
3264
2909
  }
3265
- // CUBE MAP METHODS
3266
- /* eslint-disable max-statements, max-len */
3267
- async setCubeMapImageData(options) {
3268
- const { gl } = this;
3269
- const { width, height, pixels, data, format = 6408 /* RGBA */, type = 5121 /* UNSIGNED_BYTE */ } = options;
3270
- const imageDataMap = pixels || data;
3271
- const resolvedFaces = await Promise.all(
3272
- _WEBGLTexture.FACES.map((face) => {
3273
- const facePixels = imageDataMap[face];
3274
- return Promise.all(Array.isArray(facePixels) ? facePixels : [facePixels]);
3275
- })
3276
- );
3277
- this.bind();
3278
- _WEBGLTexture.FACES.forEach((face, index) => {
3279
- if (resolvedFaces[index].length > 1 && this.props.mipmaps !== false) {
3280
- import_core9.log.warn(`${this.id} has mipmap and multiple LODs.`)();
3281
- }
3282
- resolvedFaces[index].forEach((image, lodLevel) => {
3283
- if (width && height) {
3284
- gl.texImage2D(face, lodLevel, format, width, height, 0, format, type, image);
3285
- } else {
3286
- gl.texImage2D(face, lodLevel, format, format, type, image);
3287
- }
3288
- });
3289
- });
3290
- this.unbind();
2910
+ /**
2911
+ * Sets an entire texture cube array
2912
+ * @param data
2913
+ */
2914
+ setTextureCubeArrayData(data) {
2915
+ throw new Error("setTextureCubeArrayData not supported in WebGL2.");
3291
2916
  }
2917
+ setTextureCubeFaceData(lodData, face, depth = 0) {
2918
+ if (Array.isArray(lodData) && lodData.length > 1 && this.props.mipmaps !== false) {
2919
+ import_core7.log.warn(`${this.id} has mipmap and multiple LODs.`)();
2920
+ }
2921
+ const faceDepth = import_core7.Texture.CubeFaces.indexOf(face);
2922
+ this.setTexture2DData(lodData, faceDepth);
2923
+ }
2924
+ // INTERNAL METHODS
3292
2925
  /** @todo update this method to accept LODs */
3293
2926
  setImageDataForFace(options) {
3294
2927
  const {
@@ -3319,132 +2952,158 @@ var __exports__ = (() => {
3319
2952
  } else {
3320
2953
  gl.texImage2D(face, 0, format, format, type, imageData);
3321
2954
  }
3322
- return this;
3323
2955
  }
3324
- /** Image 3D copies from Typed Array or WebGLBuffer */
3325
- setImageData3D(options) {
3326
- const {
3327
- level = 0,
3328
- dataFormat,
3329
- format,
3330
- type,
3331
- // = GL.UNSIGNED_BYTE,
3332
- width,
3333
- height,
3334
- depth = 1,
3335
- offset = 0,
3336
- data,
3337
- parameters = {}
3338
- } = options;
3339
- this.trackDeallocatedMemory("Texture");
3340
- this.gl.bindTexture(this.target, this.handle);
3341
- const webglTextureFormat = getWebGLTextureParameters(format);
3342
- withGLParameters(this.gl, parameters, () => {
3343
- if (ArrayBuffer.isView(data)) {
3344
- this.gl.texImage3D(
3345
- this.target,
3346
- level,
3347
- webglTextureFormat.format,
3348
- width,
3349
- height,
3350
- depth,
3351
- 0,
3352
- webglTextureFormat.dataFormat,
3353
- webglTextureFormat.type,
3354
- // dataType: getWebGL,
3355
- data
3356
- );
2956
+ _getImageDataMap(faceData) {
2957
+ for (let i = 0; i < import_core7.Texture.CubeFaces.length; ++i) {
2958
+ const faceName = import_core7.Texture.CubeFaces[i];
2959
+ if (faceData[faceName]) {
2960
+ faceData[34069 /* TEXTURE_CUBE_MAP_POSITIVE_X */ + i] = faceData[faceName];
2961
+ delete faceData[faceName];
3357
2962
  }
3358
- if (data instanceof WEBGLBuffer) {
3359
- this.gl.bindBuffer(35052 /* PIXEL_UNPACK_BUFFER */, data.handle);
3360
- this.gl.texImage3D(
3361
- this.target,
3362
- level,
3363
- dataFormat,
3364
- width,
3365
- height,
3366
- depth,
3367
- 0,
3368
- format,
3369
- type,
3370
- offset
3371
- );
3372
- }
3373
- });
3374
- if (data && data.byteLength) {
3375
- this.trackAllocatedMemory(data.byteLength, "Texture");
3376
- } else {
3377
- const bytesPerPixel = getTextureFormatBytesPerPixel(this.props.format);
3378
- this.trackAllocatedMemory(this.width * this.height * this.depth * bytesPerPixel, "Texture");
3379
2963
  }
3380
- this.loaded = true;
3381
- return this;
2964
+ return faceData;
3382
2965
  }
3383
2966
  // RESOURCE METHODS
3384
2967
  /**
3385
2968
  * Sets sampler parameters on texture
3386
2969
  */
3387
2970
  _setSamplerParameters(parameters) {
3388
- if ((0, import_core9.isObjectEmpty)(parameters)) {
3389
- return;
3390
- }
3391
- logParameters(parameters);
3392
- this.gl.bindTexture(this.target, this.handle);
2971
+ import_core7.log.log(1, "texture sampler parameters", parameters)();
2972
+ this.gl.bindTexture(this.glTarget, this.handle);
3393
2973
  for (const [pname, pvalue] of Object.entries(parameters)) {
3394
2974
  const param = Number(pname);
3395
2975
  const value = pvalue;
3396
2976
  switch (param) {
3397
2977
  case 33082 /* TEXTURE_MIN_LOD */:
3398
2978
  case 33083 /* TEXTURE_MAX_LOD */:
3399
- this.gl.texParameterf(this.target, param, value);
2979
+ this.gl.texParameterf(this.glTarget, param, value);
2980
+ break;
2981
+ case 10241 /* TEXTURE_MIN_FILTER */:
2982
+ this.gl.texParameteri(this.glTarget, param, value);
2983
+ break;
2984
+ case 10242 /* TEXTURE_WRAP_S */:
2985
+ case 10243 /* TEXTURE_WRAP_T */:
2986
+ this.gl.texParameteri(this.glTarget, param, value);
2987
+ break;
2988
+ case 34046 /* TEXTURE_MAX_ANISOTROPY_EXT */:
2989
+ if (this.device.features.has("texture-filterable-anisotropic-webgl")) {
2990
+ this.gl.texParameteri(this.glTarget, param, value);
2991
+ }
3400
2992
  break;
3401
2993
  default:
3402
- this.gl.texParameteri(this.target, param, value);
2994
+ this.gl.texParameteri(this.glTarget, param, value);
3403
2995
  break;
3404
2996
  }
3405
2997
  }
3406
- this.gl.bindTexture(this.target, null);
3407
- return;
2998
+ this.gl.bindTexture(this.glTarget, null);
3408
2999
  }
3409
- };
3410
- var WEBGLTexture = _WEBGLTexture;
3411
- // TODO - remove?
3412
- __publicField(WEBGLTexture, "FACES", [
3413
- 34069 /* TEXTURE_CUBE_MAP_POSITIVE_X */,
3414
- 34070 /* TEXTURE_CUBE_MAP_NEGATIVE_X */,
3415
- 34071 /* TEXTURE_CUBE_MAP_POSITIVE_Y */,
3416
- 34072 /* TEXTURE_CUBE_MAP_NEGATIVE_Y */,
3417
- 34073 /* TEXTURE_CUBE_MAP_POSITIVE_Z */,
3418
- 34074 /* TEXTURE_CUBE_MAP_NEGATIVE_Z */
3419
- ]);
3420
- function getWebGLTextureTarget(props) {
3421
- switch (props.dimension) {
3422
- case "2d":
3423
- return 3553 /* TEXTURE_2D */;
3424
- case "cube":
3425
- return 34067 /* TEXTURE_CUBE_MAP */;
3426
- case "2d-array":
3427
- return 35866 /* TEXTURE_2D_ARRAY */;
3428
- case "3d":
3429
- return 32879 /* TEXTURE_3D */;
3430
- case "1d":
3431
- case "cube-array":
3432
- default:
3433
- throw new Error(props.dimension);
3000
+ // CLASSIC
3001
+ /*
3002
+ setCubeMapData(options: {
3003
+ width: number;
3004
+ height: number;
3005
+ data: Record<GL, Texture2DData> | Record<TextureCubeFace, Texture2DData>;
3006
+ format?: any;
3007
+ type?: any;
3008
+ /** @deprecated Use .data *
3009
+ pixels: any;
3010
+ }): void {
3011
+ const {gl} = this;
3012
+
3013
+ const {width, height, pixels, data, format = GL.RGBA, type = GL.UNSIGNED_BYTE} = options;
3014
+
3015
+ // pixel data (imageDataMap) is an Object from Face to Image or Promise.
3016
+ // For example:
3017
+ // {
3018
+ // GL.TEXTURE_CUBE_MAP_POSITIVE_X : Image-or-Promise,
3019
+ // GL.TEXTURE_CUBE_MAP_NEGATIVE_X : Image-or-Promise,
3020
+ // ... }
3021
+ // To provide multiple level-of-details (LODs) this can be Face to Array
3022
+ // of Image or Promise, like this
3023
+ // {
3024
+ // GL.TEXTURE_CUBE_MAP_POSITIVE_X : [Image-or-Promise-LOD-0, Image-or-Promise-LOD-1],
3025
+ // GL.TEXTURE_CUBE_MAP_NEGATIVE_X : [Image-or-Promise-LOD-0, Image-or-Promise-LOD-1],
3026
+ // ... }
3027
+
3028
+ const imageDataMap = this._getImageDataMap(pixels || data);
3029
+
3030
+ const resolvedFaces = WEBGLTexture.FACES.map(face => {
3031
+ const facePixels = imageDataMap[face];
3032
+ return Array.isArray(facePixels) ? facePixels : [facePixels];
3033
+ });
3034
+ this.bind();
3035
+
3036
+ WEBGLTexture.FACES.forEach((face, index) => {
3037
+ if (resolvedFaces[index].length > 1 && this.props.mipmaps !== false) {
3038
+ // If the user provides multiple LODs, then automatic mipmap
3039
+ // generation generateMipmap() should be disabled to avoid overwritting them.
3040
+ log.warn(`${this.id} has mipmap and multiple LODs.`)();
3041
+ }
3042
+ resolvedFaces[index].forEach((image, lodLevel) => {
3043
+ // TODO: adjust width & height for LOD!
3044
+ if (width && height) {
3045
+ gl.texImage2D(face, lodLevel, format, width, height, 0 /* border*, format, type, image);
3046
+ } else {
3047
+ gl.texImage2D(face, lodLevel, format, format, type, image);
3048
+ }
3049
+ });
3050
+ });
3051
+
3052
+ this.unbind();
3053
+ }
3054
+ */
3055
+ // INTERNAL SETTERS
3056
+ /**
3057
+ * Copy a region of data from a CPU memory buffer into this texture.
3058
+ * @todo - GLUnpackParameters parameters
3059
+ */
3060
+ _setMipLevel(depth, level, textureData, glTarget = this.glTarget) {
3061
+ if (import_core7.Texture.isExternalImage(textureData)) {
3062
+ copyCPUImageToMipLevel(this.device.gl, textureData, { ...this, depth, level, glTarget });
3063
+ return;
3064
+ }
3065
+ if (import_core7.Texture.isTextureLevelData(textureData)) {
3066
+ copyCPUDataToMipLevel(this.device.gl, textureData.data, {
3067
+ ...this,
3068
+ depth,
3069
+ level,
3070
+ glTarget
3071
+ });
3072
+ return;
3073
+ }
3074
+ throw new Error("Texture: invalid image data");
3434
3075
  }
3435
- }
3436
- function logParameters(parameters) {
3437
- import_core9.log.log(1, "texture sampler parameters", parameters)();
3438
- }
3076
+ // HELPERS
3077
+ getActiveUnit() {
3078
+ return this.gl.getParameter(34016 /* ACTIVE_TEXTURE */) - 33984 /* TEXTURE0 */;
3079
+ }
3080
+ bind(textureUnit) {
3081
+ const { gl } = this;
3082
+ if (textureUnit !== void 0) {
3083
+ this.textureUnit = textureUnit;
3084
+ gl.activeTexture(gl.TEXTURE0 + textureUnit);
3085
+ }
3086
+ gl.bindTexture(this.glTarget, this.handle);
3087
+ return textureUnit;
3088
+ }
3089
+ unbind(textureUnit) {
3090
+ const { gl } = this;
3091
+ if (textureUnit !== void 0) {
3092
+ this.textureUnit = textureUnit;
3093
+ gl.activeTexture(gl.TEXTURE0 + textureUnit);
3094
+ }
3095
+ gl.bindTexture(this.glTarget, null);
3096
+ return textureUnit;
3097
+ }
3098
+ };
3439
3099
 
3440
3100
  // src/adapter/resources/webgl-framebuffer.ts
3441
- var WEBGLFramebuffer = class extends import_core10.Framebuffer {
3101
+ var WEBGLFramebuffer = class extends import_core8.Framebuffer {
3442
3102
  device;
3443
3103
  gl;
3444
3104
  handle;
3445
- get texture() {
3446
- return this.colorAttachments[0];
3447
- }
3105
+ colorAttachments = [];
3106
+ depthStencilAttachment = null;
3448
3107
  constructor(device, props) {
3449
3108
  super(device, props);
3450
3109
  const isDefaultFramebuffer = props.handle === null;
@@ -3462,11 +3121,11 @@ var __exports__ = (() => {
3462
3121
  const attachment = this.colorAttachments[i];
3463
3122
  const attachmentPoint = 36064 /* COLOR_ATTACHMENT0 */ + i;
3464
3123
  if (attachment) {
3465
- this._attachOne(attachmentPoint, attachment);
3124
+ this._attachTexture(attachmentPoint, attachment);
3466
3125
  }
3467
3126
  }
3468
3127
  if (this.depthStencilAttachment) {
3469
- this._attachOne(
3128
+ this._attachTexture(
3470
3129
  getDepthStencilAttachmentWebGL(this.depthStencilAttachment.props.format),
3471
3130
  this.depthStencilAttachment
3472
3131
  );
@@ -3499,73 +3158,55 @@ var __exports__ = (() => {
3499
3158
  });
3500
3159
  }
3501
3160
  /**
3502
- * Attachment resize is expected to be a noop if size is same
3503
- */
3504
- resizeAttachments(width, height) {
3505
- if (this.handle === null) {
3506
- this.width = this.gl.drawingBufferWidth;
3507
- this.height = this.gl.drawingBufferHeight;
3161
+ * Attachment resize is expected to be a noop if size is same
3162
+ *
3163
+ protected override resizeAttachments(width: number, height: number): this {
3164
+ // for default framebuffer, just update the stored size
3165
+ if (this.handle === null) {
3166
+ // assert(width === undefined && height === undefined);
3167
+ this.width = this.gl.drawingBufferWidth;
3168
+ this.height = this.gl.drawingBufferHeight;
3169
+ return this;
3170
+ }
3171
+
3172
+ if (width === undefined) {
3173
+ width = this.gl.drawingBufferWidth;
3174
+ }
3175
+ if (height === undefined) {
3176
+ height = this.gl.drawingBufferHeight;
3177
+ }
3178
+
3179
+ // TODO Not clear that this is better than default destroy/create implementation
3180
+
3181
+ for (const colorAttachment of this.colorAttachments) {
3182
+ colorAttachment.texture.clone({width, height});
3183
+ }
3184
+ if (this.depthStencilAttachment) {
3185
+ this.depthStencilAttachment.texture.resize({width, height});
3186
+ }
3508
3187
  return this;
3509
3188
  }
3510
- if (width === void 0) {
3511
- width = this.gl.drawingBufferWidth;
3512
- }
3513
- if (height === void 0) {
3514
- height = this.gl.drawingBufferHeight;
3515
- }
3516
- for (const colorAttachment of this.colorAttachments) {
3517
- colorAttachment.texture.resize({ width, height });
3518
- }
3519
- if (this.depthStencilAttachment) {
3520
- this.depthStencilAttachment.texture.resize({ width, height });
3521
- }
3522
- return this;
3523
- }
3189
+ */
3524
3190
  /** Attach one attachment */
3525
- _attachOne(attachmentPoint, attachment) {
3526
- if (Array.isArray(attachment)) {
3527
- const [texture, layer = 0, level = 0] = attachment;
3528
- this._attachTexture(attachmentPoint, texture, layer, level);
3529
- return texture;
3530
- }
3531
- if (attachment instanceof WEBGLTexture) {
3532
- this._attachTexture(attachmentPoint, attachment, 0, 0);
3533
- return attachment;
3534
- }
3535
- if (attachment instanceof WEBGLTextureView) {
3536
- const textureView = attachment;
3537
- this._attachTexture(
3538
- attachmentPoint,
3539
- textureView.texture,
3540
- textureView.props.baseMipLevel,
3541
- textureView.props.baseArrayLayer
3542
- );
3543
- return attachment.texture;
3544
- }
3545
- throw new Error("attach");
3546
- }
3547
- // TODO - we do not seem to need render buffers in WebGL 2
3548
- // protected _attachWEBGLRenderbuffer(attachment: GL, renderbuffer: WEBGLRenderbuffer): void {
3549
- // this.gl.framebufferRenderbuffer(
3550
- // GL.FRAMEBUFFER,
3551
- // attachment,
3552
- // GL.RENDERBUFFER,
3553
- // renderbuffer.handle
3554
- // );
3555
- // }
3191
+ _attachTexture(attachmentPoint, textureView) {
3192
+ this._attachTextureView(attachmentPoint, textureView);
3193
+ }
3556
3194
  /**
3557
3195
  * @param attachment
3558
3196
  * @param texture
3559
3197
  * @param layer = 0 - index into WEBGLTextureArray and Texture3D or face for `TextureCubeMap`
3560
3198
  * @param level = 0 - mipmapLevel
3561
3199
  */
3562
- _attachTexture(attachment, texture, layer, level) {
3200
+ _attachTextureView(attachment, textureView) {
3563
3201
  const { gl } = this.device;
3564
- gl.bindTexture(texture.target, texture.handle);
3565
- switch (texture.target) {
3202
+ const { texture } = textureView;
3203
+ const level = textureView.props.baseMipLevel;
3204
+ const layer = textureView.props.baseArrayLayer;
3205
+ gl.bindTexture(texture.glTarget, texture.handle);
3206
+ switch (texture.glTarget) {
3566
3207
  case 35866 /* TEXTURE_2D_ARRAY */:
3567
3208
  case 32879 /* TEXTURE_3D */:
3568
- gl.framebufferTextureLayer(36160 /* FRAMEBUFFER */, attachment, texture.target, level, layer);
3209
+ gl.framebufferTextureLayer(36160 /* FRAMEBUFFER */, attachment, texture.handle, level, layer);
3569
3210
  break;
3570
3211
  case 34067 /* TEXTURE_CUBE_MAP */:
3571
3212
  const face = mapIndexToCubeMapFace(layer);
@@ -3575,9 +3216,9 @@ var __exports__ = (() => {
3575
3216
  gl.framebufferTexture2D(36160 /* FRAMEBUFFER */, attachment, 3553 /* TEXTURE_2D */, texture.handle, level);
3576
3217
  break;
3577
3218
  default:
3578
- (0, import_core10.assert)(false, "Illegal texture type");
3219
+ throw new Error("Illegal texture type");
3579
3220
  }
3580
- gl.bindTexture(texture.target, null);
3221
+ gl.bindTexture(texture.glTarget, null);
3581
3222
  }
3582
3223
  };
3583
3224
  function mapIndexToCubeMapFace(layer) {
@@ -3603,8 +3244,10 @@ var __exports__ = (() => {
3603
3244
  }
3604
3245
 
3605
3246
  // src/adapter/webgl-canvas-context.ts
3606
- var WebGLCanvasContext = class extends import_core11.CanvasContext {
3247
+ var WebGLCanvasContext = class extends import_core9.CanvasContext {
3607
3248
  device;
3249
+ format = "rgba8unorm";
3250
+ depthStencilFormat = "depth24plus";
3608
3251
  presentationSize;
3609
3252
  _framebuffer = null;
3610
3253
  constructor(device, props) {
@@ -3654,31 +3297,57 @@ var __exports__ = (() => {
3654
3297
  };
3655
3298
 
3656
3299
  // src/context/debug/spector.ts
3657
- var import_core12 = __toESM(require_core(), 1);
3658
- var DEFAULT_SPECTOR_PROPS = {
3659
- spector: import_core12.log.get("spector") || import_core12.log.get("spectorjs")
3660
- };
3661
- var SPECTOR_CDN_URL = "https://cdn.jsdelivr.net/npm/spectorjs@0.9.30/dist/spector.bundle.js";
3300
+ var import_core10 = __toESM(require_core(), 1);
3301
+
3302
+ // src/utils/load-script.ts
3303
+ async function loadScript(scriptUrl, scriptId) {
3304
+ const head = document.getElementsByTagName("head")[0];
3305
+ if (!head) {
3306
+ throw new Error("loadScript");
3307
+ }
3308
+ const script = document.createElement("script");
3309
+ script.setAttribute("type", "text/javascript");
3310
+ script.setAttribute("src", scriptUrl);
3311
+ if (scriptId) {
3312
+ script.id = scriptId;
3313
+ }
3314
+ return new Promise((resolve, reject) => {
3315
+ script.onload = resolve;
3316
+ script.onerror = (error) => reject(new Error(`Unable to load script '${scriptUrl}': ${error}`));
3317
+ head.appendChild(script);
3318
+ });
3319
+ }
3320
+
3321
+ // src/context/debug/spector.ts
3662
3322
  var LOG_LEVEL = 1;
3663
3323
  var spector = null;
3664
3324
  var initialized = false;
3325
+ var DEFAULT_SPECTOR_PROPS = {
3326
+ debugWithSpectorJS: import_core10.log.get("spector") || import_core10.log.get("spectorjs"),
3327
+ // https://github.com/BabylonJS/Spector.js#basic-usage
3328
+ // https://forum.babylonjs.com/t/spectorcdn-is-temporarily-off/48241
3329
+ // spectorUrl: 'https://spectorcdn.babylonjs.com/spector.bundle.js';
3330
+ spectorUrl: "https://cdn.jsdelivr.net/npm/spectorjs@0.9.30/dist/spector.bundle.js",
3331
+ gl: void 0
3332
+ };
3665
3333
  async function loadSpectorJS(props) {
3666
3334
  if (!globalThis.SPECTOR) {
3667
3335
  try {
3668
- await (0, import_core12.loadScript)(SPECTOR_CDN_URL);
3336
+ await loadScript(props.spectorUrl || DEFAULT_SPECTOR_PROPS.spectorUrl);
3669
3337
  } catch (error) {
3670
- import_core12.log.warn(String(error));
3338
+ import_core10.log.warn(String(error));
3671
3339
  }
3672
3340
  }
3673
3341
  }
3674
3342
  function initializeSpectorJS(props) {
3675
3343
  props = { ...DEFAULT_SPECTOR_PROPS, ...props };
3676
- if (!props?.spector) {
3344
+ if (!props.debugWithSpectorJS) {
3677
3345
  return null;
3678
3346
  }
3679
- if (!spector && globalThis.SPECTOR) {
3680
- import_core12.log.probe(LOG_LEVEL, "SPECTOR found and initialized")();
3681
- spector = new globalThis.SPECTOR.Spector();
3347
+ if (!spector && globalThis.SPECTOR && !globalThis.luma?.spector) {
3348
+ import_core10.log.probe(LOG_LEVEL, "SPECTOR found and initialized. Start with `luma.spector.displayUI()`")();
3349
+ const { Spector } = globalThis.SPECTOR;
3350
+ spector = new Spector();
3682
3351
  if (globalThis.luma) {
3683
3352
  globalThis.luma.spector = spector;
3684
3353
  }
@@ -3690,22 +3359,22 @@ var __exports__ = (() => {
3690
3359
  initialized = true;
3691
3360
  spector.spyCanvases();
3692
3361
  spector?.onCaptureStarted.add(
3693
- (capture) => import_core12.log.info("Spector capture started:", capture)()
3362
+ (capture) => import_core10.log.info("Spector capture started:", capture)()
3694
3363
  );
3695
3364
  spector?.onCapture.add((capture) => {
3696
- import_core12.log.info("Spector capture complete:", capture)();
3365
+ import_core10.log.info("Spector capture complete:", capture)();
3697
3366
  spector?.getResultUI();
3698
3367
  spector?.resultView.display();
3699
3368
  spector?.resultView.addCapture(capture);
3700
3369
  });
3701
3370
  }
3702
- if (props?.canvas) {
3703
- if (typeof props.spector === "string" && props.spector !== props.canvas.id) {
3704
- return spector;
3705
- }
3706
- spector?.startCapture(props?.canvas, 500);
3371
+ if (props.gl) {
3372
+ const gl = props.gl;
3373
+ const device = gl.device;
3374
+ spector?.startCapture(props.gl, 500);
3375
+ gl.device = device;
3707
3376
  new Promise((resolve) => setTimeout(resolve, 2e3)).then((_) => {
3708
- import_core12.log.info("Spector capture stopped after 2 seconds")();
3377
+ import_core10.log.info("Spector capture stopped after 2 seconds")();
3709
3378
  spector?.stopCapture();
3710
3379
  });
3711
3380
  }
@@ -3713,7 +3382,7 @@ var __exports__ = (() => {
3713
3382
  }
3714
3383
 
3715
3384
  // src/context/debug/webgl-developer-tools.ts
3716
- var import_core13 = __toESM(require_core(), 1);
3385
+ var import_core11 = __toESM(require_core(), 1);
3717
3386
 
3718
3387
  // ../../node_modules/@probe.gl/env/dist/lib/globals.js
3719
3388
  var document_ = globalThis.document || {};
@@ -3777,13 +3446,10 @@ var __exports__ = (() => {
3777
3446
  if (isBrowser() && !globalThis.WebGLDebugUtils) {
3778
3447
  globalThis.global = globalThis.global || globalThis;
3779
3448
  globalThis.global.module = {};
3780
- await (0, import_core13.loadScript)(WEBGL_DEBUG_CDN_URL);
3449
+ await loadScript(WEBGL_DEBUG_CDN_URL);
3781
3450
  }
3782
3451
  }
3783
3452
  function makeDebugContext(gl, props = {}) {
3784
- if (!gl) {
3785
- return null;
3786
- }
3787
3453
  return props.debug ? getDebugContext(gl, props) : getRealContext(gl);
3788
3454
  }
3789
3455
  function getRealContext(gl) {
@@ -3792,7 +3458,7 @@ var __exports__ = (() => {
3792
3458
  }
3793
3459
  function getDebugContext(gl, props) {
3794
3460
  if (!globalThis.WebGLDebugUtils) {
3795
- import_core13.log.warn("webgl-debug not loaded")();
3461
+ import_core11.log.warn("webgl-debug not loaded")();
3796
3462
  return gl;
3797
3463
  }
3798
3464
  const data = getWebGLContextData(gl);
@@ -3831,7 +3497,7 @@ var __exports__ = (() => {
3831
3497
  const errorMessage = globalThis.WebGLDebugUtils.glEnumToString(err);
3832
3498
  const functionArgs = globalThis.WebGLDebugUtils.glFunctionArgsToString(functionName, args);
3833
3499
  const message2 = `${errorMessage} in gl.${functionName}(${functionArgs})`;
3834
- import_core13.log.error(message2)();
3500
+ import_core11.log.error(message2)();
3835
3501
  debugger;
3836
3502
  if (props.throwOnError) {
3837
3503
  throw new Error(message2);
@@ -3839,9 +3505,9 @@ var __exports__ = (() => {
3839
3505
  }
3840
3506
  function onValidateGLFunc(props, functionName, functionArgs) {
3841
3507
  let functionString = "";
3842
- if (import_core13.log.level >= 1) {
3508
+ if (import_core11.log.level >= 1) {
3843
3509
  functionString = getFunctionString(functionName, functionArgs);
3844
- import_core13.log.log(1, functionString)();
3510
+ import_core11.log.log(1, functionString)();
3845
3511
  }
3846
3512
  if (props.break && props.break.length > 0) {
3847
3513
  functionString = functionString || getFunctionString(functionName, functionArgs);
@@ -3858,15 +3524,147 @@ var __exports__ = (() => {
3858
3524
  if (props.throwOnError) {
3859
3525
  throw new Error(`Undefined argument: ${functionString}`);
3860
3526
  } else {
3861
- import_core13.log.error(`Undefined argument: ${functionString}`)();
3527
+ import_core11.log.error(`Undefined argument: ${functionString}`)();
3862
3528
  debugger;
3863
3529
  }
3864
3530
  }
3865
3531
  }
3866
3532
  }
3867
3533
 
3534
+ // src/utils/uid.ts
3535
+ var uidCounters = {};
3536
+ function uid(id = "id") {
3537
+ uidCounters[id] = uidCounters[id] || 1;
3538
+ const count = uidCounters[id]++;
3539
+ return `${id}-${count}`;
3540
+ }
3541
+
3542
+ // src/adapter/resources/webgl-buffer.ts
3543
+ var import_core12 = __toESM(require_core(), 1);
3544
+ var WEBGLBuffer = class extends import_core12.Buffer {
3545
+ device;
3546
+ gl;
3547
+ handle;
3548
+ /** Target in OpenGL defines the type of buffer */
3549
+ glTarget;
3550
+ /** Usage is a hint on how frequently the buffer will be updates */
3551
+ glUsage;
3552
+ /** Index type is needed when issuing draw calls, so we pre-compute it */
3553
+ glIndexType = 5123 /* UNSIGNED_SHORT */;
3554
+ /** Number of bytes allocated on the GPU for this buffer */
3555
+ byteLength;
3556
+ /** Number of bytes used */
3557
+ bytesUsed;
3558
+ constructor(device, props = {}) {
3559
+ super(device, props);
3560
+ this.device = device;
3561
+ this.gl = this.device.gl;
3562
+ const handle = typeof props === "object" ? props.handle : void 0;
3563
+ this.handle = handle || this.gl.createBuffer();
3564
+ device.setSpectorMetadata(this.handle, { ...this.props, data: typeof this.props.data });
3565
+ this.glTarget = getWebGLTarget(this.props.usage);
3566
+ this.glUsage = getWebGLUsage(this.props.usage);
3567
+ this.glIndexType = this.props.indexType === "uint32" ? 5125 /* UNSIGNED_INT */ : 5123 /* UNSIGNED_SHORT */;
3568
+ if (props.data) {
3569
+ this._initWithData(props.data, props.byteOffset, props.byteLength);
3570
+ } else {
3571
+ this._initWithByteLength(props.byteLength || 0);
3572
+ }
3573
+ }
3574
+ // PRIVATE METHODS
3575
+ /** Allocate a new buffer and initialize to contents of typed array */
3576
+ _initWithData(data, byteOffset = 0, byteLength = data.byteLength + byteOffset) {
3577
+ const glTarget = this.glTarget;
3578
+ this.gl.bindBuffer(glTarget, this.handle);
3579
+ this.gl.bufferData(glTarget, byteLength, this.glUsage);
3580
+ this.gl.bufferSubData(glTarget, byteOffset, data);
3581
+ this.gl.bindBuffer(glTarget, null);
3582
+ this.bytesUsed = byteLength;
3583
+ this.byteLength = byteLength;
3584
+ this._setDebugData(data, byteOffset, byteLength);
3585
+ this.trackAllocatedMemory(byteLength);
3586
+ }
3587
+ // Allocate a GPU buffer of specified size.
3588
+ _initWithByteLength(byteLength) {
3589
+ let data = byteLength;
3590
+ if (byteLength === 0) {
3591
+ data = new Float32Array(0);
3592
+ }
3593
+ const glTarget = this.glTarget;
3594
+ this.gl.bindBuffer(glTarget, this.handle);
3595
+ this.gl.bufferData(glTarget, data, this.glUsage);
3596
+ this.gl.bindBuffer(glTarget, null);
3597
+ this.bytesUsed = byteLength;
3598
+ this.byteLength = byteLength;
3599
+ this._setDebugData(null, 0, byteLength);
3600
+ this.trackAllocatedMemory(byteLength);
3601
+ return this;
3602
+ }
3603
+ destroy() {
3604
+ if (!this.destroyed && this.handle) {
3605
+ this.removeStats();
3606
+ this.trackDeallocatedMemory();
3607
+ this.gl.deleteBuffer(this.handle);
3608
+ this.destroyed = true;
3609
+ this.handle = null;
3610
+ }
3611
+ }
3612
+ write(data, byteOffset = 0) {
3613
+ const srcOffset = 0;
3614
+ const byteLength = void 0;
3615
+ const glTarget = 36663 /* COPY_WRITE_BUFFER */;
3616
+ this.gl.bindBuffer(glTarget, this.handle);
3617
+ if (srcOffset !== 0 || byteLength !== void 0) {
3618
+ this.gl.bufferSubData(glTarget, byteOffset, data, srcOffset, byteLength);
3619
+ } else {
3620
+ this.gl.bufferSubData(glTarget, byteOffset, data);
3621
+ }
3622
+ this.gl.bindBuffer(glTarget, null);
3623
+ this._setDebugData(data, byteOffset, data.byteLength);
3624
+ }
3625
+ /** Asynchronously read data from the buffer */
3626
+ async readAsync(byteOffset = 0, byteLength) {
3627
+ return this.readSyncWebGL(byteOffset, byteLength);
3628
+ }
3629
+ /** Synchronously read data from the buffer. WebGL only. */
3630
+ readSyncWebGL(byteOffset = 0, byteLength) {
3631
+ byteLength = byteLength ?? this.byteLength - byteOffset;
3632
+ const data = new Uint8Array(byteLength);
3633
+ const dstOffset = 0;
3634
+ this.gl.bindBuffer(36662 /* COPY_READ_BUFFER */, this.handle);
3635
+ this.gl.getBufferSubData(36662 /* COPY_READ_BUFFER */, byteOffset, data, dstOffset, byteLength);
3636
+ this.gl.bindBuffer(36662 /* COPY_READ_BUFFER */, null);
3637
+ this._setDebugData(data, byteOffset, byteLength);
3638
+ return data;
3639
+ }
3640
+ };
3641
+ function getWebGLTarget(usage) {
3642
+ if (usage & import_core12.Buffer.INDEX) {
3643
+ return 34963 /* ELEMENT_ARRAY_BUFFER */;
3644
+ }
3645
+ if (usage & import_core12.Buffer.VERTEX) {
3646
+ return 34962 /* ARRAY_BUFFER */;
3647
+ }
3648
+ if (usage & import_core12.Buffer.UNIFORM) {
3649
+ return 35345 /* UNIFORM_BUFFER */;
3650
+ }
3651
+ return 34962 /* ARRAY_BUFFER */;
3652
+ }
3653
+ function getWebGLUsage(usage) {
3654
+ if (usage & import_core12.Buffer.INDEX) {
3655
+ return 35044 /* STATIC_DRAW */;
3656
+ }
3657
+ if (usage & import_core12.Buffer.VERTEX) {
3658
+ return 35044 /* STATIC_DRAW */;
3659
+ }
3660
+ if (usage & import_core12.Buffer.UNIFORM) {
3661
+ return 35048 /* DYNAMIC_DRAW */;
3662
+ }
3663
+ return 35044 /* STATIC_DRAW */;
3664
+ }
3665
+
3868
3666
  // src/adapter/resources/webgl-shader.ts
3869
- var import_core14 = __toESM(require_core(), 1);
3667
+ var import_core13 = __toESM(require_core(), 1);
3870
3668
 
3871
3669
  // src/adapter/helpers/parse-shader-compiler-log.ts
3872
3670
  function parseShaderCompilerLog(errLog) {
@@ -3913,7 +3711,7 @@ var __exports__ = (() => {
3913
3711
  }
3914
3712
 
3915
3713
  // src/adapter/resources/webgl-shader.ts
3916
- var WEBGLShader = class extends import_core14.Shader {
3714
+ var WEBGLShader = class extends import_core13.Shader {
3917
3715
  device;
3918
3716
  handle;
3919
3717
  constructor(device, props) {
@@ -3943,24 +3741,24 @@ var __exports__ = (() => {
3943
3741
  return this.getCompilationInfoSync();
3944
3742
  }
3945
3743
  getCompilationInfoSync() {
3946
- const log9 = this.device.gl.getShaderInfoLog(this.handle);
3947
- return parseShaderCompilerLog(log9);
3744
+ const log10 = this.device.gl.getShaderInfoLog(this.handle);
3745
+ return log10 ? parseShaderCompilerLog(log10) : [];
3948
3746
  }
3949
3747
  getTranslatedSource() {
3950
3748
  const extensions = this.device.getExtension("WEBGL_debug_shaders");
3951
3749
  const ext = extensions.WEBGL_debug_shaders;
3952
- return ext?.getTranslatedShaderSource(this.handle);
3750
+ return ext?.getTranslatedShaderSource(this.handle) || null;
3953
3751
  }
3954
3752
  // PRIVATE METHODS
3955
3753
  /** Compile a shader and get compilation status */
3956
3754
  async _compile(source) {
3957
- const addGLSLVersion = (source2) => source2.startsWith("#version ") ? source2 : `#version 100
3755
+ const addGLSLVersion = (source2) => source2.startsWith("#version ") ? source2 : `#version 300 es
3958
3756
  ${source2}`;
3959
3757
  source = addGLSLVersion(source);
3960
3758
  const { gl } = this.device;
3961
3759
  gl.shaderSource(this.handle, source);
3962
3760
  gl.compileShader(this.handle);
3963
- if (import_core14.log.level === 0) {
3761
+ if (import_core13.log.level === 0) {
3964
3762
  this.compilationStatus = "pending";
3965
3763
  return;
3966
3764
  }
@@ -3972,9 +3770,9 @@ ${source2}`;
3972
3770
  }
3973
3771
  return;
3974
3772
  }
3975
- import_core14.log.once(1, "Shader compilation is asynchronous")();
3773
+ import_core13.log.once(1, "Shader compilation is asynchronous")();
3976
3774
  await this._waitForCompilationComplete();
3977
- import_core14.log.info(2, `Shader ${this.id} - async compilation complete: ${this.compilationStatus}`)();
3775
+ import_core13.log.info(2, `Shader ${this.id} - async compilation complete: ${this.compilationStatus}`)();
3978
3776
  this._getCompilationStatus();
3979
3777
  this.debugShader();
3980
3778
  }
@@ -4006,25 +3804,35 @@ ${source2}`;
4006
3804
  };
4007
3805
 
4008
3806
  // src/adapter/resources/webgl-render-pass.ts
4009
- var import_core15 = __toESM(require_core(), 1);
3807
+ var import_core14 = __toESM(require_core(), 1);
4010
3808
  var GL_DEPTH_BUFFER_BIT = 256;
4011
3809
  var GL_STENCIL_BUFFER_BIT = 1024;
4012
3810
  var GL_COLOR_BUFFER_BIT = 16384;
4013
3811
  var GL_COLOR = 6144;
4014
3812
  var COLOR_CHANNELS = [1, 2, 4, 8];
4015
- var WEBGLRenderPass = class extends import_core15.RenderPass {
3813
+ var WEBGLRenderPass = class extends import_core14.RenderPass {
4016
3814
  device;
4017
3815
  /** Parameters that should be applied before each draw call */
4018
3816
  glParameters;
4019
3817
  constructor(device, props) {
4020
3818
  super(device, props);
4021
3819
  this.device = device;
4022
- pushContextState(this.device.gl);
4023
- this.setParameters(this.props.parameters);
3820
+ let viewport;
3821
+ if (!props?.parameters?.viewport) {
3822
+ if (props?.framebuffer) {
3823
+ const { width, height } = props.framebuffer;
3824
+ viewport = [0, 0, width, height];
3825
+ } else {
3826
+ const [width, height] = device.getCanvasContext().getDrawingBufferSize();
3827
+ viewport = [0, 0, width, height];
3828
+ }
3829
+ }
3830
+ this.device.pushState();
3831
+ this.setParameters({ viewport, ...this.props.parameters });
4024
3832
  this.clear();
4025
3833
  }
4026
3834
  end() {
4027
- popContextState(this.device.gl);
3835
+ this.device.popState();
4028
3836
  }
4029
3837
  pushDebugGroup(groupLabel) {
4030
3838
  }
@@ -4040,9 +3848,7 @@ ${source2}`;
4040
3848
  */
4041
3849
  setParameters(parameters = {}) {
4042
3850
  const glParameters = { ...this.glParameters };
4043
- if (this.props.framebuffer) {
4044
- glParameters.framebuffer = this.props.framebuffer;
4045
- }
3851
+ glParameters.framebuffer = this.props.framebuffer || null;
4046
3852
  if (this.props.depthReadOnly) {
4047
3853
  glParameters.depthMask = !this.props.depthReadOnly;
4048
3854
  }
@@ -4148,11 +3954,7 @@ ${source2}`;
4148
3954
  };
4149
3955
 
4150
3956
  // src/adapter/resources/webgl-render-pipeline.ts
4151
- var import_core17 = __toESM(require_core(), 1);
4152
- var import_core18 = __toESM(require_core(), 1);
4153
-
4154
- // src/classic/accessor.ts
4155
- var import_core16 = __toESM(require_core(), 1);
3957
+ var import_core15 = __toESM(require_core(), 1);
4156
3958
 
4157
3959
  // src/classic/typed-array-utils.ts
4158
3960
  var ERR_TYPE_DEDUCTION = "Failed to deduce GL constant from typed array";
@@ -4214,12 +4016,6 @@ ${source2}`;
4214
4016
  normalized: false,
4215
4017
  integer: false
4216
4018
  };
4217
- var PROP_CHECKS = {
4218
- deprecatedProps: {
4219
- instanced: "divisor",
4220
- isInstanced: "divisor"
4221
- }
4222
- };
4223
4019
  var Accessor = class {
4224
4020
  offset;
4225
4021
  stride;
@@ -4235,7 +4031,6 @@ ${source2}`;
4235
4031
  return ArrayType.BYTES_PER_ELEMENT;
4236
4032
  }
4237
4033
  static getBytesPerVertex(accessor) {
4238
- (0, import_core16.assert)(accessor.size);
4239
4034
  const ArrayType = getTypedArrayFromGLType(accessor.type || 5126 /* FLOAT */);
4240
4035
  return ArrayType.BYTES_PER_ELEMENT * accessor.size;
4241
4036
  }
@@ -4264,7 +4059,6 @@ ${source2}`;
4264
4059
  // PRIVATE
4265
4060
  // eslint-disable-next-line complexity, max-statements
4266
4061
  _assign(props = {}) {
4267
- props = (0, import_core16.checkProps)("Accessor", props, PROP_CHECKS);
4268
4062
  if (props.type !== void 0) {
4269
4063
  this.type = props.type;
4270
4064
  if (props.type === 5124 /* INT */ || props.type === 5125 /* UNSIGNED_INT */) {
@@ -4707,6 +4501,34 @@ ${source2}`;
4707
4501
  throw new Error("Illegal uniform");
4708
4502
  }
4709
4503
 
4504
+ // ../../node_modules/@math.gl/types/dist/is-array.js
4505
+ function isTypedArray(value) {
4506
+ return ArrayBuffer.isView(value) && !(value instanceof DataView) ? value : null;
4507
+ }
4508
+ function isNumericArray(value) {
4509
+ if (Array.isArray(value)) {
4510
+ return value.length === 0 || typeof value[0] === "number" ? value : null;
4511
+ }
4512
+ return isTypedArray(value);
4513
+ }
4514
+
4515
+ // src/utils/split-uniforms-and-bindings.ts
4516
+ function isUniformValue(value) {
4517
+ return isNumericArray(value) !== null || typeof value === "number" || typeof value === "boolean";
4518
+ }
4519
+ function splitUniformsAndBindings(uniforms) {
4520
+ const result = { bindings: {}, uniforms: {} };
4521
+ Object.keys(uniforms).forEach((name) => {
4522
+ const uniform = uniforms[name];
4523
+ if (isUniformValue(uniform)) {
4524
+ result.uniforms[name] = uniform;
4525
+ } else {
4526
+ result.bindings[name] = uniform;
4527
+ }
4528
+ });
4529
+ return result;
4530
+ }
4531
+
4710
4532
  // src/adapter/helpers/webgl-topology-utils.ts
4711
4533
  function getGLDrawMode(topology) {
4712
4534
  switch (topology) {
@@ -4716,14 +4538,10 @@ ${source2}`;
4716
4538
  return 1 /* LINES */;
4717
4539
  case "line-strip":
4718
4540
  return 3 /* LINE_STRIP */;
4719
- case "line-loop-webgl":
4720
- return 2 /* LINE_LOOP */;
4721
4541
  case "triangle-list":
4722
4542
  return 4 /* TRIANGLES */;
4723
4543
  case "triangle-strip":
4724
4544
  return 5 /* TRIANGLE_STRIP */;
4725
- case "triangle-fan-webgl":
4726
- return 6 /* TRIANGLE_FAN */;
4727
4545
  default:
4728
4546
  throw new Error(topology);
4729
4547
  }
@@ -4736,14 +4554,10 @@ ${source2}`;
4736
4554
  return 1 /* LINES */;
4737
4555
  case "line-strip":
4738
4556
  return 1 /* LINES */;
4739
- case "line-loop-webgl":
4740
- return 1 /* LINES */;
4741
4557
  case "triangle-list":
4742
4558
  return 4 /* TRIANGLES */;
4743
4559
  case "triangle-strip":
4744
4560
  return 4 /* TRIANGLES */;
4745
- case "triangle-fan-webgl":
4746
- return 4 /* TRIANGLES */;
4747
4561
  default:
4748
4562
  throw new Error(topology);
4749
4563
  }
@@ -4751,7 +4565,7 @@ ${source2}`;
4751
4565
 
4752
4566
  // src/adapter/resources/webgl-render-pipeline.ts
4753
4567
  var LOG_PROGRAM_PERF_PRIORITY = 4;
4754
- var WEBGLRenderPipeline = class extends import_core17.RenderPipeline {
4568
+ var WEBGLRenderPipeline = class extends import_core15.RenderPipeline {
4755
4569
  /** The WebGL device that created this render pipeline */
4756
4570
  device;
4757
4571
  /** Handle to underlying WebGL program */
@@ -4776,27 +4590,18 @@ ${source2}`;
4776
4590
  this.device = device;
4777
4591
  this.handle = this.props.handle || this.device.gl.createProgram();
4778
4592
  this.device.setSpectorMetadata(this.handle, { id: this.props.id });
4779
- this.vs = (0, import_core17.cast)(props.vs);
4780
- this.fs = (0, import_core17.cast)(props.fs);
4593
+ this.vs = props.vs;
4594
+ this.fs = props.fs;
4781
4595
  const { varyings, bufferMode = 35981 /* SEPARATE_ATTRIBS */ } = props;
4782
4596
  if (varyings && varyings.length > 0) {
4783
4597
  this.varyings = varyings;
4784
4598
  this.device.gl.transformFeedbackVaryings(this.handle, varyings, bufferMode);
4785
4599
  }
4786
4600
  this._linkShaders();
4787
- import_core17.log.time(1, `RenderPipeline ${this.id} - shaderLayout introspection`)();
4601
+ import_core15.log.time(1, `RenderPipeline ${this.id} - shaderLayout introspection`)();
4788
4602
  this.introspectedLayout = getShaderLayout(this.device.gl, this.handle);
4789
- import_core17.log.timeEnd(1, `RenderPipeline ${this.id} - shaderLayout introspection`)();
4790
- this.shaderLayout = (0, import_core18.mergeShaderLayout)(this.introspectedLayout, props.shaderLayout);
4791
- switch (this.props.topology) {
4792
- case "triangle-fan-webgl":
4793
- case "line-loop-webgl":
4794
- import_core17.log.warn(
4795
- `Primitive topology ${this.props.topology} is deprecated and will be removed in v9.1`
4796
- );
4797
- break;
4798
- default:
4799
- }
4603
+ import_core15.log.timeEnd(1, `RenderPipeline ${this.id} - shaderLayout introspection`)();
4604
+ this.shaderLayout = mergeShaderLayout(this.introspectedLayout, props.shaderLayout);
4800
4605
  }
4801
4606
  destroy() {
4802
4607
  if (this.handle) {
@@ -4814,14 +4619,15 @@ ${source2}`;
4814
4619
  if (!binding) {
4815
4620
  const validBindings = this.shaderLayout.bindings.map((binding2) => `"${binding2.name}"`).join(", ");
4816
4621
  if (!options?.disableWarnings) {
4817
- import_core17.log.warn(
4818
- `Unknown binding "${name}" in render pipeline "${this.id}", expected one of ${validBindings}`
4622
+ import_core15.log.warn(
4623
+ `No binding "${name}" in render pipeline "${this.id}", expected one of ${validBindings}`,
4624
+ value
4819
4625
  )();
4820
4626
  }
4821
4627
  continue;
4822
4628
  }
4823
4629
  if (!value) {
4824
- import_core17.log.warn(`Unsetting binding "${name}" in render pipeline "${this.id}"`)();
4630
+ import_core15.log.warn(`Unsetting binding "${name}" in render pipeline "${this.id}"`)();
4825
4631
  }
4826
4632
  switch (binding.type) {
4827
4633
  case "uniform":
@@ -4835,7 +4641,7 @@ ${source2}`;
4835
4641
  }
4836
4642
  break;
4837
4643
  case "sampler":
4838
- import_core17.log.warn(`Ignoring sampler ${name}`)();
4644
+ import_core15.log.warn(`Ignoring sampler ${name}`)();
4839
4645
  break;
4840
4646
  default:
4841
4647
  throw new Error(binding.type);
@@ -4867,17 +4673,13 @@ ${source2}`;
4867
4673
  const isIndexed = Boolean(vertexArray.indexBuffer);
4868
4674
  const glIndexType = vertexArray.indexBuffer?.glIndexType;
4869
4675
  if (this.linkStatus !== "success") {
4870
- import_core17.log.info(2, `RenderPipeline:${this.id}.draw() aborted - waiting for shader linking`)();
4676
+ import_core15.log.info(2, `RenderPipeline:${this.id}.draw() aborted - waiting for shader linking`)();
4871
4677
  return false;
4872
4678
  }
4873
- if (!this._areTexturesRenderable() || vertexCount === 0) {
4874
- import_core17.log.info(2, `RenderPipeline:${this.id}.draw() aborted - textures not yet loaded`)();
4679
+ if (!this._areTexturesRenderable()) {
4680
+ import_core15.log.info(2, `RenderPipeline:${this.id}.draw() aborted - textures not yet loaded`)();
4875
4681
  return false;
4876
4682
  }
4877
- if (vertexCount === 0) {
4878
- import_core17.log.info(2, `RenderPipeline:${this.id}.draw() aborted - no vertices to draw`)();
4879
- return true;
4880
- }
4881
4683
  this.device.gl.useProgram(this.handle);
4882
4684
  vertexArray.bindBeforeRender(renderPass);
4883
4685
  if (transformFeedback) {
@@ -4917,9 +4719,9 @@ ${source2}`;
4917
4719
  }
4918
4720
  // DEPRECATED METHODS
4919
4721
  setUniformsWebGL(uniforms) {
4920
- const { bindings } = (0, import_core17.splitUniformsAndBindings)(uniforms);
4722
+ const { bindings } = splitUniformsAndBindings(uniforms);
4921
4723
  Object.keys(bindings).forEach((name) => {
4922
- import_core17.log.warn(
4724
+ import_core15.log.warn(
4923
4725
  `Unsupported value "${JSON.stringify(
4924
4726
  bindings[name]
4925
4727
  )}" used in setUniforms() for key ${name}. Use setBindings() instead?`
@@ -4934,19 +4736,19 @@ ${source2}`;
4934
4736
  const { gl } = this.device;
4935
4737
  gl.attachShader(this.handle, this.vs.handle);
4936
4738
  gl.attachShader(this.handle, this.fs.handle);
4937
- import_core17.log.time(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
4739
+ import_core15.log.time(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
4938
4740
  gl.linkProgram(this.handle);
4939
- import_core17.log.timeEnd(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
4940
- if (import_core17.log.level === 0) {
4741
+ import_core15.log.timeEnd(LOG_PROGRAM_PERF_PRIORITY, `linkProgram for ${this.id}`)();
4742
+ if (import_core15.log.level === 0) {
4941
4743
  }
4942
4744
  if (!this.device.features.has("compilation-status-async-webgl")) {
4943
4745
  const status2 = this._getLinkStatus();
4944
4746
  this._reportLinkStatus(status2);
4945
4747
  return;
4946
4748
  }
4947
- import_core17.log.once(1, "RenderPipeline linking is asynchronous")();
4749
+ import_core15.log.once(1, "RenderPipeline linking is asynchronous")();
4948
4750
  await this._waitForLinkComplete();
4949
- import_core17.log.info(2, `RenderPipeline ${this.id} - async linking complete: ${this.linkStatus}`)();
4751
+ import_core15.log.info(2, `RenderPipeline ${this.id} - async linking complete: ${this.linkStatus}`)();
4950
4752
  const status = this._getLinkStatus();
4951
4753
  this._reportLinkStatus(status);
4952
4754
  }
@@ -5012,10 +4814,15 @@ ${source2}`;
5012
4814
  */
5013
4815
  _areTexturesRenderable() {
5014
4816
  let texturesRenderable = true;
4817
+ for (const bindingInfo of this.shaderLayout.bindings) {
4818
+ if (!this.bindings[bindingInfo.name] && !this.bindings[bindingInfo.name.replace(/Uniforms$/, "")]) {
4819
+ import_core15.log.warn(`Binding ${bindingInfo.name} not found in ${this.id}`)();
4820
+ texturesRenderable = false;
4821
+ }
4822
+ }
5015
4823
  for (const [, texture] of Object.entries(this.bindings)) {
5016
4824
  if (texture instanceof WEBGLTexture) {
5017
4825
  texture.update();
5018
- texturesRenderable = texturesRenderable && texture.loaded;
5019
4826
  }
5020
4827
  }
5021
4828
  return texturesRenderable;
@@ -5068,7 +4875,7 @@ ${source2}`;
5068
4875
  } else if (value instanceof WEBGLTexture) {
5069
4876
  texture = value;
5070
4877
  } else if (value instanceof WEBGLFramebuffer && value.colorAttachments[0] instanceof WEBGLTextureView) {
5071
- import_core17.log.warn(
4878
+ import_core15.log.warn(
5072
4879
  "Passing framebuffer in texture binding may be deprecated. Use fbo.colorAttachments[0] instead"
5073
4880
  )();
5074
4881
  texture = value.colorAttachments[0].texture;
@@ -5076,7 +4883,7 @@ ${source2}`;
5076
4883
  throw new Error("No texture");
5077
4884
  }
5078
4885
  gl.activeTexture(33984 /* TEXTURE0 */ + textureUnit);
5079
- gl.bindTexture(texture.target, texture.handle);
4886
+ gl.bindTexture(texture.glTarget, texture.handle);
5080
4887
  textureUnit += 1;
5081
4888
  break;
5082
4889
  case "sampler":
@@ -5101,16 +4908,29 @@ ${source2}`;
5101
4908
  }
5102
4909
  }
5103
4910
  };
4911
+ function mergeShaderLayout(baseLayout, overrideLayout) {
4912
+ const mergedLayout = {
4913
+ ...baseLayout,
4914
+ attributes: baseLayout.attributes.map((attribute) => ({ ...attribute }))
4915
+ };
4916
+ for (const attribute of overrideLayout?.attributes || []) {
4917
+ const baseAttribute = mergedLayout.attributes.find((attr) => attr.name === attribute.name);
4918
+ if (!baseAttribute) {
4919
+ import_core15.log.warn(`shader layout attribute ${attribute.name} not present in shader`);
4920
+ } else {
4921
+ baseAttribute.type = attribute.type || baseAttribute.type;
4922
+ baseAttribute.stepMode = attribute.stepMode || baseAttribute.stepMode;
4923
+ }
4924
+ }
4925
+ return mergedLayout;
4926
+ }
5104
4927
 
5105
4928
  // src/adapter/resources/webgl-command-encoder.ts
5106
- var import_core20 = __toESM(require_core(), 1);
4929
+ var import_core17 = __toESM(require_core(), 1);
5107
4930
 
5108
4931
  // src/adapter/resources/webgl-command-buffer.ts
5109
- var import_core19 = __toESM(require_core(), 1);
5110
- function cast2(value) {
5111
- return value;
5112
- }
5113
- var WEBGLCommandBuffer = class extends import_core19.CommandBuffer {
4932
+ var import_core16 = __toESM(require_core(), 1);
4933
+ var WEBGLCommandBuffer = class extends import_core16.CommandBuffer {
5114
4934
  device;
5115
4935
  commands = [];
5116
4936
  constructor(device) {
@@ -5137,8 +4957,8 @@ ${source2}`;
5137
4957
  }
5138
4958
  };
5139
4959
  function _copyBufferToBuffer(device, options) {
5140
- const source = cast2(options.source);
5141
- const destination = cast2(options.destination);
4960
+ const source = options.source;
4961
+ const destination = options.destination;
5142
4962
  device.gl.bindBuffer(36662 /* COPY_READ_BUFFER */, source.handle);
5143
4963
  device.gl.bindBuffer(36663 /* COPY_WRITE_BUFFER */, destination.handle);
5144
4964
  device.gl.copyBufferSubData(
@@ -5197,8 +5017,10 @@ ${source2}`;
5197
5017
  const webglBuffer = destination;
5198
5018
  const sourceWidth = width || framebuffer.width;
5199
5019
  const sourceHeight = height || framebuffer.height;
5200
- const sourceParams = getWebGLTextureParameters(framebuffer.texture.props.format);
5201
- const sourceFormat = sourceParams.dataFormat;
5020
+ const sourceParams = getTextureFormatWebGL(
5021
+ framebuffer.colorAttachments[0].texture.props.format
5022
+ );
5023
+ const sourceFormat = sourceParams.format;
5202
5024
  const sourceType = sourceParams.type;
5203
5025
  device.gl.bindBuffer(35051 /* PIXEL_PACK_BUFFER */, webglBuffer.handle);
5204
5026
  prevHandle = device.gl.bindFramebuffer(36160 /* FRAMEBUFFER */, framebuffer.handle);
@@ -5261,7 +5083,7 @@ ${source2}`;
5261
5083
  width = Number.isFinite(width) ? width : texture.width;
5262
5084
  height = Number.isFinite(height) ? height : texture.height;
5263
5085
  texture.bind(0);
5264
- textureTarget = texture.target;
5086
+ textureTarget = texture.glTarget;
5265
5087
  } else {
5266
5088
  throw new Error("invalid destination");
5267
5089
  }
@@ -5304,7 +5126,7 @@ ${source2}`;
5304
5126
  }
5305
5127
  }
5306
5128
  function getFramebuffer(source) {
5307
- if (source instanceof import_core19.Texture) {
5129
+ if (source instanceof import_core16.Texture) {
5308
5130
  const { width, height, id } = source;
5309
5131
  const framebuffer = source.device.createFramebuffer({
5310
5132
  id: `framebuffer-for-${id}`,
@@ -5318,7 +5140,7 @@ ${source2}`;
5318
5140
  }
5319
5141
 
5320
5142
  // src/adapter/resources/webgl-command-encoder.ts
5321
- var WEBGLCommandEncoder = class extends import_core20.CommandEncoder {
5143
+ var WEBGLCommandEncoder = class extends import_core17.CommandEncoder {
5322
5144
  device;
5323
5145
  commandBuffer;
5324
5146
  constructor(device, props) {
@@ -5357,8 +5179,31 @@ ${source2}`;
5357
5179
  };
5358
5180
 
5359
5181
  // src/adapter/resources/webgl-vertex-array.ts
5360
- var import_core21 = __toESM(require_core(), 1);
5361
- var WEBGLVertexArray = class extends import_core21.VertexArray {
5182
+ var import_core18 = __toESM(require_core(), 1);
5183
+
5184
+ // src/utils/fill-array.ts
5185
+ function fillArray(options) {
5186
+ const { target, source, start = 0, count = 1 } = options;
5187
+ const length = source.length;
5188
+ const total = count * length;
5189
+ let copied = 0;
5190
+ for (let i = start; copied < length; copied++) {
5191
+ target[i++] = source[copied];
5192
+ }
5193
+ while (copied < total) {
5194
+ if (copied < total - copied) {
5195
+ target.copyWithin(start + copied, start, start + copied);
5196
+ copied *= 2;
5197
+ } else {
5198
+ target.copyWithin(start + copied, start, start + total - copied);
5199
+ copied = total;
5200
+ }
5201
+ }
5202
+ return options.target;
5203
+ }
5204
+
5205
+ // src/adapter/resources/webgl-vertex-array.ts
5206
+ var WEBGLVertexArray = class extends import_core18.VertexArray {
5362
5207
  get [Symbol.toStringTag]() {
5363
5208
  return "VertexArray";
5364
5209
  }
@@ -5526,8 +5371,8 @@ ${source2}`;
5526
5371
  this.buffer = this.buffer || this.device.createBuffer({ byteLength });
5527
5372
  updateNeeded = updateNeeded || !compareConstantArrayValues(constantValue, this.bufferValue);
5528
5373
  if (updateNeeded) {
5529
- const typedArray = (0, import_core21.getScratchArray)(value.constructor, length);
5530
- (0, import_core21.fillArray)({ target: typedArray, source: constantValue, start: 0, count: length });
5374
+ const typedArray = (0, import_core18.getScratchArray)(value.constructor, length);
5375
+ fillArray({ target: typedArray, source: constantValue, start: 0, count: length });
5531
5376
  this.buffer.write(typedArray);
5532
5377
  this.bufferValue = value;
5533
5378
  }
@@ -5553,8 +5398,8 @@ ${source2}`;
5553
5398
  }
5554
5399
 
5555
5400
  // src/adapter/resources/webgl-transform-feedback.ts
5556
- var import_core22 = __toESM(require_core(), 1);
5557
- var WEBGLTransformFeedback = class extends import_core22.TransformFeedback {
5401
+ var import_core19 = __toESM(require_core(), 1);
5402
+ var WEBGLTransformFeedback = class extends import_core19.TransformFeedback {
5558
5403
  device;
5559
5404
  gl;
5560
5405
  handle;
@@ -5617,7 +5462,7 @@ ${source2}`;
5617
5462
  const { buffer, byteLength, byteOffset } = this._getBufferRange(bufferOrRange);
5618
5463
  if (location < 0) {
5619
5464
  this.unusedBuffers[locationOrName] = buffer;
5620
- import_core22.log.warn(`${this.id} unusedBuffers varying buffer ${locationOrName}`)();
5465
+ import_core19.log.warn(`${this.id} unusedBuffers varying buffer ${locationOrName}`)();
5621
5466
  return;
5622
5467
  }
5623
5468
  this.buffers[location] = { buffer, byteLength, byteOffset };
@@ -5704,8 +5549,8 @@ ${source2}`;
5704
5549
  }
5705
5550
 
5706
5551
  // src/adapter/resources/webgl-query-set.ts
5707
- var import_core23 = __toESM(require_core(), 1);
5708
- var WEBGLQuerySet = class extends import_core23.QuerySet {
5552
+ var import_core20 = __toESM(require_core(), 1);
5553
+ var WEBGLQuerySet = class extends import_core20.QuerySet {
5709
5554
  device;
5710
5555
  handle;
5711
5556
  target = null;
@@ -5838,10 +5683,9 @@ ${source2}`;
5838
5683
  };
5839
5684
 
5840
5685
  // src/classic/copy-and-blit.ts
5841
- var import_core25 = __toESM(require_core(), 1);
5686
+ var import_core21 = __toESM(require_core(), 1);
5842
5687
 
5843
5688
  // src/classic/format-utils.ts
5844
- var import_core24 = __toESM(require_core(), 1);
5845
5689
  function glFormatToComponents(format) {
5846
5690
  switch (format) {
5847
5691
  case 6406 /* ALPHA */:
@@ -5858,7 +5702,6 @@ ${source2}`;
5858
5702
  case 34836 /* RGBA32F */:
5859
5703
  return 4;
5860
5704
  default:
5861
- (0, import_core24.assert)(false);
5862
5705
  return 0;
5863
5706
  }
5864
5707
  }
@@ -5873,7 +5716,6 @@ ${source2}`;
5873
5716
  case 5126 /* FLOAT */:
5874
5717
  return 4;
5875
5718
  default:
5876
- (0, import_core24.assert)(false);
5877
5719
  return 0;
5878
5720
  }
5879
5721
  }
@@ -5883,7 +5725,6 @@ ${source2}`;
5883
5725
  const {
5884
5726
  sourceX = 0,
5885
5727
  sourceY = 0,
5886
- sourceFormat = 6408 /* RGBA */,
5887
5728
  sourceAttachment = 36064 /* COLOR_ATTACHMENT0 */
5888
5729
  // TODO - support gl.readBuffer
5889
5730
  } = options || {};
@@ -5892,16 +5733,19 @@ ${source2}`;
5892
5733
  // following parameters are auto deduced if not provided
5893
5734
  sourceWidth,
5894
5735
  sourceHeight,
5736
+ sourceDepth,
5737
+ sourceFormat,
5895
5738
  sourceType
5896
5739
  } = options || {};
5897
5740
  const { framebuffer, deleteFramebuffer } = getFramebuffer2(source);
5898
- (0, import_core25.assert)(framebuffer);
5899
5741
  const { gl, handle } = framebuffer;
5900
- sourceWidth = sourceWidth || framebuffer.width;
5901
- sourceHeight = sourceHeight || framebuffer.height;
5902
5742
  const attachment = sourceAttachment - 36064 /* COLOR_ATTACHMENT0 */;
5903
- sourceType = sourceType || framebuffer.colorAttachments[attachment]?.texture?.type || 5121 /* UNSIGNED_BYTE */;
5904
- target = getPixelArray(target, sourceType, sourceFormat, sourceWidth, sourceHeight);
5743
+ sourceWidth ||= framebuffer.width;
5744
+ sourceHeight ||= framebuffer.height;
5745
+ sourceDepth = framebuffer.colorAttachments[attachment]?.texture?.depth || 1;
5746
+ sourceFormat ||= framebuffer.colorAttachments[attachment]?.texture?.glFormat || 6408 /* RGBA */;
5747
+ sourceType ||= framebuffer.colorAttachments[attachment]?.texture?.glType || 5121 /* UNSIGNED_BYTE */;
5748
+ target = getPixelArray(target, sourceType, sourceFormat, sourceWidth, sourceHeight, sourceDepth);
5905
5749
  sourceType = sourceType || getGLTypeFromTypedArray(target);
5906
5750
  const prevHandle = gl.bindFramebuffer(36160 /* FRAMEBUFFER */, handle);
5907
5751
  gl.readPixels(sourceX, sourceY, sourceWidth, sourceHeight, sourceFormat, sourceType, target);
@@ -5921,7 +5765,6 @@ ${source2}`;
5921
5765
  } = options || {};
5922
5766
  let { sourceWidth, sourceHeight, sourceType } = options || {};
5923
5767
  const { framebuffer, deleteFramebuffer } = getFramebuffer2(source);
5924
- (0, import_core25.assert)(framebuffer);
5925
5768
  sourceWidth = sourceWidth || framebuffer.width;
5926
5769
  sourceHeight = sourceHeight || framebuffer.height;
5927
5770
  const webglFramebuffer = framebuffer;
@@ -5949,7 +5792,7 @@ ${source2}`;
5949
5792
  return webglBufferTarget;
5950
5793
  }
5951
5794
  function getFramebuffer2(source) {
5952
- if (!(source instanceof import_core25.Framebuffer)) {
5795
+ if (!(source instanceof import_core21.Framebuffer)) {
5953
5796
  return { framebuffer: toFramebuffer(source), deleteFramebuffer: true };
5954
5797
  }
5955
5798
  return { framebuffer: source, deleteFramebuffer: false };
@@ -5965,7 +5808,7 @@ ${source2}`;
5965
5808
  });
5966
5809
  return framebuffer;
5967
5810
  }
5968
- function getPixelArray(pixelArray, type, format, width, height) {
5811
+ function getPixelArray(pixelArray, type, format, width, height, depth) {
5969
5812
  if (pixelArray) {
5970
5813
  return pixelArray;
5971
5814
  }
@@ -5976,11 +5819,9 @@ ${source2}`;
5976
5819
  }
5977
5820
 
5978
5821
  // src/classic/clear.ts
5979
- var import_core26 = __toESM(require_core(), 1);
5980
5822
  var GL_DEPTH_BUFFER_BIT2 = 256;
5981
5823
  var GL_STENCIL_BUFFER_BIT2 = 1024;
5982
5824
  var GL_COLOR_BUFFER_BIT2 = 16384;
5983
- var ERR_ARGUMENTS = "clear: bad arguments";
5984
5825
  function clear(device, options) {
5985
5826
  const { framebuffer = null, color = null, depth = null, stencil = null } = options || {};
5986
5827
  const parameters = {};
@@ -6006,7 +5847,6 @@ ${source2}`;
6006
5847
  parameters.clearStencil = depth;
6007
5848
  }
6008
5849
  }
6009
- (0, import_core26.assert)(clearFlags !== 0, ERR_ARGUMENTS);
6010
5850
  const gl = device.gl;
6011
5851
  withGLParameters(gl, parameters, () => {
6012
5852
  gl.clear(clearFlags);
@@ -6014,8 +5854,10 @@ ${source2}`;
6014
5854
  }
6015
5855
 
6016
5856
  // src/adapter/webgl-device.ts
6017
- var LOG_LEVEL2 = 1;
6018
- var _WebGLDevice = class extends import_core27.Device {
5857
+ var WebGLDevice = class extends import_core22.Device {
5858
+ //
5859
+ // Public `Device` API
5860
+ //
6019
5861
  /** type of this device */
6020
5862
  type = "webgl";
6021
5863
  /** The underlying WebGL context */
@@ -6026,66 +5868,21 @@ ${source2}`;
6026
5868
  canvasContext;
6027
5869
  lost;
6028
5870
  _resolveContextLost;
6029
- //
6030
- // Static methods, expected to be present by `luma.createDevice()`
6031
- //
6032
- /** Check if WebGL 2 is available */
6033
- static isSupported() {
6034
- return typeof WebGL2RenderingContext !== "undefined";
6035
- }
6036
- /**
6037
- * Get a device instance from a GL context
6038
- * Creates and instruments the device if not already created
6039
- * @param gl
6040
- * @returns
6041
- */
6042
- static attach(gl) {
6043
- if (gl instanceof _WebGLDevice) {
6044
- return gl;
6045
- }
6046
- if (gl?.device instanceof import_core27.Device) {
6047
- return gl.device;
6048
- }
6049
- if (!isWebGL(gl)) {
6050
- throw new Error("Invalid WebGL2RenderingContext");
6051
- }
6052
- return new _WebGLDevice({ gl });
6053
- }
6054
- static async create(props = {}) {
6055
- import_core27.log.groupCollapsed(LOG_LEVEL2, "WebGLDevice created")();
6056
- const promises = [];
6057
- if (props.debug) {
6058
- promises.push(loadWebGLDeveloperTools());
6059
- }
6060
- if (props.spector) {
6061
- promises.push(loadSpectorJS());
6062
- }
6063
- if (typeof props.canvas === "string") {
6064
- promises.push(import_core27.CanvasContext.pageLoaded);
6065
- }
6066
- const results = await Promise.allSettled(promises);
6067
- for (const result of results) {
6068
- if (result.status === "rejected") {
6069
- import_core27.log.error(`Failed to initialize debug libraries ${result.reason}`)();
6070
- }
6071
- }
6072
- import_core27.log.probe(LOG_LEVEL2 + 1, "DOM is loaded")();
6073
- if (props.gl?.device) {
6074
- import_core27.log.warn("reattaching existing device")();
6075
- return _WebGLDevice.attach(props.gl);
6076
- }
6077
- const device = new _WebGLDevice(props);
6078
- const message2 = `Created ${device.type}${device.debug ? " debug" : ""} context: ${device.info.vendor}, ${device.info.renderer} for canvas: ${device.canvasContext.id}`;
6079
- import_core27.log.probe(LOG_LEVEL2, message2)();
6080
- import_core27.log.table(LOG_LEVEL2, device.info)();
6081
- import_core27.log.groupEnd(LOG_LEVEL2)();
6082
- return device;
6083
- }
5871
+ /** WebGL2 context. */
5872
+ gl;
5873
+ debug = false;
5874
+ /** State used by luma.gl classes: TODO - move to canvasContext*/
5875
+ _canvasSizeInfo = { clientWidth: 0, clientHeight: 0, devicePixelRatio: 1 };
5876
+ /** State used by luma.gl classes - TODO - not used? */
5877
+ _extensions = {};
5878
+ _polyfilled = false;
5879
+ /** Instance of Spector.js (if initialized) */
5880
+ spectorJS;
6084
5881
  //
6085
5882
  // Public API
6086
5883
  //
6087
5884
  constructor(props) {
6088
- super({ ...props, id: props.id || (0, import_core27.uid)("webgl-device") });
5885
+ super({ ...props, id: props.id || uid("webgl-device") });
6089
5886
  const device = props.gl?.device;
6090
5887
  if (device) {
6091
5888
  throw new Error(`WebGL context already attached to device ${device.id}`);
@@ -6095,24 +5892,20 @@ ${source2}`;
6095
5892
  this.lost = new Promise((resolve) => {
6096
5893
  this._resolveContextLost = resolve;
6097
5894
  });
6098
- let gl = props.gl || null;
6099
- gl ||= createBrowserContext(this.canvasContext.canvas, {
5895
+ this.handle = createBrowserContext(this.canvasContext.canvas, {
6100
5896
  ...props,
6101
5897
  onContextLost: (event) => this._resolveContextLost?.({
6102
5898
  reason: "destroyed",
6103
5899
  message: "Entered sleep mode, or too many apps or browser tabs are using the GPU."
6104
5900
  })
6105
5901
  });
6106
- if (!gl) {
5902
+ this.gl = this.handle;
5903
+ if (!this.handle) {
6107
5904
  throw new Error("WebGL context creation failed");
6108
5905
  }
6109
- this.handle = gl;
6110
- this.gl = gl;
5906
+ this.spectorJS = initializeSpectorJS({ ...this.props, gl: this.handle });
6111
5907
  this.gl.device = this;
6112
5908
  this.gl._version = 2;
6113
- if (props.spector) {
6114
- this.spectorJS = initializeSpectorJS({ ...this.props, canvas: this.handle.canvas });
6115
- }
6116
5909
  this.info = getDeviceInfo(this.gl, this._extensions);
6117
5910
  this.limits = new WebGLDeviceLimits(this.gl);
6118
5911
  this.features = new WebGLDeviceFeatures(this.gl, this._extensions, this.props.disabledFeatures);
@@ -6120,17 +5913,15 @@ ${source2}`;
6120
5913
  this.features.initializeFeatures();
6121
5914
  }
6122
5915
  this.canvasContext.resize();
6123
- const { enable: enable2 = true, copyState = false } = props;
6124
- trackContextState(this.gl, {
6125
- enable: enable2,
6126
- copyState,
6127
- log: (...args) => import_core27.log.log(1, ...args)()
5916
+ const glState = new WebGLStateTracker(this.gl, {
5917
+ log: (...args) => import_core22.log.log(1, ...args)()
6128
5918
  });
5919
+ glState.trackState(this.gl, { copyState: false });
6129
5920
  if (props.debug) {
6130
5921
  this.gl = makeDebugContext(this.gl, { ...props, throwOnError: true });
6131
5922
  this.debug = true;
6132
- import_core27.log.level = Math.max(import_core27.log.level, 1);
6133
- import_core27.log.warn("WebGL debug mode activated. Performance reduced.")();
5923
+ import_core22.log.level = Math.max(import_core22.log.level, 1);
5924
+ import_core22.log.warn("WebGL debug mode activated. Performance reduced.")();
6134
5925
  }
6135
5926
  }
6136
5927
  /**
@@ -6142,9 +5933,6 @@ ${source2}`;
6142
5933
  get isLost() {
6143
5934
  return this.gl.isContextLost();
6144
5935
  }
6145
- getSize() {
6146
- return [this.gl.drawingBufferWidth, this.gl.drawingBufferHeight];
6147
- }
6148
5936
  isTextureFormatSupported(format) {
6149
5937
  return isTextureFormatSupported(this.gl, format, this._extensions);
6150
5938
  }
@@ -6162,6 +5950,7 @@ ${source2}`;
6162
5950
  const newProps = this._getBufferProps(props);
6163
5951
  return new WEBGLBuffer(this, newProps);
6164
5952
  }
5953
+ // _createTexture(props: TextureProps): WEBGLTexture {
6165
5954
  _createTexture(props) {
6166
5955
  return new WEBGLTexture(this, props);
6167
5956
  }
@@ -6199,7 +5988,7 @@ ${source2}`;
6199
5988
  throw new Error("ComputePass not supported in WebGL");
6200
5989
  }
6201
5990
  renderPass = null;
6202
- createCommandEncoder(props) {
5991
+ createCommandEncoder(props = {}) {
6203
5992
  return new WEBGLCommandEncoder(this, props);
6204
5993
  }
6205
5994
  /**
@@ -6235,22 +6024,12 @@ ${source2}`;
6235
6024
  clear(this, options);
6236
6025
  }
6237
6026
  resetWebGL() {
6238
- import_core27.log.warn("WebGLDevice.resetWebGL is deprecated, use only for debugging")();
6027
+ import_core22.log.warn("WebGLDevice.resetWebGL is deprecated, use only for debugging")();
6239
6028
  resetGLParameters(this.gl);
6240
6029
  }
6241
6030
  //
6242
6031
  // WebGL-only API (not part of `Device` API)
6243
6032
  //
6244
- /** WebGL2 context. */
6245
- gl;
6246
- debug = false;
6247
- /** State used by luma.gl classes: TODO - move to canvasContext*/
6248
- _canvasSizeInfo = { clientWidth: 0, clientHeight: 0, devicePixelRatio: 1 };
6249
- /** State used by luma.gl classes - TODO - not used? */
6250
- _extensions = {};
6251
- _polyfilled = false;
6252
- /** Instance of Spector.js (if initialized) */
6253
- spectorJS;
6254
6033
  /**
6255
6034
  * Triggers device (or WebGL context) loss.
6256
6035
  * @note primarily intended for testing how application reacts to device loss
@@ -6271,11 +6050,13 @@ ${source2}`;
6271
6050
  }
6272
6051
  /** Save current WebGL context state onto an internal stack */
6273
6052
  pushState() {
6274
- pushContextState(this.gl);
6053
+ const webglState = WebGLStateTracker.get(this.gl);
6054
+ webglState.push();
6275
6055
  }
6276
6056
  /** Restores previously saved context state */
6277
6057
  popState() {
6278
- popContextState(this.gl);
6058
+ const webglState = WebGLStateTracker.get(this.gl);
6059
+ webglState.pop();
6279
6060
  }
6280
6061
  /**
6281
6062
  * Storing data on a special field on WebGLObjects makes that data visible in SPECTOR chrome debug extension
@@ -6312,7 +6093,7 @@ ${source2}`;
6312
6093
  this._constants = this._constants || new Array(maxVertexAttributes).fill(null);
6313
6094
  const currentConstant = this._constants[location];
6314
6095
  if (currentConstant && compareConstantArrayValues2(currentConstant, constant)) {
6315
- import_core27.log.info(
6096
+ import_core22.log.info(
6316
6097
  1,
6317
6098
  `setConstantAttributeWebGL(${location}) could have been skipped, value unchanged`
6318
6099
  )();
@@ -6329,7 +6110,7 @@ ${source2}`;
6329
6110
  setConstantUintArray(this, location, constant);
6330
6111
  break;
6331
6112
  default:
6332
- (0, import_core27.assert)(false);
6113
+ throw new Error("constant");
6333
6114
  }
6334
6115
  }
6335
6116
  /** Ensure extensions are only requested once */
@@ -6338,18 +6119,6 @@ ${source2}`;
6338
6119
  return this._extensions;
6339
6120
  }
6340
6121
  };
6341
- var WebGLDevice = _WebGLDevice;
6342
- //
6343
- // Public `Device` API
6344
- //
6345
- /** type of this device */
6346
- __publicField(WebGLDevice, "type", "webgl");
6347
- function isWebGL(gl) {
6348
- if (typeof WebGL2RenderingContext !== "undefined" && gl instanceof WebGL2RenderingContext) {
6349
- return true;
6350
- }
6351
- return Boolean(gl && Number.isFinite(gl._version));
6352
- }
6353
6122
  function setConstantFloatArray(device, location, array) {
6354
6123
  switch (array.length) {
6355
6124
  case 1:
@@ -6365,7 +6134,6 @@ ${source2}`;
6365
6134
  device.gl.vertexAttrib4fv(location, array);
6366
6135
  break;
6367
6136
  default:
6368
- (0, import_core27.assert)(false);
6369
6137
  }
6370
6138
  }
6371
6139
  function setConstantIntArray(device, location, array) {
@@ -6386,216 +6154,180 @@ ${source2}`;
6386
6154
  return true;
6387
6155
  }
6388
6156
 
6389
- // src/adapter/objects/webgl-resource.ts
6390
- var import_core28 = __toESM(require_core(), 1);
6391
- var ERR_RESOURCE_METHOD_UNDEFINED = "Resource subclass must define virtual methods";
6392
- var WebGLResource = class extends import_core28.Resource {
6393
- device;
6394
- gl;
6395
- gl2;
6396
- _handle;
6397
- _bound = false;
6398
- // Only meaningful for resources that allocate GPU memory
6399
- byteLength = 0;
6400
- constructor(device, props, defaultProps) {
6401
- super(device, props, defaultProps);
6402
- this.device = device;
6403
- const gl = this.device.gl;
6404
- const { id } = props || {};
6405
- this.gl = gl;
6406
- this.gl2 = gl;
6407
- this.id = id || (0, import_core28.uid)(this.constructor.name);
6408
- this._handle = props?.handle;
6409
- if (this._handle === void 0) {
6410
- this._handle = this._createHandle();
6411
- }
6412
- this.byteLength = 0;
6157
+ // src/context/polyfills/polyfill-webgl1-extensions.ts
6158
+ var WEBGL1_STATIC_EXTENSIONS = {
6159
+ WEBGL_depth_texture: {
6160
+ UNSIGNED_INT_24_8_WEBGL: 34042 /* UNSIGNED_INT_24_8 */
6161
+ },
6162
+ OES_element_index_uint: {},
6163
+ OES_texture_float: {},
6164
+ OES_texture_half_float: {
6165
+ // @ts-expect-error different numbers?
6166
+ HALF_FLOAT_OES: 5131 /* HALF_FLOAT */
6167
+ },
6168
+ EXT_color_buffer_float: {},
6169
+ OES_standard_derivatives: {
6170
+ FRAGMENT_SHADER_DERIVATIVE_HINT_OES: 35723 /* FRAGMENT_SHADER_DERIVATIVE_HINT */
6171
+ },
6172
+ EXT_frag_depth: {},
6173
+ EXT_blend_minmax: {
6174
+ MIN_EXT: 32775 /* MIN */,
6175
+ MAX_EXT: 32776 /* MAX */
6176
+ },
6177
+ EXT_shader_texture_lod: {}
6178
+ };
6179
+ var getWEBGL_draw_buffers = (gl) => ({
6180
+ drawBuffersWEBGL(buffers) {
6181
+ return gl.drawBuffers(buffers);
6182
+ },
6183
+ COLOR_ATTACHMENT0_WEBGL: 36064 /* COLOR_ATTACHMENT0 */,
6184
+ COLOR_ATTACHMENT1_WEBGL: 36065 /* COLOR_ATTACHMENT1 */,
6185
+ COLOR_ATTACHMENT2_WEBGL: 36066 /* COLOR_ATTACHMENT2 */,
6186
+ COLOR_ATTACHMENT3_WEBGL: 36067 /* COLOR_ATTACHMENT3 */
6187
+ });
6188
+ var getOES_vertex_array_object = (gl) => ({
6189
+ VERTEX_ARRAY_BINDING_OES: 34229 /* VERTEX_ARRAY_BINDING */,
6190
+ createVertexArrayOES() {
6191
+ return gl.createVertexArray();
6192
+ },
6193
+ deleteVertexArrayOES(vertexArray) {
6194
+ return gl.deleteVertexArray(vertexArray);
6195
+ },
6196
+ isVertexArrayOES(vertexArray) {
6197
+ return gl.isVertexArray(vertexArray);
6198
+ },
6199
+ bindVertexArrayOES(vertexArray) {
6200
+ return gl.bindVertexArray(vertexArray);
6413
6201
  }
6414
- toString() {
6415
- return `${this.constructor.name}(${this.id})`;
6202
+ });
6203
+ var getANGLE_instanced_arrays = (gl) => ({
6204
+ VERTEX_ATTRIB_ARRAY_DIVISOR_ANGLE: 35070,
6205
+ drawArraysInstancedANGLE(...args) {
6206
+ return gl.drawArraysInstanced(...args);
6207
+ },
6208
+ drawElementsInstancedANGLE(...args) {
6209
+ return gl.drawElementsInstanced(...args);
6210
+ },
6211
+ vertexAttribDivisorANGLE(...args) {
6212
+ return gl.vertexAttribDivisor(...args);
6416
6213
  }
6417
- get handle() {
6418
- return this._handle;
6214
+ });
6215
+ function enforceWebGL2(enforce = true) {
6216
+ const prototype = HTMLCanvasElement.prototype;
6217
+ if (!enforce && prototype.originalGetContext) {
6218
+ prototype.getContext = prototype.originalGetContext;
6219
+ prototype.originalGetContext = void 0;
6220
+ return;
6419
6221
  }
6420
- delete({ deleteChildren = false } = {}) {
6421
- const children = this._handle && this._deleteHandle(this._handle);
6422
- if (this._handle) {
6423
- this.removeStats();
6424
- }
6425
- this._handle = null;
6426
- if (children && deleteChildren) {
6427
- children.filter(Boolean).forEach((child) => child.destroy());
6222
+ prototype.originalGetContext = prototype.getContext;
6223
+ prototype.getContext = function(contextId, options) {
6224
+ if (contextId === "webgl" || contextId === "experimental-webgl") {
6225
+ const context = this.originalGetContext("webgl2", options);
6226
+ if (context instanceof HTMLElement) {
6227
+ polyfillWebGL1Extensions(context);
6228
+ }
6229
+ return context;
6428
6230
  }
6429
- return this;
6430
- }
6431
- bind(funcOrHandle = this.handle) {
6432
- if (typeof funcOrHandle !== "function") {
6433
- this._bindHandle(funcOrHandle);
6434
- return this;
6231
+ return this.originalGetContext(contextId, options);
6232
+ };
6233
+ }
6234
+ function polyfillWebGL1Extensions(gl) {
6235
+ gl.getExtension("EXT_color_buffer_float");
6236
+ const boundExtensions = {
6237
+ ...WEBGL1_STATIC_EXTENSIONS,
6238
+ WEBGL_disjoint_timer_query: gl.getExtension("EXT_disjoint_timer_query_webgl2"),
6239
+ WEBGL_draw_buffers: getWEBGL_draw_buffers(gl),
6240
+ OES_vertex_array_object: getOES_vertex_array_object(gl),
6241
+ ANGLE_instanced_arrays: getANGLE_instanced_arrays(gl)
6242
+ };
6243
+ const originalGetExtension = gl.getExtension;
6244
+ gl.getExtension = function(extensionName) {
6245
+ const ext = originalGetExtension.call(gl, extensionName);
6246
+ if (ext) {
6247
+ return ext;
6435
6248
  }
6436
- let value;
6437
- if (!this._bound) {
6438
- this._bindHandle(this.handle);
6439
- this._bound = true;
6440
- value = funcOrHandle();
6441
- this._bound = false;
6442
- this._bindHandle(null);
6443
- } else {
6444
- value = funcOrHandle();
6249
+ if (extensionName in boundExtensions) {
6250
+ return boundExtensions[extensionName];
6445
6251
  }
6446
- return value;
6447
- }
6448
- unbind() {
6449
- this.bind(null);
6450
- }
6451
- // Install stubs for removed methods
6452
- stubRemovedMethods(className, version, methodNames) {
6453
- return (0, import_core28.stubRemovedMethods)(this, className, version, methodNames);
6454
- }
6455
- // PUBLIC VIRTUAL METHODS
6456
- initialize(props) {
6457
- }
6458
- // PROTECTED METHODS - These must be overridden by subclass
6459
- _createHandle() {
6460
- throw new Error(ERR_RESOURCE_METHOD_UNDEFINED);
6461
- }
6462
- _deleteHandle() {
6463
- throw new Error(ERR_RESOURCE_METHOD_UNDEFINED);
6464
- }
6465
- _bindHandle(handle) {
6466
- throw new Error(ERR_RESOURCE_METHOD_UNDEFINED);
6467
- }
6468
- _getOptsFromHandle() {
6469
- throw new Error(ERR_RESOURCE_METHOD_UNDEFINED);
6252
+ return null;
6253
+ };
6254
+ const originalGetSupportedExtensions = gl.getSupportedExtensions;
6255
+ gl.getSupportedExtensions = function() {
6256
+ const extensions = originalGetSupportedExtensions.apply(gl) || [];
6257
+ return extensions?.concat(Object.keys(boundExtensions));
6258
+ };
6259
+ }
6260
+
6261
+ // src/adapter/webgl-adapter.ts
6262
+ var LOG_LEVEL2 = 1;
6263
+ var WebGLAdapter = class extends import_core23.Adapter {
6264
+ /** type of device's created by this adapter */
6265
+ type = "webgl";
6266
+ constructor() {
6267
+ super();
6268
+ import_core23.Device.defaultProps = { ...import_core23.Device.defaultProps, ...DEFAULT_SPECTOR_PROPS };
6269
+ WebGLDevice.adapter = this;
6470
6270
  }
6471
- _getParameter(pname, props) {
6472
- throw new Error(ERR_RESOURCE_METHOD_UNDEFINED);
6271
+ /** Check if WebGL 2 is available */
6272
+ isSupported() {
6273
+ return typeof WebGL2RenderingContext !== "undefined";
6473
6274
  }
6474
- _setParameter(pname, value) {
6475
- throw new Error(ERR_RESOURCE_METHOD_UNDEFINED);
6275
+ /** Force any created WebGL contexts to be WebGL2 contexts, polyfilled with WebGL1 extensions */
6276
+ enforceWebGL2(enable2) {
6277
+ enforceWebGL2(enable2);
6476
6278
  }
6477
- // PRIVATE METHODS
6478
- /*
6479
- _addStats() {
6480
- const name = this.constructor.name;
6481
- const stats = lumaStats.get('Resource Counts');
6482
-
6483
- stats.get('Resources Created').incrementCount();
6484
- stats.get(`${name}s Created`).incrementCount();
6485
- stats.get(`${name}s Active`).incrementCount();
6486
- }
6487
-
6488
- _removeStats() {
6489
- const name = this.constructor.name;
6490
- const stats = lumaStats.get('Resource Counts');
6491
-
6492
- stats.get(`${name}s Active`).decrementCount();
6279
+ /**
6280
+ * Get a device instance from a GL context
6281
+ * Creates and instruments the device if not already created
6282
+ * @param gl
6283
+ * @returns
6284
+ */
6285
+ async attach(gl) {
6286
+ if (gl instanceof WebGLDevice) {
6287
+ return gl;
6493
6288
  }
6494
-
6495
- trackAllocatedMemory(bytes, name = this.constructor.name) {
6496
- const stats = lumaStats.get('Memory Usage');
6497
-
6498
- stats.get('GPU Memory').addCount(bytes);
6499
- stats.get(`${name} Memory`).addCount(bytes);
6500
- this.byteLength = bytes;
6289
+ if (gl?.device instanceof import_core23.Device) {
6290
+ return gl.device;
6501
6291
  }
6502
-
6503
- trackDeallocatedMemory(name = this.constructor.name) {
6504
- const stats = lumaStats.get('Memory Usage');
6505
-
6506
- stats.get('GPU Memory').subtractCount(this.byteLength);
6507
- stats.get(`${name} Memory`).subtractCount(this.byteLength);
6508
- this.byteLength = 0;
6292
+ if (!isWebGL(gl)) {
6293
+ throw new Error("Invalid WebGL2RenderingContext");
6509
6294
  }
6510
- */
6511
- };
6512
-
6513
- // src/adapter/objects/webgl-renderbuffer.ts
6514
- var import_core29 = __toESM(require_core(), 1);
6515
- var _WEBGLRenderbuffer = class extends WebGLResource {
6516
- get [Symbol.toStringTag]() {
6517
- return "Renderbuffer";
6518
- }
6519
- get width() {
6520
- return this.props.width;
6521
- }
6522
- get height() {
6523
- return this.props.height;
6524
- }
6525
- get format() {
6526
- return this.props.format;
6527
- }
6528
- get samples() {
6529
- return this.props.samples;
6530
- }
6531
- get attachment() {
6532
- return;
6295
+ return new WebGLDevice({ gl });
6533
6296
  }
6534
- /** WebGL format constant */
6535
- glFormat;
6536
- static isTextureFormatSupported(device, format) {
6537
- return isRenderbufferFormatSupported(device.gl, format, device._extensions);
6538
- }
6539
- constructor(device, props) {
6540
- if (typeof props.format === "number") {
6541
- throw new Error("Renderbuffer");
6297
+ async create(props = {}) {
6298
+ import_core23.log.groupCollapsed(LOG_LEVEL2, "WebGLDevice created")();
6299
+ const promises = [];
6300
+ if (props.debug) {
6301
+ promises.push(loadWebGLDeveloperTools());
6542
6302
  }
6543
- super(device, props, _WEBGLRenderbuffer.defaultProps);
6544
- this.glFormat = convertTextureFormatToGL(this.props.format);
6545
- this._initialize(this.props);
6546
- }
6547
- resize(size) {
6548
- if (size.width !== this.width || size.height !== this.height) {
6549
- Object.assign(this.props, { ...size, format: this.format, samples: this.samples });
6550
- this._initialize(this.props);
6303
+ if (props.debugWithSpectorJS) {
6304
+ promises.push(loadSpectorJS(props));
6551
6305
  }
6552
- }
6553
- // PRIVATE METHODS
6554
- /** Creates and initializes a renderbuffer object's data store */
6555
- _initialize(props) {
6556
- const { format, width, height, samples } = props;
6557
- (0, import_core29.assert)(format, "Needs format");
6558
- this.trackDeallocatedMemory();
6559
- this.gl.bindRenderbuffer(36161 /* RENDERBUFFER */, this.handle);
6560
- if (samples !== 0) {
6561
- this.gl.renderbufferStorageMultisample(
6562
- 36161 /* RENDERBUFFER */,
6563
- samples,
6564
- this.glFormat,
6565
- width,
6566
- height
6567
- );
6568
- } else {
6569
- this.gl.renderbufferStorage(36161 /* RENDERBUFFER */, this.glFormat, width, height);
6306
+ if (typeof props.canvas === "string") {
6307
+ promises.push(import_core23.CanvasContext.pageLoaded);
6570
6308
  }
6571
- this.gl.bindRenderbuffer(36161 /* RENDERBUFFER */, null);
6572
- this.trackAllocatedMemory(
6573
- width * height * (samples || 1) * getTextureFormatBytesPerPixel(this.format)
6574
- );
6575
- }
6576
- // RESOURCE IMPLEMENTATION
6577
- _createHandle() {
6578
- return this.gl.createRenderbuffer();
6579
- }
6580
- _deleteHandle() {
6581
- this.gl.deleteRenderbuffer(this.handle);
6582
- this.trackDeallocatedMemory();
6583
- }
6584
- _bindHandle(handle) {
6585
- this.gl.bindRenderbuffer(36161 /* RENDERBUFFER */, handle);
6309
+ const results = await Promise.allSettled(promises);
6310
+ for (const result of results) {
6311
+ if (result.status === "rejected") {
6312
+ import_core23.log.error(`Failed to initialize debug libraries ${result.reason}`)();
6313
+ }
6314
+ }
6315
+ import_core23.log.probe(LOG_LEVEL2 + 1, "DOM is loaded")();
6316
+ const device = new WebGLDevice(props);
6317
+ const message2 = `Created ${device.type}${device.debug ? " debug" : ""} context: ${device.info.vendor}, ${device.info.renderer} for canvas: ${device.canvasContext.id}`;
6318
+ import_core23.log.probe(LOG_LEVEL2, message2)();
6319
+ import_core23.log.table(LOG_LEVEL2, device.info)();
6320
+ import_core23.log.groupEnd(LOG_LEVEL2)();
6321
+ return device;
6586
6322
  }
6587
6323
  };
6588
- var WEBGLRenderbuffer = _WEBGLRenderbuffer;
6589
- __publicField(WEBGLRenderbuffer, "defaultProps", {
6590
- id: void 0,
6591
- handle: void 0,
6592
- userData: void 0,
6593
- format: void 0,
6594
- // 'depth16unorm'
6595
- width: 1,
6596
- height: 1,
6597
- samples: 0
6598
- });
6324
+ function isWebGL(gl) {
6325
+ if (typeof WebGL2RenderingContext !== "undefined" && gl instanceof WebGL2RenderingContext) {
6326
+ return true;
6327
+ }
6328
+ return Boolean(gl && Number.isFinite(gl._version));
6329
+ }
6330
+ var webgl2Adapter = new WebGLAdapter();
6599
6331
  return __toCommonJS(bundle_exports);
6600
6332
  })();
6601
6333
  return __exports__;