super-three 0.167.0 → 0.168.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 (311) hide show
  1. package/build/three.cjs +165 -44
  2. package/build/three.module.js +165 -45
  3. package/build/three.module.min.js +1 -1
  4. package/build/three.webgpu.js +23600 -21931
  5. package/build/three.webgpu.min.js +1 -1
  6. package/examples/jsm/Addons.js +3 -1
  7. package/examples/jsm/animation/AnimationClipCreator.js +1 -1
  8. package/examples/jsm/capabilities/WebGL.js +27 -21
  9. package/examples/jsm/controls/ArcballControls.js +174 -158
  10. package/examples/jsm/controls/DragControls.js +260 -132
  11. package/examples/jsm/controls/FirstPersonControls.js +175 -163
  12. package/examples/jsm/controls/FlyControls.js +194 -188
  13. package/examples/jsm/controls/OrbitControls.js +777 -786
  14. package/examples/jsm/controls/PointerLockControls.js +24 -15
  15. package/examples/jsm/controls/TrackballControls.js +453 -452
  16. package/examples/jsm/effects/AnaglyphEffect.js +6 -13
  17. package/examples/jsm/effects/ParallaxBarrierEffect.js +17 -11
  18. package/examples/jsm/effects/StereoEffect.js +6 -1
  19. package/examples/jsm/environments/RoomEnvironment.js +1 -1
  20. package/examples/jsm/exporters/GLTFExporter.js +6 -1
  21. package/examples/jsm/exporters/USDZExporter.js +29 -8
  22. package/examples/jsm/helpers/LightProbeHelper.js +42 -43
  23. package/examples/jsm/loaders/KTX2Loader.js +19 -7
  24. package/examples/jsm/loaders/MaterialXLoader.js +11 -4
  25. package/examples/jsm/loaders/PCDLoader.js +9 -9
  26. package/examples/jsm/objects/SkyMesh.js +188 -0
  27. package/examples/jsm/objects/Water2Mesh.js +159 -0
  28. package/examples/jsm/objects/WaterMesh.js +102 -0
  29. package/examples/jsm/physics/RapierPhysics.js +20 -0
  30. package/examples/jsm/postprocessing/OutlinePass.js +31 -46
  31. package/examples/jsm/postprocessing/SSAARenderPass.js +3 -1
  32. package/examples/jsm/shaders/BleachBypassShader.js +1 -2
  33. package/examples/jsm/shaders/OutputShader.js +1 -1
  34. package/examples/jsm/transpiler/TSLEncoder.js +8 -8
  35. package/examples/jsm/utils/TextureUtils.js +1 -1
  36. package/package.json +2 -1
  37. package/src/Three.WebGPU.js +6 -0
  38. package/src/Three.js +1 -0
  39. package/src/constants.js +1 -1
  40. package/src/extras/Controls.js +32 -0
  41. package/src/loaders/ObjectLoader.js +3 -3
  42. package/src/{nodes/loaders → loaders/nodes}/NodeLoader.js +4 -4
  43. package/src/{nodes/loaders → loaders/nodes}/NodeMaterialLoader.js +1 -2
  44. package/src/materials/Material.js +4 -7
  45. package/src/{nodes/materials → materials/nodes}/InstancedPointsNodeMaterial.js +33 -24
  46. package/src/{nodes/materials → materials/nodes}/Line2NodeMaterial.js +34 -37
  47. package/src/{nodes/materials → materials/nodes}/LineBasicNodeMaterial.js +3 -4
  48. package/src/{nodes/materials → materials/nodes}/LineDashedNodeMaterial.js +7 -9
  49. package/src/{nodes/materials → materials/nodes}/MeshBasicNodeMaterial.js +11 -11
  50. package/src/{nodes/materials → materials/nodes}/MeshLambertNodeMaterial.js +5 -5
  51. package/src/{nodes/materials → materials/nodes}/MeshMatcapNodeMaterial.js +8 -8
  52. package/src/materials/nodes/MeshNormalNodeMaterial.js +40 -0
  53. package/src/{nodes/materials → materials/nodes}/MeshPhongNodeMaterial.js +9 -8
  54. package/src/{nodes/materials → materials/nodes}/MeshPhysicalNodeMaterial.js +18 -17
  55. package/src/{nodes/materials → materials/nodes}/MeshSSSNodeMaterial.js +6 -6
  56. package/src/{nodes/materials → materials/nodes}/MeshStandardNodeMaterial.js +17 -11
  57. package/src/{nodes/materials → materials/nodes}/MeshToonNodeMaterial.js +4 -4
  58. package/src/{nodes/materials → materials/nodes}/NodeMaterial.js +67 -86
  59. package/src/{nodes/materials/Materials.js → materials/nodes/NodeMaterials.js} +1 -1
  60. package/src/{nodes/materials → materials/nodes}/PointsNodeMaterial.js +3 -4
  61. package/src/{nodes/materials → materials/nodes}/ShadowNodeMaterial.js +4 -4
  62. package/src/{nodes/materials → materials/nodes}/SpriteNodeMaterial.js +11 -11
  63. package/src/{nodes/materials → materials/nodes}/VolumeNodeMaterial.js +14 -16
  64. package/src/nodes/Nodes.js +103 -159
  65. package/src/nodes/TSL.js +176 -0
  66. package/src/nodes/accessors/AccessorsUtils.js +8 -8
  67. package/src/nodes/accessors/BatchNode.js +48 -20
  68. package/src/nodes/accessors/{BitangentNode.js → Bitangent.js} +9 -9
  69. package/src/nodes/accessors/BufferAttributeNode.js +5 -5
  70. package/src/nodes/accessors/BufferNode.js +4 -4
  71. package/src/nodes/accessors/{CameraNode.js → Camera.js} +10 -10
  72. package/src/nodes/accessors/ClippingNode.js +16 -14
  73. package/src/nodes/accessors/CubeTextureNode.js +5 -7
  74. package/src/nodes/accessors/InstanceNode.js +17 -13
  75. package/src/nodes/accessors/InstancedPointsMaterialNode.js +4 -4
  76. package/src/nodes/accessors/MaterialNode.js +52 -55
  77. package/src/nodes/accessors/MaterialProperties.js +3 -0
  78. package/src/nodes/accessors/MaterialReferenceNode.js +6 -4
  79. package/src/nodes/accessors/ModelNode.js +11 -11
  80. package/src/nodes/accessors/ModelViewProjectionNode.js +6 -7
  81. package/src/nodes/accessors/MorphNode.js +12 -12
  82. package/src/nodes/accessors/Normal.js +62 -0
  83. package/src/nodes/accessors/Object3DNode.js +10 -10
  84. package/src/nodes/accessors/PointUVNode.js +4 -4
  85. package/src/nodes/accessors/Position.js +10 -0
  86. package/src/nodes/accessors/ReferenceBaseNode.js +143 -0
  87. package/src/nodes/accessors/ReferenceNode.js +13 -7
  88. package/src/nodes/accessors/ReflectVector.js +10 -0
  89. package/src/nodes/accessors/RendererReferenceNode.js +6 -6
  90. package/src/nodes/accessors/SceneNode.js +5 -6
  91. package/src/nodes/accessors/SkinningNode.js +84 -21
  92. package/src/nodes/accessors/StorageBufferNode.js +4 -5
  93. package/src/nodes/accessors/StorageTextureNode.js +5 -5
  94. package/src/nodes/accessors/Tangent.js +22 -0
  95. package/src/nodes/accessors/Texture3DNode.js +11 -11
  96. package/src/nodes/accessors/{TextureBicubicNode.js → TextureBicubic.js} +3 -32
  97. package/src/nodes/accessors/TextureNode.js +16 -21
  98. package/src/nodes/accessors/TextureSizeNode.js +4 -6
  99. package/src/nodes/accessors/{UniformsNode.js → UniformArrayNode.js} +17 -8
  100. package/src/nodes/accessors/UserDataNode.js +4 -4
  101. package/src/nodes/accessors/VelocityNode.js +83 -0
  102. package/src/nodes/accessors/VertexColorNode.js +4 -4
  103. package/src/nodes/code/CodeNode.js +5 -5
  104. package/src/nodes/code/ExpressionNode.js +4 -4
  105. package/src/nodes/code/FunctionCallNode.js +5 -5
  106. package/src/nodes/code/FunctionNode.js +5 -23
  107. package/src/nodes/code/ScriptableNode.js +4 -6
  108. package/src/nodes/code/ScriptableValueNode.js +4 -6
  109. package/src/nodes/core/AssignNode.js +5 -5
  110. package/src/nodes/core/AttributeNode.js +7 -20
  111. package/src/nodes/core/BypassNode.js +5 -5
  112. package/src/nodes/core/CacheNode.js +5 -5
  113. package/src/nodes/core/ConstNode.js +2 -2
  114. package/src/nodes/core/ContextNode.js +17 -11
  115. package/src/nodes/core/IndexNode.js +12 -7
  116. package/src/nodes/core/InputNode.js +2 -2
  117. package/src/nodes/core/MRTNode.js +12 -6
  118. package/src/nodes/core/Node.js +39 -19
  119. package/src/nodes/core/NodeBuilder.js +46 -33
  120. package/src/nodes/core/NodeUtils.js +1 -0
  121. package/src/nodes/core/OutputStructNode.js +4 -4
  122. package/src/nodes/core/ParameterNode.js +4 -4
  123. package/src/nodes/core/PropertyNode.js +32 -32
  124. package/src/nodes/core/StackNode.js +26 -10
  125. package/src/nodes/core/StructTypeNode.js +2 -2
  126. package/src/nodes/core/TempNode.js +2 -2
  127. package/src/nodes/core/UniformGroupNode.js +8 -9
  128. package/src/nodes/core/UniformNode.js +4 -4
  129. package/src/nodes/core/VarNode.js +6 -6
  130. package/src/nodes/core/VaryingNode.js +5 -5
  131. package/src/nodes/display/AfterImageNode.js +9 -9
  132. package/src/nodes/display/AnaglyphPassNode.js +61 -0
  133. package/src/nodes/display/AnamorphicNode.js +11 -11
  134. package/src/nodes/display/BleachBypass.js +26 -0
  135. package/src/nodes/display/BlendMode.js +54 -0
  136. package/src/nodes/display/BloomNode.js +21 -19
  137. package/src/nodes/display/BumpMapNode.js +7 -12
  138. package/src/nodes/display/ColorAdjustment.js +46 -0
  139. package/src/nodes/display/ColorSpaceFunctions.js +38 -0
  140. package/src/nodes/display/ColorSpaceNode.js +40 -63
  141. package/src/nodes/display/DenoiseNode.js +20 -17
  142. package/src/nodes/display/DepthOfFieldNode.js +8 -6
  143. package/src/nodes/display/DotScreenNode.js +10 -22
  144. package/src/nodes/display/FXAANode.js +17 -15
  145. package/src/nodes/display/FilmNode.js +7 -6
  146. package/src/nodes/display/FrontFacingNode.js +5 -5
  147. package/src/nodes/display/GTAONode.js +19 -15
  148. package/src/nodes/display/GaussianBlurNode.js +11 -8
  149. package/src/nodes/display/Lut3DNode.js +6 -5
  150. package/src/nodes/display/MotionBlur.js +25 -0
  151. package/src/nodes/display/NormalMapNode.js +8 -10
  152. package/src/nodes/display/ParallaxBarrierPassNode.js +55 -0
  153. package/src/nodes/display/PassNode.js +84 -8
  154. package/src/nodes/display/PixelationPassNode.js +12 -7
  155. package/src/nodes/display/PosterizeNode.js +4 -6
  156. package/src/nodes/display/RGBShiftNode.js +8 -7
  157. package/src/nodes/display/RenderOutputNode.js +9 -9
  158. package/src/nodes/display/SSAAPassNode.js +284 -0
  159. package/src/nodes/display/Sepia.js +17 -0
  160. package/src/nodes/display/SobelOperatorNode.js +9 -7
  161. package/src/nodes/display/StereoCompositePassNode.js +107 -0
  162. package/src/nodes/display/StereoPassNode.js +80 -0
  163. package/src/nodes/display/ToneMappingFunctions.js +190 -0
  164. package/src/nodes/display/ToneMappingNode.js +12 -173
  165. package/src/nodes/display/TransitionNode.js +9 -8
  166. package/src/nodes/display/ViewportDepthNode.js +30 -29
  167. package/src/nodes/display/ViewportDepthTextureNode.js +6 -8
  168. package/src/nodes/display/ViewportNode.js +26 -25
  169. package/src/nodes/display/ViewportSharedTextureNode.js +6 -8
  170. package/src/nodes/display/ViewportTextureNode.js +7 -10
  171. package/src/nodes/fog/FogExp2Node.js +4 -6
  172. package/src/nodes/fog/FogNode.js +5 -7
  173. package/src/nodes/fog/FogRangeNode.js +4 -6
  174. package/src/nodes/functions/BSDF/BRDF_GGX.js +4 -4
  175. package/src/nodes/functions/BSDF/BRDF_Lambert.js +2 -2
  176. package/src/nodes/functions/BSDF/BRDF_Sheen.js +6 -6
  177. package/src/nodes/functions/BSDF/DFGApprox.js +2 -2
  178. package/src/nodes/functions/BSDF/D_GGX.js +2 -2
  179. package/src/nodes/functions/BSDF/D_GGX_Anisotropic.js +3 -3
  180. package/src/nodes/functions/BSDF/EnvironmentBRDF.js +2 -2
  181. package/src/nodes/functions/BSDF/F_Schlick.js +2 -2
  182. package/src/nodes/functions/BSDF/LTC.js +6 -6
  183. package/src/nodes/functions/BSDF/Schlick_to_F0.js +2 -2
  184. package/src/nodes/functions/BSDF/V_GGX_SmithCorrelated.js +2 -2
  185. package/src/nodes/functions/BSDF/V_GGX_SmithCorrelated_Anisotropic.js +2 -2
  186. package/src/nodes/functions/BasicLightingModel.js +1 -1
  187. package/src/nodes/functions/PhongLightingModel.js +5 -5
  188. package/src/nodes/functions/PhysicalLightingModel.js +32 -31
  189. package/src/nodes/functions/ShadowMaskModel.js +1 -1
  190. package/src/nodes/functions/ToonLightingModel.js +3 -3
  191. package/src/nodes/functions/material/getGeometryRoughness.js +4 -4
  192. package/src/nodes/functions/material/getRoughness.js +2 -2
  193. package/src/nodes/geometry/RangeNode.js +4 -4
  194. package/src/nodes/gpgpu/ComputeNode.js +5 -5
  195. package/src/nodes/lighting/AONode.js +2 -2
  196. package/src/nodes/lighting/AmbientLightNode.js +2 -7
  197. package/src/nodes/lighting/AnalyticLightNode.js +34 -13
  198. package/src/nodes/lighting/BasicEnvironmentNode.js +4 -3
  199. package/src/nodes/lighting/BasicLightMapNode.js +3 -3
  200. package/src/nodes/lighting/DirectionalLightNode.js +2 -7
  201. package/src/nodes/lighting/EnvironmentNode.js +20 -19
  202. package/src/nodes/lighting/HemisphereLightNode.js +3 -7
  203. package/src/nodes/lighting/IESSpotLightNode.js +3 -8
  204. package/src/nodes/lighting/IrradianceNode.js +2 -2
  205. package/src/nodes/lighting/LightNode.js +5 -5
  206. package/src/nodes/lighting/LightProbeNode.js +76 -0
  207. package/src/nodes/lighting/LightUtils.js +3 -3
  208. package/src/nodes/lighting/LightingContextNode.js +15 -17
  209. package/src/nodes/lighting/LightingNode.js +2 -2
  210. package/src/nodes/lighting/LightsNode.js +94 -76
  211. package/src/nodes/lighting/PointLightNode.js +3 -8
  212. package/src/nodes/lighting/RectAreaLightNode.js +2 -6
  213. package/src/nodes/lighting/SpotLightNode.js +3 -8
  214. package/src/nodes/materialx/MaterialXNodes.js +2 -2
  215. package/src/nodes/materialx/lib/mx_hsv.js +36 -31
  216. package/src/nodes/materialx/lib/mx_noise.js +96 -96
  217. package/src/nodes/materialx/lib/mx_transform_color.js +2 -2
  218. package/src/nodes/math/{CondNode.js → ConditionalNode.js} +18 -7
  219. package/src/nodes/math/Hash.js +13 -0
  220. package/src/nodes/math/MathNode.js +124 -124
  221. package/src/nodes/math/MathUtils.js +0 -7
  222. package/src/nodes/math/OperatorNode.js +94 -52
  223. package/src/nodes/math/TriNoise3D.js +19 -29
  224. package/src/nodes/pmrem/PMREMNode.js +58 -15
  225. package/src/nodes/pmrem/PMREMUtils.js +46 -46
  226. package/src/nodes/procedural/Checker.js +14 -0
  227. package/src/nodes/tsl/TSLBase.js +30 -0
  228. package/src/nodes/{shadernode/ShaderNode.js → tsl/TSLCore.js} +105 -97
  229. package/src/nodes/utils/ArrayElementNode.js +2 -2
  230. package/src/nodes/utils/ConvertNode.js +2 -2
  231. package/src/nodes/utils/CubeMapNode.js +157 -0
  232. package/src/nodes/utils/Discard.js +8 -0
  233. package/src/nodes/utils/EquirectUVNode.js +5 -5
  234. package/src/nodes/utils/FlipNode.js +65 -0
  235. package/src/nodes/utils/FunctionOverloadingNode.js +5 -5
  236. package/src/nodes/utils/JoinNode.js +2 -2
  237. package/src/nodes/utils/LoopNode.js +12 -6
  238. package/src/nodes/utils/MatcapUVNode.js +6 -6
  239. package/src/nodes/utils/MaxMipLevelNode.js +4 -4
  240. package/src/nodes/utils/OscNode.js +7 -7
  241. package/src/nodes/utils/Packing.js +4 -0
  242. package/src/nodes/utils/RTTNode.js +8 -8
  243. package/src/nodes/utils/ReflectorNode.js +8 -3
  244. package/src/nodes/utils/RemapNode.js +7 -7
  245. package/src/nodes/utils/RotateNode.js +4 -12
  246. package/src/nodes/utils/SetNode.js +2 -2
  247. package/src/nodes/utils/SplitNode.js +2 -2
  248. package/src/nodes/utils/SpriteSheetUVNode.js +5 -5
  249. package/src/nodes/utils/SpriteUtils.js +47 -0
  250. package/src/nodes/utils/StorageArrayElementNode.js +4 -6
  251. package/src/nodes/utils/TimerNode.js +5 -5
  252. package/src/nodes/utils/TriplanarTexturesNode.js +7 -9
  253. package/src/nodes/utils/UVUtils.js +19 -0
  254. package/src/nodes/utils/ViewportUtils.js +14 -0
  255. package/src/objects/BatchedMesh.js +2 -3
  256. package/src/renderers/WebGLRenderer.js +24 -0
  257. package/src/renderers/common/Backend.js +2 -2
  258. package/src/renderers/common/Background.js +3 -1
  259. package/src/renderers/common/BindGroup.js +3 -1
  260. package/src/renderers/common/Bindings.js +13 -15
  261. package/src/renderers/common/ClippingContext.js +14 -5
  262. package/src/renderers/common/CubeRenderTarget.js +9 -3
  263. package/src/renderers/common/PostProcessing.js +4 -1
  264. package/src/renderers/common/QuadMesh.js +2 -0
  265. package/src/renderers/common/RenderContext.js +24 -0
  266. package/src/renderers/common/RenderList.js +1 -1
  267. package/src/renderers/common/RenderObject.js +2 -2
  268. package/src/renderers/common/Renderer.js +75 -49
  269. package/src/renderers/common/SampledTexture.js +12 -3
  270. package/src/renderers/common/StandardRenderer.js +18 -0
  271. package/src/renderers/common/Textures.js +8 -12
  272. package/src/renderers/common/extras/PMREMGenerator.js +12 -13
  273. package/src/renderers/common/nodes/NodeBuilderState.js +1 -1
  274. package/src/renderers/common/nodes/NodeLibrary.js +118 -0
  275. package/src/renderers/common/nodes/NodeSampledTexture.js +2 -2
  276. package/src/renderers/common/nodes/Nodes.js +36 -9
  277. package/src/renderers/common/nodes/StandardNodeLibrary.js +105 -0
  278. package/src/renderers/shaders/ShaderChunk/tonemapping_pars_fragment.glsl.js +2 -2
  279. package/src/renderers/webgl/WebGLProgram.js +1 -1
  280. package/src/renderers/webgl/WebGLProperties.js +7 -0
  281. package/src/renderers/webgl/WebGLTextures.js +61 -4
  282. package/src/renderers/webgl-fallback/WebGLBackend.js +88 -68
  283. package/src/renderers/webgl-fallback/nodes/GLSLNodeBuilder.js +57 -9
  284. package/src/renderers/webgl-fallback/utils/WebGLState.js +21 -0
  285. package/src/renderers/webgl-fallback/utils/WebGLTextureUtils.js +28 -21
  286. package/src/renderers/webgpu/WebGPUBackend.js +86 -68
  287. package/src/renderers/webgpu/WebGPURenderer.js +8 -8
  288. package/src/renderers/webgpu/nodes/WGSLNodeBuilder.js +99 -63
  289. package/src/renderers/webgpu/utils/WebGPUBindingUtils.js +45 -21
  290. package/src/renderers/webgpu/utils/WebGPUConstants.js +2 -1
  291. package/src/renderers/webgpu/utils/WebGPUPipelineUtils.js +6 -15
  292. package/src/renderers/webgpu/utils/WebGPUTexturePassUtils.js +62 -5
  293. package/src/renderers/webgpu/utils/WebGPUTextureUtils.js +36 -21
  294. package/src/renderers/webgpu/utils/WebGPUUtils.js +18 -1
  295. package/src/renderers/webxr/WebXRManager.js +32 -25
  296. package/examples/jsm/loaders/LogLuvLoader.js +0 -606
  297. package/src/nodes/accessors/NormalNode.js +0 -14
  298. package/src/nodes/accessors/PositionNode.js +0 -10
  299. package/src/nodes/accessors/ReflectVectorNode.js +0 -10
  300. package/src/nodes/accessors/TangentNode.js +0 -23
  301. package/src/nodes/core/NodeKeywords.js +0 -80
  302. package/src/nodes/display/BlendModeNode.js +0 -128
  303. package/src/nodes/display/ColorAdjustmentNode.js +0 -104
  304. package/src/nodes/materials/MeshNormalNodeMaterial.js +0 -40
  305. package/src/nodes/math/HashNode.js +0 -34
  306. package/src/nodes/procedural/CheckerNode.js +0 -42
  307. package/src/nodes/utils/DiscardNode.js +0 -28
  308. package/src/nodes/utils/PackingNode.js +0 -55
  309. package/src/nodes/utils/RotateUVNode.js +0 -35
  310. /package/src/{nodes/loaders → loaders/nodes}/NodeObjectLoader.js +0 -0
  311. /package/src/nodes/accessors/{UVNode.js → UV.js} +0 -0
