super-three 0.163.0 → 0.164.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 (114) hide show
  1. package/build/three.cjs +473 -245
  2. package/build/three.module.js +473 -245
  3. package/build/three.module.min.js +2 -2
  4. package/examples/jsm/animation/CCDIKSolver.js +4 -2
  5. package/examples/jsm/exporters/GLTFExporter.js +45 -1
  6. package/examples/jsm/exporters/USDZExporter.js +7 -1
  7. package/examples/jsm/libs/draco/README.md +2 -2
  8. package/examples/jsm/loaders/EXRLoader.js +283 -99
  9. package/examples/jsm/loaders/GLTFLoader.js +53 -0
  10. package/examples/jsm/loaders/KTX2Loader.js +3 -6
  11. package/examples/jsm/loaders/VRMLLoader.js +1 -1
  12. package/examples/jsm/loaders/lwo/IFFParser.js +8 -5
  13. package/examples/jsm/materials/MeshGouraudMaterial.js +7 -1
  14. package/examples/jsm/math/Octree.js +26 -20
  15. package/examples/jsm/nodes/Nodes.js +4 -3
  16. package/examples/jsm/nodes/accessors/AccessorsUtils.js +16 -1
  17. package/examples/jsm/nodes/accessors/ClippingNode.js +3 -2
  18. package/examples/jsm/nodes/accessors/MaterialNode.js +107 -3
  19. package/examples/jsm/nodes/accessors/StorageBufferNode.js +9 -0
  20. package/examples/jsm/nodes/accessors/TextureNode.js +21 -3
  21. package/examples/jsm/nodes/accessors/TextureSizeNode.js +1 -1
  22. package/examples/jsm/nodes/code/FunctionNode.js +0 -8
  23. package/examples/jsm/nodes/core/Node.js +8 -0
  24. package/examples/jsm/nodes/core/NodeBuilder.js +5 -9
  25. package/examples/jsm/nodes/core/OutputStructNode.js +2 -1
  26. package/examples/jsm/nodes/core/PropertyNode.js +10 -0
  27. package/examples/jsm/nodes/display/BumpMapNode.js +7 -26
  28. package/examples/jsm/nodes/display/FrontFacingNode.js +13 -0
  29. package/examples/jsm/nodes/display/ViewportDepthNode.js +1 -1
  30. package/examples/jsm/nodes/display/ViewportNode.js +4 -2
  31. package/examples/jsm/nodes/display/ViewportTextureNode.js +4 -1
  32. package/examples/jsm/nodes/functions/BSDF/BRDF_GGX.js +26 -7
  33. package/examples/jsm/nodes/functions/BSDF/D_GGX_Anisotropic.js +28 -0
  34. package/examples/jsm/nodes/functions/BSDF/V_GGX_SmithCorrelated.js +1 -3
  35. package/examples/jsm/nodes/functions/BSDF/V_GGX_SmithCorrelated_Anisotropic.js +29 -0
  36. package/examples/jsm/nodes/functions/PhongLightingModel.js +1 -1
  37. package/examples/jsm/nodes/functions/PhysicalLightingModel.js +164 -10
  38. package/examples/jsm/nodes/functions/ShadowMaskModel.js +31 -0
  39. package/examples/jsm/nodes/lighting/AnalyticLightNode.js +18 -4
  40. package/examples/jsm/nodes/lighting/DirectionalLightNode.js +2 -1
  41. package/examples/jsm/nodes/lighting/EnvironmentNode.js +11 -2
  42. package/examples/jsm/nodes/lighting/IrradianceNode.js +24 -0
  43. package/examples/jsm/nodes/lighting/LightsNode.js +11 -1
  44. package/examples/jsm/nodes/lighting/PointLightNode.js +2 -1
  45. package/examples/jsm/nodes/lighting/SpotLightNode.js +2 -1
  46. package/examples/jsm/nodes/materials/Line2NodeMaterial.js +10 -6
  47. package/examples/jsm/nodes/materials/Materials.js +1 -0
  48. package/examples/jsm/nodes/materials/MeshNormalNodeMaterial.js +0 -2
  49. package/examples/jsm/nodes/materials/MeshPhongNodeMaterial.js +2 -2
  50. package/examples/jsm/nodes/materials/MeshPhysicalNodeMaterial.js +76 -5
  51. package/examples/jsm/nodes/materials/MeshStandardNodeMaterial.js +11 -4
  52. package/examples/jsm/nodes/materials/NodeMaterial.js +31 -41
  53. package/examples/jsm/nodes/materials/ShadowNodeMaterial.js +34 -0
  54. package/examples/jsm/nodes/pmrem/PMREMUtils.js +1 -1
  55. package/examples/jsm/nodes/shadernode/ShaderNode.js +2 -8
  56. package/examples/jsm/physics/JoltPhysics.js +281 -0
  57. package/examples/jsm/postprocessing/RenderTransitionPass.js +193 -0
  58. package/examples/jsm/renderers/common/Background.js +3 -3
  59. package/examples/jsm/renderers/common/ClippingContext.js +1 -1
  60. package/examples/jsm/renderers/common/RenderList.js +1 -1
  61. package/examples/jsm/renderers/common/RenderObject.js +43 -1
  62. package/examples/jsm/renderers/common/Renderer.js +129 -14
  63. package/examples/jsm/renderers/common/Textures.js +1 -1
  64. package/examples/jsm/renderers/common/extras/PMREMGenerator.js +13 -17
  65. package/examples/jsm/renderers/common/nodes/Nodes.js +31 -47
  66. package/examples/jsm/renderers/webgl/WebGLBackend.js +7 -21
  67. package/examples/jsm/renderers/webgl/WebGLBufferRenderer.js +5 -1
  68. package/examples/jsm/renderers/webgl/nodes/GLSLNodeBuilder.js +6 -0
  69. package/examples/jsm/renderers/webgl/utils/WebGLTextureUtils.js +21 -7
  70. package/examples/jsm/renderers/webgl/utils/WebGLUtils.js +3 -21
  71. package/examples/jsm/renderers/webgpu/WebGPUBackend.js +33 -45
  72. package/examples/jsm/renderers/webgpu/nodes/WGSLNodeBuilder.js +16 -1
  73. package/examples/jsm/renderers/webgpu/utils/WebGPUAttributeUtils.js +4 -1
  74. package/examples/jsm/transpiler/GLSLDecoder.js +1 -1
  75. package/examples/jsm/transpiler/ShaderToyDecoder.js +1 -1
  76. package/examples/jsm/utils/SceneUtils.js +60 -1
  77. package/examples/jsm/webxr/OculusHandModel.js +3 -2
  78. package/examples/jsm/webxr/XRHandModelFactory.js +4 -2
  79. package/package.json +1 -1
  80. package/src/constants.js +1 -1
  81. package/src/core/RenderTarget.js +8 -0
  82. package/src/extras/PMREMGenerator.js +12 -11
  83. package/src/loaders/FileLoader.js +1 -1
  84. package/src/loaders/MaterialLoader.js +1 -0
  85. package/src/materials/Material.js +2 -0
  86. package/src/materials/MeshPhysicalMaterial.js +20 -0
  87. package/src/objects/BatchedMesh.js +23 -0
  88. package/src/objects/Line.js +66 -43
  89. package/src/renderers/WebGLRenderer.js +92 -61
  90. package/src/renderers/shaders/ShaderChunk/lights_physical_fragment.glsl.js +6 -0
  91. package/src/renderers/shaders/ShaderChunk/lights_physical_pars_fragment.glsl.js +1 -0
  92. package/src/renderers/shaders/ShaderChunk/tonemapping_pars_fragment.glsl.js +17 -9
  93. package/src/renderers/shaders/ShaderChunk/transmission_fragment.glsl.js +1 -1
  94. package/src/renderers/shaders/ShaderChunk/transmission_pars_fragment.glsl.js +47 -13
  95. package/src/renderers/shaders/ShaderChunk.js +0 -2
  96. package/src/renderers/shaders/ShaderLib/meshphysical.glsl.js +4 -0
  97. package/src/renderers/shaders/ShaderLib.js +1 -0
  98. package/src/renderers/webgl/WebGLBackground.js +18 -3
  99. package/src/renderers/webgl/WebGLBufferRenderer.js +36 -0
  100. package/src/renderers/webgl/WebGLCapabilities.js +33 -1
  101. package/src/renderers/webgl/WebGLIndexedBufferRenderer.js +36 -0
  102. package/src/renderers/webgl/WebGLMaterials.js +6 -0
  103. package/src/renderers/webgl/WebGLProgram.js +3 -5
  104. package/src/renderers/webgl/WebGLPrograms.js +5 -0
  105. package/src/renderers/webgl/WebGLRenderStates.js +6 -2
  106. package/src/renderers/webgl/WebGLShadowMap.js +25 -25
  107. package/src/renderers/webgl/WebGLTextures.js +68 -60
  108. package/src/renderers/webgl/WebGLUtils.js +3 -21
  109. package/src/renderers/webxr/WebXRManager.js +2 -4
  110. package/examples/jsm/renderers/webgl-legacy/nodes/GLSL1NodeBuilder.js +0 -318
  111. package/examples/jsm/renderers/webgl-legacy/nodes/SlotNode.js +0 -26
  112. package/examples/jsm/renderers/webgl-legacy/nodes/WebGLNodeBuilder.js +0 -792
  113. package/examples/jsm/renderers/webgl-legacy/nodes/WebGLNodes.js +0 -51
  114. package/src/renderers/shaders/ShaderChunk/lightmap_fragment.glsl.js +0 -10
@@ -1,9 +1,9 @@
1
1
  /**
2
2
  * @license
3
- * Copyright 2010-2023 Three.js Authors
3
+ * Copyright 2010-2024 Three.js Authors
4
4
  * SPDX-License-Identifier: MIT
5
5
  */
6
- const REVISION = '163';
6
+ const REVISION = '164';
7
7
 
8
8
  const MOUSE = { LEFT: 0, MIDDLE: 1, RIGHT: 2, ROTATE: 0, DOLLY: 1, PAN: 2 };
9
9
  const TOUCH = { ROTATE: 0, PAN: 1, DOLLY_PAN: 2, DOLLY_ROTATE: 3 };
