@luma.gl/engine 9.3.0-alpha.6 → 9.3.0-alpha.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (128) hide show
  1. package/dist/animation-loop/animation-loop.d.ts.map +1 -1
  2. package/dist/animation-loop/animation-loop.js +3 -0
  3. package/dist/animation-loop/animation-loop.js.map +1 -1
  4. package/dist/compute/computation.d.ts +3 -7
  5. package/dist/compute/computation.d.ts.map +1 -1
  6. package/dist/compute/computation.js +14 -12
  7. package/dist/compute/computation.js.map +1 -1
  8. package/dist/dist.dev.js +1751 -831
  9. package/dist/dist.min.js +296 -148
  10. package/dist/dynamic-texture/dynamic-texture.d.ts +9 -2
  11. package/dist/dynamic-texture/dynamic-texture.d.ts.map +1 -1
  12. package/dist/dynamic-texture/dynamic-texture.js +54 -5
  13. package/dist/dynamic-texture/dynamic-texture.js.map +1 -1
  14. package/dist/dynamic-texture/texture-data.d.ts +4 -1
  15. package/dist/dynamic-texture/texture-data.d.ts.map +1 -1
  16. package/dist/dynamic-texture/texture-data.js +19 -2
  17. package/dist/dynamic-texture/texture-data.js.map +1 -1
  18. package/dist/geometry/gpu-geometry.d.ts.map +1 -1
  19. package/dist/geometry/gpu-geometry.js +8 -3
  20. package/dist/geometry/gpu-geometry.js.map +1 -1
  21. package/dist/index.cjs +1711 -847
  22. package/dist/index.cjs.map +4 -4
  23. package/dist/index.d.ts +12 -3
  24. package/dist/index.d.ts.map +1 -1
  25. package/dist/index.js +8 -3
  26. package/dist/index.js.map +1 -1
  27. package/dist/material/material-factory.d.ts +73 -0
  28. package/dist/material/material-factory.d.ts.map +1 -0
  29. package/dist/material/material-factory.js +111 -0
  30. package/dist/material/material-factory.js.map +1 -0
  31. package/dist/material/material.d.ts +84 -0
  32. package/dist/material/material.d.ts.map +1 -0
  33. package/dist/material/material.js +176 -0
  34. package/dist/material/material.js.map +1 -0
  35. package/dist/model/model.d.ts +14 -6
  36. package/dist/model/model.d.ts.map +1 -1
  37. package/dist/model/model.js +69 -25
  38. package/dist/model/model.js.map +1 -1
  39. package/dist/model/split-uniforms-and-bindings.d.ts +4 -3
  40. package/dist/model/split-uniforms-and-bindings.d.ts.map +1 -1
  41. package/dist/model/split-uniforms-and-bindings.js +2 -2
  42. package/dist/model/split-uniforms-and-bindings.js.map +1 -1
  43. package/dist/models/directional-light-model.d.ts +7 -0
  44. package/dist/models/directional-light-model.d.ts.map +1 -0
  45. package/dist/models/directional-light-model.js +23 -0
  46. package/dist/models/directional-light-model.js.map +1 -0
  47. package/dist/models/light-model-utils.d.ts +69 -0
  48. package/dist/models/light-model-utils.d.ts.map +1 -0
  49. package/dist/models/light-model-utils.js +395 -0
  50. package/dist/models/light-model-utils.js.map +1 -0
  51. package/dist/models/point-light-model.d.ts +7 -0
  52. package/dist/models/point-light-model.d.ts.map +1 -0
  53. package/dist/models/point-light-model.js +22 -0
  54. package/dist/models/point-light-model.js.map +1 -0
  55. package/dist/models/spot-light-model.d.ts +7 -0
  56. package/dist/models/spot-light-model.d.ts.map +1 -0
  57. package/dist/models/spot-light-model.js +23 -0
  58. package/dist/models/spot-light-model.js.map +1 -0
  59. package/dist/modules/picking/color-picking.d.ts +5 -9
  60. package/dist/modules/picking/color-picking.d.ts.map +1 -1
  61. package/dist/modules/picking/color-picking.js +122 -115
  62. package/dist/modules/picking/color-picking.js.map +1 -1
  63. package/dist/modules/picking/index-picking.d.ts +2 -2
  64. package/dist/modules/picking/index-picking.d.ts.map +1 -1
  65. package/dist/modules/picking/index-picking.js +36 -10
  66. package/dist/modules/picking/index-picking.js.map +1 -1
  67. package/dist/modules/picking/legacy-color-picking.d.ts +26 -0
  68. package/dist/modules/picking/legacy-color-picking.d.ts.map +1 -0
  69. package/dist/modules/picking/legacy-color-picking.js +7 -0
  70. package/dist/modules/picking/legacy-color-picking.js.map +1 -0
  71. package/dist/modules/picking/picking-manager.d.ts +29 -3
  72. package/dist/modules/picking/picking-manager.d.ts.map +1 -1
  73. package/dist/modules/picking/picking-manager.js +188 -41
  74. package/dist/modules/picking/picking-manager.js.map +1 -1
  75. package/dist/modules/picking/picking-uniforms.d.ts +12 -11
  76. package/dist/modules/picking/picking-uniforms.d.ts.map +1 -1
  77. package/dist/modules/picking/picking-uniforms.js +26 -13
  78. package/dist/modules/picking/picking-uniforms.js.map +1 -1
  79. package/dist/modules/picking/picking.d.ts +25 -0
  80. package/dist/modules/picking/picking.d.ts.map +1 -0
  81. package/dist/modules/picking/picking.js +18 -0
  82. package/dist/modules/picking/picking.js.map +1 -0
  83. package/dist/shader-inputs.d.ts +9 -7
  84. package/dist/shader-inputs.d.ts.map +1 -1
  85. package/dist/shader-inputs.js +84 -4
  86. package/dist/shader-inputs.js.map +1 -1
  87. package/dist/utils/shader-module-utils.d.ts +7 -0
  88. package/dist/utils/shader-module-utils.d.ts.map +1 -0
  89. package/dist/utils/shader-module-utils.js +46 -0
  90. package/dist/utils/shader-module-utils.js.map +1 -0
  91. package/package.json +4 -4
  92. package/src/animation-loop/animation-loop.ts +3 -0
  93. package/src/compute/computation.ts +31 -17
  94. package/src/dynamic-texture/dynamic-texture.ts +79 -7
  95. package/src/dynamic-texture/texture-data.ts +25 -4
  96. package/src/geometry/gpu-geometry.ts +8 -3
  97. package/src/index.ts +29 -4
  98. package/src/material/material-factory.ts +157 -0
  99. package/src/material/material.ts +254 -0
  100. package/src/model/model.ts +108 -40
  101. package/src/model/split-uniforms-and-bindings.ts +8 -6
  102. package/src/models/directional-light-model.ts +32 -0
  103. package/src/models/light-model-utils.ts +587 -0
  104. package/src/models/point-light-model.ts +31 -0
  105. package/src/models/spot-light-model.ts +32 -0
  106. package/src/modules/picking/color-picking.ts +123 -122
  107. package/src/modules/picking/index-picking.ts +36 -10
  108. package/src/modules/picking/legacy-color-picking.ts +8 -0
  109. package/src/modules/picking/picking-manager.ts +252 -50
  110. package/src/modules/picking/picking-uniforms.ts +38 -23
  111. package/src/modules/picking/picking.ts +22 -0
  112. package/src/shader-inputs.ts +165 -15
  113. package/src/utils/shader-module-utils.ts +65 -0
  114. package/dist/factories/pipeline-factory.d.ts +0 -39
  115. package/dist/factories/pipeline-factory.d.ts.map +0 -1
  116. package/dist/factories/pipeline-factory.js +0 -216
  117. package/dist/factories/pipeline-factory.js.map +0 -1
  118. package/dist/factories/shader-factory.d.ts +0 -19
  119. package/dist/factories/shader-factory.d.ts.map +0 -1
  120. package/dist/factories/shader-factory.js +0 -83
  121. package/dist/factories/shader-factory.js.map +0 -1
  122. package/dist/types.d.ts +0 -7
  123. package/dist/types.d.ts.map +0 -1
  124. package/dist/types.js +0 -5
  125. package/dist/types.js.map +0 -1
  126. package/src/factories/pipeline-factory.ts +0 -266
  127. package/src/factories/shader-factory.ts +0 -101
  128. package/src/types.ts +0 -11