@@ -31,7 +31,7 @@ const supports = {
31
31
  };
32
32
 
33
33
  const wgslFnOpLib = {
34
- '^^': 'threejs_xor'
34
+ '^^': 'tsl_xor'
35
35
  };
36
36
 
37
37
  const wgslTypeLib = {
@@ -72,55 +72,18 @@ const wgslTypeLib = {
72
72
  bmat4: 'mat4x4<bool>'
73
73
  };
74
74
 
75
- const wgslMethods = {
76
- dFdx: 'dpdx',
77
- dFdy: '- dpdy',
78
- mod_float: 'threejs_mod_float',
79
- mod_vec2: 'threejs_mod_vec2',
80
- mod_vec3: 'threejs_mod_vec3',
81
- mod_vec4: 'threejs_mod_vec4',
82
- equals_bool: 'threejs_equals_bool',
83
- equals_bvec2: 'threejs_equals_bvec2',
84
- equals_bvec3: 'threejs_equals_bvec3',
85
- equals_bvec4: 'threejs_equals_bvec4',
86
- lessThanEqual: 'threejs_lessThanEqual',
87
- greaterThan: 'threejs_greaterThan',
88
- inversesqrt: 'inverseSqrt',
89
- bitcast: 'bitcast<f32>'
90
- };
91
-
92
75
  const wgslPolyfill = {
93
- threejs_xor: new CodeNode( `
94
- fn threejs_xor( a : bool, b : bool ) -> bool {
95
-
96
- return ( a || b ) && !( a && b );
97
-
98
- }
99
- ` ),
100
- lessThanEqual: new CodeNode( `
101
- fn threejs_lessThanEqual( a : vec3<f32>, b : vec3<f32> ) -> vec3<bool> {
102
-
103
- return vec3<bool>( a.x <= b.x, a.y <= b.y, a.z <= b.z );
104
-
105
- }
106
- ` ),
107
- greaterThan: new CodeNode( `
108
- fn threejs_greaterThan( a : vec3<f32>, b : vec3<f32> ) -> vec3<bool> {
109
-
110
- return vec3<bool>( a.x > b.x, a.y > b.y, a.z > b.z );
111
-
112
- }
113
- ` ),
114
- mod_float: new CodeNode( 'fn threejs_mod_float( x : f32, y : f32 ) -> f32 { return x - y * floor( x / y ); }' ),
115
- mod_vec2: new CodeNode( 'fn threejs_mod_vec2( x : vec2f, y : vec2f ) -> vec2f { return x - y * floor( x / y ); }' ),
116
- mod_vec3: new CodeNode( 'fn threejs_mod_vec3( x : vec3f, y : vec3f ) -> vec3f { return x - y * floor( x / y ); }' ),
117
- mod_vec4: new CodeNode( 'fn threejs_mod_vec4( x : vec4f, y : vec4f ) -> vec4f { return x - y * floor( x / y ); }' ),
118
- equals_bool: new CodeNode( 'fn threejs_equals_bool( a : bool, b : bool ) -> bool { return a == b; }' ),
119
- equals_bvec2: new CodeNode( 'fn threejs_equals_bvec2( a : vec2f, b : vec2f ) -> vec2<bool> { return vec2<bool>( a.x == b.x, a.y == b.y ); }' ),
120
- equals_bvec3: new CodeNode( 'fn threejs_equals_bvec3( a : vec3f, b : vec3f ) -> vec3<bool> { return vec3<bool>( a.x == b.x, a.y == b.y, a.z == b.z ); }' ),
121
- equals_bvec4: new CodeNode( 'fn threejs_equals_bvec4( a : vec4f, b : vec4f ) -> vec4<bool> { return vec4<bool>( a.x == b.x, a.y == b.y, a.z == b.z, a.w == b.w ); }' ),
76
+ tsl_xor: new CodeNode( 'fn tsl_xor( a : bool, b : bool ) -> bool { return ( a || b ) && !( a && b ); }' ),
77
+ mod_float: new CodeNode( 'fn tsl_mod_float( x : f32, y : f32 ) -> f32 { return x - y * floor( x / y ); }' ),
78
+ mod_vec2: new CodeNode( 'fn tsl_mod_vec2( x : vec2f, y : vec2f ) -> vec2f { return x - y * floor( x / y ); }' ),
79
+ mod_vec3: new CodeNode( 'fn tsl_mod_vec3( x : vec3f, y : vec3f ) -> vec3f { return x - y * floor( x / y ); }' ),
80
+ mod_vec4: new CodeNode( 'fn tsl_mod_vec4( x : vec4f, y : vec4f ) -> vec4f { return x - y * floor( x / y ); }' ),
81
+ equals_bool: new CodeNode( 'fn tsl_equals_bool( a : bool, b : bool ) -> bool { return a == b; }' ),
82
+ equals_bvec2: new CodeNode( 'fn tsl_equals_bvec2( a : vec2f, b : vec2f ) -> vec2<bool> { return vec2<bool>( a.x == b.x, a.y == b.y ); }' ),
83
+ equals_bvec3: new CodeNode( 'fn tsl_equals_bvec3( a : vec3f, b : vec3f ) -> vec3<bool> { return vec3<bool>( a.x == b.x, a.y == b.y, a.z == b.z ); }' ),
84
+ equals_bvec4: new CodeNode( 'fn tsl_equals_bvec4( a : vec4f, b : vec4f ) -> vec4<bool> { return vec4<bool>( a.x == b.x, a.y == b.y, a.z == b.z, a.w == b.w ); }' ),
122
85
  repeatWrapping: new CodeNode( `
123
- fn threejs_repeatWrapping( uv : vec2<f32>, dimension : vec2<u32> ) -> vec2<u32> {
86
+ fn tsl_repeatWrapping( uv : vec2<f32>, dimension : vec2<u32> ) -> vec2<u32> {
124
87
 
125
88
  let uvScaled = vec2<u32>( uv * vec2<f32>( dimension ) );
126
89
 
@@ -129,7 +92,7 @@ fn threejs_repeatWrapping( uv : vec2<f32>, dimension : vec2<u32> ) -> vec2<u32>
129
92
  }
130
93
  ` ),
131
94
  biquadraticTexture: new CodeNode( `
132
- fn threejs_biquadraticTexture( map : texture_2d<f32>, coord : vec2f, level : i32 ) -> vec4f {
95
+ fn tsl_biquadraticTexture( map : texture_2d<f32>, coord : vec2f, level : i32 ) -> vec4f {
133
96
 
134
97
  let res = vec2f( textureDimensions( map, level ) );
135
98
 
@@ -153,6 +116,39 @@ fn threejs_biquadraticTexture( map : texture_2d<f32>, coord : vec2f, level : i32
153
116
  ` )
154
117
  };
155
118
 
119
+ const wgslMethods = {
120
+ dFdx: 'dpdx',
121
+ dFdy: '- dpdy',
122
+ mod_float: 'tsl_mod_float',
123
+ mod_vec2: 'tsl_mod_vec2',
124
+ mod_vec3: 'tsl_mod_vec3',
125
+ mod_vec4: 'tsl_mod_vec4',
126
+ equals_bool: 'tsl_equals_bool',
127
+ equals_bvec2: 'tsl_equals_bvec2',
128
+ equals_bvec3: 'tsl_equals_bvec3',
129
+ equals_bvec4: 'tsl_equals_bvec4',
130
+ inversesqrt: 'inverseSqrt',
131
+ bitcast: 'bitcast<f32>'
132
+ };
133
+
134
+ // WebGPU issue: does not support pow() with negative base on Windows
135
+
136
+ if ( /Windows/g.test( navigator.userAgent ) ) {
137
+
138
+ wgslPolyfill.pow_float = new CodeNode( 'fn tsl_pow_float( a : f32, b : f32 ) -> f32 { return select( -pow( -a, b ), pow( a, b ), a > 0.0 ); }' );
139
+ wgslPolyfill.pow_vec2 = new CodeNode( 'fn tsl_pow_vec2( a : vec2f, b : vec2f ) -> vec2f { return vec2f( tsl_pow_float( a.x, b.x ), tsl_pow_float( a.y, b.y ) ); }', [ wgslPolyfill.pow_float ] );
140
+ wgslPolyfill.pow_vec3 = new CodeNode( 'fn tsl_pow_vec3( a : vec3f, b : vec3f ) -> vec3f { return vec3f( tsl_pow_float( a.x, b.x ), tsl_pow_float( a.y, b.y ), tsl_pow_float( a.z, b.z ) ); }', [ wgslPolyfill.pow_float ] );
141
+ wgslPolyfill.pow_vec4 = new CodeNode( 'fn tsl_pow_vec4( a : vec4f, b : vec4f ) -> vec4f { return vec4f( tsl_pow_float( a.x, b.x ), tsl_pow_float( a.y, b.y ), tsl_pow_float( a.z, b.z ), tsl_pow_float( a.w, b.w ) ); }', [ wgslPolyfill.pow_float ] );
142
+
143
+ wgslMethods.pow_float = 'tsl_pow_float';
144
+ wgslMethods.pow_vec2 = 'tsl_pow_vec2';
145
+ wgslMethods.pow_vec3 = 'tsl_pow_vec3';
146
+ wgslMethods.pow_vec4 = 'tsl_pow_vec4';
147
+
148
+ }
149
+
150
+ //
151
+
156
152
  class WGSLNodeBuilder extends NodeBuilder {
157
153
 
158
154
  constructor( object, renderer ) {
@@ -167,7 +163,7 @@ class WGSLNodeBuilder extends NodeBuilder {
167
163
 
168
164
  }
169
165
 
170
- needsColorSpaceToLinear( texture ) {
166
+ needsToWorkingColorSpace( texture ) {
171
167
 
172
168
  return texture.isVideoTexture === true && texture.colorSpace !== NoColorSpace;
173
169
 
@@ -235,7 +231,7 @@ class WGSLNodeBuilder extends NodeBuilder {
235
231
 
236
232
  this._include( 'biquadraticTexture' );
237
233
 
238
- return `threejs_biquadraticTexture( ${ textureProperty }, ${ uvSnippet }, i32( ${ levelSnippet } ) )`;
234
+ return `tsl_biquadraticTexture( ${ textureProperty }, ${ uvSnippet }, i32( ${ levelSnippet } ) )`;
239
235
 
240
236
  }
241
237
 
@@ -245,7 +241,7 @@ class WGSLNodeBuilder extends NodeBuilder {
245
241
 
246
242
  const dimension = texture.isMultisampleRenderTargetTexture === true ? `textureDimensions( ${ textureProperty } )` : `textureDimensions( ${ textureProperty }, 0 )`;
247
243
 
248
- return `textureLoad( ${ textureProperty }, threejs_repeatWrapping( ${ uvSnippet }, ${ dimension } ), i32( ${ levelSnippet } ) )`;
244
+ return `textureLoad( ${ textureProperty }, tsl_repeatWrapping( ${ uvSnippet }, ${ dimension } ), i32( ${ levelSnippet } ) )`;
249
245
 
250
246
  }
251
247
 
@@ -271,7 +267,7 @@ class WGSLNodeBuilder extends NodeBuilder {
271
267
 
272
268
  isUnfilterable( texture ) {
273
269
 
274
- return this.getComponentTypeFromTexture( texture ) !== 'float' || ( texture.isDataTexture === true && texture.type === FloatType ) || texture.isMultisampleRenderTargetTexture === true;
270
+ return this.getComponentTypeFromTexture( texture ) !== 'float' || ( ! this.isAvailable( 'float32Filterable' ) && texture.isDataTexture === true && texture.type === FloatType ) || texture.isMultisampleRenderTargetTexture === true;
275
271
 
276
272
  }
277
273
 
@@ -602,12 +598,18 @@ class WGSLNodeBuilder extends NodeBuilder {
602
598
 
603
599
  //
604
600
 
605
- const code = `fn ${ layout.name }( ${ parameters.join( ', ' ) } ) -> ${ this.getType( layout.type ) } {
601
+ let code = `fn ${ layout.name }( ${ parameters.join( ', ' ) } ) -> ${ this.getType( layout.type ) } {
606
602
  ${ flowData.vars }
607
603
  ${ flowData.code }
608
- return ${ flowData.result };
604
+ `;
605
+
606
+ if ( flowData.result ) {
609
607
 
610
- }`;
608
+ code += `\treturn ${ flowData.result };\n`;
609
+
610
+ }
611
+
612
+ code += '\n}\n';
611
613
 
612
614
  //
613
615
 
@@ -627,6 +629,28 @@ ${ flowData.code }
627
629
 
628
630
  }
629
631
 
632
+ getInvocationLocalIndex() {
633
+
634
+ return this.getBuiltin( 'local_invocation_index', 'invocationLocalIndex', 'u32', 'attribute' );
635
+
636
+ }
637
+
638
+ getSubgroupSize() {
639
+
640
+ this.enableSubGroups();
641
+
642
+ return this.getBuiltin( 'subgroup_size', 'subgroupSize', 'u32', 'attribute' );
643
+
644
+ }
645
+
646
+ getSubgroupIndex() {
647
+
648
+ this.enableSubGroups();
649
+
650
+ return this.getBuiltin( 'subgroup_invocation_id', 'subgroupIndex', 'u32', 'attribute' );
651
+
652
+ }
653
+
630
654
  getDrawIndex() {
631
655
 
632
656
  return null;
@@ -641,7 +665,7 @@ ${ flowData.code }
641
665
 
642
666
  getFragCoord() {
643
667
 
644
- return this.getBuiltin( 'position', 'fragCoord', 'vec4<f32>' ) + '.xyz';
668
+ return this.getBuiltin( 'position', 'fragCoord', 'vec4<f32>' ) + '.xy';
645
669
 
646
670
  }
647
671
 
@@ -659,8 +683,8 @@ ${ flowData.code }
659
683
 
660
684
  enableDirective( name, shaderStage = this.shaderStage ) {
661
685
 
662
- const stage = this.directives[ shaderStage ] || ( this.directives[ shaderStage ] = [] );
663
- stage.push( name );
686
+ const stage = this.directives[ shaderStage ] || ( this.directives[ shaderStage ] = new Set() );
687
+ stage.add( name );
664
688
 
665
689
  }
666
690
 
@@ -673,7 +697,7 @@ ${ flowData.code }
673
697
 
674
698
  for ( const directive of directives ) {
675
699
 
676
- snippets.push( `enable ${directive}` );
700
+ snippets.push( `enable ${directive};` );
677
701
 
678
702
  }
679
703
 
@@ -683,6 +707,18 @@ ${ flowData.code }
683
707
 
684
708
  }
685
709
 
710
+ enableSubGroups() {
711
+
712
+ this.enableDirective( 'subgroups' );
713
+
714
+ }
715
+
716
+ enableSubgroupsF16() {
717
+
718
+ this.enableDirective( 'subgroups-f16' );
719
+
720
+ }
721
+
686
722
  enableClipDistances() {
687
723
 
688
724
  this.enableDirective( 'clip_distances' );
@@ -771,7 +807,7 @@ ${ flowData.code }
771
807
 
772
808
  const builtins = this.getBuiltins( 'output' );
773
809
 
774
- if ( builtins ) snippets.push( builtins );
810
+ if ( builtins ) snippets.push( '\t' + builtins );
775
811
 
776
812
  return snippets.join( ',\n' );
777
813
 
@@ -925,7 +961,7 @@ ${ flowData.code }
925
961
 
926
962
  textureType = 'texture_cube<f32>';
927
963
 
928
- } else if ( texture.isDataArrayTexture === true ) {
964
+ } else if ( texture.isDataArrayTexture === true || texture.isCompressedArrayTexture === true ) {
929
965
 
930
966
  textureType = 'texture_2d_array<f32>';
931
967
 
@@ -1177,7 +1213,7 @@ ${ flowData.code }
1177
1213
 
1178
1214
  return `${ this.getSignature() }
1179
1215
  // directives
1180
- ${shaderData.directives};
1216
+ ${shaderData.directives}
1181
1217
 
1182
1218
  // uniforms
1183
1219
  ${shaderData.uniforms}
@@ -9,6 +9,7 @@ class WebGPUBindingUtils {
9
9
  constructor( backend ) {
10
10
 
11
11
  this.backend = backend;
12
+ this.bindGroupLayoutCache = new WeakMap();
12
13
 
13
14
  }
14
15
 
@@ -95,9 +96,15 @@ class WebGPUBindingUtils {
95
96
 
96
97
  } else if ( type === FloatType ) {
97
98
 
98
- // @TODO: Add support for this soon: backend.hasFeature( 'float32-filterable' )
99
+ if ( this.backend.hasFeature( 'float32-filterable' ) ) {
99
100
 
100
- texture.sampleType = GPUTextureSampleType.UnfilterableFloat;
101
+ texture.sampleType = GPUTextureSampleType.Float;
102
+
103
+ } else {
104
+
105
+ texture.sampleType = GPUTextureSampleType.UnfilterableFloat;
106
+
107
+ }
101
108
 
102
109
  }
103
110
 
@@ -107,7 +114,7 @@ class WebGPUBindingUtils {
107
114
 
108
115
  texture.viewDimension = GPUTextureViewDimension.Cube;
109
116
 
110
- } else if ( binding.texture.isDataArrayTexture ) {
117
+ } else if ( binding.texture.isDataArrayTexture || binding.texture.isCompressedArrayTexture ) {
111
118
 
112
119
  texture.viewDimension = GPUTextureViewDimension.TwoDArray;
113
120
 
@@ -135,12 +142,20 @@ class WebGPUBindingUtils {
135
142
 
136
143
  createBindings( bindGroup ) {
137
144
 
138
- const backend = this.backend;
145
+ const { backend, bindGroupLayoutCache } = this;
139
146
  const bindingsData = backend.get( bindGroup );
140
147
 
141
148
  // setup (static) binding layout and (dynamic) binding group
142
149
 
143
- const bindLayoutGPU = this.createBindingsLayout( bindGroup );
150
+ let bindLayoutGPU = bindGroupLayoutCache.get( bindGroup.bindingsReference );
151
+
152
+ if ( bindLayoutGPU === undefined ) {
153
+
154
+ bindLayoutGPU = this.createBindingsLayout( bindGroup );
155
+ bindGroupLayoutCache.set( bindGroup.bindingsReference, bindLayoutGPU );
156
+
157
+ }
158
+
144
159
  const bindGroupGPU = this.createBindGroup( bindGroup, bindLayoutGPU );
145
160
 
146
161
  bindingsData.layout = bindLayoutGPU;
@@ -219,37 +234,46 @@ class WebGPUBindingUtils {
219
234
 
220
235
  const textureData = backend.get( binding.texture );
221
236
 
222
- let dimensionViewGPU;
237
+ let resourceGPU;
238
+
239
+ if ( textureData.externalTexture !== undefined ) {
223
240
 
224
- if ( binding.isSampledCubeTexture ) {
241
+ resourceGPU = device.importExternalTexture( { source: textureData.externalTexture } );
225
242
 
226
- dimensionViewGPU = GPUTextureViewDimension.Cube;
243
+ } else {
227
244
 
228
- } else if ( binding.isSampledTexture3D ) {
245
+ const mipLevelCount = binding.store ? 1 : textureData.texture.mipLevelCount;
246
+ const propertyName = `view-${ textureData.texture.width }-${ textureData.texture.height }-${ mipLevelCount }`;
229
247
 
230
- dimensionViewGPU = GPUTextureViewDimension.ThreeD;
248
+ resourceGPU = textureData[ propertyName ];
231
249
 
232
- } else if ( binding.texture.isDataArrayTexture ) {
250
+ if ( resourceGPU === undefined ) {
233
251
 
234
- dimensionViewGPU = GPUTextureViewDimension.TwoDArray;
252
+ const aspectGPU = GPUTextureAspect.All;
235
253
 
236
- } else {
254
+ let dimensionViewGPU;
237
255
 
238
- dimensionViewGPU = GPUTextureViewDimension.TwoD;
256
+ if ( binding.isSampledCubeTexture ) {
239
257
 
240
- }
258
+ dimensionViewGPU = GPUTextureViewDimension.Cube;
241
259
 
242
- let resourceGPU;
260
+ } else if ( binding.isSampledTexture3D ) {
243
261
 
244
- if ( textureData.externalTexture !== undefined ) {
262
+ dimensionViewGPU = GPUTextureViewDimension.ThreeD;
245
263
 
246
- resourceGPU = device.importExternalTexture( { source: textureData.externalTexture } );
264
+ } else if ( binding.texture.isDataArrayTexture || binding.texture.isCompressedArrayTexture ) {
247
265
 
248
- } else {
266
+ dimensionViewGPU = GPUTextureViewDimension.TwoDArray;
267
+
268
+ } else {
249
269
 
250
- const aspectGPU = GPUTextureAspect.All;
270
+ dimensionViewGPU = GPUTextureViewDimension.TwoD;
251
271
 
252
- resourceGPU = textureData.texture.createView( { aspect: aspectGPU, dimension: dimensionViewGPU, mipLevelCount: binding.store ? 1 : textureData.mipLevelCount } );
272
+ }
273
+
274
+ resourceGPU = textureData[ propertyName ] = textureData.texture.createView( { aspect: aspectGPU, dimension: dimensionViewGPU, mipLevelCount } );
275
+
276
+ }
253
277
 
254
278
  }
255
279
 
@@ -328,5 +328,6 @@ export const GPUFeatureName = {
328
328
  BGRA8UNormStorage: 'bgra8unorm-storage',
329
329
  Float32Filterable: 'float32-filterable',
330
330
  ClipDistances: 'clip-distances',
331
- DualSourceBlending: 'dual-source-blending'
331
+ DualSourceBlending: 'dual-source-blending',
332
+ Subgroups: 'subgroups'
332
333
  };
@@ -123,7 +123,7 @@ class WebGPUPipelineUtils {
123
123
  const sampleCount = this._getSampleCount( renderObject.context );
124
124
 
125
125
  const pipelineDescriptor = {
126
- label: 'renderPipeline',
126
+ label: `renderPipeline_${ material.name || material.type }_${ material.id }`,
127
127
  vertex: Object.assign( {}, vertexModule, { buffers: vertexBuffers } ),
128
128
  fragment: Object.assign( {}, fragmentModule, { targets } ),
129
129
  primitive: primitiveState,
@@ -168,17 +168,14 @@ class WebGPUPipelineUtils {
168
168
 
169
169
  }
170
170
 
171
- createBundleEncoder( renderContext, renderObject ) {
171
+ createBundleEncoder( renderContext ) {
172
172
 
173
173
  const backend = this.backend;
174
174
  const { utils, device } = backend;
175
175
 
176
- const renderContextData = backend.get( renderContext );
177
- const renderObjectData = backend.get( renderObject );
178
-
179
176
  const depthStencilFormat = utils.getCurrentDepthStencilFormat( renderContext );
180
177
  const colorFormat = utils.getCurrentColorFormat( renderContext );
181
- const sampleCount = this._getSampleCount( renderObject.context );
178
+ const sampleCount = this._getSampleCount( renderContext );
182
179
 
183
180
  const descriptor = {
184
181
  label: 'renderBundleEncoder',
@@ -187,13 +184,7 @@ class WebGPUPipelineUtils {
187
184
  sampleCount
188
185
  };
189
186
 
190
- const bundleEncoder = device.createRenderBundleEncoder( descriptor );
191
-
192
- renderObjectData.bundleEncoder = bundleEncoder;
193
- renderContextData.currentSets = { attributes: {} };
194
- renderContextData._renderBundleViewport = renderContext.width + '_' + renderContext.height;
195
-
196
- return bundleEncoder;
187
+ return device.createRenderBundleEncoder( descriptor );
197
188
 
198
189
  }
199
190
 
@@ -280,11 +271,11 @@ class WebGPUPipelineUtils {
280
271
  switch ( blending ) {
281
272
 
282
273
  case NormalBlending:
283
- setBlend( GPUBlendFactor.SrcAlpha, GPUBlendFactor.OneMinusSrcAlpha, GPUBlendFactor.One, GPUBlendFactor.OneMinusSrcAlpha );
274
+ setBlend( GPUBlendFactor.One, GPUBlendFactor.OneMinusSrcAlpha, GPUBlendFactor.One, GPUBlendFactor.OneMinusSrcAlpha );
284
275
  break;
285
276
 
286
277
  case AdditiveBlending:
287
- setBlend( GPUBlendFactor.SrcAlpha, GPUBlendFactor.One, GPUBlendFactor.One, GPUBlendFactor.One );
278
+ setBlend( GPUBlendFactor.One, GPUBlendFactor.One, GPUBlendFactor.One, GPUBlendFactor.One );
288
279
  break;
289
280
 
290
281
  case SubtractiveBlending:
@@ -1,9 +1,12 @@
1
+ import DataMap from '../../common/DataMap.js';
1
2
  import { GPUTextureViewDimension, GPUIndexFormat, GPUFilterMode, GPUPrimitiveTopology, GPULoadOp, GPUStoreOp } from './WebGPUConstants.js';
2
3
 
3
- class WebGPUTexturePassUtils {
4
+ class WebGPUTexturePassUtils extends DataMap {
4
5
 
5
6
  constructor( device ) {
6
7
 
8
+ super();
9
+
7
10
  this.device = device;
8
11
 
9
12
  const mipmapVertexSource = `
@@ -99,6 +102,7 @@ fn main( @location( 0 ) vTex : vec2<f32> ) -> @location( 0 ) vec4<f32> {
99
102
  if ( pipeline === undefined ) {
100
103
 
101
104
  pipeline = this.device.createRenderPipeline( {
105
+ label: `mipmap-${ format }`,
102
106
  vertex: {
103
107
  module: this.mipmapVertexShaderModule,
104
108
  entryPoint: 'main'
@@ -130,6 +134,7 @@ fn main( @location( 0 ) vTex : vec2<f32> ) -> @location( 0 ) vec4<f32> {
130
134
  if ( pipeline === undefined ) {
131
135
 
132
136
  pipeline = this.device.createRenderPipeline( {
137
+ label: `flipY-${ format }`,
133
138
  vertex: {
134
139
  module: this.mipmapVertexShaderModule,
135
140
  entryPoint: 'main'
@@ -226,9 +231,33 @@ fn main( @location( 0 ) vTex : vec2<f32> ) -> @location( 0 ) vec4<f32> {
226
231
 
227
232
  generateMipmaps( textureGPU, textureGPUDescriptor, baseArrayLayer = 0 ) {
228
233
 
229
- const pipeline = this.getTransferPipeline( textureGPUDescriptor.format );
234
+ const textureData = this.get( textureGPU );
235
+
236
+ if ( textureData.useCount === undefined ) {
237
+
238
+ textureData.useCount = 0;
239
+ textureData.layers = [];
240
+
241
+ }
242
+
243
+ const passes = textureData.layers[ baseArrayLayer ] || this._mipmapCreateBundles( textureGPU, textureGPUDescriptor, baseArrayLayer );
230
244
 
231
245
  const commandEncoder = this.device.createCommandEncoder( {} );
246
+
247
+ this._mipmapRunBundles( commandEncoder, passes );
248
+
249
+ this.device.queue.submit( [ commandEncoder.finish() ] );
250
+
251
+ if ( textureData.useCount !== 0 ) textureData.layers[ baseArrayLayer ] = passes;
252
+
253
+ textureData.useCount ++;
254
+
255
+ }
256
+
257
+ _mipmapCreateBundles( textureGPU, textureGPUDescriptor, baseArrayLayer ) {
258
+
259
+ const pipeline = this.getTransferPipeline( textureGPUDescriptor.format );
260
+
232
261
  const bindGroupLayout = pipeline.getBindGroupLayout( 0 ); // @TODO: Consider making this static.
233
262
 
234
263
  let srcView = textureGPU.createView( {
@@ -238,6 +267,8 @@ fn main( @location( 0 ) vTex : vec2<f32> ) -> @location( 0 ) vec4<f32> {
238
267
  baseArrayLayer
239
268
  } );
240
269
 
270
+ const passes = [];
271
+
241
272
  for ( let i = 1; i < textureGPUDescriptor.mipLevelCount; i ++ ) {
242
273
 
243
274
  const bindGroup = this.device.createBindGroup( {
@@ -258,25 +289,51 @@ fn main( @location( 0 ) vTex : vec2<f32> ) -> @location( 0 ) vec4<f32> {
258
289
  baseArrayLayer
259
290
  } );
260
291
 
261
- const passEncoder = commandEncoder.beginRenderPass( {
292
+ const passDescriptor = {
262
293
  colorAttachments: [ {
263
294
  view: dstView,
264
295
  loadOp: GPULoadOp.Clear,
265
296
  storeOp: GPUStoreOp.Store,
266
297
  clearValue: [ 0, 0, 0, 0 ]
267
298
  } ]
299
+ };
300
+
301
+ const passEncoder = this.device.createRenderBundleEncoder( {
302
+ colorFormats: [ textureGPUDescriptor.format ]
268
303
  } );
269
304
 
270
305
  passEncoder.setPipeline( pipeline );
271
306
  passEncoder.setBindGroup( 0, bindGroup );
272
307
  passEncoder.draw( 4, 1, 0, 0 );
273
- passEncoder.end();
308
+
309
+ passes.push( {
310
+ renderBundles: [ passEncoder.finish() ],
311
+ passDescriptor
312
+ } );
274
313
 
275
314
  srcView = dstView;
276
315
 
277
316
  }
278
317
 
279
- this.device.queue.submit( [ commandEncoder.finish() ] );
318
+ return passes;
319
+
320
+ }
321
+
322
+ _mipmapRunBundles( commandEncoder, passes ) {
323
+
324
+ const levels = passes.length;
325
+
326
+ for ( let i = 0; i < levels; i ++ ) {
327
+
328
+ const pass = passes[ i ];
329
+
330
+ const passEncoder = commandEncoder.beginRenderPass( pass.passDescriptor );
331
+
332
+ passEncoder.executeBundles( pass.renderBundles );
333
+
334
+ passEncoder.end();
335
+
336
+ }
280
337
 
281
338
  }
282
339