@@ -2921,6 +2921,8 @@ class RenderTarget extends EventDispatcher {
2921
2921
  minFilter: LinearFilter,
2922
2922
  depthBuffer: true,
2923
2923
  stencilBuffer: false,
2924
+ resolveDepthBuffer: true,
2925
+ resolveStencilBuffer: true,
2924
2926
  depthTexture: null,
2925
2927
  samples: 0,
2926
2928
  count: 1
@@ -2945,6 +2947,9 @@ class RenderTarget extends EventDispatcher {
2945
2947
  this.depthBuffer = options.depthBuffer;
2946
2948
  this.stencilBuffer = options.stencilBuffer;
2947
2949
 
2950
+ this.resolveDepthBuffer = options.resolveDepthBuffer;
2951
+ this.resolveStencilBuffer = options.resolveStencilBuffer;
2952
+
2948
2953
  this.depthTexture = options.depthTexture;
2949
2954
 
2950
2955
  this.samples = options.samples;
@@ -3022,6 +3027,9 @@ class RenderTarget extends EventDispatcher {
3022
3027
  this.depthBuffer = source.depthBuffer;
3023
3028
  this.stencilBuffer = source.stencilBuffer;
3024
3029
 
3030
+ this.resolveDepthBuffer = source.resolveDepthBuffer;
3031
+ this.resolveStencilBuffer = source.resolveStencilBuffer;
3032
+
3025
3033
  if ( source.depthTexture !== null ) this.depthTexture = source.depthTexture.clone();
3026
3034
 
3027
3035
  this.samples = source.samples;
@@ -9237,6 +9245,8 @@ class Material extends EventDispatcher {
9237
9245
 
9238
9246
  }
9239
9247
 
9248
+ if ( this.dispersion !== undefined ) data.dispersion = this.dispersion;
9249
+
9240
9250
  if ( this.iridescence !== undefined ) data.iridescence = this.iridescence;
9241
9251
  if ( this.iridescenceIOR !== undefined ) data.iridescenceIOR = this.iridescenceIOR;
9242
9252
  if ( this.iridescenceThicknessRange !== undefined ) data.iridescenceThicknessRange = this.iridescenceThicknessRange;
@@ -11785,7 +11795,7 @@ class Mesh extends Object3D {
11785
11795
 
11786
11796
  }
11787
11797
 
11788
- function checkIntersection( object, material, raycaster, ray, pA, pB, pC, point ) {
11798
+ function checkIntersection$1( object, material, raycaster, ray, pA, pB, pC, point ) {
11789
11799
 
11790
11800
  let intersect;
11791
11801
 
@@ -11822,7 +11832,7 @@ function checkGeometryIntersection( object, material, raycaster, ray, uv, uv1, n
11822
11832
  object.getVertexPosition( b, _vB$1 );
11823
11833
  object.getVertexPosition( c, _vC$1 );
11824
11834
 
11825
- const intersection = checkIntersection( object, material, raycaster, ray, _vA$1, _vB$1, _vC$1, _intersectionPoint );
11835
+ const intersection = checkIntersection$1( object, material, raycaster, ray, _vA$1, _vB$1, _vC$1, _intersectionPoint );
11826
11836
 
11827
11837
  if ( intersection ) {
11828
11838
 
@@ -13816,8 +13826,6 @@ var fog_pars_fragment = "#ifdef USE_FOG\n\tuniform vec3 fogColor;\n\tvarying flo
13816
13826
 
13817
13827
  var gradientmap_pars_fragment = "#ifdef USE_GRADIENTMAP\n\tuniform sampler2D gradientMap;\n#endif\nvec3 getGradientIrradiance( vec3 normal, vec3 lightDirection ) {\n\tfloat dotNL = dot( normal, lightDirection );\n\tvec2 coord = vec2( dotNL * 0.5 + 0.5, 0.0 );\n\t#ifdef USE_GRADIENTMAP\n\t\treturn vec3( texture2D( gradientMap, coord ).r );\n\t#else\n\t\tvec2 fw = fwidth( coord ) * 0.5;\n\t\treturn mix( vec3( 0.7 ), vec3( 1.0 ), smoothstep( 0.7 - fw.x, 0.7 + fw.x, coord.x ) );\n\t#endif\n}";
13818
13828
 
13819
- var lightmap_fragment = "#ifdef USE_LIGHTMAP\n\tvec4 lightMapTexel = texture2D( lightMap, vLightMapUv );\n\tvec3 lightMapIrradiance = lightMapTexel.rgb * lightMapIntensity;\n\treflectedLight.indirectDiffuse += lightMapIrradiance;\n#endif";
13820
-
13821
13829
  var lightmap_pars_fragment = "#ifdef USE_LIGHTMAP\n\tuniform sampler2D lightMap;\n\tuniform float lightMapIntensity;\n#endif";
13822
13830
 
13823
13831
  var lights_lambert_fragment = "LambertMaterial material;\nmaterial.diffuseColor = diffuseColor.rgb;\nmaterial.specularStrength = specularStrength;";
@@ -13836,9 +13844,9 @@ var lights_phong_fragment = "BlinnPhongMaterial material;\nmaterial.diffuseColor
13836
13844
 
13837
13845
  var lights_phong_pars_fragment = "varying vec3 vViewPosition;\nstruct BlinnPhongMaterial {\n\tvec3 diffuseColor;\n\tvec3 specularColor;\n\tfloat specularShininess;\n\tfloat specularStrength;\n};\nvoid RE_Direct_BlinnPhong( const in IncidentLight directLight, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in BlinnPhongMaterial material, inout ReflectedLight reflectedLight ) {\n\tfloat dotNL = saturate( dot( geometryNormal, directLight.direction ) );\n\tvec3 irradiance = dotNL * directLight.color;\n\treflectedLight.directDiffuse += irradiance * BRDF_Lambert( material.diffuseColor );\n\treflectedLight.directSpecular += irradiance * BRDF_BlinnPhong( directLight.direction, geometryViewDir, geometryNormal, material.specularColor, material.specularShininess ) * material.specularStrength;\n}\nvoid RE_IndirectDiffuse_BlinnPhong( const in vec3 irradiance, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in BlinnPhongMaterial material, inout ReflectedLight reflectedLight ) {\n\treflectedLight.indirectDiffuse += irradiance * BRDF_Lambert( material.diffuseColor );\n}\n#define RE_Direct\t\t\t\tRE_Direct_BlinnPhong\n#define RE_IndirectDiffuse\t\tRE_IndirectDiffuse_BlinnPhong";
13838
13846
 
13839
- var lights_physical_fragment = "PhysicalMaterial material;\nmaterial.diffuseColor = diffuseColor.rgb * ( 1.0 - metalnessFactor );\nvec3 dxy = max( abs( dFdx( nonPerturbedNormal ) ), abs( dFdy( nonPerturbedNormal ) ) );\nfloat geometryRoughness = max( max( dxy.x, dxy.y ), dxy.z );\nmaterial.roughness = max( roughnessFactor, 0.0525 );material.roughness += geometryRoughness;\nmaterial.roughness = min( material.roughness, 1.0 );\n#ifdef IOR\n\tmaterial.ior = ior;\n\t#ifdef USE_SPECULAR\n\t\tfloat specularIntensityFactor = specularIntensity;\n\t\tvec3 specularColorFactor = specularColor;\n\t\t#ifdef USE_SPECULAR_COLORMAP\n\t\t\tspecularColorFactor *= texture2D( specularColorMap, vSpecularColorMapUv ).rgb;\n\t\t#endif\n\t\t#ifdef USE_SPECULAR_INTENSITYMAP\n\t\t\tspecularIntensityFactor *= texture2D( specularIntensityMap, vSpecularIntensityMapUv ).a;\n\t\t#endif\n\t\tmaterial.specularF90 = mix( specularIntensityFactor, 1.0, metalnessFactor );\n\t#else\n\t\tfloat specularIntensityFactor = 1.0;\n\t\tvec3 specularColorFactor = vec3( 1.0 );\n\t\tmaterial.specularF90 = 1.0;\n\t#endif\n\tmaterial.specularColor = mix( min( pow2( ( material.ior - 1.0 ) / ( material.ior + 1.0 ) ) * specularColorFactor, vec3( 1.0 ) ) * specularIntensityFactor, diffuseColor.rgb, metalnessFactor );\n#else\n\tmaterial.specularColor = mix( vec3( 0.04 ), diffuseColor.rgb, metalnessFactor );\n\tmaterial.specularF90 = 1.0;\n#endif\n#ifdef USE_CLEARCOAT\n\tmaterial.clearcoat = clearcoat;\n\tmaterial.clearcoatRoughness = clearcoatRoughness;\n\tmaterial.clearcoatF0 = vec3( 0.04 );\n\tmaterial.clearcoatF90 = 1.0;\n\t#ifdef USE_CLEARCOATMAP\n\t\tmaterial.clearcoat *= texture2D( clearcoatMap, vClearcoatMapUv ).x;\n\t#endif\n\t#ifdef USE_CLEARCOAT_ROUGHNESSMAP\n\t\tmaterial.clearcoatRoughness *= texture2D( clearcoatRoughnessMap, vClearcoatRoughnessMapUv ).y;\n\t#endif\n\tmaterial.clearcoat = saturate( material.clearcoat );\tmaterial.clearcoatRoughness = max( material.clearcoatRoughness, 0.0525 );\n\tmaterial.clearcoatRoughness += geometryRoughness;\n\tmaterial.clearcoatRoughness = min( material.clearcoatRoughness, 1.0 );\n#endif\n#ifdef USE_IRIDESCENCE\n\tmaterial.iridescence = iridescence;\n\tmaterial.iridescenceIOR = iridescenceIOR;\n\t#ifdef USE_IRIDESCENCEMAP\n\t\tmaterial.iridescence *= texture2D( iridescenceMap, vIridescenceMapUv ).r;\n\t#endif\n\t#ifdef USE_IRIDESCENCE_THICKNESSMAP\n\t\tmaterial.iridescenceThickness = (iridescenceThicknessMaximum - iridescenceThicknessMinimum) * texture2D( iridescenceThicknessMap, vIridescenceThicknessMapUv ).g + iridescenceThicknessMinimum;\n\t#else\n\t\tmaterial.iridescenceThickness = iridescenceThicknessMaximum;\n\t#endif\n#endif\n#ifdef USE_SHEEN\n\tmaterial.sheenColor = sheenColor;\n\t#ifdef USE_SHEEN_COLORMAP\n\t\tmaterial.sheenColor *= texture2D( sheenColorMap, vSheenColorMapUv ).rgb;\n\t#endif\n\tmaterial.sheenRoughness = clamp( sheenRoughness, 0.07, 1.0 );\n\t#ifdef USE_SHEEN_ROUGHNESSMAP\n\t\tmaterial.sheenRoughness *= texture2D( sheenRoughnessMap, vSheenRoughnessMapUv ).a;\n\t#endif\n#endif\n#ifdef USE_ANISOTROPY\n\t#ifdef USE_ANISOTROPYMAP\n\t\tmat2 anisotropyMat = mat2( anisotropyVector.x, anisotropyVector.y, - anisotropyVector.y, anisotropyVector.x );\n\t\tvec3 anisotropyPolar = texture2D( anisotropyMap, vAnisotropyMapUv ).rgb;\n\t\tvec2 anisotropyV = anisotropyMat * normalize( 2.0 * anisotropyPolar.rg - vec2( 1.0 ) ) * anisotropyPolar.b;\n\t#else\n\t\tvec2 anisotropyV = anisotropyVector;\n\t#endif\n\tmaterial.anisotropy = length( anisotropyV );\n\tif( material.anisotropy == 0.0 ) {\n\t\tanisotropyV = vec2( 1.0, 0.0 );\n\t} else {\n\t\tanisotropyV /= material.anisotropy;\n\t\tmaterial.anisotropy = saturate( material.anisotropy );\n\t}\n\tmaterial.alphaT = mix( pow2( material.roughness ), 1.0, pow2( material.anisotropy ) );\n\tmaterial.anisotropyT = tbn[ 0 ] * anisotropyV.x + tbn[ 1 ] * anisotropyV.y;\n\tmaterial.anisotropyB = tbn[ 1 ] * anisotropyV.x - tbn[ 0 ] * anisotropyV.y;\n#endif";
13847
+ var lights_physical_fragment = "PhysicalMaterial material;\nmaterial.diffuseColor = diffuseColor.rgb * ( 1.0 - metalnessFactor );\nvec3 dxy = max( abs( dFdx( nonPerturbedNormal ) ), abs( dFdy( nonPerturbedNormal ) ) );\nfloat geometryRoughness = max( max( dxy.x, dxy.y ), dxy.z );\nmaterial.roughness = max( roughnessFactor, 0.0525 );material.roughness += geometryRoughness;\nmaterial.roughness = min( material.roughness, 1.0 );\n#ifdef IOR\n\tmaterial.ior = ior;\n\t#ifdef USE_SPECULAR\n\t\tfloat specularIntensityFactor = specularIntensity;\n\t\tvec3 specularColorFactor = specularColor;\n\t\t#ifdef USE_SPECULAR_COLORMAP\n\t\t\tspecularColorFactor *= texture2D( specularColorMap, vSpecularColorMapUv ).rgb;\n\t\t#endif\n\t\t#ifdef USE_SPECULAR_INTENSITYMAP\n\t\t\tspecularIntensityFactor *= texture2D( specularIntensityMap, vSpecularIntensityMapUv ).a;\n\t\t#endif\n\t\tmaterial.specularF90 = mix( specularIntensityFactor, 1.0, metalnessFactor );\n\t#else\n\t\tfloat specularIntensityFactor = 1.0;\n\t\tvec3 specularColorFactor = vec3( 1.0 );\n\t\tmaterial.specularF90 = 1.0;\n\t#endif\n\tmaterial.specularColor = mix( min( pow2( ( material.ior - 1.0 ) / ( material.ior + 1.0 ) ) * specularColorFactor, vec3( 1.0 ) ) * specularIntensityFactor, diffuseColor.rgb, metalnessFactor );\n#else\n\tmaterial.specularColor = mix( vec3( 0.04 ), diffuseColor.rgb, metalnessFactor );\n\tmaterial.specularF90 = 1.0;\n#endif\n#ifdef USE_CLEARCOAT\n\tmaterial.clearcoat = clearcoat;\n\tmaterial.clearcoatRoughness = clearcoatRoughness;\n\tmaterial.clearcoatF0 = vec3( 0.04 );\n\tmaterial.clearcoatF90 = 1.0;\n\t#ifdef USE_CLEARCOATMAP\n\t\tmaterial.clearcoat *= texture2D( clearcoatMap, vClearcoatMapUv ).x;\n\t#endif\n\t#ifdef USE_CLEARCOAT_ROUGHNESSMAP\n\t\tmaterial.clearcoatRoughness *= texture2D( clearcoatRoughnessMap, vClearcoatRoughnessMapUv ).y;\n\t#endif\n\tmaterial.clearcoat = saturate( material.clearcoat );\tmaterial.clearcoatRoughness = max( material.clearcoatRoughness, 0.0525 );\n\tmaterial.clearcoatRoughness += geometryRoughness;\n\tmaterial.clearcoatRoughness = min( material.clearcoatRoughness, 1.0 );\n#endif\n#ifdef USE_DISPERSION\n\tmaterial.dispersion = dispersion;\n#endif\n#ifdef USE_IRIDESCENCE\n\tmaterial.iridescence = iridescence;\n\tmaterial.iridescenceIOR = iridescenceIOR;\n\t#ifdef USE_IRIDESCENCEMAP\n\t\tmaterial.iridescence *= texture2D( iridescenceMap, vIridescenceMapUv ).r;\n\t#endif\n\t#ifdef USE_IRIDESCENCE_THICKNESSMAP\n\t\tmaterial.iridescenceThickness = (iridescenceThicknessMaximum - iridescenceThicknessMinimum) * texture2D( iridescenceThicknessMap, vIridescenceThicknessMapUv ).g + iridescenceThicknessMinimum;\n\t#else\n\t\tmaterial.iridescenceThickness = iridescenceThicknessMaximum;\n\t#endif\n#endif\n#ifdef USE_SHEEN\n\tmaterial.sheenColor = sheenColor;\n\t#ifdef USE_SHEEN_COLORMAP\n\t\tmaterial.sheenColor *= texture2D( sheenColorMap, vSheenColorMapUv ).rgb;\n\t#endif\n\tmaterial.sheenRoughness = clamp( sheenRoughness, 0.07, 1.0 );\n\t#ifdef USE_SHEEN_ROUGHNESSMAP\n\t\tmaterial.sheenRoughness *= texture2D( sheenRoughnessMap, vSheenRoughnessMapUv ).a;\n\t#endif\n#endif\n#ifdef USE_ANISOTROPY\n\t#ifdef USE_ANISOTROPYMAP\n\t\tmat2 anisotropyMat = mat2( anisotropyVector.x, anisotropyVector.y, - anisotropyVector.y, anisotropyVector.x );\n\t\tvec3 anisotropyPolar = texture2D( anisotropyMap, vAnisotropyMapUv ).rgb;\n\t\tvec2 anisotropyV = anisotropyMat * normalize( 2.0 * anisotropyPolar.rg - vec2( 1.0 ) ) * anisotropyPolar.b;\n\t#else\n\t\tvec2 anisotropyV = anisotropyVector;\n\t#endif\n\tmaterial.anisotropy = length( anisotropyV );\n\tif( material.anisotropy == 0.0 ) {\n\t\tanisotropyV = vec2( 1.0, 0.0 );\n\t} else {\n\t\tanisotropyV /= material.anisotropy;\n\t\tmaterial.anisotropy = saturate( material.anisotropy );\n\t}\n\tmaterial.alphaT = mix( pow2( material.roughness ), 1.0, pow2( material.anisotropy ) );\n\tmaterial.anisotropyT = tbn[ 0 ] * anisotropyV.x + tbn[ 1 ] * anisotropyV.y;\n\tmaterial.anisotropyB = tbn[ 1 ] * anisotropyV.x - tbn[ 0 ] * anisotropyV.y;\n#endif";
13840
13848
 
13841
- var lights_physical_pars_fragment = "struct PhysicalMaterial {\n\tvec3 diffuseColor;\n\tfloat roughness;\n\tvec3 specularColor;\n\tfloat specularF90;\n\t#ifdef USE_CLEARCOAT\n\t\tfloat clearcoat;\n\t\tfloat clearcoatRoughness;\n\t\tvec3 clearcoatF0;\n\t\tfloat clearcoatF90;\n\t#endif\n\t#ifdef USE_IRIDESCENCE\n\t\tfloat iridescence;\n\t\tfloat iridescenceIOR;\n\t\tfloat iridescenceThickness;\n\t\tvec3 iridescenceFresnel;\n\t\tvec3 iridescenceF0;\n\t#endif\n\t#ifdef USE_SHEEN\n\t\tvec3 sheenColor;\n\t\tfloat sheenRoughness;\n\t#endif\n\t#ifdef IOR\n\t\tfloat ior;\n\t#endif\n\t#ifdef USE_TRANSMISSION\n\t\tfloat transmission;\n\t\tfloat transmissionAlpha;\n\t\tfloat thickness;\n\t\tfloat attenuationDistance;\n\t\tvec3 attenuationColor;\n\t#endif\n\t#ifdef USE_ANISOTROPY\n\t\tfloat anisotropy;\n\t\tfloat alphaT;\n\t\tvec3 anisotropyT;\n\t\tvec3 anisotropyB;\n\t#endif\n};\nvec3 clearcoatSpecularDirect = vec3( 0.0 );\nvec3 clearcoatSpecularIndirect = vec3( 0.0 );\nvec3 sheenSpecularDirect = vec3( 0.0 );\nvec3 sheenSpecularIndirect = vec3(0.0 );\nvec3 Schlick_to_F0( const in vec3 f, const in float f90, const in float dotVH ) {\n float x = clamp( 1.0 - dotVH, 0.0, 1.0 );\n float x2 = x * x;\n float x5 = clamp( x * x2 * x2, 0.0, 0.9999 );\n return ( f - vec3( f90 ) * x5 ) / ( 1.0 - x5 );\n}\nfloat V_GGX_SmithCorrelated( const in float alpha, const in float dotNL, const in float dotNV ) {\n\tfloat a2 = pow2( alpha );\n\tfloat gv = dotNL * sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNV ) );\n\tfloat gl = dotNV * sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNL ) );\n\treturn 0.5 / max( gv + gl, EPSILON );\n}\nfloat D_GGX( const in float alpha, const in float dotNH ) {\n\tfloat a2 = pow2( alpha );\n\tfloat denom = pow2( dotNH ) * ( a2 - 1.0 ) + 1.0;\n\treturn RECIPROCAL_PI * a2 / pow2( denom );\n}\n#ifdef USE_ANISOTROPY\n\tfloat V_GGX_SmithCorrelated_Anisotropic( const in float alphaT, const in float alphaB, const in float dotTV, const in float dotBV, const in float dotTL, const in float dotBL, const in float dotNV, const in float dotNL ) {\n\t\tfloat gv = dotNL * length( vec3( alphaT * dotTV, alphaB * dotBV, dotNV ) );\n\t\tfloat gl = dotNV * length( vec3( alphaT * dotTL, alphaB * dotBL, dotNL ) );\n\t\tfloat v = 0.5 / ( gv + gl );\n\t\treturn saturate(v);\n\t}\n\tfloat D_GGX_Anisotropic( const in float alphaT, const in float alphaB, const in float dotNH, const in float dotTH, const in float dotBH ) {\n\t\tfloat a2 = alphaT * alphaB;\n\t\thighp vec3 v = vec3( alphaB * dotTH, alphaT * dotBH, a2 * dotNH );\n\t\thighp float v2 = dot( v, v );\n\t\tfloat w2 = a2 / v2;\n\t\treturn RECIPROCAL_PI * a2 * pow2 ( w2 );\n\t}\n#endif\n#ifdef USE_CLEARCOAT\n\tvec3 BRDF_GGX_Clearcoat( const in vec3 lightDir, const in vec3 viewDir, const in vec3 normal, const in PhysicalMaterial material) {\n\t\tvec3 f0 = material.clearcoatF0;\n\t\tfloat f90 = material.clearcoatF90;\n\t\tfloat roughness = material.clearcoatRoughness;\n\t\tfloat alpha = pow2( roughness );\n\t\tvec3 halfDir = normalize( lightDir + viewDir );\n\t\tfloat dotNL = saturate( dot( normal, lightDir ) );\n\t\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\t\tfloat dotNH = saturate( dot( normal, halfDir ) );\n\t\tfloat dotVH = saturate( dot( viewDir, halfDir ) );\n\t\tvec3 F = F_Schlick( f0, f90, dotVH );\n\t\tfloat V = V_GGX_SmithCorrelated( alpha, dotNL, dotNV );\n\t\tfloat D = D_GGX( alpha, dotNH );\n\t\treturn F * ( V * D );\n\t}\n#endif\nvec3 BRDF_GGX( const in vec3 lightDir, const in vec3 viewDir, const in vec3 normal, const in PhysicalMaterial material ) {\n\tvec3 f0 = material.specularColor;\n\tfloat f90 = material.specularF90;\n\tfloat roughness = material.roughness;\n\tfloat alpha = pow2( roughness );\n\tvec3 halfDir = normalize( lightDir + viewDir );\n\tfloat dotNL = saturate( dot( normal, lightDir ) );\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tfloat dotNH = saturate( dot( normal, halfDir ) );\n\tfloat dotVH = saturate( dot( viewDir, halfDir ) );\n\tvec3 F = F_Schlick( f0, f90, dotVH );\n\t#ifdef USE_IRIDESCENCE\n\t\tF = mix( F, material.iridescenceFresnel, material.iridescence );\n\t#endif\n\t#ifdef USE_ANISOTROPY\n\t\tfloat dotTL = dot( material.anisotropyT, lightDir );\n\t\tfloat dotTV = dot( material.anisotropyT, viewDir );\n\t\tfloat dotTH = dot( material.anisotropyT, halfDir );\n\t\tfloat dotBL = dot( material.anisotropyB, lightDir );\n\t\tfloat dotBV = dot( material.anisotropyB, viewDir );\n\t\tfloat dotBH = dot( material.anisotropyB, halfDir );\n\t\tfloat V = V_GGX_SmithCorrelated_Anisotropic( material.alphaT, alpha, dotTV, dotBV, dotTL, dotBL, dotNV, dotNL );\n\t\tfloat D = D_GGX_Anisotropic( material.alphaT, alpha, dotNH, dotTH, dotBH );\n\t#else\n\t\tfloat V = V_GGX_SmithCorrelated( alpha, dotNL, dotNV );\n\t\tfloat D = D_GGX( alpha, dotNH );\n\t#endif\n\treturn F * ( V * D );\n}\nvec2 LTC_Uv( const in vec3 N, const in vec3 V, const in float roughness ) {\n\tconst float LUT_SIZE = 64.0;\n\tconst float LUT_SCALE = ( LUT_SIZE - 1.0 ) / LUT_SIZE;\n\tconst float LUT_BIAS = 0.5 / LUT_SIZE;\n\tfloat dotNV = saturate( dot( N, V ) );\n\tvec2 uv = vec2( roughness, sqrt( 1.0 - dotNV ) );\n\tuv = uv * LUT_SCALE + LUT_BIAS;\n\treturn uv;\n}\nfloat LTC_ClippedSphereFormFactor( const in vec3 f ) {\n\tfloat l = length( f );\n\treturn max( ( l * l + f.z ) / ( l + 1.0 ), 0.0 );\n}\nvec3 LTC_EdgeVectorFormFactor( const in vec3 v1, const in vec3 v2 ) {\n\tfloat x = dot( v1, v2 );\n\tfloat y = abs( x );\n\tfloat a = 0.8543985 + ( 0.4965155 + 0.0145206 * y ) * y;\n\tfloat b = 3.4175940 + ( 4.1616724 + y ) * y;\n\tfloat v = a / b;\n\tfloat theta_sintheta = ( x > 0.0 ) ? v : 0.5 * inversesqrt( max( 1.0 - x * x, 1e-7 ) ) - v;\n\treturn cross( v1, v2 ) * theta_sintheta;\n}\nvec3 LTC_Evaluate( const in vec3 N, const in vec3 V, const in vec3 P, const in mat3 mInv, const in vec3 rectCoords[ 4 ] ) {\n\tvec3 v1 = rectCoords[ 1 ] - rectCoords[ 0 ];\n\tvec3 v2 = rectCoords[ 3 ] - rectCoords[ 0 ];\n\tvec3 lightNormal = cross( v1, v2 );\n\tif( dot( lightNormal, P - rectCoords[ 0 ] ) < 0.0 ) return vec3( 0.0 );\n\tvec3 T1, T2;\n\tT1 = normalize( V - N * dot( V, N ) );\n\tT2 = - cross( N, T1 );\n\tmat3 mat = mInv * transposeMat3( mat3( T1, T2, N ) );\n\tvec3 coords[ 4 ];\n\tcoords[ 0 ] = mat * ( rectCoords[ 0 ] - P );\n\tcoords[ 1 ] = mat * ( rectCoords[ 1 ] - P );\n\tcoords[ 2 ] = mat * ( rectCoords[ 2 ] - P );\n\tcoords[ 3 ] = mat * ( rectCoords[ 3 ] - P );\n\tcoords[ 0 ] = normalize( coords[ 0 ] );\n\tcoords[ 1 ] = normalize( coords[ 1 ] );\n\tcoords[ 2 ] = normalize( coords[ 2 ] );\n\tcoords[ 3 ] = normalize( coords[ 3 ] );\n\tvec3 vectorFormFactor = vec3( 0.0 );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 0 ], coords[ 1 ] );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 1 ], coords[ 2 ] );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 2 ], coords[ 3 ] );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 3 ], coords[ 0 ] );\n\tfloat result = LTC_ClippedSphereFormFactor( vectorFormFactor );\n\treturn vec3( result );\n}\n#if defined( USE_SHEEN )\nfloat D_Charlie( float roughness, float dotNH ) {\n\tfloat alpha = pow2( roughness );\n\tfloat invAlpha = 1.0 / alpha;\n\tfloat cos2h = dotNH * dotNH;\n\tfloat sin2h = max( 1.0 - cos2h, 0.0078125 );\n\treturn ( 2.0 + invAlpha ) * pow( sin2h, invAlpha * 0.5 ) / ( 2.0 * PI );\n}\nfloat V_Neubelt( float dotNV, float dotNL ) {\n\treturn saturate( 1.0 / ( 4.0 * ( dotNL + dotNV - dotNL * dotNV ) ) );\n}\nvec3 BRDF_Sheen( const in vec3 lightDir, const in vec3 viewDir, const in vec3 normal, vec3 sheenColor, const in float sheenRoughness ) {\n\tvec3 halfDir = normalize( lightDir + viewDir );\n\tfloat dotNL = saturate( dot( normal, lightDir ) );\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tfloat dotNH = saturate( dot( normal, halfDir ) );\n\tfloat D = D_Charlie( sheenRoughness, dotNH );\n\tfloat V = V_Neubelt( dotNV, dotNL );\n\treturn sheenColor * ( D * V );\n}\n#endif\nfloat IBLSheenBRDF( const in vec3 normal, const in vec3 viewDir, const in float roughness ) {\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tfloat r2 = roughness * roughness;\n\tfloat a = roughness < 0.25 ? -339.2 * r2 + 161.4 * roughness - 25.9 : -8.48 * r2 + 14.3 * roughness - 9.95;\n\tfloat b = roughness < 0.25 ? 44.0 * r2 - 23.7 * roughness + 3.26 : 1.97 * r2 - 3.27 * roughness + 0.72;\n\tfloat DG = exp( a * dotNV + b ) + ( roughness < 0.25 ? 0.0 : 0.1 * ( roughness - 0.25 ) );\n\treturn saturate( DG * RECIPROCAL_PI );\n}\nvec2 DFGApprox( const in vec3 normal, const in vec3 viewDir, const in float roughness ) {\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tconst vec4 c0 = vec4( - 1, - 0.0275, - 0.572, 0.022 );\n\tconst vec4 c1 = vec4( 1, 0.0425, 1.04, - 0.04 );\n\tvec4 r = roughness * c0 + c1;\n\tfloat a004 = min( r.x * r.x, exp2( - 9.28 * dotNV ) ) * r.x + r.y;\n\tvec2 fab = vec2( - 1.04, 1.04 ) * a004 + r.zw;\n\treturn fab;\n}\nvec3 EnvironmentBRDF( const in vec3 normal, const in vec3 viewDir, const in vec3 specularColor, const in float specularF90, const in float roughness ) {\n\tvec2 fab = DFGApprox( normal, viewDir, roughness );\n\treturn specularColor * fab.x + specularF90 * fab.y;\n}\n#ifdef USE_IRIDESCENCE\nvoid computeMultiscatteringIridescence( const in vec3 normal, const in vec3 viewDir, const in vec3 specularColor, const in float specularF90, const in float iridescence, const in vec3 iridescenceF0, const in float roughness, inout vec3 singleScatter, inout vec3 multiScatter ) {\n#else\nvoid computeMultiscattering( const in vec3 normal, const in vec3 viewDir, const in vec3 specularColor, const in float specularF90, const in float roughness, inout vec3 singleScatter, inout vec3 multiScatter ) {\n#endif\n\tvec2 fab = DFGApprox( normal, viewDir, roughness );\n\t#ifdef USE_IRIDESCENCE\n\t\tvec3 Fr = mix( specularColor, iridescenceF0, iridescence );\n\t#else\n\t\tvec3 Fr = specularColor;\n\t#endif\n\tvec3 FssEss = Fr * fab.x + specularF90 * fab.y;\n\tfloat Ess = fab.x + fab.y;\n\tfloat Ems = 1.0 - Ess;\n\tvec3 Favg = Fr + ( 1.0 - Fr ) * 0.047619;\tvec3 Fms = FssEss * Favg / ( 1.0 - Ems * Favg );\n\tsingleScatter += FssEss;\n\tmultiScatter += Fms * Ems;\n}\n#if NUM_RECT_AREA_LIGHTS > 0\n\tvoid RE_Direct_RectArea_Physical( const in RectAreaLight rectAreaLight, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {\n\t\tvec3 normal = geometryNormal;\n\t\tvec3 viewDir = geometryViewDir;\n\t\tvec3 position = geometryPosition;\n\t\tvec3 lightPos = rectAreaLight.position;\n\t\tvec3 halfWidth = rectAreaLight.halfWidth;\n\t\tvec3 halfHeight = rectAreaLight.halfHeight;\n\t\tvec3 lightColor = rectAreaLight.color;\n\t\tfloat roughness = material.roughness;\n\t\tvec3 rectCoords[ 4 ];\n\t\trectCoords[ 0 ] = lightPos + halfWidth - halfHeight;\t\trectCoords[ 1 ] = lightPos - halfWidth - halfHeight;\n\t\trectCoords[ 2 ] = lightPos - halfWidth + halfHeight;\n\t\trectCoords[ 3 ] = lightPos + halfWidth + halfHeight;\n\t\tvec2 uv = LTC_Uv( normal, viewDir, roughness );\n\t\tvec4 t1 = texture2D( ltc_1, uv );\n\t\tvec4 t2 = texture2D( ltc_2, uv );\n\t\tmat3 mInv = mat3(\n\t\t\tvec3( t1.x, 0, t1.y ),\n\t\t\tvec3( 0, 1, 0 ),\n\t\t\tvec3( t1.z, 0, t1.w )\n\t\t);\n\t\tvec3 fresnel = ( material.specularColor * t2.x + ( vec3( 1.0 ) - material.specularColor ) * t2.y );\n\t\treflectedLight.directSpecular += lightColor * fresnel * LTC_Evaluate( normal, viewDir, position, mInv, rectCoords );\n\t\treflectedLight.directDiffuse += lightColor * material.diffuseColor * LTC_Evaluate( normal, viewDir, position, mat3( 1.0 ), rectCoords );\n\t}\n#endif\nvoid RE_Direct_Physical( const in IncidentLight directLight, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {\n\tfloat dotNL = saturate( dot( geometryNormal, directLight.direction ) );\n\tvec3 irradiance = dotNL * directLight.color;\n\t#ifdef USE_CLEARCOAT\n\t\tfloat dotNLcc = saturate( dot( geometryClearcoatNormal, directLight.direction ) );\n\t\tvec3 ccIrradiance = dotNLcc * directLight.color;\n\t\tclearcoatSpecularDirect += ccIrradiance * BRDF_GGX_Clearcoat( directLight.direction, geometryViewDir, geometryClearcoatNormal, material );\n\t#endif\n\t#ifdef USE_SHEEN\n\t\tsheenSpecularDirect += irradiance * BRDF_Sheen( directLight.direction, geometryViewDir, geometryNormal, material.sheenColor, material.sheenRoughness );\n\t#endif\n\treflectedLight.directSpecular += irradiance * BRDF_GGX( directLight.direction, geometryViewDir, geometryNormal, material );\n\treflectedLight.directDiffuse += irradiance * BRDF_Lambert( material.diffuseColor );\n}\nvoid RE_IndirectDiffuse_Physical( const in vec3 irradiance, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {\n\treflectedLight.indirectDiffuse += irradiance * BRDF_Lambert( material.diffuseColor );\n}\nvoid RE_IndirectSpecular_Physical( const in vec3 radiance, const in vec3 irradiance, const in vec3 clearcoatRadiance, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight) {\n\t#ifdef USE_CLEARCOAT\n\t\tclearcoatSpecularIndirect += clearcoatRadiance * EnvironmentBRDF( geometryClearcoatNormal, geometryViewDir, material.clearcoatF0, material.clearcoatF90, material.clearcoatRoughness );\n\t#endif\n\t#ifdef USE_SHEEN\n\t\tsheenSpecularIndirect += irradiance * material.sheenColor * IBLSheenBRDF( geometryNormal, geometryViewDir, material.sheenRoughness );\n\t#endif\n\tvec3 singleScattering = vec3( 0.0 );\n\tvec3 multiScattering = vec3( 0.0 );\n\tvec3 cosineWeightedIrradiance = irradiance * RECIPROCAL_PI;\n\t#ifdef USE_IRIDESCENCE\n\t\tcomputeMultiscatteringIridescence( geometryNormal, geometryViewDir, material.specularColor, material.specularF90, material.iridescence, material.iridescenceFresnel, material.roughness, singleScattering, multiScattering );\n\t#else\n\t\tcomputeMultiscattering( geometryNormal, geometryViewDir, material.specularColor, material.specularF90, material.roughness, singleScattering, multiScattering );\n\t#endif\n\tvec3 totalScattering = singleScattering + multiScattering;\n\tvec3 diffuse = material.diffuseColor * ( 1.0 - max( max( totalScattering.r, totalScattering.g ), totalScattering.b ) );\n\treflectedLight.indirectSpecular += radiance * singleScattering;\n\treflectedLight.indirectSpecular += multiScattering * cosineWeightedIrradiance;\n\treflectedLight.indirectDiffuse += diffuse * cosineWeightedIrradiance;\n}\n#define RE_Direct\t\t\t\tRE_Direct_Physical\n#define RE_Direct_RectArea\t\tRE_Direct_RectArea_Physical\n#define RE_IndirectDiffuse\t\tRE_IndirectDiffuse_Physical\n#define RE_IndirectSpecular\t\tRE_IndirectSpecular_Physical\nfloat computeSpecularOcclusion( const in float dotNV, const in float ambientOcclusion, const in float roughness ) {\n\treturn saturate( pow( dotNV + ambientOcclusion, exp2( - 16.0 * roughness - 1.0 ) ) - 1.0 + ambientOcclusion );\n}";
13849
+ var lights_physical_pars_fragment = "struct PhysicalMaterial {\n\tvec3 diffuseColor;\n\tfloat roughness;\n\tvec3 specularColor;\n\tfloat specularF90;\n\tfloat dispersion;\n\t#ifdef USE_CLEARCOAT\n\t\tfloat clearcoat;\n\t\tfloat clearcoatRoughness;\n\t\tvec3 clearcoatF0;\n\t\tfloat clearcoatF90;\n\t#endif\n\t#ifdef USE_IRIDESCENCE\n\t\tfloat iridescence;\n\t\tfloat iridescenceIOR;\n\t\tfloat iridescenceThickness;\n\t\tvec3 iridescenceFresnel;\n\t\tvec3 iridescenceF0;\n\t#endif\n\t#ifdef USE_SHEEN\n\t\tvec3 sheenColor;\n\t\tfloat sheenRoughness;\n\t#endif\n\t#ifdef IOR\n\t\tfloat ior;\n\t#endif\n\t#ifdef USE_TRANSMISSION\n\t\tfloat transmission;\n\t\tfloat transmissionAlpha;\n\t\tfloat thickness;\n\t\tfloat attenuationDistance;\n\t\tvec3 attenuationColor;\n\t#endif\n\t#ifdef USE_ANISOTROPY\n\t\tfloat anisotropy;\n\t\tfloat alphaT;\n\t\tvec3 anisotropyT;\n\t\tvec3 anisotropyB;\n\t#endif\n};\nvec3 clearcoatSpecularDirect = vec3( 0.0 );\nvec3 clearcoatSpecularIndirect = vec3( 0.0 );\nvec3 sheenSpecularDirect = vec3( 0.0 );\nvec3 sheenSpecularIndirect = vec3(0.0 );\nvec3 Schlick_to_F0( const in vec3 f, const in float f90, const in float dotVH ) {\n float x = clamp( 1.0 - dotVH, 0.0, 1.0 );\n float x2 = x * x;\n float x5 = clamp( x * x2 * x2, 0.0, 0.9999 );\n return ( f - vec3( f90 ) * x5 ) / ( 1.0 - x5 );\n}\nfloat V_GGX_SmithCorrelated( const in float alpha, const in float dotNL, const in float dotNV ) {\n\tfloat a2 = pow2( alpha );\n\tfloat gv = dotNL * sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNV ) );\n\tfloat gl = dotNV * sqrt( a2 + ( 1.0 - a2 ) * pow2( dotNL ) );\n\treturn 0.5 / max( gv + gl, EPSILON );\n}\nfloat D_GGX( const in float alpha, const in float dotNH ) {\n\tfloat a2 = pow2( alpha );\n\tfloat denom = pow2( dotNH ) * ( a2 - 1.0 ) + 1.0;\n\treturn RECIPROCAL_PI * a2 / pow2( denom );\n}\n#ifdef USE_ANISOTROPY\n\tfloat V_GGX_SmithCorrelated_Anisotropic( const in float alphaT, const in float alphaB, const in float dotTV, const in float dotBV, const in float dotTL, const in float dotBL, const in float dotNV, const in float dotNL ) {\n\t\tfloat gv = dotNL * length( vec3( alphaT * dotTV, alphaB * dotBV, dotNV ) );\n\t\tfloat gl = dotNV * length( vec3( alphaT * dotTL, alphaB * dotBL, dotNL ) );\n\t\tfloat v = 0.5 / ( gv + gl );\n\t\treturn saturate(v);\n\t}\n\tfloat D_GGX_Anisotropic( const in float alphaT, const in float alphaB, const in float dotNH, const in float dotTH, const in float dotBH ) {\n\t\tfloat a2 = alphaT * alphaB;\n\t\thighp vec3 v = vec3( alphaB * dotTH, alphaT * dotBH, a2 * dotNH );\n\t\thighp float v2 = dot( v, v );\n\t\tfloat w2 = a2 / v2;\n\t\treturn RECIPROCAL_PI * a2 * pow2 ( w2 );\n\t}\n#endif\n#ifdef USE_CLEARCOAT\n\tvec3 BRDF_GGX_Clearcoat( const in vec3 lightDir, const in vec3 viewDir, const in vec3 normal, const in PhysicalMaterial material) {\n\t\tvec3 f0 = material.clearcoatF0;\n\t\tfloat f90 = material.clearcoatF90;\n\t\tfloat roughness = material.clearcoatRoughness;\n\t\tfloat alpha = pow2( roughness );\n\t\tvec3 halfDir = normalize( lightDir + viewDir );\n\t\tfloat dotNL = saturate( dot( normal, lightDir ) );\n\t\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\t\tfloat dotNH = saturate( dot( normal, halfDir ) );\n\t\tfloat dotVH = saturate( dot( viewDir, halfDir ) );\n\t\tvec3 F = F_Schlick( f0, f90, dotVH );\n\t\tfloat V = V_GGX_SmithCorrelated( alpha, dotNL, dotNV );\n\t\tfloat D = D_GGX( alpha, dotNH );\n\t\treturn F * ( V * D );\n\t}\n#endif\nvec3 BRDF_GGX( const in vec3 lightDir, const in vec3 viewDir, const in vec3 normal, const in PhysicalMaterial material ) {\n\tvec3 f0 = material.specularColor;\n\tfloat f90 = material.specularF90;\n\tfloat roughness = material.roughness;\n\tfloat alpha = pow2( roughness );\n\tvec3 halfDir = normalize( lightDir + viewDir );\n\tfloat dotNL = saturate( dot( normal, lightDir ) );\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tfloat dotNH = saturate( dot( normal, halfDir ) );\n\tfloat dotVH = saturate( dot( viewDir, halfDir ) );\n\tvec3 F = F_Schlick( f0, f90, dotVH );\n\t#ifdef USE_IRIDESCENCE\n\t\tF = mix( F, material.iridescenceFresnel, material.iridescence );\n\t#endif\n\t#ifdef USE_ANISOTROPY\n\t\tfloat dotTL = dot( material.anisotropyT, lightDir );\n\t\tfloat dotTV = dot( material.anisotropyT, viewDir );\n\t\tfloat dotTH = dot( material.anisotropyT, halfDir );\n\t\tfloat dotBL = dot( material.anisotropyB, lightDir );\n\t\tfloat dotBV = dot( material.anisotropyB, viewDir );\n\t\tfloat dotBH = dot( material.anisotropyB, halfDir );\n\t\tfloat V = V_GGX_SmithCorrelated_Anisotropic( material.alphaT, alpha, dotTV, dotBV, dotTL, dotBL, dotNV, dotNL );\n\t\tfloat D = D_GGX_Anisotropic( material.alphaT, alpha, dotNH, dotTH, dotBH );\n\t#else\n\t\tfloat V = V_GGX_SmithCorrelated( alpha, dotNL, dotNV );\n\t\tfloat D = D_GGX( alpha, dotNH );\n\t#endif\n\treturn F * ( V * D );\n}\nvec2 LTC_Uv( const in vec3 N, const in vec3 V, const in float roughness ) {\n\tconst float LUT_SIZE = 64.0;\n\tconst float LUT_SCALE = ( LUT_SIZE - 1.0 ) / LUT_SIZE;\n\tconst float LUT_BIAS = 0.5 / LUT_SIZE;\n\tfloat dotNV = saturate( dot( N, V ) );\n\tvec2 uv = vec2( roughness, sqrt( 1.0 - dotNV ) );\n\tuv = uv * LUT_SCALE + LUT_BIAS;\n\treturn uv;\n}\nfloat LTC_ClippedSphereFormFactor( const in vec3 f ) {\n\tfloat l = length( f );\n\treturn max( ( l * l + f.z ) / ( l + 1.0 ), 0.0 );\n}\nvec3 LTC_EdgeVectorFormFactor( const in vec3 v1, const in vec3 v2 ) {\n\tfloat x = dot( v1, v2 );\n\tfloat y = abs( x );\n\tfloat a = 0.8543985 + ( 0.4965155 + 0.0145206 * y ) * y;\n\tfloat b = 3.4175940 + ( 4.1616724 + y ) * y;\n\tfloat v = a / b;\n\tfloat theta_sintheta = ( x > 0.0 ) ? v : 0.5 * inversesqrt( max( 1.0 - x * x, 1e-7 ) ) - v;\n\treturn cross( v1, v2 ) * theta_sintheta;\n}\nvec3 LTC_Evaluate( const in vec3 N, const in vec3 V, const in vec3 P, const in mat3 mInv, const in vec3 rectCoords[ 4 ] ) {\n\tvec3 v1 = rectCoords[ 1 ] - rectCoords[ 0 ];\n\tvec3 v2 = rectCoords[ 3 ] - rectCoords[ 0 ];\n\tvec3 lightNormal = cross( v1, v2 );\n\tif( dot( lightNormal, P - rectCoords[ 0 ] ) < 0.0 ) return vec3( 0.0 );\n\tvec3 T1, T2;\n\tT1 = normalize( V - N * dot( V, N ) );\n\tT2 = - cross( N, T1 );\n\tmat3 mat = mInv * transposeMat3( mat3( T1, T2, N ) );\n\tvec3 coords[ 4 ];\n\tcoords[ 0 ] = mat * ( rectCoords[ 0 ] - P );\n\tcoords[ 1 ] = mat * ( rectCoords[ 1 ] - P );\n\tcoords[ 2 ] = mat * ( rectCoords[ 2 ] - P );\n\tcoords[ 3 ] = mat * ( rectCoords[ 3 ] - P );\n\tcoords[ 0 ] = normalize( coords[ 0 ] );\n\tcoords[ 1 ] = normalize( coords[ 1 ] );\n\tcoords[ 2 ] = normalize( coords[ 2 ] );\n\tcoords[ 3 ] = normalize( coords[ 3 ] );\n\tvec3 vectorFormFactor = vec3( 0.0 );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 0 ], coords[ 1 ] );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 1 ], coords[ 2 ] );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 2 ], coords[ 3 ] );\n\tvectorFormFactor += LTC_EdgeVectorFormFactor( coords[ 3 ], coords[ 0 ] );\n\tfloat result = LTC_ClippedSphereFormFactor( vectorFormFactor );\n\treturn vec3( result );\n}\n#if defined( USE_SHEEN )\nfloat D_Charlie( float roughness, float dotNH ) {\n\tfloat alpha = pow2( roughness );\n\tfloat invAlpha = 1.0 / alpha;\n\tfloat cos2h = dotNH * dotNH;\n\tfloat sin2h = max( 1.0 - cos2h, 0.0078125 );\n\treturn ( 2.0 + invAlpha ) * pow( sin2h, invAlpha * 0.5 ) / ( 2.0 * PI );\n}\nfloat V_Neubelt( float dotNV, float dotNL ) {\n\treturn saturate( 1.0 / ( 4.0 * ( dotNL + dotNV - dotNL * dotNV ) ) );\n}\nvec3 BRDF_Sheen( const in vec3 lightDir, const in vec3 viewDir, const in vec3 normal, vec3 sheenColor, const in float sheenRoughness ) {\n\tvec3 halfDir = normalize( lightDir + viewDir );\n\tfloat dotNL = saturate( dot( normal, lightDir ) );\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tfloat dotNH = saturate( dot( normal, halfDir ) );\n\tfloat D = D_Charlie( sheenRoughness, dotNH );\n\tfloat V = V_Neubelt( dotNV, dotNL );\n\treturn sheenColor * ( D * V );\n}\n#endif\nfloat IBLSheenBRDF( const in vec3 normal, const in vec3 viewDir, const in float roughness ) {\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tfloat r2 = roughness * roughness;\n\tfloat a = roughness < 0.25 ? -339.2 * r2 + 161.4 * roughness - 25.9 : -8.48 * r2 + 14.3 * roughness - 9.95;\n\tfloat b = roughness < 0.25 ? 44.0 * r2 - 23.7 * roughness + 3.26 : 1.97 * r2 - 3.27 * roughness + 0.72;\n\tfloat DG = exp( a * dotNV + b ) + ( roughness < 0.25 ? 0.0 : 0.1 * ( roughness - 0.25 ) );\n\treturn saturate( DG * RECIPROCAL_PI );\n}\nvec2 DFGApprox( const in vec3 normal, const in vec3 viewDir, const in float roughness ) {\n\tfloat dotNV = saturate( dot( normal, viewDir ) );\n\tconst vec4 c0 = vec4( - 1, - 0.0275, - 0.572, 0.022 );\n\tconst vec4 c1 = vec4( 1, 0.0425, 1.04, - 0.04 );\n\tvec4 r = roughness * c0 + c1;\n\tfloat a004 = min( r.x * r.x, exp2( - 9.28 * dotNV ) ) * r.x + r.y;\n\tvec2 fab = vec2( - 1.04, 1.04 ) * a004 + r.zw;\n\treturn fab;\n}\nvec3 EnvironmentBRDF( const in vec3 normal, const in vec3 viewDir, const in vec3 specularColor, const in float specularF90, const in float roughness ) {\n\tvec2 fab = DFGApprox( normal, viewDir, roughness );\n\treturn specularColor * fab.x + specularF90 * fab.y;\n}\n#ifdef USE_IRIDESCENCE\nvoid computeMultiscatteringIridescence( const in vec3 normal, const in vec3 viewDir, const in vec3 specularColor, const in float specularF90, const in float iridescence, const in vec3 iridescenceF0, const in float roughness, inout vec3 singleScatter, inout vec3 multiScatter ) {\n#else\nvoid computeMultiscattering( const in vec3 normal, const in vec3 viewDir, const in vec3 specularColor, const in float specularF90, const in float roughness, inout vec3 singleScatter, inout vec3 multiScatter ) {\n#endif\n\tvec2 fab = DFGApprox( normal, viewDir, roughness );\n\t#ifdef USE_IRIDESCENCE\n\t\tvec3 Fr = mix( specularColor, iridescenceF0, iridescence );\n\t#else\n\t\tvec3 Fr = specularColor;\n\t#endif\n\tvec3 FssEss = Fr * fab.x + specularF90 * fab.y;\n\tfloat Ess = fab.x + fab.y;\n\tfloat Ems = 1.0 - Ess;\n\tvec3 Favg = Fr + ( 1.0 - Fr ) * 0.047619;\tvec3 Fms = FssEss * Favg / ( 1.0 - Ems * Favg );\n\tsingleScatter += FssEss;\n\tmultiScatter += Fms * Ems;\n}\n#if NUM_RECT_AREA_LIGHTS > 0\n\tvoid RE_Direct_RectArea_Physical( const in RectAreaLight rectAreaLight, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {\n\t\tvec3 normal = geometryNormal;\n\t\tvec3 viewDir = geometryViewDir;\n\t\tvec3 position = geometryPosition;\n\t\tvec3 lightPos = rectAreaLight.position;\n\t\tvec3 halfWidth = rectAreaLight.halfWidth;\n\t\tvec3 halfHeight = rectAreaLight.halfHeight;\n\t\tvec3 lightColor = rectAreaLight.color;\n\t\tfloat roughness = material.roughness;\n\t\tvec3 rectCoords[ 4 ];\n\t\trectCoords[ 0 ] = lightPos + halfWidth - halfHeight;\t\trectCoords[ 1 ] = lightPos - halfWidth - halfHeight;\n\t\trectCoords[ 2 ] = lightPos - halfWidth + halfHeight;\n\t\trectCoords[ 3 ] = lightPos + halfWidth + halfHeight;\n\t\tvec2 uv = LTC_Uv( normal, viewDir, roughness );\n\t\tvec4 t1 = texture2D( ltc_1, uv );\n\t\tvec4 t2 = texture2D( ltc_2, uv );\n\t\tmat3 mInv = mat3(\n\t\t\tvec3( t1.x, 0, t1.y ),\n\t\t\tvec3( 0, 1, 0 ),\n\t\t\tvec3( t1.z, 0, t1.w )\n\t\t);\n\t\tvec3 fresnel = ( material.specularColor * t2.x + ( vec3( 1.0 ) - material.specularColor ) * t2.y );\n\t\treflectedLight.directSpecular += lightColor * fresnel * LTC_Evaluate( normal, viewDir, position, mInv, rectCoords );\n\t\treflectedLight.directDiffuse += lightColor * material.diffuseColor * LTC_Evaluate( normal, viewDir, position, mat3( 1.0 ), rectCoords );\n\t}\n#endif\nvoid RE_Direct_Physical( const in IncidentLight directLight, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {\n\tfloat dotNL = saturate( dot( geometryNormal, directLight.direction ) );\n\tvec3 irradiance = dotNL * directLight.color;\n\t#ifdef USE_CLEARCOAT\n\t\tfloat dotNLcc = saturate( dot( geometryClearcoatNormal, directLight.direction ) );\n\t\tvec3 ccIrradiance = dotNLcc * directLight.color;\n\t\tclearcoatSpecularDirect += ccIrradiance * BRDF_GGX_Clearcoat( directLight.direction, geometryViewDir, geometryClearcoatNormal, material );\n\t#endif\n\t#ifdef USE_SHEEN\n\t\tsheenSpecularDirect += irradiance * BRDF_Sheen( directLight.direction, geometryViewDir, geometryNormal, material.sheenColor, material.sheenRoughness );\n\t#endif\n\treflectedLight.directSpecular += irradiance * BRDF_GGX( directLight.direction, geometryViewDir, geometryNormal, material );\n\treflectedLight.directDiffuse += irradiance * BRDF_Lambert( material.diffuseColor );\n}\nvoid RE_IndirectDiffuse_Physical( const in vec3 irradiance, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight ) {\n\treflectedLight.indirectDiffuse += irradiance * BRDF_Lambert( material.diffuseColor );\n}\nvoid RE_IndirectSpecular_Physical( const in vec3 radiance, const in vec3 irradiance, const in vec3 clearcoatRadiance, const in vec3 geometryPosition, const in vec3 geometryNormal, const in vec3 geometryViewDir, const in vec3 geometryClearcoatNormal, const in PhysicalMaterial material, inout ReflectedLight reflectedLight) {\n\t#ifdef USE_CLEARCOAT\n\t\tclearcoatSpecularIndirect += clearcoatRadiance * EnvironmentBRDF( geometryClearcoatNormal, geometryViewDir, material.clearcoatF0, material.clearcoatF90, material.clearcoatRoughness );\n\t#endif\n\t#ifdef USE_SHEEN\n\t\tsheenSpecularIndirect += irradiance * material.sheenColor * IBLSheenBRDF( geometryNormal, geometryViewDir, material.sheenRoughness );\n\t#endif\n\tvec3 singleScattering = vec3( 0.0 );\n\tvec3 multiScattering = vec3( 0.0 );\n\tvec3 cosineWeightedIrradiance = irradiance * RECIPROCAL_PI;\n\t#ifdef USE_IRIDESCENCE\n\t\tcomputeMultiscatteringIridescence( geometryNormal, geometryViewDir, material.specularColor, material.specularF90, material.iridescence, material.iridescenceFresnel, material.roughness, singleScattering, multiScattering );\n\t#else\n\t\tcomputeMultiscattering( geometryNormal, geometryViewDir, material.specularColor, material.specularF90, material.roughness, singleScattering, multiScattering );\n\t#endif\n\tvec3 totalScattering = singleScattering + multiScattering;\n\tvec3 diffuse = material.diffuseColor * ( 1.0 - max( max( totalScattering.r, totalScattering.g ), totalScattering.b ) );\n\treflectedLight.indirectSpecular += radiance * singleScattering;\n\treflectedLight.indirectSpecular += multiScattering * cosineWeightedIrradiance;\n\treflectedLight.indirectDiffuse += diffuse * cosineWeightedIrradiance;\n}\n#define RE_Direct\t\t\t\tRE_Direct_Physical\n#define RE_Direct_RectArea\t\tRE_Direct_RectArea_Physical\n#define RE_IndirectDiffuse\t\tRE_IndirectDiffuse_Physical\n#define RE_IndirectSpecular\t\tRE_IndirectSpecular_Physical\nfloat computeSpecularOcclusion( const in float dotNV, const in float ambientOcclusion, const in float roughness ) {\n\treturn saturate( pow( dotNV + ambientOcclusion, exp2( - 16.0 * roughness - 1.0 ) ) - 1.0 + ambientOcclusion );\n}";
13842
13850
 
13843
13851
  var lights_fragment_begin = "\nvec3 geometryPosition = - vViewPosition;\nvec3 geometryNormal = normal;\nvec3 geometryViewDir = ( isOrthographic ) ? vec3( 0, 0, 1 ) : normalize( vViewPosition );\nvec3 geometryClearcoatNormal = vec3( 0.0 );\n#ifdef USE_CLEARCOAT\n\tgeometryClearcoatNormal = clearcoatNormal;\n#endif\n#ifdef USE_IRIDESCENCE\n\tfloat dotNVi = saturate( dot( normal, geometryViewDir ) );\n\tif ( material.iridescenceThickness == 0.0 ) {\n\t\tmaterial.iridescence = 0.0;\n\t} else {\n\t\tmaterial.iridescence = saturate( material.iridescence );\n\t}\n\tif ( material.iridescence > 0.0 ) {\n\t\tmaterial.iridescenceFresnel = evalIridescence( 1.0, material.iridescenceIOR, dotNVi, material.iridescenceThickness, material.specularColor );\n\t\tmaterial.iridescenceF0 = Schlick_to_F0( material.iridescenceFresnel, 1.0, dotNVi );\n\t}\n#endif\nIncidentLight directLight;\n#if ( NUM_POINT_LIGHTS > 0 ) && defined( RE_Direct )\n\tPointLight pointLight;\n\t#if defined( USE_SHADOWMAP ) && NUM_POINT_LIGHT_SHADOWS > 0\n\tPointLightShadow pointLightShadow;\n\t#endif\n\t#pragma unroll_loop_start\n\tfor ( int i = 0; i < NUM_POINT_LIGHTS; i ++ ) {\n\t\tpointLight = pointLights[ i ];\n\t\tgetPointLightInfo( pointLight, geometryPosition, directLight );\n\t\t#if defined( USE_SHADOWMAP ) && ( UNROLLED_LOOP_INDEX < NUM_POINT_LIGHT_SHADOWS )\n\t\tpointLightShadow = pointLightShadows[ i ];\n\t\tdirectLight.color *= ( directLight.visible && receiveShadow ) ? getPointShadow( pointShadowMap[ i ], pointLightShadow.shadowMapSize, pointLightShadow.shadowBias, pointLightShadow.shadowRadius, vPointShadowCoord[ i ], pointLightShadow.shadowCameraNear, pointLightShadow.shadowCameraFar ) : 1.0;\n\t\t#endif\n\t\tRE_Direct( directLight, geometryPosition, geometryNormal, geometryViewDir, geometryClearcoatNormal, material, reflectedLight );\n\t}\n\t#pragma unroll_loop_end\n#endif\n#if ( NUM_SPOT_LIGHTS > 0 ) && defined( RE_Direct )\n\tSpotLight spotLight;\n\tvec4 spotColor;\n\tvec3 spotLightCoord;\n\tbool inSpotLightMap;\n\t#if defined( USE_SHADOWMAP ) && NUM_SPOT_LIGHT_SHADOWS > 0\n\tSpotLightShadow spotLightShadow;\n\t#endif\n\t#pragma unroll_loop_start\n\tfor ( int i = 0; i < NUM_SPOT_LIGHTS; i ++ ) {\n\t\tspotLight = spotLights[ i ];\n\t\tgetSpotLightInfo( spotLight, geometryPosition, directLight );\n\t\t#if ( UNROLLED_LOOP_INDEX < NUM_SPOT_LIGHT_SHADOWS_WITH_MAPS )\n\t\t#define SPOT_LIGHT_MAP_INDEX UNROLLED_LOOP_INDEX\n\t\t#elif ( UNROLLED_LOOP_INDEX < NUM_SPOT_LIGHT_SHADOWS )\n\t\t#define SPOT_LIGHT_MAP_INDEX NUM_SPOT_LIGHT_MAPS\n\t\t#else\n\t\t#define SPOT_LIGHT_MAP_INDEX ( UNROLLED_LOOP_INDEX - NUM_SPOT_LIGHT_SHADOWS + NUM_SPOT_LIGHT_SHADOWS_WITH_MAPS )\n\t\t#endif\n\t\t#if ( SPOT_LIGHT_MAP_INDEX < NUM_SPOT_LIGHT_MAPS )\n\t\t\tspotLightCoord = vSpotLightCoord[ i ].xyz / vSpotLightCoord[ i ].w;\n\t\t\tinSpotLightMap = all( lessThan( abs( spotLightCoord * 2. - 1. ), vec3( 1.0 ) ) );\n\t\t\tspotColor = texture2D( spotLightMap[ SPOT_LIGHT_MAP_INDEX ], spotLightCoord.xy );\n\t\t\tdirectLight.color = inSpotLightMap ? directLight.color * spotColor.rgb : directLight.color;\n\t\t#endif\n\t\t#undef SPOT_LIGHT_MAP_INDEX\n\t\t#if defined( USE_SHADOWMAP ) && ( UNROLLED_LOOP_INDEX < NUM_SPOT_LIGHT_SHADOWS )\n\t\tspotLightShadow = spotLightShadows[ i ];\n\t\tdirectLight.color *= ( directLight.visible && receiveShadow ) ? getShadow( spotShadowMap[ i ], spotLightShadow.shadowMapSize, spotLightShadow.shadowBias, spotLightShadow.shadowRadius, vSpotLightCoord[ i ] ) : 1.0;\n\t\t#endif\n\t\tRE_Direct( directLight, geometryPosition, geometryNormal, geometryViewDir, geometryClearcoatNormal, material, reflectedLight );\n\t}\n\t#pragma unroll_loop_end\n#endif\n#if ( NUM_DIR_LIGHTS > 0 ) && defined( RE_Direct )\n\tDirectionalLight directionalLight;\n\t#if defined( USE_SHADOWMAP ) && NUM_DIR_LIGHT_SHADOWS > 0\n\tDirectionalLightShadow directionalLightShadow;\n\t#endif\n\t#pragma unroll_loop_start\n\tfor ( int i = 0; i < NUM_DIR_LIGHTS; i ++ ) {\n\t\tdirectionalLight = directionalLights[ i ];\n\t\tgetDirectionalLightInfo( directionalLight, directLight );\n\t\t#if defined( USE_SHADOWMAP ) && ( UNROLLED_LOOP_INDEX < NUM_DIR_LIGHT_SHADOWS )\n\t\tdirectionalLightShadow = directionalLightShadows[ i ];\n\t\tdirectLight.color *= ( directLight.visible && receiveShadow ) ? getShadow( directionalShadowMap[ i ], directionalLightShadow.shadowMapSize, directionalLightShadow.shadowBias, directionalLightShadow.shadowRadius, vDirectionalShadowCoord[ i ] ) : 1.0;\n\t\t#endif\n\t\tRE_Direct( directLight, geometryPosition, geometryNormal, geometryViewDir, geometryClearcoatNormal, material, reflectedLight );\n\t}\n\t#pragma unroll_loop_end\n#endif\n#if ( NUM_RECT_AREA_LIGHTS > 0 ) && defined( RE_Direct_RectArea )\n\tRectAreaLight rectAreaLight;\n\t#pragma unroll_loop_start\n\tfor ( int i = 0; i < NUM_RECT_AREA_LIGHTS; i ++ ) {\n\t\trectAreaLight = rectAreaLights[ i ];\n\t\tRE_Direct_RectArea( rectAreaLight, geometryPosition, geometryNormal, geometryViewDir, geometryClearcoatNormal, material, reflectedLight );\n\t}\n\t#pragma unroll_loop_end\n#endif\n#if defined( RE_IndirectDiffuse )\n\tvec3 iblIrradiance = vec3( 0.0 );\n\tvec3 irradiance = getAmbientLightIrradiance( ambientLightColor );\n\t#if defined( USE_LIGHT_PROBES )\n\t\tirradiance += getLightProbeIrradiance( lightProbe, geometryNormal );\n\t#endif\n\t#if ( NUM_HEMI_LIGHTS > 0 )\n\t\t#pragma unroll_loop_start\n\t\tfor ( int i = 0; i < NUM_HEMI_LIGHTS; i ++ ) {\n\t\t\tirradiance += getHemisphereLightIrradiance( hemisphereLights[ i ], geometryNormal );\n\t\t}\n\t\t#pragma unroll_loop_end\n\t#endif\n#endif\n#if defined( RE_IndirectSpecular )\n\tvec3 radiance = vec3( 0.0 );\n\tvec3 clearcoatRadiance = vec3( 0.0 );\n#endif";
13844
13852
 
@@ -13934,11 +13942,11 @@ var specularmap_pars_fragment = "#ifdef USE_SPECULARMAP\n\tuniform sampler2D spe
13934
13942
 
13935
13943
  var tonemapping_fragment = "#if defined( TONE_MAPPING )\n\tgl_FragColor.rgb = toneMapping( gl_FragColor.rgb );\n#endif";
13936
13944
 
13937
- var tonemapping_pars_fragment = "#ifndef saturate\n#define saturate( a ) clamp( a, 0.0, 1.0 )\n#endif\nuniform float toneMappingExposure;\nvec3 LinearToneMapping( vec3 color ) {\n\treturn saturate( toneMappingExposure * color );\n}\nvec3 ReinhardToneMapping( vec3 color ) {\n\tcolor *= toneMappingExposure;\n\treturn saturate( color / ( vec3( 1.0 ) + color ) );\n}\nvec3 OptimizedCineonToneMapping( vec3 color ) {\n\tcolor *= toneMappingExposure;\n\tcolor = max( vec3( 0.0 ), color - 0.004 );\n\treturn pow( ( color * ( 6.2 * color + 0.5 ) ) / ( color * ( 6.2 * color + 1.7 ) + 0.06 ), vec3( 2.2 ) );\n}\nvec3 RRTAndODTFit( vec3 v ) {\n\tvec3 a = v * ( v + 0.0245786 ) - 0.000090537;\n\tvec3 b = v * ( 0.983729 * v + 0.4329510 ) + 0.238081;\n\treturn a / b;\n}\nvec3 ACESFilmicToneMapping( vec3 color ) {\n\tconst mat3 ACESInputMat = mat3(\n\t\tvec3( 0.59719, 0.07600, 0.02840 ),\t\tvec3( 0.35458, 0.90834, 0.13383 ),\n\t\tvec3( 0.04823, 0.01566, 0.83777 )\n\t);\n\tconst mat3 ACESOutputMat = mat3(\n\t\tvec3( 1.60475, -0.10208, -0.00327 ),\t\tvec3( -0.53108, 1.10813, -0.07276 ),\n\t\tvec3( -0.07367, -0.00605, 1.07602 )\n\t);\n\tcolor *= toneMappingExposure / 0.6;\n\tcolor = ACESInputMat * color;\n\tcolor = RRTAndODTFit( color );\n\tcolor = ACESOutputMat * color;\n\treturn saturate( color );\n}\nconst mat3 LINEAR_REC2020_TO_LINEAR_SRGB = mat3(\n\tvec3( 1.6605, - 0.1246, - 0.0182 ),\n\tvec3( - 0.5876, 1.1329, - 0.1006 ),\n\tvec3( - 0.0728, - 0.0083, 1.1187 )\n);\nconst mat3 LINEAR_SRGB_TO_LINEAR_REC2020 = mat3(\n\tvec3( 0.6274, 0.0691, 0.0164 ),\n\tvec3( 0.3293, 0.9195, 0.0880 ),\n\tvec3( 0.0433, 0.0113, 0.8956 )\n);\nvec3 agxDefaultContrastApprox( vec3 x ) {\n\tvec3 x2 = x * x;\n\tvec3 x4 = x2 * x2;\n\treturn + 15.5 * x4 * x2\n\t\t- 40.14 * x4 * x\n\t\t+ 31.96 * x4\n\t\t- 6.868 * x2 * x\n\t\t+ 0.4298 * x2\n\t\t+ 0.1191 * x\n\t\t- 0.00232;\n}\nvec3 AgXToneMapping( vec3 color ) {\n\tconst mat3 AgXInsetMatrix = mat3(\n\t\tvec3( 0.856627153315983, 0.137318972929847, 0.11189821299995 ),\n\t\tvec3( 0.0951212405381588, 0.761241990602591, 0.0767994186031903 ),\n\t\tvec3( 0.0482516061458583, 0.101439036467562, 0.811302368396859 )\n\t);\n\tconst mat3 AgXOutsetMatrix = mat3(\n\t\tvec3( 1.1271005818144368, - 0.1413297634984383, - 0.14132976349843826 ),\n\t\tvec3( - 0.11060664309660323, 1.157823702216272, - 0.11060664309660294 ),\n\t\tvec3( - 0.016493938717834573, - 0.016493938717834257, 1.2519364065950405 )\n\t);\n\tconst float AgxMinEv = - 12.47393;\tconst float AgxMaxEv = 4.026069;\n\tcolor *= toneMappingExposure;\n\tcolor = LINEAR_SRGB_TO_LINEAR_REC2020 * color;\n\tcolor = AgXInsetMatrix * color;\n\tcolor = max( color, 1e-10 );\tcolor = log2( color );\n\tcolor = ( color - AgxMinEv ) / ( AgxMaxEv - AgxMinEv );\n\tcolor = clamp( color, 0.0, 1.0 );\n\tcolor = agxDefaultContrastApprox( color );\n\tcolor = AgXOutsetMatrix * color;\n\tcolor = pow( max( vec3( 0.0 ), color ), vec3( 2.2 ) );\n\tcolor = LINEAR_REC2020_TO_LINEAR_SRGB * color;\n\tcolor = clamp( color, 0.0, 1.0 );\n\treturn color;\n}\nvec3 NeutralToneMapping( vec3 color ) {\n\tfloat startCompression = 0.8 - 0.04;\n\tfloat desaturation = 0.15;\n\tcolor *= toneMappingExposure;\n\tfloat x = min(color.r, min(color.g, color.b));\n\tfloat offset = x < 0.08 ? x - 6.25 * x * x : 0.04;\n\tcolor -= offset;\n\tfloat peak = max(color.r, max(color.g, color.b));\n\tif (peak < startCompression) return color;\n\tfloat d = 1. - startCompression;\n\tfloat newPeak = 1. - d * d / (peak + d - startCompression);\n\tcolor *= newPeak / peak;\n\tfloat g = 1. - 1. / (desaturation * (peak - newPeak) + 1.);\n\treturn mix(color, newPeak * vec3(1, 1, 1), g);\n}\nvec3 CustomToneMapping( vec3 color ) { return color; }";
13945
+ var tonemapping_pars_fragment = "#ifndef saturate\n#define saturate( a ) clamp( a, 0.0, 1.0 )\n#endif\nuniform float toneMappingExposure;\nvec3 LinearToneMapping( vec3 color ) {\n\treturn saturate( toneMappingExposure * color );\n}\nvec3 ReinhardToneMapping( vec3 color ) {\n\tcolor *= toneMappingExposure;\n\treturn saturate( color / ( vec3( 1.0 ) + color ) );\n}\nvec3 OptimizedCineonToneMapping( vec3 color ) {\n\tcolor *= toneMappingExposure;\n\tcolor = max( vec3( 0.0 ), color - 0.004 );\n\treturn pow( ( color * ( 6.2 * color + 0.5 ) ) / ( color * ( 6.2 * color + 1.7 ) + 0.06 ), vec3( 2.2 ) );\n}\nvec3 RRTAndODTFit( vec3 v ) {\n\tvec3 a = v * ( v + 0.0245786 ) - 0.000090537;\n\tvec3 b = v * ( 0.983729 * v + 0.4329510 ) + 0.238081;\n\treturn a / b;\n}\nvec3 ACESFilmicToneMapping( vec3 color ) {\n\tconst mat3 ACESInputMat = mat3(\n\t\tvec3( 0.59719, 0.07600, 0.02840 ),\t\tvec3( 0.35458, 0.90834, 0.13383 ),\n\t\tvec3( 0.04823, 0.01566, 0.83777 )\n\t);\n\tconst mat3 ACESOutputMat = mat3(\n\t\tvec3( 1.60475, -0.10208, -0.00327 ),\t\tvec3( -0.53108, 1.10813, -0.07276 ),\n\t\tvec3( -0.07367, -0.00605, 1.07602 )\n\t);\n\tcolor *= toneMappingExposure / 0.6;\n\tcolor = ACESInputMat * color;\n\tcolor = RRTAndODTFit( color );\n\tcolor = ACESOutputMat * color;\n\treturn saturate( color );\n}\nconst mat3 LINEAR_REC2020_TO_LINEAR_SRGB = mat3(\n\tvec3( 1.6605, - 0.1246, - 0.0182 ),\n\tvec3( - 0.5876, 1.1329, - 0.1006 ),\n\tvec3( - 0.0728, - 0.0083, 1.1187 )\n);\nconst mat3 LINEAR_SRGB_TO_LINEAR_REC2020 = mat3(\n\tvec3( 0.6274, 0.0691, 0.0164 ),\n\tvec3( 0.3293, 0.9195, 0.0880 ),\n\tvec3( 0.0433, 0.0113, 0.8956 )\n);\nvec3 agxDefaultContrastApprox( vec3 x ) {\n\tvec3 x2 = x * x;\n\tvec3 x4 = x2 * x2;\n\treturn + 15.5 * x4 * x2\n\t\t- 40.14 * x4 * x\n\t\t+ 31.96 * x4\n\t\t- 6.868 * x2 * x\n\t\t+ 0.4298 * x2\n\t\t+ 0.1191 * x\n\t\t- 0.00232;\n}\nvec3 AgXToneMapping( vec3 color ) {\n\tconst mat3 AgXInsetMatrix = mat3(\n\t\tvec3( 0.856627153315983, 0.137318972929847, 0.11189821299995 ),\n\t\tvec3( 0.0951212405381588, 0.761241990602591, 0.0767994186031903 ),\n\t\tvec3( 0.0482516061458583, 0.101439036467562, 0.811302368396859 )\n\t);\n\tconst mat3 AgXOutsetMatrix = mat3(\n\t\tvec3( 1.1271005818144368, - 0.1413297634984383, - 0.14132976349843826 ),\n\t\tvec3( - 0.11060664309660323, 1.157823702216272, - 0.11060664309660294 ),\n\t\tvec3( - 0.016493938717834573, - 0.016493938717834257, 1.2519364065950405 )\n\t);\n\tconst float AgxMinEv = - 12.47393;\tconst float AgxMaxEv = 4.026069;\n\tcolor *= toneMappingExposure;\n\tcolor = LINEAR_SRGB_TO_LINEAR_REC2020 * color;\n\tcolor = AgXInsetMatrix * color;\n\tcolor = max( color, 1e-10 );\tcolor = log2( color );\n\tcolor = ( color - AgxMinEv ) / ( AgxMaxEv - AgxMinEv );\n\tcolor = clamp( color, 0.0, 1.0 );\n\tcolor = agxDefaultContrastApprox( color );\n\tcolor = AgXOutsetMatrix * color;\n\tcolor = pow( max( vec3( 0.0 ), color ), vec3( 2.2 ) );\n\tcolor = LINEAR_REC2020_TO_LINEAR_SRGB * color;\n\tcolor = clamp( color, 0.0, 1.0 );\n\treturn color;\n}\nvec3 NeutralToneMapping( vec3 color ) {\n\tconst float StartCompression = 0.8 - 0.04;\n\tconst float Desaturation = 0.15;\n\tcolor *= toneMappingExposure;\n\tfloat x = min( color.r, min( color.g, color.b ) );\n\tfloat offset = x < 0.08 ? x - 6.25 * x * x : 0.04;\n\tcolor -= offset;\n\tfloat peak = max( color.r, max( color.g, color.b ) );\n\tif ( peak < StartCompression ) return color;\n\tfloat d = 1. - StartCompression;\n\tfloat newPeak = 1. - d * d / ( peak + d - StartCompression );\n\tcolor *= newPeak / peak;\n\tfloat g = 1. - 1. / ( Desaturation * ( peak - newPeak ) + 1. );\n\treturn mix( color, vec3( newPeak ), g );\n}\nvec3 CustomToneMapping( vec3 color ) { return color; }";
13938
13946
 
13939
- var transmission_fragment = "#ifdef USE_TRANSMISSION\n\tmaterial.transmission = transmission;\n\tmaterial.transmissionAlpha = 1.0;\n\tmaterial.thickness = thickness;\n\tmaterial.attenuationDistance = attenuationDistance;\n\tmaterial.attenuationColor = attenuationColor;\n\t#ifdef USE_TRANSMISSIONMAP\n\t\tmaterial.transmission *= texture2D( transmissionMap, vTransmissionMapUv ).r;\n\t#endif\n\t#ifdef USE_THICKNESSMAP\n\t\tmaterial.thickness *= texture2D( thicknessMap, vThicknessMapUv ).g;\n\t#endif\n\tvec3 pos = vWorldPosition;\n\tvec3 v = normalize( cameraPosition - pos );\n\tvec3 n = inverseTransformDirection( normal, viewMatrix );\n\tvec4 transmitted = getIBLVolumeRefraction(\n\t\tn, v, material.roughness, material.diffuseColor, material.specularColor, material.specularF90,\n\t\tpos, modelMatrix, viewMatrix, projectionMatrix, material.ior, material.thickness,\n\t\tmaterial.attenuationColor, material.attenuationDistance );\n\tmaterial.transmissionAlpha = mix( material.transmissionAlpha, transmitted.a, material.transmission );\n\ttotalDiffuse = mix( totalDiffuse, transmitted.rgb, material.transmission );\n#endif";
13947
+ var transmission_fragment = "#ifdef USE_TRANSMISSION\n\tmaterial.transmission = transmission;\n\tmaterial.transmissionAlpha = 1.0;\n\tmaterial.thickness = thickness;\n\tmaterial.attenuationDistance = attenuationDistance;\n\tmaterial.attenuationColor = attenuationColor;\n\t#ifdef USE_TRANSMISSIONMAP\n\t\tmaterial.transmission *= texture2D( transmissionMap, vTransmissionMapUv ).r;\n\t#endif\n\t#ifdef USE_THICKNESSMAP\n\t\tmaterial.thickness *= texture2D( thicknessMap, vThicknessMapUv ).g;\n\t#endif\n\tvec3 pos = vWorldPosition;\n\tvec3 v = normalize( cameraPosition - pos );\n\tvec3 n = inverseTransformDirection( normal, viewMatrix );\n\tvec4 transmitted = getIBLVolumeRefraction(\n\t\tn, v, material.roughness, material.diffuseColor, material.specularColor, material.specularF90,\n\t\tpos, modelMatrix, viewMatrix, projectionMatrix, material.dispersion, material.ior, material.thickness,\n\t\tmaterial.attenuationColor, material.attenuationDistance );\n\tmaterial.transmissionAlpha = mix( material.transmissionAlpha, transmitted.a, material.transmission );\n\ttotalDiffuse = mix( totalDiffuse, transmitted.rgb, material.transmission );\n#endif";
13940
13948
 
13941
- var transmission_pars_fragment = "#ifdef USE_TRANSMISSION\n\tuniform float transmission;\n\tuniform float thickness;\n\tuniform float attenuationDistance;\n\tuniform vec3 attenuationColor;\n\t#ifdef USE_TRANSMISSIONMAP\n\t\tuniform sampler2D transmissionMap;\n\t#endif\n\t#ifdef USE_THICKNESSMAP\n\t\tuniform sampler2D thicknessMap;\n\t#endif\n\tuniform vec2 transmissionSamplerSize;\n\tuniform sampler2D transmissionSamplerMap;\n\tuniform mat4 modelMatrix;\n\tuniform mat4 projectionMatrix;\n\tvarying vec3 vWorldPosition;\n\tfloat w0( float a ) {\n\t\treturn ( 1.0 / 6.0 ) * ( a * ( a * ( - a + 3.0 ) - 3.0 ) + 1.0 );\n\t}\n\tfloat w1( float a ) {\n\t\treturn ( 1.0 / 6.0 ) * ( a * a * ( 3.0 * a - 6.0 ) + 4.0 );\n\t}\n\tfloat w2( float a ){\n\t\treturn ( 1.0 / 6.0 ) * ( a * ( a * ( - 3.0 * a + 3.0 ) + 3.0 ) + 1.0 );\n\t}\n\tfloat w3( float a ) {\n\t\treturn ( 1.0 / 6.0 ) * ( a * a * a );\n\t}\n\tfloat g0( float a ) {\n\t\treturn w0( a ) + w1( a );\n\t}\n\tfloat g1( float a ) {\n\t\treturn w2( a ) + w3( a );\n\t}\n\tfloat h0( float a ) {\n\t\treturn - 1.0 + w1( a ) / ( w0( a ) + w1( a ) );\n\t}\n\tfloat h1( float a ) {\n\t\treturn 1.0 + w3( a ) / ( w2( a ) + w3( a ) );\n\t}\n\tvec4 bicubic( sampler2D tex, vec2 uv, vec4 texelSize, float lod ) {\n\t\tuv = uv * texelSize.zw + 0.5;\n\t\tvec2 iuv = floor( uv );\n\t\tvec2 fuv = fract( uv );\n\t\tfloat g0x = g0( fuv.x );\n\t\tfloat g1x = g1( fuv.x );\n\t\tfloat h0x = h0( fuv.x );\n\t\tfloat h1x = h1( fuv.x );\n\t\tfloat h0y = h0( fuv.y );\n\t\tfloat h1y = h1( fuv.y );\n\t\tvec2 p0 = ( vec2( iuv.x + h0x, iuv.y + h0y ) - 0.5 ) * texelSize.xy;\n\t\tvec2 p1 = ( vec2( iuv.x + h1x, iuv.y + h0y ) - 0.5 ) * texelSize.xy;\n\t\tvec2 p2 = ( vec2( iuv.x + h0x, iuv.y + h1y ) - 0.5 ) * texelSize.xy;\n\t\tvec2 p3 = ( vec2( iuv.x + h1x, iuv.y + h1y ) - 0.5 ) * texelSize.xy;\n\t\treturn g0( fuv.y ) * ( g0x * textureLod( tex, p0, lod ) + g1x * textureLod( tex, p1, lod ) ) +\n\t\t\tg1( fuv.y ) * ( g0x * textureLod( tex, p2, lod ) + g1x * textureLod( tex, p3, lod ) );\n\t}\n\tvec4 textureBicubic( sampler2D sampler, vec2 uv, float lod ) {\n\t\tvec2 fLodSize = vec2( textureSize( sampler, int( lod ) ) );\n\t\tvec2 cLodSize = vec2( textureSize( sampler, int( lod + 1.0 ) ) );\n\t\tvec2 fLodSizeInv = 1.0 / fLodSize;\n\t\tvec2 cLodSizeInv = 1.0 / cLodSize;\n\t\tvec4 fSample = bicubic( sampler, uv, vec4( fLodSizeInv, fLodSize ), floor( lod ) );\n\t\tvec4 cSample = bicubic( sampler, uv, vec4( cLodSizeInv, cLodSize ), ceil( lod ) );\n\t\treturn mix( fSample, cSample, fract( lod ) );\n\t}\n\tvec3 getVolumeTransmissionRay( const in vec3 n, const in vec3 v, const in float thickness, const in float ior, const in mat4 modelMatrix ) {\n\t\tvec3 refractionVector = refract( - v, normalize( n ), 1.0 / ior );\n\t\tvec3 modelScale;\n\t\tmodelScale.x = length( vec3( modelMatrix[ 0 ].xyz ) );\n\t\tmodelScale.y = length( vec3( modelMatrix[ 1 ].xyz ) );\n\t\tmodelScale.z = length( vec3( modelMatrix[ 2 ].xyz ) );\n\t\treturn normalize( refractionVector ) * thickness * modelScale;\n\t}\n\tfloat applyIorToRoughness( const in float roughness, const in float ior ) {\n\t\treturn roughness * clamp( ior * 2.0 - 2.0, 0.0, 1.0 );\n\t}\n\tvec4 getTransmissionSample( const in vec2 fragCoord, const in float roughness, const in float ior ) {\n\t\tfloat lod = log2( transmissionSamplerSize.x ) * applyIorToRoughness( roughness, ior );\n\t\treturn textureBicubic( transmissionSamplerMap, fragCoord.xy, lod );\n\t}\n\tvec3 volumeAttenuation( const in float transmissionDistance, const in vec3 attenuationColor, const in float attenuationDistance ) {\n\t\tif ( isinf( attenuationDistance ) ) {\n\t\t\treturn vec3( 1.0 );\n\t\t} else {\n\t\t\tvec3 attenuationCoefficient = -log( attenuationColor ) / attenuationDistance;\n\t\t\tvec3 transmittance = exp( - attenuationCoefficient * transmissionDistance );\t\t\treturn transmittance;\n\t\t}\n\t}\n\tvec4 getIBLVolumeRefraction( const in vec3 n, const in vec3 v, const in float roughness, const in vec3 diffuseColor,\n\t\tconst in vec3 specularColor, const in float specularF90, const in vec3 position, const in mat4 modelMatrix,\n\t\tconst in mat4 viewMatrix, const in mat4 projMatrix, const in float ior, const in float thickness,\n\t\tconst in vec3 attenuationColor, const in float attenuationDistance ) {\n\t\tvec3 transmissionRay = getVolumeTransmissionRay( n, v, thickness, ior, modelMatrix );\n\t\tvec3 refractedRayExit = position + transmissionRay;\n\t\tvec4 ndcPos = projMatrix * viewMatrix * vec4( refractedRayExit, 1.0 );\n\t\tvec2 refractionCoords = ndcPos.xy / ndcPos.w;\n\t\trefractionCoords += 1.0;\n\t\trefractionCoords /= 2.0;\n\t\tvec4 transmittedLight = getTransmissionSample( refractionCoords, roughness, ior );\n\t\tvec3 transmittance = diffuseColor * volumeAttenuation( length( transmissionRay ), attenuationColor, attenuationDistance );\n\t\tvec3 attenuatedColor = transmittance * transmittedLight.rgb;\n\t\tvec3 F = EnvironmentBRDF( n, v, specularColor, specularF90, roughness );\n\t\tfloat transmittanceFactor = ( transmittance.r + transmittance.g + transmittance.b ) / 3.0;\n\t\treturn vec4( ( 1.0 - F ) * attenuatedColor, 1.0 - ( 1.0 - transmittedLight.a ) * transmittanceFactor );\n\t}\n#endif";
13949
+ var transmission_pars_fragment = "#ifdef USE_TRANSMISSION\n\tuniform float transmission;\n\tuniform float thickness;\n\tuniform float attenuationDistance;\n\tuniform vec3 attenuationColor;\n\t#ifdef USE_TRANSMISSIONMAP\n\t\tuniform sampler2D transmissionMap;\n\t#endif\n\t#ifdef USE_THICKNESSMAP\n\t\tuniform sampler2D thicknessMap;\n\t#endif\n\tuniform vec2 transmissionSamplerSize;\n\tuniform sampler2D transmissionSamplerMap;\n\tuniform mat4 modelMatrix;\n\tuniform mat4 projectionMatrix;\n\tvarying vec3 vWorldPosition;\n\tfloat w0( float a ) {\n\t\treturn ( 1.0 / 6.0 ) * ( a * ( a * ( - a + 3.0 ) - 3.0 ) + 1.0 );\n\t}\n\tfloat w1( float a ) {\n\t\treturn ( 1.0 / 6.0 ) * ( a * a * ( 3.0 * a - 6.0 ) + 4.0 );\n\t}\n\tfloat w2( float a ){\n\t\treturn ( 1.0 / 6.0 ) * ( a * ( a * ( - 3.0 * a + 3.0 ) + 3.0 ) + 1.0 );\n\t}\n\tfloat w3( float a ) {\n\t\treturn ( 1.0 / 6.0 ) * ( a * a * a );\n\t}\n\tfloat g0( float a ) {\n\t\treturn w0( a ) + w1( a );\n\t}\n\tfloat g1( float a ) {\n\t\treturn w2( a ) + w3( a );\n\t}\n\tfloat h0( float a ) {\n\t\treturn - 1.0 + w1( a ) / ( w0( a ) + w1( a ) );\n\t}\n\tfloat h1( float a ) {\n\t\treturn 1.0 + w3( a ) / ( w2( a ) + w3( a ) );\n\t}\n\tvec4 bicubic( sampler2D tex, vec2 uv, vec4 texelSize, float lod ) {\n\t\tuv = uv * texelSize.zw + 0.5;\n\t\tvec2 iuv = floor( uv );\n\t\tvec2 fuv = fract( uv );\n\t\tfloat g0x = g0( fuv.x );\n\t\tfloat g1x = g1( fuv.x );\n\t\tfloat h0x = h0( fuv.x );\n\t\tfloat h1x = h1( fuv.x );\n\t\tfloat h0y = h0( fuv.y );\n\t\tfloat h1y = h1( fuv.y );\n\t\tvec2 p0 = ( vec2( iuv.x + h0x, iuv.y + h0y ) - 0.5 ) * texelSize.xy;\n\t\tvec2 p1 = ( vec2( iuv.x + h1x, iuv.y + h0y ) - 0.5 ) * texelSize.xy;\n\t\tvec2 p2 = ( vec2( iuv.x + h0x, iuv.y + h1y ) - 0.5 ) * texelSize.xy;\n\t\tvec2 p3 = ( vec2( iuv.x + h1x, iuv.y + h1y ) - 0.5 ) * texelSize.xy;\n\t\treturn g0( fuv.y ) * ( g0x * textureLod( tex, p0, lod ) + g1x * textureLod( tex, p1, lod ) ) +\n\t\t\tg1( fuv.y ) * ( g0x * textureLod( tex, p2, lod ) + g1x * textureLod( tex, p3, lod ) );\n\t}\n\tvec4 textureBicubic( sampler2D sampler, vec2 uv, float lod ) {\n\t\tvec2 fLodSize = vec2( textureSize( sampler, int( lod ) ) );\n\t\tvec2 cLodSize = vec2( textureSize( sampler, int( lod + 1.0 ) ) );\n\t\tvec2 fLodSizeInv = 1.0 / fLodSize;\n\t\tvec2 cLodSizeInv = 1.0 / cLodSize;\n\t\tvec4 fSample = bicubic( sampler, uv, vec4( fLodSizeInv, fLodSize ), floor( lod ) );\n\t\tvec4 cSample = bicubic( sampler, uv, vec4( cLodSizeInv, cLodSize ), ceil( lod ) );\n\t\treturn mix( fSample, cSample, fract( lod ) );\n\t}\n\tvec3 getVolumeTransmissionRay( const in vec3 n, const in vec3 v, const in float thickness, const in float ior, const in mat4 modelMatrix ) {\n\t\tvec3 refractionVector = refract( - v, normalize( n ), 1.0 / ior );\n\t\tvec3 modelScale;\n\t\tmodelScale.x = length( vec3( modelMatrix[ 0 ].xyz ) );\n\t\tmodelScale.y = length( vec3( modelMatrix[ 1 ].xyz ) );\n\t\tmodelScale.z = length( vec3( modelMatrix[ 2 ].xyz ) );\n\t\treturn normalize( refractionVector ) * thickness * modelScale;\n\t}\n\tfloat applyIorToRoughness( const in float roughness, const in float ior ) {\n\t\treturn roughness * clamp( ior * 2.0 - 2.0, 0.0, 1.0 );\n\t}\n\tvec4 getTransmissionSample( const in vec2 fragCoord, const in float roughness, const in float ior ) {\n\t\tfloat lod = log2( transmissionSamplerSize.x ) * applyIorToRoughness( roughness, ior );\n\t\treturn textureBicubic( transmissionSamplerMap, fragCoord.xy, lod );\n\t}\n\tvec3 volumeAttenuation( const in float transmissionDistance, const in vec3 attenuationColor, const in float attenuationDistance ) {\n\t\tif ( isinf( attenuationDistance ) ) {\n\t\t\treturn vec3( 1.0 );\n\t\t} else {\n\t\t\tvec3 attenuationCoefficient = -log( attenuationColor ) / attenuationDistance;\n\t\t\tvec3 transmittance = exp( - attenuationCoefficient * transmissionDistance );\t\t\treturn transmittance;\n\t\t}\n\t}\n\tvec4 getIBLVolumeRefraction( const in vec3 n, const in vec3 v, const in float roughness, const in vec3 diffuseColor,\n\t\tconst in vec3 specularColor, const in float specularF90, const in vec3 position, const in mat4 modelMatrix,\n\t\tconst in mat4 viewMatrix, const in mat4 projMatrix, const in float dispersion, const in float ior, const in float thickness,\n\t\tconst in vec3 attenuationColor, const in float attenuationDistance ) {\n\t\tvec4 transmittedLight;\n\t\tvec3 transmittance;\n\t\t#ifdef USE_DISPERSION\n\t\t\tfloat halfSpread = ( ior - 1.0 ) * 0.025 * dispersion;\n\t\t\tvec3 iors = vec3( ior - halfSpread, ior, ior + halfSpread );\n\t\t\tfor ( int i = 0; i < 3; i ++ ) {\n\t\t\t\tvec3 transmissionRay = getVolumeTransmissionRay( n, v, thickness, iors[ i ], modelMatrix );\n\t\t\t\tvec3 refractedRayExit = position + transmissionRay;\n\t\t\n\t\t\t\tvec4 ndcPos = projMatrix * viewMatrix * vec4( refractedRayExit, 1.0 );\n\t\t\t\tvec2 refractionCoords = ndcPos.xy / ndcPos.w;\n\t\t\t\trefractionCoords += 1.0;\n\t\t\t\trefractionCoords /= 2.0;\n\t\t\n\t\t\t\tvec4 transmissionSample = getTransmissionSample( refractionCoords, roughness, iors[ i ] );\n\t\t\t\ttransmittedLight[ i ] = transmissionSample[ i ];\n\t\t\t\ttransmittedLight.a += transmissionSample.a;\n\t\t\t\ttransmittance[ i ] = diffuseColor[ i ] * volumeAttenuation( length( transmissionRay ), attenuationColor, attenuationDistance )[ i ];\n\t\t\t}\n\t\t\ttransmittedLight.a /= 3.0;\n\t\t\n\t\t#else\n\t\t\n\t\t\tvec3 transmissionRay = getVolumeTransmissionRay( n, v, thickness, ior, modelMatrix );\n\t\t\tvec3 refractedRayExit = position + transmissionRay;\n\t\t\tvec4 ndcPos = projMatrix * viewMatrix * vec4( refractedRayExit, 1.0 );\n\t\t\tvec2 refractionCoords = ndcPos.xy / ndcPos.w;\n\t\t\trefractionCoords += 1.0;\n\t\t\trefractionCoords /= 2.0;\n\t\t\ttransmittedLight = getTransmissionSample( refractionCoords, roughness, ior );\n\t\t\ttransmittance = diffuseColor * volumeAttenuation( length( transmissionRay ), attenuationColor, attenuationDistance );\n\t\t\n\t\t#endif\n\t\tvec3 attenuatedColor = transmittance * transmittedLight.rgb;\n\t\tvec3 F = EnvironmentBRDF( n, v, specularColor, specularF90, roughness );\n\t\tfloat transmittanceFactor = ( transmittance.r + transmittance.g + transmittance.b ) / 3.0;\n\t\treturn vec4( ( 1.0 - F ) * attenuatedColor, 1.0 - ( 1.0 - transmittedLight.a ) * transmittanceFactor );\n\t}\n#endif";
13942
13950
 
13943
13951
  var uv_pars_fragment = "#if defined( USE_UV ) || defined( USE_ANISOTROPY )\n\tvarying vec2 vUv;\n#endif\n#ifdef USE_MAP\n\tvarying vec2 vMapUv;\n#endif\n#ifdef USE_ALPHAMAP\n\tvarying vec2 vAlphaMapUv;\n#endif\n#ifdef USE_LIGHTMAP\n\tvarying vec2 vLightMapUv;\n#endif\n#ifdef USE_AOMAP\n\tvarying vec2 vAoMapUv;\n#endif\n#ifdef USE_BUMPMAP\n\tvarying vec2 vBumpMapUv;\n#endif\n#ifdef USE_NORMALMAP\n\tvarying vec2 vNormalMapUv;\n#endif\n#ifdef USE_EMISSIVEMAP\n\tvarying vec2 vEmissiveMapUv;\n#endif\n#ifdef USE_METALNESSMAP\n\tvarying vec2 vMetalnessMapUv;\n#endif\n#ifdef USE_ROUGHNESSMAP\n\tvarying vec2 vRoughnessMapUv;\n#endif\n#ifdef USE_ANISOTROPYMAP\n\tvarying vec2 vAnisotropyMapUv;\n#endif\n#ifdef USE_CLEARCOATMAP\n\tvarying vec2 vClearcoatMapUv;\n#endif\n#ifdef USE_CLEARCOAT_NORMALMAP\n\tvarying vec2 vClearcoatNormalMapUv;\n#endif\n#ifdef USE_CLEARCOAT_ROUGHNESSMAP\n\tvarying vec2 vClearcoatRoughnessMapUv;\n#endif\n#ifdef USE_IRIDESCENCEMAP\n\tvarying vec2 vIridescenceMapUv;\n#endif\n#ifdef USE_IRIDESCENCE_THICKNESSMAP\n\tvarying vec2 vIridescenceThicknessMapUv;\n#endif\n#ifdef USE_SHEEN_COLORMAP\n\tvarying vec2 vSheenColorMapUv;\n#endif\n#ifdef USE_SHEEN_ROUGHNESSMAP\n\tvarying vec2 vSheenRoughnessMapUv;\n#endif\n#ifdef USE_SPECULARMAP\n\tvarying vec2 vSpecularMapUv;\n#endif\n#ifdef USE_SPECULAR_COLORMAP\n\tvarying vec2 vSpecularColorMapUv;\n#endif\n#ifdef USE_SPECULAR_INTENSITYMAP\n\tvarying vec2 vSpecularIntensityMapUv;\n#endif\n#ifdef USE_TRANSMISSIONMAP\n\tuniform mat3 transmissionMapTransform;\n\tvarying vec2 vTransmissionMapUv;\n#endif\n#ifdef USE_THICKNESSMAP\n\tuniform mat3 thicknessMapTransform;\n\tvarying vec2 vThicknessMapUv;\n#endif";
13944
13952
 
@@ -13998,7 +14006,7 @@ const fragment$6 = "#define PHONG\nuniform vec3 diffuse;\nuniform vec3 emissive;
13998
14006
 
13999
14007
  const vertex$5 = "#define STANDARD\nvarying vec3 vViewPosition;\n#ifdef USE_TRANSMISSION\n\tvarying vec3 vWorldPosition;\n#endif\n#include <common>\n#include <batching_pars_vertex>\n#include <uv_pars_vertex>\n#include <displacementmap_pars_vertex>\n#include <color_pars_vertex>\n#include <fog_pars_vertex>\n#include <normal_pars_vertex>\n#include <morphtarget_pars_vertex>\n#include <skinning_pars_vertex>\n#include <shadowmap_pars_vertex>\n#include <logdepthbuf_pars_vertex>\n#include <clipping_planes_pars_vertex>\nvoid main() {\n\t#include <uv_vertex>\n\t#include <color_vertex>\n\t#include <morphinstance_vertex>\n\t#include <morphcolor_vertex>\n\t#include <batching_vertex>\n\t#include <beginnormal_vertex>\n\t#include <morphnormal_vertex>\n\t#include <skinbase_vertex>\n\t#include <skinnormal_vertex>\n\t#include <defaultnormal_vertex>\n\t#include <normal_vertex>\n\t#include <begin_vertex>\n\t#include <morphtarget_vertex>\n\t#include <skinning_vertex>\n\t#include <displacementmap_vertex>\n\t#include <project_vertex>\n\t#include <logdepthbuf_vertex>\n\t#include <clipping_planes_vertex>\n\tvViewPosition = - mvPosition.xyz;\n\t#include <worldpos_vertex>\n\t#include <shadowmap_vertex>\n\t#include <fog_vertex>\n#ifdef USE_TRANSMISSION\n\tvWorldPosition = worldPosition.xyz;\n#endif\n}";
14000
14008
 
14001
- const fragment$5 = "#define STANDARD\n#ifdef PHYSICAL\n\t#define IOR\n\t#define USE_SPECULAR\n#endif\nuniform vec3 diffuse;\nuniform vec3 emissive;\nuniform float roughness;\nuniform float metalness;\nuniform float opacity;\n#ifdef IOR\n\tuniform float ior;\n#endif\n#ifdef USE_SPECULAR\n\tuniform float specularIntensity;\n\tuniform vec3 specularColor;\n\t#ifdef USE_SPECULAR_COLORMAP\n\t\tuniform sampler2D specularColorMap;\n\t#endif\n\t#ifdef USE_SPECULAR_INTENSITYMAP\n\t\tuniform sampler2D specularIntensityMap;\n\t#endif\n#endif\n#ifdef USE_CLEARCOAT\n\tuniform float clearcoat;\n\tuniform float clearcoatRoughness;\n#endif\n#ifdef USE_IRIDESCENCE\n\tuniform float iridescence;\n\tuniform float iridescenceIOR;\n\tuniform float iridescenceThicknessMinimum;\n\tuniform float iridescenceThicknessMaximum;\n#endif\n#ifdef USE_SHEEN\n\tuniform vec3 sheenColor;\n\tuniform float sheenRoughness;\n\t#ifdef USE_SHEEN_COLORMAP\n\t\tuniform sampler2D sheenColorMap;\n\t#endif\n\t#ifdef USE_SHEEN_ROUGHNESSMAP\n\t\tuniform sampler2D sheenRoughnessMap;\n\t#endif\n#endif\n#ifdef USE_ANISOTROPY\n\tuniform vec2 anisotropyVector;\n\t#ifdef USE_ANISOTROPYMAP\n\t\tuniform sampler2D anisotropyMap;\n\t#endif\n#endif\nvarying vec3 vViewPosition;\n#include <common>\n#include <packing>\n#include <dithering_pars_fragment>\n#include <color_pars_fragment>\n#include <uv_pars_fragment>\n#include <map_pars_fragment>\n#include <alphamap_pars_fragment>\n#include <alphatest_pars_fragment>\n#include <alphahash_pars_fragment>\n#include <aomap_pars_fragment>\n#include <lightmap_pars_fragment>\n#include <emissivemap_pars_fragment>\n#include <iridescence_fragment>\n#include <cube_uv_reflection_fragment>\n#include <envmap_common_pars_fragment>\n#include <envmap_physical_pars_fragment>\n#include <fog_pars_fragment>\n#include <lights_pars_begin>\n#include <normal_pars_fragment>\n#include <lights_physical_pars_fragment>\n#include <transmission_pars_fragment>\n#include <shadowmap_pars_fragment>\n#include <bumpmap_pars_fragment>\n#include <normalmap_pars_fragment>\n#include <clearcoat_pars_fragment>\n#include <iridescence_pars_fragment>\n#include <roughnessmap_pars_fragment>\n#include <metalnessmap_pars_fragment>\n#include <logdepthbuf_pars_fragment>\n#include <clipping_planes_pars_fragment>\nvoid main() {\n\tvec4 diffuseColor = vec4( diffuse, opacity );\n\t#include <clipping_planes_fragment>\n\tReflectedLight reflectedLight = ReflectedLight( vec3( 0.0 ), vec3( 0.0 ), vec3( 0.0 ), vec3( 0.0 ) );\n\tvec3 totalEmissiveRadiance = emissive;\n\t#include <logdepthbuf_fragment>\n\t#include <map_fragment>\n\t#include <color_fragment>\n\t#include <alphamap_fragment>\n\t#include <alphatest_fragment>\n\t#include <alphahash_fragment>\n\t#include <roughnessmap_fragment>\n\t#include <metalnessmap_fragment>\n\t#include <normal_fragment_begin>\n\t#include <normal_fragment_maps>\n\t#include <clearcoat_normal_fragment_begin>\n\t#include <clearcoat_normal_fragment_maps>\n\t#include <emissivemap_fragment>\n\t#include <lights_physical_fragment>\n\t#include <lights_fragment_begin>\n\t#include <lights_fragment_maps>\n\t#include <lights_fragment_end>\n\t#include <aomap_fragment>\n\tvec3 totalDiffuse = reflectedLight.directDiffuse + reflectedLight.indirectDiffuse;\n\tvec3 totalSpecular = reflectedLight.directSpecular + reflectedLight.indirectSpecular;\n\t#include <transmission_fragment>\n\tvec3 outgoingLight = totalDiffuse + totalSpecular + totalEmissiveRadiance;\n\t#ifdef USE_SHEEN\n\t\tfloat sheenEnergyComp = 1.0 - 0.157 * max3( material.sheenColor );\n\t\toutgoingLight = outgoingLight * sheenEnergyComp + sheenSpecularDirect + sheenSpecularIndirect;\n\t#endif\n\t#ifdef USE_CLEARCOAT\n\t\tfloat dotNVcc = saturate( dot( geometryClearcoatNormal, geometryViewDir ) );\n\t\tvec3 Fcc = F_Schlick( material.clearcoatF0, material.clearcoatF90, dotNVcc );\n\t\toutgoingLight = outgoingLight * ( 1.0 - material.clearcoat * Fcc ) + ( clearcoatSpecularDirect + clearcoatSpecularIndirect ) * material.clearcoat;\n\t#endif\n\t#include <opaque_fragment>\n\t#include <tonemapping_fragment>\n\t#include <colorspace_fragment>\n\t#include <fog_fragment>\n\t#include <premultiplied_alpha_fragment>\n\t#include <dithering_fragment>\n}";
14009
+ const fragment$5 = "#define STANDARD\n#ifdef PHYSICAL\n\t#define IOR\n\t#define USE_SPECULAR\n#endif\nuniform vec3 diffuse;\nuniform vec3 emissive;\nuniform float roughness;\nuniform float metalness;\nuniform float opacity;\n#ifdef IOR\n\tuniform float ior;\n#endif\n#ifdef USE_SPECULAR\n\tuniform float specularIntensity;\n\tuniform vec3 specularColor;\n\t#ifdef USE_SPECULAR_COLORMAP\n\t\tuniform sampler2D specularColorMap;\n\t#endif\n\t#ifdef USE_SPECULAR_INTENSITYMAP\n\t\tuniform sampler2D specularIntensityMap;\n\t#endif\n#endif\n#ifdef USE_CLEARCOAT\n\tuniform float clearcoat;\n\tuniform float clearcoatRoughness;\n#endif\n#ifdef USE_DISPERSION\n\tuniform float dispersion;\n#endif\n#ifdef USE_IRIDESCENCE\n\tuniform float iridescence;\n\tuniform float iridescenceIOR;\n\tuniform float iridescenceThicknessMinimum;\n\tuniform float iridescenceThicknessMaximum;\n#endif\n#ifdef USE_SHEEN\n\tuniform vec3 sheenColor;\n\tuniform float sheenRoughness;\n\t#ifdef USE_SHEEN_COLORMAP\n\t\tuniform sampler2D sheenColorMap;\n\t#endif\n\t#ifdef USE_SHEEN_ROUGHNESSMAP\n\t\tuniform sampler2D sheenRoughnessMap;\n\t#endif\n#endif\n#ifdef USE_ANISOTROPY\n\tuniform vec2 anisotropyVector;\n\t#ifdef USE_ANISOTROPYMAP\n\t\tuniform sampler2D anisotropyMap;\n\t#endif\n#endif\nvarying vec3 vViewPosition;\n#include <common>\n#include <packing>\n#include <dithering_pars_fragment>\n#include <color_pars_fragment>\n#include <uv_pars_fragment>\n#include <map_pars_fragment>\n#include <alphamap_pars_fragment>\n#include <alphatest_pars_fragment>\n#include <alphahash_pars_fragment>\n#include <aomap_pars_fragment>\n#include <lightmap_pars_fragment>\n#include <emissivemap_pars_fragment>\n#include <iridescence_fragment>\n#include <cube_uv_reflection_fragment>\n#include <envmap_common_pars_fragment>\n#include <envmap_physical_pars_fragment>\n#include <fog_pars_fragment>\n#include <lights_pars_begin>\n#include <normal_pars_fragment>\n#include <lights_physical_pars_fragment>\n#include <transmission_pars_fragment>\n#include <shadowmap_pars_fragment>\n#include <bumpmap_pars_fragment>\n#include <normalmap_pars_fragment>\n#include <clearcoat_pars_fragment>\n#include <iridescence_pars_fragment>\n#include <roughnessmap_pars_fragment>\n#include <metalnessmap_pars_fragment>\n#include <logdepthbuf_pars_fragment>\n#include <clipping_planes_pars_fragment>\nvoid main() {\n\tvec4 diffuseColor = vec4( diffuse, opacity );\n\t#include <clipping_planes_fragment>\n\tReflectedLight reflectedLight = ReflectedLight( vec3( 0.0 ), vec3( 0.0 ), vec3( 0.0 ), vec3( 0.0 ) );\n\tvec3 totalEmissiveRadiance = emissive;\n\t#include <logdepthbuf_fragment>\n\t#include <map_fragment>\n\t#include <color_fragment>\n\t#include <alphamap_fragment>\n\t#include <alphatest_fragment>\n\t#include <alphahash_fragment>\n\t#include <roughnessmap_fragment>\n\t#include <metalnessmap_fragment>\n\t#include <normal_fragment_begin>\n\t#include <normal_fragment_maps>\n\t#include <clearcoat_normal_fragment_begin>\n\t#include <clearcoat_normal_fragment_maps>\n\t#include <emissivemap_fragment>\n\t#include <lights_physical_fragment>\n\t#include <lights_fragment_begin>\n\t#include <lights_fragment_maps>\n\t#include <lights_fragment_end>\n\t#include <aomap_fragment>\n\tvec3 totalDiffuse = reflectedLight.directDiffuse + reflectedLight.indirectDiffuse;\n\tvec3 totalSpecular = reflectedLight.directSpecular + reflectedLight.indirectSpecular;\n\t#include <transmission_fragment>\n\tvec3 outgoingLight = totalDiffuse + totalSpecular + totalEmissiveRadiance;\n\t#ifdef USE_SHEEN\n\t\tfloat sheenEnergyComp = 1.0 - 0.157 * max3( material.sheenColor );\n\t\toutgoingLight = outgoingLight * sheenEnergyComp + sheenSpecularDirect + sheenSpecularIndirect;\n\t#endif\n\t#ifdef USE_CLEARCOAT\n\t\tfloat dotNVcc = saturate( dot( geometryClearcoatNormal, geometryViewDir ) );\n\t\tvec3 Fcc = F_Schlick( material.clearcoatF0, material.clearcoatF90, dotNVcc );\n\t\toutgoingLight = outgoingLight * ( 1.0 - material.clearcoat * Fcc ) + ( clearcoatSpecularDirect + clearcoatSpecularIndirect ) * material.clearcoat;\n\t#endif\n\t#include <opaque_fragment>\n\t#include <tonemapping_fragment>\n\t#include <colorspace_fragment>\n\t#include <fog_fragment>\n\t#include <premultiplied_alpha_fragment>\n\t#include <dithering_fragment>\n}";
14002
14010
 
14003
14011
  const vertex$4 = "#define TOON\nvarying vec3 vViewPosition;\n#include <common>\n#include <batching_pars_vertex>\n#include <uv_pars_vertex>\n#include <displacementmap_pars_vertex>\n#include <color_pars_vertex>\n#include <fog_pars_vertex>\n#include <normal_pars_vertex>\n#include <morphtarget_pars_vertex>\n#include <skinning_pars_vertex>\n#include <shadowmap_pars_vertex>\n#include <logdepthbuf_pars_vertex>\n#include <clipping_planes_pars_vertex>\nvoid main() {\n\t#include <uv_vertex>\n\t#include <color_vertex>\n\t#include <morphinstance_vertex>\n\t#include <morphcolor_vertex>\n\t#include <batching_vertex>\n\t#include <beginnormal_vertex>\n\t#include <morphnormal_vertex>\n\t#include <skinbase_vertex>\n\t#include <skinnormal_vertex>\n\t#include <defaultnormal_vertex>\n\t#include <normal_vertex>\n\t#include <begin_vertex>\n\t#include <morphtarget_vertex>\n\t#include <skinning_vertex>\n\t#include <displacementmap_vertex>\n\t#include <project_vertex>\n\t#include <logdepthbuf_vertex>\n\t#include <clipping_planes_vertex>\n\tvViewPosition = - mvPosition.xyz;\n\t#include <worldpos_vertex>\n\t#include <shadowmap_vertex>\n\t#include <fog_vertex>\n}";
14004
14012
 
@@ -14060,7 +14068,6 @@ const ShaderChunk = {
14060
14068
  fog_fragment: fog_fragment,
14061
14069
  fog_pars_fragment: fog_pars_fragment,
14062
14070
  gradientmap_pars_fragment: gradientmap_pars_fragment,
14063
- lightmap_fragment: lightmap_fragment,
14064
14071
  lightmap_pars_fragment: lightmap_pars_fragment,
14065
14072
  lights_lambert_fragment: lights_lambert_fragment,
14066
14073
  lights_lambert_pars_fragment: lights_lambert_pars_fragment,
@@ -14696,6 +14703,7 @@ ShaderLib.physical = {
14696
14703
  clearcoatRoughness: { value: 0 },
14697
14704
  clearcoatRoughnessMap: { value: null },
14698
14705
  clearcoatRoughnessMapTransform: { value: /*@__PURE__*/ new Matrix3() },
14706
+ dispersion: { value: 0 },
14699
14707
  iridescence: { value: 0 },
14700
14708
  iridescenceMap: { value: null },
14701
14709
  iridescenceMapTransform: { value: /*@__PURE__*/ new Matrix3() },
@@ -14754,9 +14762,8 @@ function WebGLBackground( renderer, cubemaps, cubeuvmaps, state, objects, alpha,
14754
14762
  let currentBackgroundVersion = 0;
14755
14763
  let currentTonemapping = null;
14756
14764
 
14757
- function render( renderList, scene ) {
14765
+ function getBackground( scene ) {
14758
14766
 
14759
- let forceClear = false;
14760
14767
  let background = scene.isScene === true ? scene.background : null;
14761
14768
 
14762
14769
  if ( background && background.isTexture ) {
@@ -14766,6 +14773,15 @@ function WebGLBackground( renderer, cubemaps, cubeuvmaps, state, objects, alpha,
14766
14773
 
14767
14774
  }
14768
14775
 
14776
+ return background;
14777
+
14778
+ }
14779
+
14780
+ function render( scene ) {
14781
+
14782
+ let forceClear = false;
14783
+ const background = getBackground( scene );
14784
+
14769
14785
  if ( background === null ) {
14770
14786
 
14771
14787
  setClear( clearColor, clearAlpha );
@@ -14795,6 +14811,12 @@ function WebGLBackground( renderer, cubemaps, cubeuvmaps, state, objects, alpha,
14795
14811
 
14796
14812
  }
14797
14813
 
14814
+ }
14815
+
14816
+ function addToRenderList( renderList, scene ) {
14817
+
14818
+ const background = getBackground( scene );
14819
+
14798
14820
  if ( background && ( background.isCubeTexture || background.mapping === CubeUVReflectionMapping ) ) {
14799
14821
 
14800
14822
  if ( boxMesh === undefined ) {
@@ -14975,7 +14997,8 @@ function WebGLBackground( renderer, cubemaps, cubeuvmaps, state, objects, alpha,
14975
14997
  setClear( clearColor, clearAlpha );
14976
14998
 
14977
14999
  },
14978
- render: render
15000
+ render: render,
15001
+ addToRenderList: addToRenderList
14979
15002
 
14980
15003
  };
14981
15004
 
@@ -15630,16 +15653,52 @@ function WebGLBufferRenderer( gl, extensions, info ) {
15630
15653
 
15631
15654
  }
15632
15655
 
15656
+ function renderMultiDrawInstances( starts, counts, drawCount, primcount ) {
15657
+
15658
+ if ( drawCount === 0 ) return;
15659
+
15660
+ const extension = extensions.get( 'WEBGL_multi_draw' );
15661
+
15662
+ if ( extension === null ) {
15663
+
15664
+ for ( let i = 0; i < starts.length; i ++ ) {
15665
+
15666
+ renderInstances( starts[ i ], counts[ i ], primcount[ i ] );
15667
+
15668
+ }
15669
+
15670
+ } else {
15671
+
15672
+ extension.multiDrawArraysInstancedWEBGL( mode, starts, 0, counts, 0, primcount, 0, drawCount );
15673
+
15674
+ let elementCount = 0;
15675
+ for ( let i = 0; i < drawCount; i ++ ) {
15676
+
15677
+ elementCount += counts[ i ];
15678
+
15679
+ }
15680
+
15681
+ for ( let i = 0; i < primcount.length; i ++ ) {
15682
+
15683
+ info.update( elementCount, mode, primcount[ i ] );
15684
+
15685
+ }
15686
+
15687
+ }
15688
+
15689
+ }
15690
+
15633
15691
  //
15634
15692
 
15635
15693
  this.setMode = setMode;
15636
15694
  this.render = render;
15637
15695
  this.renderInstances = renderInstances;
15638
15696
  this.renderMultiDraw = renderMultiDraw;
15697
+ this.renderMultiDrawInstances = renderMultiDrawInstances;
15639
15698
 
15640
15699
  }
15641
15700
 
15642
- function WebGLCapabilities( gl, extensions, parameters ) {
15701
+ function WebGLCapabilities( gl, extensions, parameters, utils ) {
15643
15702
 
15644
15703
  let maxAnisotropy;
15645
15704
 
@@ -15663,6 +15722,33 @@ function WebGLCapabilities( gl, extensions, parameters ) {
15663
15722
 
15664
15723
  }
15665
15724
 
15725
+ function textureFormatReadable( textureFormat ) {
15726
+
15727
+ if ( textureFormat !== RGBAFormat && utils.convert( textureFormat ) !== gl.getParameter( gl.IMPLEMENTATION_COLOR_READ_FORMAT ) ) {
15728
+
15729
+ return false;
15730
+
15731
+ }
15732
+
15733
+ return true;
15734
+
15735
+ }
15736
+
15737
+ function textureTypeReadable( textureType ) {
15738
+
15739
+ const halfFloatSupportedByExt = ( textureType === HalfFloatType ) && ( extensions.has( 'EXT_color_buffer_half_float' ) || extensions.has( 'EXT_color_buffer_float' ) );
15740
+
15741
+ if ( textureType !== UnsignedByteType && utils.convert( textureType ) !== gl.getParameter( gl.IMPLEMENTATION_COLOR_READ_TYPE ) && // Edge and Chrome Mac < 52 (#9513)
15742
+ textureType !== FloatType && ! halfFloatSupportedByExt ) {
15743
+
15744
+ return false;
15745
+
15746
+ }
15747
+
15748
+ return true;
15749
+
15750
+ }
15751
+
15666
15752
  function getMaxPrecision( precision ) {
15667
15753
 
15668
15754
  if ( precision === 'highp' ) {
@@ -15726,6 +15812,9 @@ function WebGLCapabilities( gl, extensions, parameters ) {
15726
15812
  getMaxAnisotropy: getMaxAnisotropy,
15727
15813
  getMaxPrecision: getMaxPrecision,
15728
15814
 
15815
+ textureFormatReadable: textureFormatReadable,
15816
+ textureTypeReadable: textureTypeReadable,
15817
+
15729
15818
  precision: precision,
15730
15819
  logarithmicDepthBuffer: logarithmicDepthBuffer,
15731
15820
 
@@ -16167,16 +16256,16 @@ const INV_PHI = 1 / PHI;
16167
16256
  // Vertices of a dodecahedron (except the opposites, which represent the
16168
16257
  // same axis), used as axis directions evenly spread on a sphere.
16169
16258
  const _axisDirections = [
16170
- /*@__PURE__*/ new Vector3( 1, 1, 1 ),
16171
- /*@__PURE__*/ new Vector3( - 1, 1, 1 ),
16172
- /*@__PURE__*/ new Vector3( 1, 1, - 1 ),
16173
- /*@__PURE__*/ new Vector3( - 1, 1, - 1 ),
16174
- /*@__PURE__*/ new Vector3( 0, PHI, INV_PHI ),
16175
- /*@__PURE__*/ new Vector3( 0, PHI, - INV_PHI ),
16176
- /*@__PURE__*/ new Vector3( INV_PHI, 0, PHI ),
16177
- /*@__PURE__*/ new Vector3( - INV_PHI, 0, PHI ),
16259
+ /*@__PURE__*/ new Vector3( - PHI, INV_PHI, 0 ),
16178
16260
  /*@__PURE__*/ new Vector3( PHI, INV_PHI, 0 ),
16179
- /*@__PURE__*/ new Vector3( - PHI, INV_PHI, 0 ) ];
16261
+ /*@__PURE__*/ new Vector3( - INV_PHI, 0, PHI ),
16262
+ /*@__PURE__*/ new Vector3( INV_PHI, 0, PHI ),
16263
+ /*@__PURE__*/ new Vector3( 0, PHI, - INV_PHI ),
16264
+ /*@__PURE__*/ new Vector3( 0, PHI, INV_PHI ),
16265
+ /*@__PURE__*/ new Vector3( - 1, 1, - 1 ),
16266
+ /*@__PURE__*/ new Vector3( 1, 1, - 1 ),
16267
+ /*@__PURE__*/ new Vector3( - 1, 1, 1 ),
16268
+ /*@__PURE__*/ new Vector3( 1, 1, 1 ) ];
16180
16269
 
16181
16270
  /**
16182
16271
  * This class generates a Prefiltered, Mipmapped Radiance Environment Map
@@ -16562,12 +16651,13 @@ class PMREMGenerator {
16562
16651
  const renderer = this._renderer;
16563
16652
  const autoClear = renderer.autoClear;
16564
16653
  renderer.autoClear = false;
16654
+ const n = this._lodPlanes.length;
16565
16655
 
16566
- for ( let i = 1; i < this._lodPlanes.length; i ++ ) {
16656
+ for ( let i = 1; i < n; i ++ ) {
16567
16657
 
16568
16658
  const sigma = Math.sqrt( this._sigmas[ i ] * this._sigmas[ i ] - this._sigmas[ i - 1 ] * this._sigmas[ i - 1 ] );
16569
16659
 
16570
- const poleAxis = _axisDirections[ ( i - 1 ) % _axisDirections.length ];
16660
+ const poleAxis = _axisDirections[ ( n - i - 1 ) % _axisDirections.length ];
16571
16661
 
16572
16662
  this._blur( cubeUVRenderTarget, i - 1, i, sigma, poleAxis );
16573
16663
 
@@ -17516,6 +17606,41 @@ function WebGLIndexedBufferRenderer( gl, extensions, info ) {
17516
17606
 
17517
17607
  }
17518
17608
 
17609
+ function renderMultiDrawInstances( starts, counts, drawCount, primcount ) {
17610
+
17611
+ if ( drawCount === 0 ) return;
17612
+
17613
+ const extension = extensions.get( 'WEBGL_multi_draw' );
17614
+
17615
+ if ( extension === null ) {
17616
+
17617
+ for ( let i = 0; i < starts.length; i ++ ) {
17618
+
17619
+ renderInstances( starts[ i ] / bytesPerElement, counts[ i ], primcount[ i ] );
17620
+
17621
+ }
17622
+
17623
+ } else {
17624
+
17625
+ extension.multiDrawElementsInstancedWEBGL( mode, counts, 0, type, starts, 0, primcount, 0, drawCount );
17626
+
17627
+ let elementCount = 0;
17628
+ for ( let i = 0; i < drawCount; i ++ ) {
17629
+
17630
+ elementCount += counts[ i ];
17631
+
17632
+ }
17633
+
17634
+ for ( let i = 0; i < primcount.length; i ++ ) {
17635
+
17636
+ info.update( elementCount, mode, primcount[ i ] );
17637
+
17638
+ }
17639
+
17640
+ }
17641
+
17642
+ }
17643
+
17519
17644
  //
17520
17645
 
17521
17646
  this.setMode = setMode;
@@ -17523,6 +17648,7 @@ function WebGLIndexedBufferRenderer( gl, extensions, info ) {
17523
17648
  this.render = render;
17524
17649
  this.renderInstances = renderInstances;
17525
17650
  this.renderMultiDraw = renderMultiDraw;
17651
+ this.renderMultiDrawInstances = renderMultiDrawInstances;
17526
17652
 
17527
17653
  }
17528
17654
 
@@ -19398,11 +19524,7 @@ function resolveIncludes( string ) {
19398
19524
 
19399
19525
  }
19400
19526
 
19401
- const shaderChunkMap = new Map( [
19402
- [ 'encodings_fragment', 'colorspace_fragment' ], // @deprecated, r154
19403
- [ 'encodings_pars_fragment', 'colorspace_pars_fragment' ], // @deprecated, r154
19404
- [ 'output_fragment', 'opaque_fragment' ], // @deprecated, r154
19405
- ] );
19527
+ const shaderChunkMap = new Map();
19406
19528
 
19407
19529
  function includeReplacer( match, include ) {
19408
19530
 
@@ -19933,6 +20055,8 @@ function WebGLProgram( renderer, cacheKey, parameters, bindingStates ) {
19933
20055
  parameters.clearcoatRoughnessMap ? '#define USE_CLEARCOAT_ROUGHNESSMAP' : '',
19934
20056
  parameters.clearcoatNormalMap ? '#define USE_CLEARCOAT_NORMALMAP' : '',
19935
20057
 
20058
+ parameters.dispersion ? '#define USE_DISPERSION' : '',
20059
+
19936
20060
  parameters.iridescence ? '#define USE_IRIDESCENCE' : '',
19937
20061
  parameters.iridescenceMap ? '#define USE_IRIDESCENCEMAP' : '',
19938
20062
  parameters.iridescenceThicknessMap ? '#define USE_IRIDESCENCE_THICKNESSMAP' : '',
@@ -20538,6 +20662,7 @@ function WebGLPrograms( renderer, cubemaps, cubeuvmaps, extensions, capabilities
20538
20662
 
20539
20663
  const HAS_ANISOTROPY = material.anisotropy > 0;
20540
20664
  const HAS_CLEARCOAT = material.clearcoat > 0;
20665
+ const HAS_DISPERSION = material.dispersion > 0;
20541
20666
  const HAS_IRIDESCENCE = material.iridescence > 0;
20542
20667
  const HAS_SHEEN = material.sheen > 0;
20543
20668
  const HAS_TRANSMISSION = material.transmission > 0;
@@ -20637,6 +20762,8 @@ function WebGLPrograms( renderer, cubemaps, cubeuvmaps, extensions, capabilities
20637
20762
  clearcoatNormalMap: HAS_CLEARCOAT_NORMALMAP,
20638
20763
  clearcoatRoughnessMap: HAS_CLEARCOAT_ROUGHNESSMAP,
20639
20764
 
20765
+ dispersion: HAS_DISPERSION,
20766
+
20640
20767
  iridescence: HAS_IRIDESCENCE,
20641
20768
  iridescenceMap: HAS_IRIDESCENCEMAP,
20642
20769
  iridescenceThicknessMap: HAS_IRIDESCENCE_THICKNESSMAP,
@@ -20917,6 +21044,8 @@ function WebGLPrograms( renderer, cubemaps, cubeuvmaps, extensions, capabilities
20917
21044
  _programLayers.enable( 18 );
20918
21045
  if ( parameters.batching )
20919
21046
  _programLayers.enable( 19 );
21047
+ if ( parameters.dispersion )
21048
+ _programLayers.enable( 20 );
20920
21049
 
20921
21050
  array.push( _programLayers.mask );
20922
21051
  _programLayers.disableAll();
@@ -21908,7 +22037,9 @@ function WebGLRenderState( extensions ) {
21908
22037
  const lightsArray = [];
21909
22038
  const shadowsArray = [];
21910
22039
 
21911
- function init() {
22040
+ function init( camera ) {
22041
+
22042
+ state.camera = camera;
21912
22043
 
21913
22044
  lightsArray.length = 0;
21914
22045
  shadowsArray.length = 0;
@@ -21943,9 +22074,11 @@ function WebGLRenderState( extensions ) {
21943
22074
  lightsArray: lightsArray,
21944
22075
  shadowsArray: shadowsArray,
21945
22076
 
22077
+ camera: null,
22078
+
21946
22079
  lights: lights,
21947
22080
 
21948
- transmissionRenderTarget: null
22081
+ transmissionRenderTarget: {}
21949
22082
  };
21950
22083
 
21951
22084
  return {
@@ -22100,7 +22233,7 @@ const vertex = "void main() {\n\tgl_Position = vec4( position, 1.0 );\n}";
22100
22233
 
22101
22234
  const fragment = "uniform sampler2D shadow_pass;\nuniform vec2 resolution;\nuniform float radius;\n#include <packing>\nvoid main() {\n\tconst float samples = float( VSM_SAMPLES );\n\tfloat mean = 0.0;\n\tfloat squared_mean = 0.0;\n\tfloat uvStride = samples <= 1.0 ? 0.0 : 2.0 / ( samples - 1.0 );\n\tfloat uvStart = samples <= 1.0 ? 0.0 : - 1.0;\n\tfor ( float i = 0.0; i < samples; i ++ ) {\n\t\tfloat uvOffset = uvStart + i * uvStride;\n\t\t#ifdef HORIZONTAL_PASS\n\t\t\tvec2 distribution = unpackRGBATo2Half( texture2D( shadow_pass, ( gl_FragCoord.xy + vec2( uvOffset, 0.0 ) * radius ) / resolution ) );\n\t\t\tmean += distribution.x;\n\t\t\tsquared_mean += distribution.y * distribution.y + distribution.x * distribution.x;\n\t\t#else\n\t\t\tfloat depth = unpackRGBAToDepth( texture2D( shadow_pass, ( gl_FragCoord.xy + vec2( 0.0, uvOffset ) * radius ) / resolution ) );\n\t\t\tmean += depth;\n\t\t\tsquared_mean += depth * depth;\n\t\t#endif\n\t}\n\tmean = mean / samples;\n\tsquared_mean = squared_mean / samples;\n\tfloat std_dev = sqrt( squared_mean - mean * mean );\n\tgl_FragColor = pack2HalfToRGBA( vec2( mean, std_dev ) );\n}";
22102
22235
 
22103
- function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22236
+ function WebGLShadowMap( renderer, objects, capabilities ) {
22104
22237
 
22105
22238
  let _frustum = new Frustum();
22106
22239
 
@@ -22114,7 +22247,7 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22114
22247
 
22115
22248
  _materialCache = {},
22116
22249
 
22117
- _maxTextureSize = _capabilities.maxTextureSize;
22250
+ _maxTextureSize = capabilities.maxTextureSize;
22118
22251
 
22119
22252
  const shadowSide = { [ FrontSide ]: BackSide, [ BackSide ]: FrontSide, [ DoubleSide ]: DoubleSide };
22120
22253
 
@@ -22164,11 +22297,11 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22164
22297
 
22165
22298
  if ( lights.length === 0 ) return;
22166
22299
 
22167
- const currentRenderTarget = _renderer.getRenderTarget();
22168
- const activeCubeFace = _renderer.getActiveCubeFace();
22169
- const activeMipmapLevel = _renderer.getActiveMipmapLevel();
22300
+ const currentRenderTarget = renderer.getRenderTarget();
22301
+ const activeCubeFace = renderer.getActiveCubeFace();
22302
+ const activeMipmapLevel = renderer.getActiveMipmapLevel();
22170
22303
 
22171
- const _state = _renderer.state;
22304
+ const _state = renderer.state;
22172
22305
 
22173
22306
  // Set GL state for depth map.
22174
22307
  _state.setBlending( NoBlending );
@@ -22242,8 +22375,8 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22242
22375
 
22243
22376
  }
22244
22377
 
22245
- _renderer.setRenderTarget( shadow.map );
22246
- _renderer.clear();
22378
+ renderer.setRenderTarget( shadow.map );
22379
+ renderer.clear();
22247
22380
 
22248
22381
  const viewportCount = shadow.getViewportCount();
22249
22382
 
@@ -22284,13 +22417,13 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22284
22417
 
22285
22418
  scope.needsUpdate = false;
22286
22419
 
22287
- _renderer.setRenderTarget( currentRenderTarget, activeCubeFace, activeMipmapLevel );
22420
+ renderer.setRenderTarget( currentRenderTarget, activeCubeFace, activeMipmapLevel );
22288
22421
 
22289
22422
  };
22290
22423
 
22291
22424
  function VSMPass( shadow, camera ) {
22292
22425
 
22293
- const geometry = _objects.update( fullScreenMesh );
22426
+ const geometry = objects.update( fullScreenMesh );
22294
22427
 
22295
22428
  if ( shadowMaterialVertical.defines.VSM_SAMPLES !== shadow.blurSamples ) {
22296
22429
 
@@ -22313,18 +22446,18 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22313
22446
  shadowMaterialVertical.uniforms.shadow_pass.value = shadow.map.texture;
22314
22447
  shadowMaterialVertical.uniforms.resolution.value = shadow.mapSize;
22315
22448
  shadowMaterialVertical.uniforms.radius.value = shadow.radius;
22316
- _renderer.setRenderTarget( shadow.mapPass );
22317
- _renderer.clear();
22318
- _renderer.renderBufferDirect( camera, null, geometry, shadowMaterialVertical, fullScreenMesh, null );
22449
+ renderer.setRenderTarget( shadow.mapPass );
22450
+ renderer.clear();
22451
+ renderer.renderBufferDirect( camera, null, geometry, shadowMaterialVertical, fullScreenMesh, null );
22319
22452
 
22320
22453
  // horizontal pass
22321
22454
 
22322
22455
  shadowMaterialHorizontal.uniforms.shadow_pass.value = shadow.mapPass.texture;
22323
22456
  shadowMaterialHorizontal.uniforms.resolution.value = shadow.mapSize;
22324
22457
  shadowMaterialHorizontal.uniforms.radius.value = shadow.radius;
22325
- _renderer.setRenderTarget( shadow.map );
22326
- _renderer.clear();
22327
- _renderer.renderBufferDirect( camera, null, geometry, shadowMaterialHorizontal, fullScreenMesh, null );
22458
+ renderer.setRenderTarget( shadow.map );
22459
+ renderer.clear();
22460
+ renderer.renderBufferDirect( camera, null, geometry, shadowMaterialHorizontal, fullScreenMesh, null );
22328
22461
 
22329
22462
  }
22330
22463
 
@@ -22342,7 +22475,7 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22342
22475
 
22343
22476
  result = ( light.isPointLight === true ) ? _distanceMaterial : _depthMaterial;
22344
22477
 
22345
- if ( ( _renderer.localClippingEnabled && material.clipShadows === true && Array.isArray( material.clippingPlanes ) && material.clippingPlanes.length !== 0 ) ||
22478
+ if ( ( renderer.localClippingEnabled && material.clipShadows === true && Array.isArray( material.clippingPlanes ) && material.clippingPlanes.length !== 0 ) ||
22346
22479
  ( material.displacementMap && material.displacementScale !== 0 ) ||
22347
22480
  ( material.alphaMap && material.alphaTest > 0 ) ||
22348
22481
  ( material.map && material.alphaTest > 0 ) ) {
@@ -22407,7 +22540,7 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22407
22540
 
22408
22541
  if ( light.isPointLight === true && result.isMeshDistanceMaterial === true ) {
22409
22542
 
22410
- const materialProperties = _renderer.properties.get( result );
22543
+ const materialProperties = renderer.properties.get( result );
22411
22544
  materialProperties.light = light;
22412
22545
 
22413
22546
  }
@@ -22428,7 +22561,7 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22428
22561
 
22429
22562
  object.modelViewMatrix.multiplyMatrices( shadowCamera.matrixWorldInverse, object.matrixWorld );
22430
22563
 
22431
- const geometry = _objects.update( object );
22564
+ const geometry = objects.update( object );
22432
22565
  const material = object.material;
22433
22566
 
22434
22567
  if ( Array.isArray( material ) ) {
@@ -22444,11 +22577,11 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22444
22577
 
22445
22578
  const depthMaterial = getDepthMaterial( object, groupMaterial, light, type );
22446
22579
 
22447
- object.onBeforeShadow( _renderer, object, camera, shadowCamera, geometry, depthMaterial, group );
22580
+ object.onBeforeShadow( renderer, object, camera, shadowCamera, geometry, depthMaterial, group );
22448
22581
 
22449
- _renderer.renderBufferDirect( shadowCamera, null, geometry, depthMaterial, object, group );
22582
+ renderer.renderBufferDirect( shadowCamera, null, geometry, depthMaterial, object, group );
22450
22583
 
22451
- object.onAfterShadow( _renderer, object, camera, shadowCamera, geometry, depthMaterial, group );
22584
+ object.onAfterShadow( renderer, object, camera, shadowCamera, geometry, depthMaterial, group );
22452
22585
 
22453
22586
  }
22454
22587
 
@@ -22458,11 +22591,11 @@ function WebGLShadowMap( _renderer, _objects, _capabilities ) {
22458
22591
 
22459
22592
  const depthMaterial = getDepthMaterial( object, material, light, type );
22460
22593
 
22461
- object.onBeforeShadow( _renderer, object, camera, shadowCamera, geometry, depthMaterial, null );
22594
+ object.onBeforeShadow( renderer, object, camera, shadowCamera, geometry, depthMaterial, null );
22462
22595
 
22463
- _renderer.renderBufferDirect( shadowCamera, null, geometry, depthMaterial, object, null );
22596
+ renderer.renderBufferDirect( shadowCamera, null, geometry, depthMaterial, object, null );
22464
22597
 
22465
- object.onAfterShadow( _renderer, object, camera, shadowCamera, geometry, depthMaterial, null );
22598
+ object.onAfterShadow( renderer, object, camera, shadowCamera, geometry, depthMaterial, null );
22466
22599
 
22467
22600
  }
22468
22601
 
@@ -24521,7 +24654,7 @@ function WebGLTextures( _gl, extensions, state, properties, capabilities, utils,
24521
24654
  let mipmap;
24522
24655
  const mipmaps = texture.mipmaps;
24523
24656
 
24524
- const useTexStorage = ( texture.isVideoTexture !== true && glInternalFormat !== RGB_ETC1_Format );
24657
+ const useTexStorage = ( texture.isVideoTexture !== true );
24525
24658
  const allocateMemory = ( sourceProperties.__version === undefined ) || ( forceUpload === true );
24526
24659
  const dataReady = source.dataReady;
24527
24660
  const levels = getMipLevels( texture, image );
@@ -25778,112 +25911,120 @@ function WebGLTextures( _gl, extensions, state, properties, capabilities, utils,
25778
25911
 
25779
25912
  }
25780
25913
 
25914
+ const invalidationArrayRead = [];
25915
+ const invalidationArrayDraw = [];
25916
+
25781
25917
  function updateMultisampleRenderTarget( renderTarget ) {
25782
25918
 
25783
- if ( ( renderTarget.samples > 0 ) && useMultisampledRTT( renderTarget ) === false ) {
25919
+ if ( renderTarget.samples > 0 ) {
25784
25920
 
25785
- const textures = renderTarget.textures;
25786
- const width = renderTarget.width;
25787
- const height = renderTarget.height;
25788
- let mask = _gl.COLOR_BUFFER_BIT;
25789
- const invalidationArray = [];
25790
- const depthStyle = renderTarget.stencilBuffer ? _gl.DEPTH_STENCIL_ATTACHMENT : _gl.DEPTH_ATTACHMENT;
25791
- const renderTargetProperties = properties.get( renderTarget );
25792
- const isMultipleRenderTargets = ( textures.length > 1 );
25921
+ if ( useMultisampledRTT( renderTarget ) === false ) {
25793
25922
 
25794
- // If MRT we need to remove FBO attachments
25795
- if ( isMultipleRenderTargets ) {
25923
+ const textures = renderTarget.textures;
25924
+ const width = renderTarget.width;
25925
+ const height = renderTarget.height;
25926
+ let mask = _gl.COLOR_BUFFER_BIT;
25927
+ const depthStyle = renderTarget.stencilBuffer ? _gl.DEPTH_STENCIL_ATTACHMENT : _gl.DEPTH_ATTACHMENT;
25928
+ const renderTargetProperties = properties.get( renderTarget );
25929
+ const isMultipleRenderTargets = ( textures.length > 1 );
25796
25930
 
25797
- for ( let i = 0; i < textures.length; i ++ ) {
25931
+ // If MRT we need to remove FBO attachments
25932
+ if ( isMultipleRenderTargets ) {
25933
+
25934
+ for ( let i = 0; i < textures.length; i ++ ) {
25798
25935
 
25799
- state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25800
- _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.RENDERBUFFER, null );
25936
+ state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25937
+ _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.RENDERBUFFER, null );
25801
25938
 
25802
- state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglFramebuffer );
25803
- _gl.framebufferTexture2D( _gl.DRAW_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.TEXTURE_2D, null, 0 );
25939
+ state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglFramebuffer );
25940
+ _gl.framebufferTexture2D( _gl.DRAW_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.TEXTURE_2D, null, 0 );
25941
+
25942
+ }
25804
25943
 
25805
25944
  }
25806
25945
 
25807
- }
25946
+ state.bindFramebuffer( _gl.READ_FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25947
+ state.bindFramebuffer( _gl.DRAW_FRAMEBUFFER, renderTargetProperties.__webglFramebuffer );
25808
25948
 
25809
- state.bindFramebuffer( _gl.READ_FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25810
- state.bindFramebuffer( _gl.DRAW_FRAMEBUFFER, renderTargetProperties.__webglFramebuffer );
25949
+ for ( let i = 0; i < textures.length; i ++ ) {
25811
25950
 
25812
- for ( let i = 0; i < textures.length; i ++ ) {
25951
+ if ( renderTarget.resolveDepthBuffer ) {
25813
25952
 
25814
- invalidationArray.push( _gl.COLOR_ATTACHMENT0 + i );
25953
+ if ( renderTarget.depthBuffer ) mask |= _gl.DEPTH_BUFFER_BIT;
25815
25954
 
25816
- if ( renderTarget.depthBuffer ) {
25955
+ // resolving stencil is slow with a D3D backend. disable it for all transmission render targets (see #27799)
25817
25956
 
25818
- invalidationArray.push( depthStyle );
25957
+ if ( renderTarget.stencilBuffer && renderTarget.resolveStencilBuffer ) mask |= _gl.STENCIL_BUFFER_BIT;
25819
25958
 
25820
- }
25959
+ }
25821
25960
 
25822
- const ignoreDepthValues = ( renderTargetProperties.__ignoreDepthValues !== undefined ) ? renderTargetProperties.__ignoreDepthValues : false;
25961
+ if ( isMultipleRenderTargets ) {
25823
25962
 
25824
- if ( ignoreDepthValues === false ) {
25963
+ _gl.framebufferRenderbuffer( _gl.READ_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0, _gl.RENDERBUFFER, renderTargetProperties.__webglColorRenderbuffer[ i ] );
25825
25964
 
25826
- if ( renderTarget.depthBuffer ) mask |= _gl.DEPTH_BUFFER_BIT;
25965
+ const webglTexture = properties.get( textures[ i ] ).__webglTexture;
25966
+ _gl.framebufferTexture2D( _gl.DRAW_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0, _gl.TEXTURE_2D, webglTexture, 0 );
25827
25967
 
25828
- // resolving stencil is slow with a D3D backend. disable it for all transmission render targets (see #27799)
25968
+ }
25829
25969
 
25830
- if ( renderTarget.stencilBuffer && renderTargetProperties.__isTransmissionRenderTarget !== true ) mask |= _gl.STENCIL_BUFFER_BIT;
25970
+ _gl.blitFramebuffer( 0, 0, width, height, 0, 0, width, height, mask, _gl.NEAREST );
25831
25971
 
25832
- }
25972
+ if ( supportsInvalidateFramebuffer === true ) {
25833
25973
 
25834
- if ( isMultipleRenderTargets ) {
25974
+ invalidationArrayRead.length = 0;
25975
+ invalidationArrayDraw.length = 0;
25835
25976
 
25836
- _gl.framebufferRenderbuffer( _gl.READ_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0, _gl.RENDERBUFFER, renderTargetProperties.__webglColorRenderbuffer[ i ] );
25977
+ invalidationArrayRead.push( _gl.COLOR_ATTACHMENT0 + i );
25837
25978
 
25838
- }
25979
+ if ( renderTarget.depthBuffer && renderTarget.resolveDepthBuffer === false ) {
25839
25980
 
25840
- if ( ignoreDepthValues === true ) {
25981
+ invalidationArrayRead.push( depthStyle );
25982
+ invalidationArrayDraw.push( depthStyle );
25841
25983
 
25842
- _gl.invalidateFramebuffer( _gl.READ_FRAMEBUFFER, [ depthStyle ] );
25843
- _gl.invalidateFramebuffer( _gl.DRAW_FRAMEBUFFER, [ depthStyle ] );
25984
+ _gl.invalidateFramebuffer( _gl.DRAW_FRAMEBUFFER, invalidationArrayDraw );
25844
25985
 
25845
- }
25986
+ }
25846
25987
 
25847
- if ( isMultipleRenderTargets ) {
25988
+ _gl.invalidateFramebuffer( _gl.READ_FRAMEBUFFER, invalidationArrayRead );
25848
25989
 
25849
- const webglTexture = properties.get( textures[ i ] ).__webglTexture;
25850
- _gl.framebufferTexture2D( _gl.DRAW_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0, _gl.TEXTURE_2D, webglTexture, 0 );
25990
+ }
25851
25991
 
25852
25992
  }
25853
25993
 
25854
- _gl.blitFramebuffer( 0, 0, width, height, 0, 0, width, height, mask, _gl.NEAREST );
25994
+ state.bindFramebuffer( _gl.READ_FRAMEBUFFER, null );
25995
+ state.bindFramebuffer( _gl.DRAW_FRAMEBUFFER, null );
25855
25996
 
25856
- if ( supportsInvalidateFramebuffer ) {
25997
+ // If MRT since pre-blit we removed the FBO we need to reconstruct the attachments
25998
+ if ( isMultipleRenderTargets ) {
25857
25999
 
25858
- _gl.invalidateFramebuffer( _gl.READ_FRAMEBUFFER, invalidationArray );
26000
+ for ( let i = 0; i < textures.length; i ++ ) {
25859
26001
 
25860
- }
26002
+ state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
26003
+ _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.RENDERBUFFER, renderTargetProperties.__webglColorRenderbuffer[ i ] );
25861
26004
 
26005
+ const webglTexture = properties.get( textures[ i ] ).__webglTexture;
25862
26006
 
25863
- }
26007
+ state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglFramebuffer );
26008
+ _gl.framebufferTexture2D( _gl.DRAW_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.TEXTURE_2D, webglTexture, 0 );
25864
26009
 
25865
- state.bindFramebuffer( _gl.READ_FRAMEBUFFER, null );
25866
- state.bindFramebuffer( _gl.DRAW_FRAMEBUFFER, null );
26010
+ }
25867
26011
 
25868
- // If MRT since pre-blit we removed the FBO we need to reconstruct the attachments
25869
- if ( isMultipleRenderTargets ) {
26012
+ }
25870
26013
 
25871
- for ( let i = 0; i < textures.length; i ++ ) {
26014
+ state.bindFramebuffer( _gl.DRAW_FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25872
26015
 
25873
- state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25874
- _gl.framebufferRenderbuffer( _gl.FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.RENDERBUFFER, renderTargetProperties.__webglColorRenderbuffer[ i ] );
26016
+ } else {
25875
26017
 
25876
- const webglTexture = properties.get( textures[ i ] ).__webglTexture;
26018
+ if ( renderTarget.depthBuffer && renderTarget.resolveDepthBuffer === false && supportsInvalidateFramebuffer ) {
25877
26019
 
25878
- state.bindFramebuffer( _gl.FRAMEBUFFER, renderTargetProperties.__webglFramebuffer );
25879
- _gl.framebufferTexture2D( _gl.DRAW_FRAMEBUFFER, _gl.COLOR_ATTACHMENT0 + i, _gl.TEXTURE_2D, webglTexture, 0 );
26020
+ const depthStyle = renderTarget.stencilBuffer ? _gl.DEPTH_STENCIL_ATTACHMENT : _gl.DEPTH_ATTACHMENT;
26021
+
26022
+ _gl.invalidateFramebuffer( _gl.DRAW_FRAMEBUFFER, [ depthStyle ] );
25880
26023
 
25881
26024
  }
25882
26025
 
25883
26026
  }
25884
26027
 
25885
- state.bindFramebuffer( _gl.DRAW_FRAMEBUFFER, renderTargetProperties.__webglMultisampledFramebuffer );
25886
-
25887
26028
  }
25888
26029
 
25889
26030
  }
@@ -26099,33 +26240,15 @@ function WebGLUtils( gl, extensions ) {
26099
26240
 
26100
26241
  }
26101
26242
 
26102
- // ETC1
26103
-
26104
- if ( p === RGB_ETC1_Format ) {
26105
-
26106
- extension = extensions.get( 'WEBGL_compressed_texture_etc1' );
26107
-
26108
- if ( extension !== null ) {
26109
-
26110
- return extension.COMPRESSED_RGB_ETC1_WEBGL;
26111
-
26112
- } else {
26113
-
26114
- return null;
26115
-
26116
- }
26117
-
26118
- }
26119
-
26120
- // ETC2
26243
+ // ETC
26121
26244
 
26122
- if ( p === RGB_ETC2_Format || p === RGBA_ETC2_EAC_Format ) {
26245
+ if ( p === RGB_ETC1_Format || p === RGB_ETC2_Format || p === RGBA_ETC2_EAC_Format ) {
26123
26246
 
26124
26247
  extension = extensions.get( 'WEBGL_compressed_texture_etc' );
26125
26248
 
26126
26249
  if ( extension !== null ) {
26127
26250
 
26128
- if ( p === RGB_ETC2_Format ) return ( transfer === SRGBTransfer ) ? extension.COMPRESSED_SRGB8_ETC2 : extension.COMPRESSED_RGB8_ETC2;
26251
+ if ( p === RGB_ETC1_Format || p === RGB_ETC2_Format ) return ( transfer === SRGBTransfer ) ? extension.COMPRESSED_SRGB8_ETC2 : extension.COMPRESSED_RGB8_ETC2;
26129
26252
  if ( p === RGBA_ETC2_EAC_Format ) return ( transfer === SRGBTransfer ) ? extension.COMPRESSED_SRGB8_ALPHA8_ETC2_EAC : extension.COMPRESSED_RGBA8_ETC2_EAC;
26130
26253
 
26131
26254
  } else {
@@ -27618,7 +27741,8 @@ class WebXRManager extends EventDispatcher {
27618
27741
  depthTexture: new DepthTexture( glProjLayer.textureWidth, glProjLayer.textureHeight, depthType, undefined, undefined, undefined, undefined, undefined, undefined, depthFormat ),
27619
27742
  stencilBuffer: attributes.stencil,
27620
27743
  colorSpace: renderer.outputColorSpace,
27621
- samples: attributes.antialias ? 4 : 0
27744
+ samples: attributes.antialias ? 4 : 0,
27745
+ resolveDepthBuffer: ( glProjLayer.ignoreDepthValues === false )
27622
27746
  };
27623
27747
 
27624
27748
  if ( scope.isMultiview ) {
@@ -27638,9 +27762,6 @@ class WebXRManager extends EventDispatcher {
27638
27762
 
27639
27763
  }
27640
27764
 
27641
- const renderTargetProperties = renderer.properties.get( newRenderTarget );
27642
- renderTargetProperties.__ignoreDepthValues = glProjLayer.ignoreDepthValues;
27643
-
27644
27765
  }
27645
27766
 
27646
27767
  newRenderTarget.isXRRenderTarget = true; // TODO Remove this when possible, see #23278
@@ -28606,6 +28727,12 @@ function WebGLMaterials( renderer, properties ) {
28606
28727
 
28607
28728
  }
28608
28729
 
28730
+ if ( material.dispersion > 0 ) {
28731
+
28732
+ uniforms.dispersion.value = material.dispersion;
28733
+
28734
+ }
28735
+
28609
28736
  if ( material.iridescence > 0 ) {
28610
28737
 
28611
28738
  uniforms.iridescence.value = material.iridescence;
@@ -29258,7 +29385,6 @@ class WebGLRenderer {
29258
29385
 
29259
29386
  const _projScreenMatrix = new Matrix4();
29260
29387
 
29261
- const _vector2 = new Vector2();
29262
29388
  const _vector3 = new Vector3();
29263
29389
 
29264
29390
  const _emptyScene = { background: null, fog: null, environment: null, overrideMaterial: null, isScene: true };
@@ -29275,10 +29401,7 @@ class WebGLRenderer {
29275
29401
 
29276
29402
  function getContext( contextName, contextAttributes ) {
29277
29403
 
29278
- const context = canvas.getContext( contextName, contextAttributes );
29279
- if ( context !== null ) return context;
29280
-
29281
- return null;
29404
+ return canvas.getContext( contextName, contextAttributes );
29282
29405
 
29283
29406
  }
29284
29407
 
@@ -29346,10 +29469,10 @@ class WebGLRenderer {
29346
29469
  extensions = new WebGLExtensions( _gl );
29347
29470
  extensions.init();
29348
29471
 
29349
- capabilities = new WebGLCapabilities( _gl, extensions, parameters );
29350
-
29351
29472
  utils = new WebGLUtils( _gl, extensions );
29352
29473
 
29474
+ capabilities = new WebGLCapabilities( _gl, extensions, parameters, utils );
29475
+
29353
29476
  state = new WebGLState( _gl );
29354
29477
 
29355
29478
  info = new WebGLInfo( _gl );
@@ -29915,7 +30038,15 @@ class WebGLRenderer {
29915
30038
 
29916
30039
  if ( object.isBatchedMesh ) {
29917
30040
 
29918
- renderer.renderMultiDraw( object._multiDrawStarts, object._multiDrawCounts, object._multiDrawCount );
30041
+ if ( object._multiDrawInstances !== null ) {
30042
+
30043
+ renderer.renderMultiDrawInstances( object._multiDrawStarts, object._multiDrawCounts, object._multiDrawCount, object._multiDrawInstances );
30044
+
30045
+ } else {
30046
+
30047
+ renderer.renderMultiDraw( object._multiDrawStarts, object._multiDrawCounts, object._multiDrawCount );
30048
+
30049
+ }
29919
30050
 
29920
30051
  } else if ( object.isInstancedMesh ) {
29921
30052
 
@@ -29965,7 +30096,7 @@ class WebGLRenderer {
29965
30096
  if ( targetScene === null ) targetScene = scene;
29966
30097
 
29967
30098
  currentRenderState = renderStates.get( targetScene );
29968
- currentRenderState.init();
30099
+ currentRenderState.init( camera );
29969
30100
 
29970
30101
  renderStateStack.push( currentRenderState );
29971
30102
 
@@ -30182,7 +30313,7 @@ class WebGLRenderer {
30182
30313
  if ( scene.isScene === true ) scene.onBeforeRender( _this, scene, camera, _currentRenderTarget );
30183
30314
 
30184
30315
  currentRenderState = renderStates.get( scene, renderStateStack.length );
30185
- currentRenderState.init();
30316
+ currentRenderState.init( camera );
30186
30317
 
30187
30318
  renderStateStack.push( currentRenderState );
30188
30319
 
@@ -30207,6 +30338,13 @@ class WebGLRenderer {
30207
30338
 
30208
30339
  }
30209
30340
 
30341
+ const renderBackground = xr.enabled === false || xr.isPresenting === false || xr.hasDepthSensing() === false;
30342
+ if ( renderBackground ) {
30343
+
30344
+ background.addToRenderList( currentRenderList, scene );
30345
+
30346
+ }
30347
+
30210
30348
  //
30211
30349
 
30212
30350
  this.info.render.frame ++;
@@ -30223,20 +30361,30 @@ class WebGLRenderer {
30223
30361
 
30224
30362
  if ( this.info.autoReset === true ) this.info.reset();
30225
30363
 
30364
+ // render scene
30226
30365
 
30227
- //
30366
+ const opaqueObjects = currentRenderList.opaque;
30367
+ const transmissiveObjects = currentRenderList.transmissive;
30228
30368
 
30229
- if ( xr.enabled === false || xr.isPresenting === false || xr.hasDepthSensing() === false ) {
30369
+ currentRenderState.setupLights( _this._useLegacyLights );
30230
30370
 
30231
- background.render( currentRenderList, scene );
30371
+ if ( camera.isArrayCamera ) {
30232
30372
 
30233
- }
30373
+ const cameras = camera.cameras;
30234
30374
 
30235
- // render scene
30375
+ if ( transmissiveObjects.length > 0 ) {
30236
30376
 
30237
- currentRenderState.setupLights( _this._useLegacyLights );
30377
+ for ( let i = 0, l = cameras.length; i < l; i ++ ) {
30238
30378
 
30239
- if ( camera.isArrayCamera ) {
30379
+ const camera2 = cameras[ i ];
30380
+
30381
+ renderTransmissionPass( opaqueObjects, transmissiveObjects, scene, camera2 );
30382
+
30383
+ }
30384
+
30385
+ }
30386
+
30387
+ if ( renderBackground ) background.render( scene );
30240
30388
 
30241
30389
  if ( xr.enabled && xr.isMultiview ) {
30242
30390
 
@@ -30246,8 +30394,6 @@ class WebGLRenderer {
30246
30394
 
30247
30395
  } else {
30248
30396
 
30249
- const cameras = camera.cameras;
30250
-
30251
30397
  for ( let i = 0, l = cameras.length; i < l; i ++ ) {
30252
30398
 
30253
30399
  const camera2 = cameras[ i ];
@@ -30260,6 +30406,10 @@ class WebGLRenderer {
30260
30406
 
30261
30407
  } else {
30262
30408
 
30409
+ if ( transmissiveObjects.length > 0 ) renderTransmissionPass( opaqueObjects, transmissiveObjects, scene, camera );
30410
+
30411
+ if ( renderBackground ) background.render( scene );
30412
+
30263
30413
  renderScene( currentRenderList, scene, camera );
30264
30414
 
30265
30415
  }
@@ -30301,6 +30451,8 @@ class WebGLRenderer {
30301
30451
 
30302
30452
  currentRenderState = renderStateStack[ renderStateStack.length - 1 ];
30303
30453
 
30454
+ if ( _clippingEnabled === true ) clipping.setGlobalState( _this.clippingPlanes, currentRenderState.state.camera );
30455
+
30304
30456
  } else {
30305
30457
 
30306
30458
  currentRenderState = null;
@@ -30445,8 +30597,6 @@ class WebGLRenderer {
30445
30597
 
30446
30598
  if ( _clippingEnabled === true ) clipping.setGlobalState( _this.clippingPlanes, camera );
30447
30599
 
30448
- if ( transmissiveObjects.length > 0 ) renderTransmissionPass( opaqueObjects, transmissiveObjects, scene, camera );
30449
-
30450
30600
  if ( viewport ) state.viewport( _currentViewport.copy( viewport ) );
30451
30601
 
30452
30602
  if ( opaqueObjects.length > 0 ) renderObjects( opaqueObjects, scene, camera );
@@ -30473,19 +30623,18 @@ class WebGLRenderer {
30473
30623
 
30474
30624
  }
30475
30625
 
30476
- if ( currentRenderState.state.transmissionRenderTarget === null ) {
30626
+ if ( currentRenderState.state.transmissionRenderTarget[ camera.id ] === undefined ) {
30477
30627
 
30478
- currentRenderState.state.transmissionRenderTarget = new WebGLRenderTarget( 1, 1, {
30628
+ currentRenderState.state.transmissionRenderTarget[ camera.id ] = new WebGLRenderTarget( 1, 1, {
30479
30629
  generateMipmaps: true,
30480
30630
  type: ( extensions.has( 'EXT_color_buffer_half_float' ) || extensions.has( 'EXT_color_buffer_float' ) ) ? HalfFloatType : UnsignedByteType,
30481
30631
  minFilter: LinearMipmapLinearFilter,
30482
30632
  samples: 4,
30483
- stencilBuffer: stencil
30633
+ stencilBuffer: stencil,
30634
+ resolveDepthBuffer: false,
30635
+ resolveStencilBuffer: false
30484
30636
  } );
30485
30637
 
30486
- const renderTargetProperties = properties.get( currentRenderState.state.transmissionRenderTarget );
30487
- renderTargetProperties.__isTransmissionRenderTarget = true;
30488
-
30489
30638
  // debug
30490
30639
 
30491
30640
  /*
@@ -30498,10 +30647,10 @@ class WebGLRenderer {
30498
30647
 
30499
30648
  }
30500
30649
 
30501
- const transmissionRenderTarget = currentRenderState.state.transmissionRenderTarget;
30650
+ const transmissionRenderTarget = currentRenderState.state.transmissionRenderTarget[ camera.id ];
30502
30651
 
30503
- _this.getDrawingBufferSize( _vector2 );
30504
- transmissionRenderTarget.setSize( _vector2.x, _vector2.y );
30652
+ const activeViewport = camera.viewport || _currentViewport;
30653
+ transmissionRenderTarget.setSize( activeViewport.z, activeViewport.w );
30505
30654
 
30506
30655
  //
30507
30656
 
@@ -30519,44 +30668,57 @@ class WebGLRenderer {
30519
30668
  const currentToneMapping = _this.toneMapping;
30520
30669
  _this.toneMapping = NoToneMapping;
30521
30670
 
30671
+ // Remove viewport from camera to avoid nested render calls resetting viewport to it (e.g Reflector).
30672
+ // Transmission render pass requires viewport to match the transmissionRenderTarget.
30673
+ const currentCameraViewport = camera.viewport;
30674
+ if ( camera.viewport !== undefined ) camera.viewport = undefined;
30675
+
30676
+ currentRenderState.setupLightsView( camera );
30677
+
30678
+ if ( _clippingEnabled === true ) clipping.setGlobalState( _this.clippingPlanes, camera );
30679
+
30522
30680
  renderObjects( opaqueObjects, scene, camera );
30523
30681
 
30524
30682
  textures.updateMultisampleRenderTarget( transmissionRenderTarget );
30525
30683
  textures.updateRenderTargetMipmap( transmissionRenderTarget );
30526
30684
 
30527
- let renderTargetNeedsUpdate = false;
30685
+ if ( extensions.has( 'WEBGL_multisampled_render_to_texture' ) === false ) { // see #28131
30528
30686
 
30529
- for ( let i = 0, l = transmissiveObjects.length; i < l; i ++ ) {
30687
+ let renderTargetNeedsUpdate = false;
30530
30688
 
30531
- const renderItem = transmissiveObjects[ i ];
30689
+ for ( let i = 0, l = transmissiveObjects.length; i < l; i ++ ) {
30532
30690
 
30533
- const object = renderItem.object;
30534
- const geometry = renderItem.geometry;
30535
- const material = renderItem.material;
30536
- const group = renderItem.group;
30691
+ const renderItem = transmissiveObjects[ i ];
30537
30692
 
30538
- if ( material.side === DoubleSide && object.layers.test( camera.layers ) ) {
30693
+ const object = renderItem.object;
30694
+ const geometry = renderItem.geometry;
30695
+ const material = renderItem.material;
30696
+ const group = renderItem.group;
30539
30697
 
30540
- const currentSide = material.side;
30698
+ if ( material.side === DoubleSide && object.layers.test( camera.layers ) ) {
30541
30699
 
30542
- material.side = BackSide;
30543
- material.needsUpdate = true;
30700
+ const currentSide = material.side;
30544
30701
 
30545
- renderObject( object, scene, camera, geometry, material, group );
30702
+ material.side = BackSide;
30703
+ material.needsUpdate = true;
30704
+
30705
+ renderObject( object, scene, camera, geometry, material, group );
30546
30706
 
30547
- material.side = currentSide;
30548
- material.needsUpdate = true;
30707
+ material.side = currentSide;
30708
+ material.needsUpdate = true;
30549
30709
 
30550
- renderTargetNeedsUpdate = true;
30710
+ renderTargetNeedsUpdate = true;
30711
+
30712
+ }
30551
30713
 
30552
30714
  }
30553
30715
 
30554
- }
30716
+ if ( renderTargetNeedsUpdate === true ) {
30555
30717
 
30556
- if ( renderTargetNeedsUpdate === true ) {
30718
+ textures.updateMultisampleRenderTarget( transmissionRenderTarget );
30719
+ textures.updateRenderTargetMipmap( transmissionRenderTarget );
30557
30720
 
30558
- textures.updateMultisampleRenderTarget( transmissionRenderTarget );
30559
- textures.updateRenderTargetMipmap( transmissionRenderTarget );
30721
+ }
30560
30722
 
30561
30723
  }
30562
30724
 
@@ -30564,6 +30726,8 @@ class WebGLRenderer {
30564
30726
 
30565
30727
  _this.setClearColor( _currentClearColor, _currentClearAlpha );
30566
30728
 
30729
+ if ( currentCameraViewport !== undefined ) camera.viewport = currentCameraViewport;
30730
+
30567
30731
  _this.toneMapping = currentToneMapping;
30568
30732
 
30569
30733
  }
@@ -31111,7 +31275,7 @@ class WebGLRenderer {
31111
31275
 
31112
31276
  }
31113
31277
 
31114
- materials.refreshMaterialUniforms( m_uniforms, material, _pixelRatio, _height, currentRenderState.state.transmissionRenderTarget );
31278
+ materials.refreshMaterialUniforms( m_uniforms, material, _pixelRatio, _height, currentRenderState.state.transmissionRenderTarget[ camera.id ] );
31115
31279
 
31116
31280
  WebGLUniforms.upload( _gl, getUniformList( materialProperties ), m_uniforms, textures );
31117
31281
 
@@ -31411,17 +31575,14 @@ class WebGLRenderer {
31411
31575
  const textureFormat = texture.format;
31412
31576
  const textureType = texture.type;
31413
31577
 
31414
- if ( textureFormat !== RGBAFormat && utils.convert( textureFormat ) !== _gl.getParameter( _gl.IMPLEMENTATION_COLOR_READ_FORMAT ) ) {
31578
+ if ( ! capabilities.textureFormatReadable( textureFormat ) ) {
31415
31579
 
31416
31580
  console.error( 'THREE.WebGLRenderer.readRenderTargetPixels: renderTarget is not in RGBA or implementation defined format.' );
31417
31581
  return;
31418
31582
 
31419
31583
  }
31420
31584
 
31421
- const halfFloatSupportedByExt = ( textureType === HalfFloatType ) && ( extensions.has( 'EXT_color_buffer_half_float' ) || extensions.has( 'EXT_color_buffer_float' ) );
31422
-
31423
- if ( textureType !== UnsignedByteType && utils.convert( textureType ) !== _gl.getParameter( _gl.IMPLEMENTATION_COLOR_READ_TYPE ) && // Edge and Chrome Mac < 52 (#9513)
31424
- textureType !== FloatType && ! halfFloatSupportedByExt ) {
31585
+ if ( ! capabilities.textureTypeReadable( textureType ) ) {
31425
31586
 
31426
31587
  console.error( 'THREE.WebGLRenderer.readRenderTargetPixels: renderTarget is not in UnsignedByteType or implementation defined type.' );
31427
31588
  return;
@@ -31505,9 +31666,9 @@ class WebGLRenderer {
31505
31666
 
31506
31667
  this.copyTextureToTexture3D = function ( sourceBox, position, srcTexture, dstTexture, level = 0 ) {
31507
31668
 
31508
- const width = Math.round( sourceBox.max.x - sourceBox.min.x );
31509
- const height = Math.round( sourceBox.max.y - sourceBox.min.y );
31510
- const depth = sourceBox.max.z - sourceBox.min.z + 1;
31669
+ const width = sourceBox.max.x - sourceBox.min.x;
31670
+ const height = sourceBox.max.y - sourceBox.min.y;
31671
+ const depth = sourceBox.max.z - sourceBox.min.z;
31511
31672
  const glFormat = utils.convert( dstTexture.format );
31512
31673
  const glType = utils.convert( dstTexture.type );
31513
31674
  let glTarget;
@@ -33726,6 +33887,7 @@ class BatchedMesh extends Mesh {
33726
33887
  this._multiDrawCounts = new Int32Array( maxGeometryCount );
33727
33888
  this._multiDrawStarts = new Int32Array( maxGeometryCount );
33728
33889
  this._multiDrawCount = 0;
33890
+ this._multiDrawInstances = null;
33729
33891
  this._visibilityChanged = true;
33730
33892
 
33731
33893
  // Local matrix per geometry by using data texture
@@ -34167,6 +34329,28 @@ class BatchedMesh extends Mesh {
34167
34329
 
34168
34330
  }
34169
34331
 
34332
+ getInstanceCountAt( id ) {
34333
+
34334
+ if ( this._multiDrawInstances === null ) return null;
34335
+
34336
+ return this._multiDrawInstances[ id ];
34337
+
34338
+ }
34339
+
34340
+ setInstanceCountAt( id, instanceCount ) {
34341
+
34342
+ if ( this._multiDrawInstances === null ) {
34343
+
34344
+ this._multiDrawInstances = new Int32Array( this._maxGeometryCount ).fill( 1 );
34345
+
34346
+ }
34347
+
34348
+ this._multiDrawInstances[ id ] = instanceCount;
34349
+
34350
+ return id;
34351
+
34352
+ }
34353
+
34170
34354
  // get bounding box and compute it if it doesn't exist
34171
34355
  getBoundingBoxAt( id, target ) {
34172
34356
 
@@ -34636,12 +34820,16 @@ class LineBasicMaterial extends Material {
34636
34820
 
34637
34821
  }
34638
34822
 
34639
- const _start$1 = /*@__PURE__*/ new Vector3();
34640
- const _end$1 = /*@__PURE__*/ new Vector3();
34823
+ const _vStart = /*@__PURE__*/ new Vector3();
34824
+ const _vEnd = /*@__PURE__*/ new Vector3();
34825
+
34641
34826
  const _inverseMatrix$1 = /*@__PURE__*/ new Matrix4();
34642
34827
  const _ray$1 = /*@__PURE__*/ new Ray();
34643
34828
  const _sphere$1 = /*@__PURE__*/ new Sphere();
34644
34829
 
34830
+ const _intersectPointOnRay = /*@__PURE__*/ new Vector3();
34831
+ const _intersectPointOnSegment = /*@__PURE__*/ new Vector3();
34832
+
34645
34833
  class Line extends Object3D {
34646
34834
 
34647
34835
  constructor( geometry = new BufferGeometry(), material = new LineBasicMaterial() ) {
@@ -34683,11 +34871,11 @@ class Line extends Object3D {
34683
34871
 
34684
34872
  for ( let i = 1, l = positionAttribute.count; i < l; i ++ ) {
34685
34873
 
34686
- _start$1.fromBufferAttribute( positionAttribute, i - 1 );
34687
- _end$1.fromBufferAttribute( positionAttribute, i );
34874
+ _vStart.fromBufferAttribute( positionAttribute, i - 1 );
34875
+ _vEnd.fromBufferAttribute( positionAttribute, i );
34688
34876
 
34689
34877
  lineDistances[ i ] = lineDistances[ i - 1 ];
34690
- lineDistances[ i ] += _start$1.distanceTo( _end$1 );
34878
+ lineDistances[ i ] += _vStart.distanceTo( _vEnd );
34691
34879
 
34692
34880
  }
34693
34881
 
@@ -34728,10 +34916,6 @@ class Line extends Object3D {
34728
34916
  const localThreshold = threshold / ( ( this.scale.x + this.scale.y + this.scale.z ) / 3 );
34729
34917
  const localThresholdSq = localThreshold * localThreshold;
34730
34918
 
34731
- const vStart = new Vector3();
34732
- const vEnd = new Vector3();
34733
- const interSegment = new Vector3();
34734
- const interRay = new Vector3();
34735
34919
  const step = this.isLineSegments ? 2 : 1;
34736
34920
 
34737
34921
  const index = geometry.index;
@@ -34748,31 +34932,28 @@ class Line extends Object3D {
34748
34932
  const a = index.getX( i );
34749
34933
  const b = index.getX( i + 1 );
34750
34934
 
34751
- vStart.fromBufferAttribute( positionAttribute, a );
34752
- vEnd.fromBufferAttribute( positionAttribute, b );
34935
+ const intersect = checkIntersection( this, raycaster, _ray$1, localThresholdSq, a, b );
34753
34936
 
34754
- const distSq = _ray$1.distanceSqToSegment( vStart, vEnd, interRay, interSegment );
34937
+ if ( intersect ) {
34755
34938
 
34756
- if ( distSq > localThresholdSq ) continue;
34939
+ intersects.push( intersect );
34757
34940
 
34758
- interRay.applyMatrix4( this.matrixWorld ); //Move back to world space for distance calculation
34941
+ }
34759
34942
 
34760
- const distance = raycaster.ray.origin.distanceTo( interRay );
34943
+ }
34761
34944
 
34762
- if ( distance < raycaster.near || distance > raycaster.far ) continue;
34945
+ if ( this.isLineLoop ) {
34763
34946
 
34764
- intersects.push( {
34947
+ const a = index.getX( end - 1 );
34948
+ const b = index.getX( start );
34765
34949
 
34766
- distance: distance,
34767
- // What do we want? intersection point on the ray or on the segment??
34768
- // point: raycaster.ray.at( distance ),
34769
- point: interSegment.clone().applyMatrix4( this.matrixWorld ),
34770
- index: i,
34771
- face: null,
34772
- faceIndex: null,
34773
- object: this
34950
+ const intersect = checkIntersection( this, raycaster, _ray$1, localThresholdSq, a, b );
34774
34951
 
34775
- } );
34952
+ if ( intersect ) {
34953
+
34954
+ intersects.push( intersect );
34955
+
34956
+ }
34776
34957
 
34777
34958
  }
34778
34959
 
@@ -34783,31 +34964,25 @@ class Line extends Object3D {
34783
34964
 
34784
34965
  for ( let i = start, l = end - 1; i < l; i += step ) {
34785
34966
 
34786
- vStart.fromBufferAttribute( positionAttribute, i );
34787
- vEnd.fromBufferAttribute( positionAttribute, i + 1 );
34967
+ const intersect = checkIntersection( this, raycaster, _ray$1, localThresholdSq, i, i + 1 );
34788
34968
 
34789
- const distSq = _ray$1.distanceSqToSegment( vStart, vEnd, interRay, interSegment );
34969
+ if ( intersect ) {
34790
34970
 
34791
- if ( distSq > localThresholdSq ) continue;
34971
+ intersects.push( intersect );
34792
34972
 
34793
- interRay.applyMatrix4( this.matrixWorld ); //Move back to world space for distance calculation
34973
+ }
34794
34974
 
34795
- const distance = raycaster.ray.origin.distanceTo( interRay );
34975
+ }
34796
34976
 
34797
- if ( distance < raycaster.near || distance > raycaster.far ) continue;
34977
+ if ( this.isLineLoop ) {
34798
34978
 
34799
- intersects.push( {
34979
+ const intersect = checkIntersection( this, raycaster, _ray$1, localThresholdSq, end - 1, start );
34800
34980
 
34801
- distance: distance,
34802
- // What do we want? intersection point on the ray or on the segment??
34803
- // point: raycaster.ray.at( distance ),
34804
- point: interSegment.clone().applyMatrix4( this.matrixWorld ),
34805
- index: i,
34806
- face: null,
34807
- faceIndex: null,
34808
- object: this
34981
+ if ( intersect ) {
34809
34982
 
34810
- } );
34983
+ intersects.push( intersect );
34984
+
34985
+ }
34811
34986
 
34812
34987
  }
34813
34988
 
@@ -34848,6 +35023,38 @@ class Line extends Object3D {
34848
35023
 
34849
35024
  }
34850
35025
 
35026
+ function checkIntersection( object, raycaster, ray, thresholdSq, a, b ) {
35027
+
35028
+ const positionAttribute = object.geometry.attributes.position;
35029
+
35030
+ _vStart.fromBufferAttribute( positionAttribute, a );
35031
+ _vEnd.fromBufferAttribute( positionAttribute, b );
35032
+
35033
+ const distSq = ray.distanceSqToSegment( _vStart, _vEnd, _intersectPointOnRay, _intersectPointOnSegment );
35034
+
35035
+ if ( distSq > thresholdSq ) return;
35036
+
35037
+ _intersectPointOnRay.applyMatrix4( object.matrixWorld ); // Move back to world space for distance calculation
35038
+
35039
+ const distance = raycaster.ray.origin.distanceTo( _intersectPointOnRay );
35040
+
35041
+ if ( distance < raycaster.near || distance > raycaster.far ) return;
35042
+
35043
+ return {
35044
+
35045
+ distance: distance,
35046
+ // What do we want? intersection point on the ray or on the segment??
35047
+ // point: raycaster.ray.at( distance ),
35048
+ point: _intersectPointOnSegment.clone().applyMatrix4( object.matrixWorld ),
35049
+ index: a,
35050
+ face: null,
35051
+ faceIndex: null,
35052
+ object: object
35053
+
35054
+ };
35055
+
35056
+ }
35057
+
34851
35058
  const _start = /*@__PURE__*/ new Vector3();
34852
35059
  const _end = /*@__PURE__*/ new Vector3();
34853
35060
 
@@ -41485,6 +41692,7 @@ class MeshPhysicalMaterial extends MeshStandardMaterial {
41485
41692
 
41486
41693
  this._anisotropy = 0;
41487
41694
  this._clearcoat = 0;
41695
+ this._dispersion = 0;
41488
41696
  this._iridescence = 0;
41489
41697
  this._sheen = 0.0;
41490
41698
  this._transmission = 0;
@@ -41547,6 +41755,24 @@ class MeshPhysicalMaterial extends MeshStandardMaterial {
41547
41755
 
41548
41756
  }
41549
41757
 
41758
+ get dispersion() {
41759
+
41760
+ return this._dispersion;
41761
+
41762
+ }
41763
+
41764
+ set dispersion( value ) {
41765
+
41766
+ if ( this._dispersion > 0 !== value > 0 ) {
41767
+
41768
+ this.version ++;
41769
+
41770
+ }
41771
+
41772
+ this._dispersion = value;
41773
+
41774
+ }
41775
+
41550
41776
  get sheen() {
41551
41777
 
41552
41778
  return this._sheen;
@@ -41605,6 +41831,7 @@ class MeshPhysicalMaterial extends MeshStandardMaterial {
41605
41831
  this.clearcoatNormalMap = source.clearcoatNormalMap;
41606
41832
  this.clearcoatNormalScale.copy( source.clearcoatNormalScale );
41607
41833
 
41834
+ this.dispersion = source.dispersion;
41608
41835
  this.ior = source.ior;
41609
41836
 
41610
41837
  this.iridescence = source.iridescence;
@@ -44278,7 +44505,7 @@ class FileLoader extends Loader {
44278
44505
 
44279
44506
  // Nginx needs X-File-Size check
44280
44507
  // https://serverfault.com/questions/482875/why-does-nginx-remove-content-length-header-for-chunked-content
44281
- const contentLength = response.headers.get( 'Content-Length' ) || response.headers.get( 'X-File-Size' );
44508
+ const contentLength = response.headers.get( 'X-File-Size' ) || response.headers.get( 'Content-Length' );
44282
44509
  const total = contentLength ? parseInt( contentLength ) : 0;
44283
44510
  const lengthComputable = total !== 0;
44284
44511
  let loaded = 0;
@@ -45879,6 +46106,7 @@ class MaterialLoader extends Loader {
45879
46106
  if ( json.shininess !== undefined ) material.shininess = json.shininess;
45880
46107
  if ( json.clearcoat !== undefined ) material.clearcoat = json.clearcoat;
45881
46108
  if ( json.clearcoatRoughness !== undefined ) material.clearcoatRoughness = json.clearcoatRoughness;
46109
+ if ( json.dispersion !== undefined ) material.dispersion = json.dispersion;
45882
46110
  if ( json.iridescence !== undefined ) material.iridescence = json.iridescence;
45883
46111
  if ( json.iridescenceIOR !== undefined ) material.iridescenceIOR = json.iridescenceIOR;
45884
46112
  if ( json.iridescenceThicknessRange !== undefined ) material.iridescenceThicknessRange = json.iridescenceThicknessRange;