super-three 0.172.0 → 0.173.0

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 (178) hide show
  1. package/LICENSE +1 -1
  2. package/build/three.cjs +439 -380
  3. package/build/three.core.js +413 -41
  4. package/build/three.core.min.js +2 -2
  5. package/build/three.module.js +28 -344
  6. package/build/three.module.min.js +2 -2
  7. package/build/three.tsl.js +11 -3
  8. package/build/three.tsl.min.js +2 -2
  9. package/build/three.webgpu.js +7550 -1798
  10. package/build/three.webgpu.min.js +2 -2
  11. package/build/three.webgpu.nodes.js +7551 -1798
  12. package/build/three.webgpu.nodes.min.js +2 -2
  13. package/examples/jsm/animation/CCDIKSolver.js +6 -5
  14. package/examples/jsm/capabilities/WebGPU.js +1 -1
  15. package/examples/jsm/controls/ArcballControls.js +23 -21
  16. package/examples/jsm/exporters/GLTFExporter.js +26 -25
  17. package/examples/jsm/geometries/TextGeometry.js +1 -12
  18. package/examples/jsm/interactive/InteractiveGroup.js +108 -51
  19. package/examples/jsm/libs/demuxer_mp4.js +109 -0
  20. package/examples/jsm/loaders/GCodeLoader.js +3 -1
  21. package/examples/jsm/loaders/GLTFLoader.js +0 -2
  22. package/examples/jsm/loaders/TDSLoader.js +0 -1
  23. package/examples/jsm/materials/MeshGouraudMaterial.js +2 -0
  24. package/examples/jsm/misc/GPUComputationRenderer.js +6 -7
  25. package/examples/jsm/misc/ProgressiveLightMap.js +4 -3
  26. package/examples/jsm/misc/ProgressiveLightMapGPU.js +4 -3
  27. package/examples/jsm/misc/Volume.js +7 -5
  28. package/examples/jsm/misc/VolumeSlice.js +5 -3
  29. package/examples/jsm/objects/WaterMesh.js +25 -20
  30. package/examples/jsm/physics/JoltPhysics.js +7 -7
  31. package/examples/jsm/physics/RapierPhysics.js +4 -4
  32. package/examples/jsm/postprocessing/OutputPass.js +2 -0
  33. package/examples/jsm/shaders/OutputShader.js +5 -1
  34. package/examples/jsm/transpiler/GLSLDecoder.js +2 -2
  35. package/examples/jsm/transpiler/TSLEncoder.js +2 -0
  36. package/package.json +1 -1
  37. package/src/Three.Core.js +2 -0
  38. package/src/Three.TSL.js +9 -1
  39. package/src/cameras/ArrayCamera.js +1 -0
  40. package/src/constants.js +6 -1
  41. package/src/core/BufferAttribute.js +4 -0
  42. package/src/core/EventDispatcher.js +8 -6
  43. package/src/extras/ImageUtils.js +1 -11
  44. package/src/loaders/nodes/NodeObjectLoader.js +1 -1
  45. package/src/materials/nodes/MeshBasicNodeMaterial.js +1 -1
  46. package/src/materials/nodes/MeshPhysicalNodeMaterial.js +1 -1
  47. package/src/materials/nodes/NodeMaterial.js +5 -5
  48. package/src/materials/nodes/NodeMaterials.js +0 -1
  49. package/src/materials/nodes/PointsNodeMaterial.js +109 -7
  50. package/src/materials/nodes/SpriteNodeMaterial.js +1 -1
  51. package/src/materials/nodes/VolumeNodeMaterial.js +3 -3
  52. package/src/materials/nodes/manager/NodeMaterialObserver.js +8 -0
  53. package/src/nodes/Nodes.js +4 -0
  54. package/src/nodes/TSL.js +4 -0
  55. package/src/nodes/accessors/Arrays.js +30 -8
  56. package/src/nodes/accessors/BatchNode.js +3 -3
  57. package/src/nodes/accessors/BufferAttributeNode.js +1 -1
  58. package/src/nodes/accessors/Camera.js +64 -3
  59. package/src/nodes/accessors/InstanceNode.js +1 -1
  60. package/src/nodes/accessors/MaterialNode.js +9 -9
  61. package/src/nodes/accessors/ModelViewProjectionNode.js +1 -1
  62. package/src/nodes/accessors/Normal.js +6 -2
  63. package/src/nodes/accessors/Object3DNode.js +0 -1
  64. package/src/nodes/accessors/Position.js +6 -6
  65. package/src/nodes/accessors/ReferenceBaseNode.js +2 -4
  66. package/src/nodes/accessors/ReferenceNode.js +2 -3
  67. package/src/nodes/accessors/StorageBufferNode.js +42 -5
  68. package/src/nodes/accessors/Tangent.js +2 -2
  69. package/src/nodes/accessors/Texture3DNode.js +1 -1
  70. package/src/nodes/accessors/TextureNode.js +12 -5
  71. package/src/nodes/accessors/UniformArrayNode.js +9 -3
  72. package/src/nodes/accessors/VelocityNode.js +0 -2
  73. package/src/nodes/code/ScriptableNode.js +3 -3
  74. package/src/nodes/core/ArrayNode.js +125 -0
  75. package/src/nodes/core/ConstNode.js +8 -0
  76. package/src/nodes/core/Node.js +14 -1
  77. package/src/nodes/core/NodeBuilder.js +229 -19
  78. package/src/nodes/core/NodeUtils.js +11 -1
  79. package/src/nodes/core/NodeVar.js +17 -1
  80. package/src/nodes/core/OutputStructNode.js +19 -9
  81. package/src/nodes/core/StackNode.js +20 -1
  82. package/src/nodes/core/StructNode.js +121 -0
  83. package/src/nodes/core/StructType.js +13 -0
  84. package/src/nodes/core/StructTypeNode.js +82 -21
  85. package/src/nodes/core/TempNode.js +1 -1
  86. package/src/nodes/core/VarNode.js +94 -7
  87. package/src/nodes/core/VaryingNode.js +19 -3
  88. package/src/nodes/display/BlendModes.js +88 -1
  89. package/src/nodes/display/BumpMapNode.js +6 -6
  90. package/src/nodes/display/NormalMapNode.js +6 -6
  91. package/src/nodes/display/PassNode.js +3 -1
  92. package/src/nodes/display/ScreenNode.js +9 -0
  93. package/src/nodes/fog/Fog.js +17 -0
  94. package/src/nodes/gpgpu/AtomicFunctionNode.js +20 -4
  95. package/src/nodes/gpgpu/ComputeBuiltinNode.js +8 -0
  96. package/src/nodes/gpgpu/WorkgroupInfoNode.js +1 -1
  97. package/src/nodes/lighting/ShadowNode.js +1 -1
  98. package/src/nodes/math/ConditionalNode.js +8 -1
  99. package/src/nodes/math/MathNode.js +14 -1
  100. package/src/nodes/math/OperatorNode.js +96 -18
  101. package/src/nodes/pmrem/PMREMUtils.js +1 -1
  102. package/src/nodes/shapes/Shapes.js +33 -0
  103. package/src/nodes/tsl/TSLBase.js +1 -0
  104. package/src/nodes/tsl/TSLCore.js +22 -2
  105. package/src/nodes/utils/ArrayElementNode.js +1 -1
  106. package/src/nodes/utils/LoopNode.js +8 -1
  107. package/src/nodes/utils/MemberNode.js +68 -0
  108. package/src/nodes/utils/StorageArrayElementNode.js +14 -0
  109. package/src/nodes/utils/Timer.js +21 -0
  110. package/src/objects/BatchedMesh.js +1 -1
  111. package/src/objects/Line.js +6 -6
  112. package/src/renderers/WebGLRenderer.js +7 -0
  113. package/src/renderers/common/Animation.js +23 -1
  114. package/src/renderers/common/Backend.js +58 -15
  115. package/src/renderers/common/Background.js +14 -0
  116. package/src/renderers/common/Binding.js +1 -1
  117. package/src/renderers/common/BufferUtils.js +1 -1
  118. package/src/renderers/common/BundleGroup.js +1 -1
  119. package/src/renderers/common/ChainMap.js +9 -7
  120. package/src/renderers/common/ClippingContext.js +1 -1
  121. package/src/renderers/common/Color4.js +7 -3
  122. package/src/renderers/common/Geometries.js +2 -23
  123. package/src/renderers/common/Info.js +1 -45
  124. package/src/renderers/common/Lighting.js +8 -6
  125. package/src/renderers/common/Pipelines.js +3 -3
  126. package/src/renderers/common/PostProcessing.js +24 -8
  127. package/src/renderers/common/QuadMesh.js +1 -1
  128. package/src/renderers/common/RenderBundles.js +9 -3
  129. package/src/renderers/common/RenderContext.js +37 -3
  130. package/src/renderers/common/RenderContexts.js +30 -17
  131. package/src/renderers/common/RenderList.js +2 -2
  132. package/src/renderers/common/RenderLists.js +9 -3
  133. package/src/renderers/common/RenderObject.js +76 -17
  134. package/src/renderers/common/RenderObjects.js +9 -7
  135. package/src/renderers/common/Renderer.js +86 -67
  136. package/src/renderers/common/SampledTexture.js +0 -1
  137. package/src/renderers/common/StorageBufferAttribute.js +1 -1
  138. package/src/renderers/common/StorageInstancedBufferAttribute.js +1 -1
  139. package/src/renderers/common/StorageTexture.js +1 -1
  140. package/src/renderers/common/Textures.js +14 -7
  141. package/src/renderers/common/TimestampQueryPool.js +39 -0
  142. package/src/renderers/common/Uniform.js +37 -1
  143. package/src/renderers/common/UniformsGroup.js +2 -0
  144. package/src/renderers/common/XRManager.js +1193 -0
  145. package/src/renderers/common/XRRenderTarget.js +74 -0
  146. package/src/renderers/common/extras/PMREMGenerator.js +53 -8
  147. package/src/renderers/common/nodes/NodeBuilderState.js +4 -4
  148. package/src/renderers/common/nodes/NodeLibrary.js +5 -5
  149. package/src/renderers/common/nodes/NodeSampledTexture.js +0 -1
  150. package/src/renderers/common/nodes/NodeUniform.js +54 -2
  151. package/src/renderers/common/nodes/Nodes.js +25 -18
  152. package/src/renderers/webgl/WebGLBackground.js +4 -0
  153. package/src/renderers/webgl-fallback/WebGLBackend.js +295 -110
  154. package/src/renderers/webgl-fallback/nodes/GLSLNodeBuilder.js +347 -17
  155. package/src/renderers/webgl-fallback/utils/WebGLAttributeUtils.js +57 -0
  156. package/src/renderers/webgl-fallback/utils/WebGLCapabilities.js +28 -0
  157. package/src/renderers/webgl-fallback/utils/WebGLExtensions.js +45 -0
  158. package/src/renderers/webgl-fallback/utils/WebGLState.js +323 -11
  159. package/src/renderers/webgl-fallback/utils/WebGLTextureUtils.js +167 -21
  160. package/src/renderers/webgl-fallback/utils/WebGLTimestampQueryPool.js +359 -0
  161. package/src/renderers/webgl-fallback/utils/WebGLUtils.js +43 -0
  162. package/src/renderers/webgpu/WebGPUBackend.js +132 -149
  163. package/src/renderers/webgpu/WebGPURenderer.Nodes.js +6 -4
  164. package/src/renderers/webgpu/WebGPURenderer.js +5 -4
  165. package/src/renderers/webgpu/nodes/WGSLNodeBuilder.js +615 -41
  166. package/src/renderers/webgpu/utils/WebGPUAttributeUtils.js +85 -6
  167. package/src/renderers/webgpu/utils/WebGPUBindingUtils.js +85 -0
  168. package/src/renderers/webgpu/utils/WebGPUPipelineUtils.js +102 -3
  169. package/src/renderers/webgpu/utils/WebGPUTexturePassUtils.js +98 -1
  170. package/src/renderers/webgpu/utils/WebGPUTextureUtils.js +257 -9
  171. package/src/renderers/webgpu/utils/WebGPUTimestampQueryPool.js +274 -0
  172. package/src/renderers/webgpu/utils/WebGPUUtils.js +86 -4
  173. package/src/renderers/webxr/WebXRManager.js +13 -2
  174. package/src/textures/VideoFrameTexture.js +35 -0
  175. package/examples/jsm/geometries/InstancedPointsGeometry.js +0 -176
  176. package/examples/jsm/objects/InstancedPoints.js +0 -19
  177. package/src/materials/nodes/InstancedPointsNodeMaterial.js +0 -209
  178. package/src/nodes/accessors/InstancedPointsMaterialNode.js +0 -37