@@ -3,19 +3,18 @@
3
3
  // Copyright (c) vis.gl contributors
4
4
 
5
5
  // A lot of imports, but then Model is where it all comes together...
6
- import type {TypedArray} from '@math.gl/types';
7
- import type {
8
- RenderPipelineProps,
9
- RenderPipelineParameters,
10
- BufferLayout,
11
- Shader,
12
- VertexArray,
13
- TransformFeedback,
14
- AttributeInfo,
15
- Binding,
16
- PrimitiveTopology
17
- } from '@luma.gl/core';
6
+ import {type TypedArray} from '@math.gl/types';
18
7
  import {
8
+ type RenderPipelineProps,
9
+ type RenderPipelineParameters,
10
+ type BufferLayout,
11
+ type Shader,
12
+ type VertexArray,
13
+ type TransformFeedback,
14
+ type AttributeInfo,
15
+ type Binding,
16
+ type BindingsByGroup,
17
+ type PrimitiveTopology,
19
18
  Device,
20
19
  DeviceFeature,
21
20
  Buffer,
@@ -24,27 +23,33 @@ import {
24
23
  Sampler,
25
24
  RenderPipeline,
26
25
  RenderPass,
26
+ PipelineFactory,
27
+ ShaderFactory,
27
28
  UniformStore,
28
29
  log,
29
- getTypedArrayConstructor,
30
- getAttributeInfosFromLayouts
30
+ dataTypeDecoder,
31
+ getAttributeInfosFromLayouts,
32
+ normalizeBindingsByGroup
31
33
  } from '@luma.gl/core';
32
34
 
33
- import type {ShaderModule, PlatformInfo} from '@luma.gl/shadertools';
35
+ import type {ShaderBindingDebugRow, ShaderModule, PlatformInfo} from '@luma.gl/shadertools';
34
36
  import {ShaderAssembler} from '@luma.gl/shadertools';
35
37
 
36
38
  import type {Geometry} from '../geometry/geometry';
37
39
  import {GPUGeometry, makeGPUGeometry} from '../geometry/gpu-geometry';
38
- import {PipelineFactory} from '../factories/pipeline-factory';
39
- import {ShaderFactory} from '../factories/shader-factory';
40
40
  import {getDebugTableForShaderLayout} from '../debug/debug-shader-layout';
41
41
  import {debugFramebuffer} from '../debug/debug-framebuffer';
42
42
  import {deepEqual} from '../utils/deep-equal';
43
43
  import {BufferLayoutHelper} from '../utils/buffer-layout-helper';
44
44
  import {sortedBufferLayoutByShaderSourceLocations} from '../utils/buffer-layout-order';
45
+ import {
46
+ mergeShaderModuleBindingsIntoLayout,
47
+ shaderModuleHasUniforms
48
+ } from '../utils/shader-module-utils';
45
49
  import {uid} from '../utils/uid';
46
50
  import {ShaderInputs} from '../shader-inputs';
47
51
  import {DynamicTexture} from '../dynamic-texture/dynamic-texture';
52
+ import {Material} from '../material/material';
48
53
 
49
54
  const LOG_DRAW_PRIORITY = 2;
50
55
  const LOG_DRAW_TIMEOUT = 10000;
@@ -62,6 +67,8 @@ export type ModelProps = Omit<RenderPipelineProps, 'vs' | 'fs' | 'bindings'> & {
62
67
 
63
68
  /** Shader inputs, used to generated uniform buffers and bindings */
64
69
  shaderInputs?: ShaderInputs;
70
+ /** Material-owned group-3 bindings */
71
+ material?: Material;
65
72
  /** Bindings */
66
73
  bindings?: Record<string, Binding | DynamicTexture>;
67
74
  /** WebGL-only uniforms */
@@ -143,6 +150,7 @@ export class Model {
143
150
  vertexCount: 0,
144
151
 
145
152
  shaderInputs: undefined!,
153
+ material: undefined!,
146
154
  pipelineFactory: undefined!,
147
155
  shaderFactory: undefined!,
148
156
  transformFeedback: undefined!,
@@ -216,6 +224,7 @@ export class Model {
216
224
  /** ShaderInputs instance */
217
225
  // @ts-expect-error Assigned in function called by constructor
218
226
  shaderInputs: ShaderInputs;
227
+ material: Material | null = null;
219
228
  // @ts-expect-error Assigned in function called by constructor
220
229
  _uniformStore: UniformStore;
221
230
 
@@ -229,6 +238,7 @@ export class Model {
229
238
 
230
239
  /** "Time" of last draw. Monotonically increasing timestamp */
231
240
  _lastDrawTimestamp: number = -1;
241
+ private _bindingTable: ShaderBindingDebugRow[] = [];
232
242
 
233
243
  get [Symbol.toStringTag](): string {
234
244
  return 'Model';
@@ -246,6 +256,8 @@ export class Model {
246
256
 
247
257
  Object.assign(this.userData, props.userData);
248
258
 
259
+ this.material = props.material || null;
260
+
249
261
  // Setup shader module inputs
250
262
  const moduleMap = Object.fromEntries(
251
263
  this.props.modules?.map(module => [module.name, module]) || []
@@ -265,6 +277,9 @@ export class Model {
265
277
  // @ts-ignore shaderInputs is assigned in setShaderInputs above.
266
278
  (this.props.modules?.length > 0 ? this.props.modules : this.shaderInputs?.getModules()) || [];
267
279
 
280
+ this.props.shaderLayout =
281
+ mergeShaderModuleBindingsIntoLayout(this.props.shaderLayout, modules) || null;
282
+
268
283
  const isWebGPU = this.device.type === 'webgpu';
269
284
 
270
285
  // WebGPU
@@ -272,7 +287,7 @@ export class Model {
272
287
  // TODO - this is wrong, compile a single shader
273
288
  if (isWebGPU && this.props.source) {
274
289
  // WGSL
275
- const {source, getUniforms} = this.props.shaderAssembler.assembleWGSLShader({
290
+ const {source, getUniforms, bindingTable} = this.props.shaderAssembler.assembleWGSLShader({
276
291
  platformInfo,
277
292
  ...this.props,
278
293
  modules
@@ -280,9 +295,16 @@ export class Model {
280
295
  this.source = source;
281
296
  // @ts-expect-error
282
297
  this._getModuleUniforms = getUniforms;
298
+ this._bindingTable = bindingTable;
283
299
  // Extract shader layout after modules have been added to WGSL source, to include any bindings added by modules
284
- // @ts-expect-error Method on WebGPUDevice
285
- this.props.shaderLayout ||= device.getShaderLayout(this.source);
300
+ const inferredShaderLayout = (
301
+ device as Device & {getShaderLayout?: (source: string) => any}
302
+ ).getShaderLayout?.(this.source);
303
+ this.props.shaderLayout =
304
+ mergeShaderModuleBindingsIntoLayout(
305
+ this.props.shaderLayout || inferredShaderLayout || null,
306
+ modules
307
+ ) || null;
286
308
  } else {
287
309
  // GLSL
288
310
  const {vs, fs, getUniforms} = this.props.shaderAssembler.assembleGLSLShaderPair({
@@ -295,6 +317,7 @@ export class Model {
295
317
  this.fs = fs;
296
318
  // @ts-expect-error
297
319
  this._getModuleUniforms = getUniforms;
320
+ this._bindingTable = [];
298
321
  }
299
322
 
300
323
  this.vertexCount = this.props.vertexCount;
@@ -389,6 +412,11 @@ export class Model {
389
412
  this._needsRedraw ||= reason;
390
413
  }
391
414
 
415
+ /** Returns WGSL binding debug rows for the assembled shader. Returns an empty array for GLSL models. */
416
+ getBindingDebugTable(): readonly ShaderBindingDebugRow[] {
417
+ return this._bindingTable;
418
+ }
419
+
392
420
  /** Update uniforms and pipeline state prior to drawing. */
393
421
  predraw(): void {
394
422
  // Update uniform buffers if needed
@@ -427,6 +455,7 @@ export class Model {
427
455
  this.pipeline = this._updatePipeline();
428
456
 
429
457
  const syncBindings = this._getBindings();
458
+ const syncBindGroups = this._getBindGroups();
430
459
 
431
460
  const {indexBuffer} = this.vertexArray;
432
461
  const indexCount = indexBuffer
@@ -445,6 +474,8 @@ export class Model {
445
474
  // and WebGL uniforms must be supplied on every draw instead of being stored
446
475
  // on the pipeline instance.
447
476
  bindings: syncBindings,
477
+ bindGroups: syncBindGroups,
478
+ _bindGroupCacheKeys: this._getBindGroupCacheKeys(),
448
479
  uniforms: this.props.uniforms,
449
480
  // WebGL shares underlying cached pipelines even for models that have different parameters and topology,
450
481
  // so we must provide our unique parameters to each draw
@@ -573,7 +604,7 @@ export class Model {
573
604
  this._uniformStore = new UniformStore(this.shaderInputs.modules);
574
605
  // Create uniform buffer bindings for all modules that actually have uniforms
575
606
  for (const [moduleName, module] of Object.entries(this.shaderInputs.modules)) {
576
- if (shaderModuleHasUniforms(module)) {
607
+ if (shaderModuleHasUniforms(module) && !this.material?.ownsModule(moduleName)) {
577
608
  const uniformBuffer = this._uniformStore.getManagedUniformBuffer(this.device, moduleName);
578
609
  this.bindings[`${moduleName}Uniforms`] = uniformBuffer;
579
610
  }
@@ -581,10 +612,15 @@ export class Model {
581
612
  this.setNeedsRedraw('shaderInputs');
582
613
  }
583
614
 
615
+ setMaterial(material: Material | null): void {
616
+ this.material = material;
617
+ this.setNeedsRedraw('material');
618
+ }
619
+
584
620
  /** Update uniform buffers from the model's shader inputs */
585
621
  updateShaderInputs(): void {
586
622
  this._uniformStore.setUniforms(this.shaderInputs.getUniformValues());
587
- this.setBindings(this.shaderInputs.getBindingValues());
623
+ this.setBindings(this._getNonMaterialBindings(this.shaderInputs.getBindingValues()));
588
624
  // TODO - this is already tracked through buffer/texture update times?
589
625
  this.setNeedsRedraw('shaderInputs');
590
626
  }
@@ -703,6 +739,11 @@ export class Model {
703
739
  return binding.id;
704
740
  }
705
741
  }
742
+ for (const binding of Object.values(this.material?.bindings || {})) {
743
+ if (binding instanceof DynamicTexture && !binding.isReady) {
744
+ return binding.id;
745
+ }
746
+ }
706
747
  return false;
707
748
  }
708
749
 
@@ -724,6 +765,32 @@ export class Model {
724
765
  return validBindings;
725
766
  }
726
767
 
768
+ _getBindGroups(): BindingsByGroup {
769
+ const shaderLayout = this.pipeline?.shaderLayout || this.props.shaderLayout || {bindings: []};
770
+ const bindGroups = shaderLayout.bindings.length
771
+ ? normalizeBindingsByGroup(shaderLayout, this._getBindings())
772
+ : {0: this._getBindings()};
773
+
774
+ if (!this.material) {
775
+ return bindGroups;
776
+ }
777
+
778
+ for (const [groupKey, groupBindings] of Object.entries(this.material.getBindingsByGroup())) {
779
+ const group = Number(groupKey);
780
+ bindGroups[group] = {
781
+ ...(bindGroups[group] || {}),
782
+ ...groupBindings
783
+ };
784
+ }
785
+
786
+ return bindGroups;
787
+ }
788
+
789
+ _getBindGroupCacheKeys(): Partial<Record<number, object>> {
790
+ const bindGroupCacheKey = this.material?.getBindGroupCacheKey(3);
791
+ return bindGroupCacheKey ? {3: bindGroupCacheKey} : {};
792
+ }
793
+
727
794
  /** Get the timestamp of the latest updated bound GPU memory resource (buffer/texture). */
728
795
  _getBindingsUpdateTimestamp(): number {
729
796
  let timestamp = 0;
@@ -741,7 +808,7 @@ export class Model {
741
808
  timestamp = Math.max(timestamp, binding.buffer.updateTimestamp);
742
809
  }
743
810
  }
744
- return timestamp;
811
+ return Math.max(timestamp, this.material?.getBindingsUpdateTimestamp() || 0);
745
812
  }
746
813
 
747
814
  /**
@@ -813,12 +880,11 @@ export class Model {
813
880
 
814
881
  this.pipeline = this.pipelineFactory.createRenderPipeline({
815
882
  ...this.props,
883
+ bindings: undefined,
816
884
  bufferLayout: this.bufferLayout,
817
885
  topology: this.topology,
818
886
  parameters: this.parameters,
819
- // TODO - why set bindings here when we reset them every frame?
820
- // Should we expose a BindGroup abstraction?
821
- bindings: this._getBindings(),
887
+ bindGroups: this._getBindGroups(),
822
888
  vs,
823
889
  fs
824
890
  });
@@ -919,15 +985,27 @@ export class Model {
919
985
 
920
986
  // TODO - fix typing of luma data types
921
987
  _getBufferOrConstantValues(attribute: Buffer | TypedArray, dataType: any): string {
922
- const TypedArrayConstructor = getTypedArrayConstructor(dataType);
988
+ const TypedArrayConstructor = dataTypeDecoder.getTypedArrayConstructor(dataType);
923
989
  const typedArray =
924
990
  attribute instanceof Buffer ? new TypedArrayConstructor(attribute.debugData) : attribute;
925
991
  return typedArray.toString();
926
992
  }
927
- }
928
993
 
929
- function shaderModuleHasUniforms(module: ShaderModule): boolean {
930
- return Boolean(module.uniformTypes && !isObjectEmpty(module.uniformTypes));
994
+ private _getNonMaterialBindings(
995
+ bindings: Record<string, Binding | DynamicTexture>
996
+ ): Record<string, Binding | DynamicTexture> {
997
+ if (!this.material) {
998
+ return bindings;
999
+ }
1000
+
1001
+ const filteredBindings: Record<string, Binding | DynamicTexture> = {};
1002
+ for (const [name, binding] of Object.entries(bindings)) {
1003
+ if (!this.material.ownsBinding(name)) {
1004
+ filteredBindings[name] = binding;
1005
+ }
1006
+ }
1007
+ return filteredBindings;
1008
+ }
931
1009
  }
932
1010
 
933
1011
  // HELPERS
@@ -943,13 +1021,3 @@ export function getPlatformInfo(device: Device): PlatformInfo {
943
1021
  features: device.features as unknown as Set<DeviceFeature>
944
1022
  };
945
1023
  }
946
-
947
- /** Returns true if given object is empty, false otherwise. */
948
- function isObjectEmpty(obj: object): boolean {
949
- // @ts-ignore key is unused
950
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
951
- for (const key in obj) {
952
- return false;
953
- }
954
- return true;
955
- }
@@ -2,7 +2,8 @@
2
2
  // SPDX-License-Identifier: MIT
3
3
  // Copyright (c) vis.gl contributors
4
4
 
5
- import type {UniformValue, Binding} from '@luma.gl/core';
5
+ import type {Binding, CompositeShaderType, UniformValue} from '@luma.gl/core';
6
+ import type {ShaderModuleUniformValue} from '@luma.gl/shadertools';
6
7
  import {isNumericArray} from '@math.gl/types';
7
8
 
8
9
  export function isUniformValue(value: unknown): value is UniformValue {
@@ -11,19 +12,20 @@ export function isUniformValue(value: unknown): value is UniformValue {
11
12
 
12
13
  type UniformsAndBindings = {
13
14
  bindings: Record<string, Binding>;
14
- uniforms: Record<string, UniformValue>;
15
+ uniforms: Record<string, ShaderModuleUniformValue>;
15
16
  };
16
17
 
17
18
  export function splitUniformsAndBindings(
18
- uniforms: Record<string, Binding | UniformValue>
19
+ uniforms: Record<string, Binding | ShaderModuleUniformValue>,
20
+ uniformTypes: Readonly<Record<string, CompositeShaderType>> = {}
19
21
  ): UniformsAndBindings {
20
22
  const result: UniformsAndBindings = {bindings: {}, uniforms: {}};
21
23
  Object.keys(uniforms).forEach(name => {
22
24
  const uniform = uniforms[name];
23
- if (isUniformValue(uniform)) {
24
- result.uniforms[name] = uniform;
25
+ if (Object.prototype.hasOwnProperty.call(uniformTypes, name) || isUniformValue(uniform)) {
26
+ result.uniforms[name] = uniform as ShaderModuleUniformValue;
25
27
  } else {
26
- result.bindings[name] = uniform;
28
+ result.bindings[name] = uniform as Binding;
27
29
  }
28
30
  });
29
31
 
@@ -0,0 +1,32 @@
1
+ // luma.gl
2
+ // SPDX-License-Identifier: MIT
3
+ // Copyright (c) vis.gl contributors
4
+
5
+ import {Device} from '@luma.gl/core';
6
+ import {ConeGeometry} from '../geometries/cone-geometry';
7
+ import {
8
+ BaseLightModel,
9
+ buildDirectionalLightInstanceData,
10
+ type DirectionalLightModelProps
11
+ } from './light-model-utils';
12
+
13
+ const DIRECTIONAL_LIGHT_GEOMETRY = new ConeGeometry({
14
+ cap: true,
15
+ nradial: 12,
16
+ nvertical: 1,
17
+ radius: 1
18
+ });
19
+
20
+ export type {DirectionalLightModelProps} from './light-model-utils';
21
+
22
+ export class DirectionalLightModel extends BaseLightModel<DirectionalLightModelProps> {
23
+ constructor(device: Device, props: DirectionalLightModelProps) {
24
+ super(device, props, {
25
+ anchorMode: 'apex',
26
+ buildInstanceData: buildDirectionalLightInstanceData,
27
+ geometry: DIRECTIONAL_LIGHT_GEOMETRY,
28
+ idPrefix: 'directional-light-model',
29
+ sizePropNames: ['directionalLightLength']
30
+ });
31
+ }
32
+ }