@@ -0,0 +1,274 @@
1
+ import { warnOnce } from '../../../utils.js';
2
+ import TimestampQueryPool from '../../common/TimestampQueryPool.js';
3
+
4
+ /**
5
+ * Manages a pool of WebGPU timestamp queries for performance measurement.
6
+ * Extends the base TimestampQueryPool to provide WebGPU-specific implementation.
7
+ * @extends TimestampQueryPool
8
+ */
9
+ class WebGPUTimestampQueryPool extends TimestampQueryPool {
10
+
11
+ /**
12
+ * Creates a new WebGPU timestamp query pool.
13
+ * @param {GPUDevice} device - The WebGPU device to create queries on.
14
+ * @param {string} type - The type identifier for this query pool.
15
+ * @param {number} [maxQueries=2048] - Maximum number of queries this pool can hold.
16
+ */
17
+ constructor( device, type, maxQueries = 2048 ) {
18
+
19
+ super( maxQueries );
20
+ this.device = device;
21
+ this.type = type;
22
+
23
+ this.querySet = this.device.createQuerySet( {
24
+ type: 'timestamp',
25
+ count: this.maxQueries,
26
+ label: `queryset_global_timestamp_${type}`
27
+ } );
28
+
29
+ const bufferSize = this.maxQueries * 8;
30
+ this.resolveBuffer = this.device.createBuffer( {
31
+ label: `buffer_timestamp_resolve_${type}`,
32
+ size: bufferSize,
33
+ usage: GPUBufferUsage.QUERY_RESOLVE | GPUBufferUsage.COPY_SRC
34
+ } );
35
+
36
+ this.resultBuffer = this.device.createBuffer( {
37
+ label: `buffer_timestamp_result_${type}`,
38
+ size: bufferSize,
39
+ usage: GPUBufferUsage.COPY_DST | GPUBufferUsage.MAP_READ
40
+ } );
41
+
42
+ }
43
+
44
+ /**
45
+ * Allocates a pair of queries for a given render context.
46
+ * @param {Object} renderContext - The render context to allocate queries for.
47
+ * @returns {?number} The base offset for the allocated queries, or null if allocation failed.
48
+ */
49
+ allocateQueriesForContext( renderContext ) {
50
+
51
+ if ( ! this.trackTimestamp || this.isDisposed ) return null;
52
+
53
+ if ( this.currentQueryIndex + 2 > this.maxQueries ) {
54
+
55
+ warnOnce( `WebGPUTimestampQueryPool [${ this.type }]: Maximum number of queries exceeded, when using trackTimestamp it is necessary to resolves the queries via renderer.resolveTimestampsAsync( THREE.TimestampQuery.${ this.type.toUpperCase() } ).` );
56
+ return null;
57
+
58
+ }
59
+
60
+ const baseOffset = this.currentQueryIndex;
61
+ this.currentQueryIndex += 2;
62
+
63
+ this.queryOffsets.set( renderContext.id, baseOffset );
64
+ return baseOffset;
65
+
66
+ }
67
+
68
+ /**
69
+ * Asynchronously resolves all pending queries and returns the total duration.
70
+ * If there's already a pending resolve operation, returns that promise instead.
71
+ * @returns {Promise<number>} The total duration in milliseconds, or the last valid value if resolution fails.
72
+ */
73
+ async resolveQueriesAsync() {
74
+
75
+ if ( ! this.trackTimestamp || this.currentQueryIndex === 0 || this.isDisposed ) {
76
+
77
+ return this.lastValue;
78
+
79
+ }
80
+
81
+ if ( this.pendingResolve ) {
82
+
83
+ return this.pendingResolve;
84
+
85
+ }
86
+
87
+ this.pendingResolve = this._resolveQueries();
88
+
89
+ try {
90
+
91
+ const result = await this.pendingResolve;
92
+ return result;
93
+
94
+ } finally {
95
+
96
+ this.pendingResolve = null;
97
+
98
+ }
99
+
100
+ }
101
+
102
+ /**
103
+ * Internal method to resolve queries and calculate total duration.
104
+ * @private
105
+ * @returns {Promise<number>} The total duration in milliseconds.
106
+ */
107
+ async _resolveQueries() {
108
+
109
+ if ( this.isDisposed ) {
110
+
111
+ return this.lastValue;
112
+
113
+ }
114
+
115
+ try {
116
+
117
+ if ( this.resultBuffer.mapState !== 'unmapped' ) {
118
+
119
+ return this.lastValue;
120
+
121
+ }
122
+
123
+ const currentOffsets = new Map( this.queryOffsets );
124
+ const queryCount = this.currentQueryIndex;
125
+ const bytesUsed = queryCount * 8;
126
+
127
+ // Reset state before GPU work
128
+ this.currentQueryIndex = 0;
129
+ this.queryOffsets.clear();
130
+
131
+ const commandEncoder = this.device.createCommandEncoder();
132
+
133
+ commandEncoder.resolveQuerySet(
134
+ this.querySet,
135
+ 0,
136
+ queryCount,
137
+ this.resolveBuffer,
138
+ 0
139
+ );
140
+
141
+ commandEncoder.copyBufferToBuffer(
142
+ this.resolveBuffer,
143
+ 0,
144
+ this.resultBuffer,
145
+ 0,
146
+ bytesUsed
147
+ );
148
+
149
+ const commandBuffer = commandEncoder.finish();
150
+ this.device.queue.submit( [ commandBuffer ] );
151
+
152
+ if ( this.resultBuffer.mapState !== 'unmapped' ) {
153
+
154
+ return this.lastValue;
155
+
156
+ }
157
+
158
+ // Create and track the mapping operation
159
+ await this.resultBuffer.mapAsync( GPUMapMode.READ, 0, bytesUsed );
160
+
161
+ if ( this.isDisposed ) {
162
+
163
+ if ( this.resultBuffer.mapState === 'mapped' ) {
164
+
165
+ this.resultBuffer.unmap();
166
+
167
+ }
168
+
169
+ return this.lastValue;
170
+
171
+ }
172
+
173
+ const times = new BigUint64Array( this.resultBuffer.getMappedRange( 0, bytesUsed ) );
174
+ let totalDuration = 0;
175
+
176
+ for ( const [ , baseOffset ] of currentOffsets ) {
177
+
178
+ const startTime = times[ baseOffset ];
179
+ const endTime = times[ baseOffset + 1 ];
180
+ const duration = Number( endTime - startTime ) / 1e6;
181
+ totalDuration += duration;
182
+
183
+ }
184
+
185
+ this.resultBuffer.unmap();
186
+ this.lastValue = totalDuration;
187
+
188
+ return totalDuration;
189
+
190
+ } catch ( error ) {
191
+
192
+ console.error( 'Error resolving queries:', error );
193
+ if ( this.resultBuffer.mapState === 'mapped' ) {
194
+
195
+ this.resultBuffer.unmap();
196
+
197
+ }
198
+
199
+ return this.lastValue;
200
+
201
+ }
202
+
203
+ }
204
+
205
+ async dispose() {
206
+
207
+ if ( this.isDisposed ) {
208
+
209
+ return;
210
+
211
+ }
212
+
213
+ this.isDisposed = true;
214
+
215
+ // Wait for pending resolve operation
216
+ if ( this.pendingResolve ) {
217
+
218
+ try {
219
+
220
+ await this.pendingResolve;
221
+
222
+ } catch ( error ) {
223
+
224
+ console.error( 'Error waiting for pending resolve:', error );
225
+
226
+ }
227
+
228
+ }
229
+
230
+ // Ensure buffer is unmapped before destroying
231
+ if ( this.resultBuffer && this.resultBuffer.mapState === 'mapped' ) {
232
+
233
+ try {
234
+
235
+ this.resultBuffer.unmap();
236
+
237
+ } catch ( error ) {
238
+
239
+ console.error( 'Error unmapping buffer:', error );
240
+
241
+ }
242
+
243
+ }
244
+
245
+ // Destroy resources
246
+ if ( this.querySet ) {
247
+
248
+ this.querySet.destroy();
249
+ this.querySet = null;
250
+
251
+ }
252
+
253
+ if ( this.resolveBuffer ) {
254
+
255
+ this.resolveBuffer.destroy();
256
+ this.resolveBuffer = null;
257
+
258
+ }
259
+
260
+ if ( this.resultBuffer ) {
261
+
262
+ this.resultBuffer.destroy();
263
+ this.resultBuffer = null;
264
+
265
+ }
266
+
267
+ this.queryOffsets.clear();
268
+ this.pendingResolve = null;
269
+
270
+ }
271
+
272
+ }
273
+
274
+ export default WebGPUTimestampQueryPool;
@@ -1,13 +1,35 @@
1
+ import { HalfFloatType, UnsignedByteType } from '../../../constants.js';
1
2
  import { GPUPrimitiveTopology, GPUTextureFormat } from './WebGPUConstants.js';
2
3
 
4
+ /**
5
+ * A WebGPU backend utility module with common helpers.
6
+ *
7
+ * @private
8
+ */
3
9
  class WebGPUUtils {
4
10
 
11
+ /**
12
+ * Constructs a new utility object.
13
+ *
14
+ * @param {WebGPUBackend} backend - The WebGPU backend.
15
+ */
5
16
  constructor( backend ) {
6
17
 
18
+ /**
19
+ * A reference to the WebGPU backend.
20
+ *
21
+ * @type {WebGPUBackend}
22
+ */
7
23
  this.backend = backend;
8
24
 
9
25
  }
10
26
 
27
+ /**
28
+ * Returns the depth/stencil GPU format for the given render context.
29
+ *
30
+ * @param {RenderContext} renderContext - The render context.
31
+ * @return {String} The depth/stencil GPU texture format.
32
+ */
11
33
  getCurrentDepthStencilFormat( renderContext ) {
12
34
 
13
35
  let format;
@@ -30,12 +52,24 @@ class WebGPUUtils {
30
52
 
31
53
  }
32
54
 
55
+ /**
56
+ * Returns the GPU format for the given texture.
57
+ *
58
+ * @param {Texture} texture - The texture.
59
+ * @return {String} The GPU texture format.
60
+ */
33
61
  getTextureFormatGPU( texture ) {
34
62
 
35
63
  return this.backend.get( texture ).format;
36
64
 
37
65
  }
38
66
 
67
+ /**
68
+ * Returns an object that defines the multi-sampling state of the given texture.
69
+ *
70
+ * @param {Texture} texture - The texture.
71
+ * @return {Object} The multi-sampling state.
72
+ */
39
73
  getTextureSampleData( texture ) {
40
74
 
41
75
  let samples;
@@ -66,6 +100,12 @@ class WebGPUUtils {
66
100
 
67
101
  }
68
102
 
103
+ /**
104
+ * Returns the default color attachment's GPU format of the current render context.
105
+ *
106
+ * @param {RenderContext} renderContext - The render context.
107
+ * @return {String} The GPU texture format of the default color attachment.
108
+ */
69
109
  getCurrentColorFormat( renderContext ) {
70
110
 
71
111
  let format;
@@ -84,6 +124,12 @@ class WebGPUUtils {
84
124
 
85
125
  }
86
126
 
127
+ /**
128
+ * Returns the output color space of the current render context.
129
+ *
130
+ * @param {RenderContext} renderContext - The render context.
131
+ * @return {String} The output color space.
132
+ */
87
133
  getCurrentColorSpace( renderContext ) {
88
134
 
89
135
  if ( renderContext.textures !== null ) {
@@ -96,6 +142,13 @@ class WebGPUUtils {
96
142
 
97
143
  }
98
144
 
145
+ /**
146
+ * Returns GPU primitive topology for the given object and material.
147
+ *
148
+ * @param {Object3D} object - The 3D object.
149
+ * @param {Material} material - The material.
150
+ * @return {String} The GPU primitive topology.
151
+ */
99
152
  getPrimitiveTopology( object, material ) {
100
153
 
101
154
  if ( object.isPoints ) return GPUPrimitiveTopology.PointList;
@@ -105,6 +158,14 @@ class WebGPUUtils {
105
158
 
106
159
  }
107
160
 
161
+ /**
162
+ * Returns a modified sample count from the given sample count value.
163
+ *
164
+ * That is required since WebGPU does not support arbitrary sample counts.
165
+ *
166
+ * @param {Number} sampleCount - The input sample count.
167
+ * @return {Number} The (potentially updated) output sample count.
168
+ */
108
169
  getSampleCount( sampleCount ) {
109
170
 
110
171
  let count = 1;
@@ -126,6 +187,12 @@ class WebGPUUtils {
126
187
 
127
188
  }
128
189
 
190
+ /**
191
+ * Returns the sample count of the given render context.
192
+ *
193
+ * @param {RenderContext} renderContext - The render context.
194
+ * @return {Number} The sample count.
195
+ */
129
196
  getSampleCountRenderContext( renderContext ) {
130
197
 
131
198
  if ( renderContext.textures !== null ) {
@@ -138,18 +205,33 @@ class WebGPUUtils {
138
205
 
139
206
  }
140
207
 
208
+ /**
209
+ * Returns the preferred canvas format.
210
+ *
211
+ * There is a separate method for this so it's possible to
212
+ * honor edge cases for specific devices.
213
+ *
214
+ * @return {String} The GPU texture format of the canvas.
215
+ */
141
216
  getPreferredCanvasFormat() {
142
217
 
143
- // TODO: Remove this check when Quest 34.5 is out
144
- // https://github.com/mrdoob/three.js/pull/29221/files#r1731833949
218
+ const outputType = this.backend.parameters.outputType;
145
219
 
146
- if ( navigator.userAgent.includes( 'Quest' ) ) {
220
+ if ( outputType === undefined ) {
221
+
222
+ return navigator.gpu.getPreferredCanvasFormat();
223
+
224
+ } else if ( outputType === UnsignedByteType ) {
147
225
 
148
226
  return GPUTextureFormat.BGRA8Unorm;
149
227
 
228
+ } else if ( outputType === HalfFloatType ) {
229
+
230
+ return GPUTextureFormat.RGBA16Float;
231
+
150
232
  } else {
151
233
 
152
- return navigator.gpu.getPreferredCanvasFormat();
234
+ throw new Error( 'Unsupported outputType' );
153
235
 
154
236
  }
155
237
 
@@ -248,6 +248,12 @@ class WebXRManager extends EventDispatcher {
248
248
 
249
249
  };
250
250
 
251
+ this.getRenderTarget = function () {
252
+
253
+ return newRenderTarget;
254
+
255
+ };
256
+
251
257
  this.getFrame = function () {
252
258
 
253
259
  return xrFrame;
@@ -286,7 +292,9 @@ class WebXRManager extends EventDispatcher {
286
292
  currentPixelRatio = renderer.getPixelRatio();
287
293
  renderer.getSize( currentSize );
288
294
 
289
- const useLayers = session.enabledFeatures !== undefined && session.enabledFeatures.includes( 'layers' );
295
+ // Check that the browser implements the necessary APIs to use an
296
+ // XRProjectionLayer rather than an XRWebGLLayer
297
+ const useLayers = typeof XRWebGLBinding !== 'undefined' && 'createProjectionLayer' in XRWebGLBinding.prototype;
290
298
 
291
299
  if ( ! useLayers ) {
292
300
 
@@ -845,8 +853,11 @@ class WebXRManager extends EventDispatcher {
845
853
  //
846
854
 
847
855
  const enabledFeatures = session.enabledFeatures;
856
+ const gpuDepthSensingEnabled = enabledFeatures &&
857
+ enabledFeatures.includes( 'depth-sensing' ) &&
858
+ session.depthUsage == 'gpu-optimized';
848
859
 
849
- if ( enabledFeatures && enabledFeatures.includes( 'depth-sensing' ) ) {
860
+ if ( gpuDepthSensingEnabled && glBinding ) {
850
861
 
851
862
  const depthData = glBinding.getDepthInformation( views[ 0 ] );
852
863
 
@@ -0,0 +1,35 @@
1
+ import { VideoTexture } from './VideoTexture.js';
2
+
3
+ class VideoFrameTexture extends VideoTexture {
4
+
5
+ constructor( mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy ) {
6
+
7
+ super( {}, mapping, wrapS, wrapT, magFilter, minFilter, format, type, anisotropy );
8
+
9
+ this.isVideoFrameTexture = true;
10
+
11
+ }
12
+
13
+ update() {
14
+
15
+ // overwrites `VideoTexture.update()` with an empty method since
16
+ // this type of texture is updated via `setFrame()`.
17
+
18
+ }
19
+
20
+ clone() {
21
+
22
+ return new this.constructor().copy( this ); // restoring Texture.clone()
23
+
24
+ }
25
+
26
+ setFrame( frame ) {
27
+
28
+ this.image = frame;
29
+ this.needsUpdate = true;
30
+
31
+ }
32
+
33
+ }
34
+
35
+ export { VideoFrameTexture };
@@ -1,176 +0,0 @@
1
- import {
2
- Box3,
3
- Float32BufferAttribute,
4
- InstancedBufferGeometry,
5
- InstancedBufferAttribute,
6
- Sphere,
7
- Vector3
8
- } from 'three';
9
-
10
- const _vector = new Vector3();
11
-
12
- class InstancedPointsGeometry extends InstancedBufferGeometry {
13
-
14
- constructor() {
15
-
16
- super();
17
-
18
- this.isInstancedPointsGeometry = true;
19
-
20
- this.type = 'InstancedPointsGeometry';
21
-
22
- const positions = [ - 1, 1, 0, 1, 1, 0, - 1, - 1, 0, 1, - 1, 0 ];
23
- const uvs = [ 0, 1, 1, 1, 0, 0, 1, 0 ];
24
- const index = [ 0, 2, 1, 2, 3, 1 ];
25
-
26
- this.setIndex( index );
27
- this.setAttribute( 'position', new Float32BufferAttribute( positions, 3 ) );
28
- this.setAttribute( 'uv', new Float32BufferAttribute( uvs, 2 ) );
29
-
30
- }
31
-
32
- applyMatrix4( matrix ) {
33
-
34
- const pos = this.attributes.instancePosition;
35
-
36
- if ( pos !== undefined ) {
37
-
38
- pos.applyMatrix4( matrix );
39
-
40
- pos.needsUpdate = true;
41
-
42
- }
43
-
44
- if ( this.boundingBox !== null ) {
45
-
46
- this.computeBoundingBox();
47
-
48
- }
49
-
50
- if ( this.boundingSphere !== null ) {
51
-
52
- this.computeBoundingSphere();
53
-
54
- }
55
-
56
- return this;
57
-
58
- }
59
-
60
- setPositions( array ) {
61
-
62
- let points;
63
-
64
- if ( array instanceof Float32Array ) {
65
-
66
- points = array;
67
-
68
- } else if ( Array.isArray( array ) ) {
69
-
70
- points = new Float32Array( array );
71
-
72
- }
73
-
74
- this.setAttribute( 'instancePosition', new InstancedBufferAttribute( points, 3 ) ); // xyz
75
-
76
- //
77
-
78
- this.computeBoundingBox();
79
- this.computeBoundingSphere();
80
-
81
- this.instanceCount = points.length / 3;
82
-
83
- return this;
84
-
85
- }
86
-
87
- setColors( array ) {
88
-
89
- let colors;
90
-
91
- if ( array instanceof Float32Array ) {
92
-
93
- colors = array;
94
-
95
- } else if ( Array.isArray( array ) ) {
96
-
97
- colors = new Float32Array( array );
98
-
99
- }
100
-
101
- this.setAttribute( 'instanceColor', new InstancedBufferAttribute( colors, 3 ) ); // rgb
102
-
103
- return this;
104
-
105
- }
106
-
107
- computeBoundingBox() {
108
-
109
- if ( this.boundingBox === null ) {
110
-
111
- this.boundingBox = new Box3();
112
-
113
- }
114
-
115
- const pos = this.attributes.instancePosition;
116
-
117
- if ( pos !== undefined ) {
118
-
119
- this.boundingBox.setFromBufferAttribute( pos );
120
-
121
- }
122
-
123
- }
124
-
125
- computeBoundingSphere() {
126
-
127
- if ( this.boundingSphere === null ) {
128
-
129
- this.boundingSphere = new Sphere();
130
-
131
- }
132
-
133
- if ( this.boundingBox === null ) {
134
-
135
- this.computeBoundingBox();
136
-
137
- }
138
-
139
- const pos = this.attributes.instancePosition;
140
-
141
- if ( pos !== undefined ) {
142
-
143
- const center = this.boundingSphere.center;
144
-
145
- this.boundingBox.getCenter( center );
146
-
147
- let maxRadiusSq = 0;
148
-
149
- for ( let i = 0, il = pos.count; i < il; i ++ ) {
150
-
151
- _vector.fromBufferAttribute( pos, i );
152
- maxRadiusSq = Math.max( maxRadiusSq, center.distanceToSquared( _vector ) );
153
-
154
- }
155
-
156
- this.boundingSphere.radius = Math.sqrt( maxRadiusSq );
157
-
158
- if ( isNaN( this.boundingSphere.radius ) ) {
159
-
160
- console.error( 'THREE.InstancedPointsGeometry.computeBoundingSphere(): Computed radius is NaN. The instanced position data is likely to have NaN values.', this );
161
-
162
- }
163
-
164
- }
165
-
166
- }
167
-
168
- toJSON() {
169
-
170
- // todo
171
-
172
- }
173
-
174
- }
175
-
176
- export default InstancedPointsGeometry;
@@ -1,19 +0,0 @@
1
- import { Mesh, InstancedPointsNodeMaterial } from 'three/webgpu';
2
-
3
- import InstancedPointsGeometry from '../geometries/InstancedPointsGeometry.js';
4
-
5
- class InstancedPoints extends Mesh {
6
-
7
- constructor( geometry = new InstancedPointsGeometry(), material = new InstancedPointsNodeMaterial() ) {
8
-
9
- super( geometry, material );
10
-
11
- this.isInstancedPoints = true;
12
-
13
- this.type = 'InstancedPoints';
14
-
15
- }
16
-
17
- }
18
-
19
- export default InstancedPoints;