@plastic-software/three 0.167.4 → 0.174.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.
- package/LICENSE +1 -1
- package/README.md +1 -1
- package/build/three.cjs +36217 -23964
- package/build/three.core.js +48830 -0
- package/build/three.core.min.js +6 -0
- package/build/three.module.js +10175 -46744
- package/build/three.module.min.js +2 -3
- package/build/three.tsl.js +550 -0
- package/build/three.tsl.min.js +6 -0
- package/build/three.webgpu.js +44348 -50671
- package/build/three.webgpu.min.js +2 -3
- package/build/three.webgpu.nodes.js +70301 -0
- package/build/three.webgpu.nodes.min.js +6 -0
- package/examples/jsm/Addons.js +3 -15
- package/examples/jsm/animation/AnimationClipCreator.js +1 -1
- package/examples/jsm/animation/CCDIKSolver.js +61 -11
- package/examples/jsm/capabilities/WebGL.js +27 -21
- package/examples/jsm/capabilities/WebGPU.js +1 -10
- package/examples/jsm/controls/ArcballControls.js +262 -231
- package/examples/jsm/controls/DragControls.js +1 -1
- package/examples/jsm/controls/FirstPersonControls.js +175 -163
- package/examples/jsm/controls/FlyControls.js +194 -188
- package/examples/jsm/controls/OrbitControls.js +801 -777
- package/examples/jsm/controls/PointerLockControls.js +26 -20
- package/examples/jsm/controls/TrackballControls.js +469 -448
- package/examples/jsm/controls/TransformControls.js +119 -68
- package/examples/jsm/csm/CSM.js +2 -2
- package/examples/jsm/csm/CSMFrustum.js +7 -4
- package/examples/jsm/csm/CSMHelper.js +2 -0
- package/examples/jsm/csm/CSMShadowNode.js +442 -0
- package/examples/jsm/curves/NURBSCurve.js +33 -2
- package/examples/jsm/curves/NURBSUtils.js +3 -0
- package/examples/jsm/effects/AnaglyphEffect.js +6 -13
- package/examples/jsm/effects/OutlineEffect.js +1 -1
- package/examples/jsm/effects/ParallaxBarrierEffect.js +17 -11
- package/examples/jsm/effects/StereoEffect.js +6 -1
- package/examples/jsm/exporters/DRACOExporter.js +4 -2
- package/examples/jsm/exporters/EXRExporter.js +19 -11
- package/examples/jsm/exporters/GLTFExporter.js +181 -109
- package/examples/jsm/exporters/KTX2Exporter.js +54 -23
- package/examples/jsm/exporters/OBJExporter.js +5 -1
- package/examples/jsm/exporters/PLYExporter.js +11 -9
- package/examples/jsm/exporters/USDZExporter.js +50 -11
- package/examples/jsm/geometries/DecalGeometry.js +73 -21
- package/examples/jsm/geometries/TextGeometry.js +1 -12
- package/examples/jsm/helpers/LightProbeHelper.js +43 -44
- package/examples/jsm/helpers/LightProbeHelperGPU.js +65 -0
- package/examples/jsm/helpers/TextureHelperGPU.js +185 -0
- package/examples/jsm/helpers/VertexNormalsHelper.js +2 -0
- package/examples/jsm/interactive/HTMLMesh.js +1 -0
- package/examples/jsm/interactive/InteractiveGroup.js +108 -51
- package/examples/jsm/interactive/SelectionHelper.js +3 -1
- package/examples/jsm/libs/basis/basis_transcoder.js +8 -10
- package/examples/jsm/libs/basis/basis_transcoder.wasm +0 -0
- package/examples/jsm/libs/demuxer_mp4.js +109 -0
- package/examples/jsm/libs/ktx-parse.module.js +1 -1
- package/examples/jsm/lighting/TiledLighting.js +18 -0
- package/examples/jsm/lights/LightProbeGenerator.js +26 -12
- package/examples/jsm/lights/RectAreaLightTexturesLib.js +1 -1
- package/examples/jsm/lines/LineGeometry.js +25 -0
- package/examples/jsm/lines/LineMaterial.js +0 -1
- package/examples/jsm/lines/LineSegmentsGeometry.js +2 -0
- package/examples/jsm/lines/webgpu/Line2.js +2 -1
- package/examples/jsm/lines/webgpu/LineSegments2.js +16 -21
- package/examples/jsm/lines/webgpu/Wireframe.js +57 -0
- package/examples/jsm/loaders/3DMLoader.js +1 -0
- package/examples/jsm/loaders/3MFLoader.js +104 -2
- package/examples/jsm/loaders/BVHLoader.js +1 -1
- package/examples/jsm/loaders/ColladaLoader.js +15 -12
- package/examples/jsm/loaders/DDSLoader.js +42 -0
- package/examples/jsm/loaders/DRACOLoader.js +3 -1
- package/examples/jsm/loaders/FBXLoader.js +71 -22
- package/examples/jsm/loaders/GCodeLoader.js +4 -2
- package/examples/jsm/loaders/GLTFLoader.js +29 -14
- package/examples/jsm/loaders/KTX2Loader.js +160 -58
- package/examples/jsm/loaders/KTXLoader.js +4 -4
- package/examples/jsm/loaders/LDrawLoader.js +22 -136
- package/examples/jsm/loaders/LottieLoader.js +2 -1
- package/examples/jsm/loaders/MTLLoader.js +27 -7
- package/examples/jsm/loaders/MaterialXLoader.js +40 -14
- package/examples/jsm/loaders/NRRDLoader.js +1 -1
- package/examples/jsm/loaders/OBJLoader.js +5 -3
- package/examples/jsm/loaders/PCDLoader.js +14 -13
- package/examples/jsm/loaders/PDBLoader.js +3 -2
- package/examples/jsm/loaders/PLYLoader.js +15 -12
- package/examples/jsm/loaders/PVRLoader.js +1 -1
- package/examples/jsm/loaders/STLLoader.js +3 -2
- package/examples/jsm/loaders/SVGLoader.js +2 -2
- package/examples/jsm/loaders/TDSLoader.js +17 -18
- package/examples/jsm/loaders/VRMLLoader.js +17 -17
- package/examples/jsm/loaders/VTKLoader.js +4 -3
- package/examples/jsm/loaders/XYZLoader.js +3 -2
- package/examples/jsm/loaders/lwo/IFFParser.js +4 -4
- package/examples/jsm/materials/LDrawConditionalLineMaterial.js +143 -0
- package/examples/jsm/materials/LDrawConditionalLineNodeMaterial.js +114 -0
- package/examples/jsm/materials/MeshGouraudMaterial.js +2 -0
- package/examples/jsm/math/ColorSpaces.js +76 -0
- package/examples/jsm/math/ConvexHull.js +1 -1
- package/examples/jsm/math/OBB.js +17 -0
- package/examples/jsm/misc/GPUComputationRenderer.js +6 -7
- package/examples/jsm/misc/ProgressiveLightMap.js +54 -41
- package/examples/jsm/misc/ProgressiveLightMapGPU.js +294 -0
- package/examples/jsm/misc/Timer.js +27 -12
- package/examples/jsm/misc/Volume.js +28 -18
- package/examples/jsm/misc/VolumeSlice.js +19 -16
- package/examples/jsm/modifiers/CurveModifier.js +10 -8
- package/examples/jsm/modifiers/CurveModifierGPU.js +235 -0
- package/examples/jsm/modifiers/SimplifyModifier.js +2 -2
- package/examples/jsm/objects/GroundedSkybox.js +4 -4
- package/examples/jsm/objects/LensflareMesh.js +324 -0
- package/examples/jsm/objects/Reflector.js +5 -2
- package/examples/jsm/objects/Sky.js +2 -2
- package/examples/jsm/objects/SkyMesh.js +14 -14
- package/examples/jsm/objects/Water2.js +1 -1
- package/examples/jsm/objects/Water2Mesh.js +11 -9
- package/examples/jsm/objects/WaterMesh.js +38 -33
- package/examples/jsm/physics/JoltPhysics.js +8 -8
- package/examples/jsm/physics/RapierPhysics.js +5 -5
- package/examples/jsm/postprocessing/AfterimagePass.js +14 -3
- package/examples/jsm/postprocessing/BloomPass.js +2 -2
- package/examples/jsm/postprocessing/EffectComposer.js +1 -2
- package/examples/jsm/postprocessing/OutlinePass.js +37 -51
- package/examples/jsm/postprocessing/OutputPass.js +2 -0
- package/examples/jsm/postprocessing/SAOPass.js +1 -2
- package/examples/jsm/postprocessing/SMAAPass.js +1 -3
- package/examples/jsm/postprocessing/SSAARenderPass.js +3 -1
- package/examples/jsm/postprocessing/SSAOPass.js +2 -4
- package/examples/jsm/postprocessing/SSRPass.js +8 -4
- package/examples/jsm/postprocessing/UnrealBloomPass.js +2 -2
- package/examples/jsm/renderers/CSS2DRenderer.js +6 -3
- package/examples/jsm/renderers/CSS3DRenderer.js +7 -4
- package/examples/jsm/renderers/SVGRenderer.js +6 -4
- package/examples/jsm/shaders/BokehShader2.js +1 -1
- package/examples/jsm/shaders/FXAAShader.js +225 -224
- package/examples/jsm/shaders/GodRaysShader.js +3 -3
- package/examples/jsm/shaders/OutputShader.js +6 -2
- package/examples/jsm/shaders/SobelOperatorShader.js +1 -1
- package/examples/jsm/transpiler/AST.js +12 -2
- package/examples/jsm/transpiler/GLSLDecoder.js +77 -31
- package/examples/jsm/transpiler/ShaderToyDecoder.js +3 -3
- package/examples/jsm/transpiler/TSLEncoder.js +96 -21
- package/examples/jsm/tsl/display/AfterImageNode.js +243 -0
- package/examples/jsm/tsl/display/AnaglyphPassNode.js +106 -0
- package/examples/jsm/tsl/display/AnamorphicNode.js +257 -0
- package/{src/nodes/display/BleachBypassNode.js → examples/jsm/tsl/display/BleachBypass.js} +11 -6
- package/{src/nodes → examples/jsm/tsl}/display/BloomNode.js +252 -67
- package/examples/jsm/tsl/display/DenoiseNode.js +332 -0
- package/{src/nodes → examples/jsm/tsl}/display/DepthOfFieldNode.js +92 -14
- package/examples/jsm/tsl/display/DotScreenNode.js +103 -0
- package/examples/jsm/tsl/display/FXAANode.js +364 -0
- package/examples/jsm/tsl/display/FilmNode.js +100 -0
- package/examples/jsm/tsl/display/GTAONode.js +521 -0
- package/examples/jsm/tsl/display/GaussianBlurNode.js +393 -0
- package/examples/jsm/tsl/display/LensflareNode.js +278 -0
- package/examples/jsm/tsl/display/Lut3DNode.js +108 -0
- package/examples/jsm/tsl/display/MotionBlur.js +33 -0
- package/examples/jsm/tsl/display/OutlineNode.js +750 -0
- package/examples/jsm/tsl/display/ParallaxBarrierPassNode.js +88 -0
- package/{src/nodes → examples/jsm/tsl}/display/PixelationPassNode.js +160 -28
- package/examples/jsm/tsl/display/RGBShiftNode.js +95 -0
- package/examples/jsm/tsl/display/SMAANode.js +767 -0
- package/examples/jsm/tsl/display/SSAAPassNode.js +357 -0
- package/examples/jsm/tsl/display/SSRNode.js +538 -0
- package/examples/jsm/tsl/display/Sepia.js +24 -0
- package/{src/nodes → examples/jsm/tsl}/display/SobelOperatorNode.js +66 -20
- package/examples/jsm/tsl/display/StereoCompositePassNode.js +184 -0
- package/examples/jsm/tsl/display/StereoPassNode.js +119 -0
- package/examples/jsm/tsl/display/TRAAPassNode.js +451 -0
- package/examples/jsm/tsl/display/TransitionNode.js +140 -0
- package/examples/jsm/tsl/display/hashBlur.js +34 -0
- package/examples/jsm/tsl/lighting/TiledLightsNode.js +395 -0
- package/examples/jsm/tsl/math/Bayer.js +18 -0
- package/examples/jsm/tsl/utils/Raymarching.js +65 -0
- package/examples/jsm/utils/BufferGeometryUtils.js +2 -2
- package/examples/jsm/utils/CameraUtils.js +4 -1
- package/examples/jsm/utils/GeometryCompressionUtils.js +38 -123
- package/examples/jsm/utils/GeometryUtils.js +22 -19
- package/examples/jsm/utils/SceneOptimizer.js +410 -0
- package/examples/jsm/utils/SceneUtils.js +2 -2
- package/examples/jsm/utils/ShadowMapViewer.js +3 -8
- package/examples/jsm/utils/ShadowMapViewerGPU.js +201 -0
- package/examples/jsm/utils/SkeletonUtils.js +84 -66
- package/examples/jsm/utils/UVsDebug.js +1 -1
- package/examples/jsm/utils/{TextureUtils.js → WebGLTextureUtils.js} +1 -0
- package/examples/jsm/utils/WebGPUTextureUtils.js +64 -0
- package/examples/jsm/webxr/OculusHandPointerModel.js +21 -21
- package/examples/jsm/webxr/Text2D.js +6 -6
- package/examples/jsm/webxr/XRControllerModelFactory.js +7 -2
- package/examples/jsm/webxr/XREstimatedLight.js +1 -1
- package/package.json +14 -9
- package/src/Three.Core.js +182 -0
- package/src/Three.Legacy.js +0 -21
- package/src/Three.TSL.js +543 -0
- package/src/Three.WebGPU.Nodes.js +23 -0
- package/src/Three.WebGPU.js +13 -184
- package/src/Three.js +1 -176
- package/src/animation/AnimationClip.js +2 -2
- package/src/animation/AnimationObjectGroup.js +2 -2
- package/src/animation/AnimationUtils.js +1 -1
- package/src/animation/PropertyBinding.js +2 -2
- package/src/audio/Audio.js +379 -2
- package/src/audio/AudioAnalyser.js +58 -1
- package/src/audio/AudioContext.js +15 -0
- package/src/audio/AudioListener.js +76 -0
- package/src/audio/PositionalAudio.js +107 -0
- package/src/cameras/ArrayCamera.js +29 -0
- package/src/cameras/Camera.js +47 -0
- package/src/cameras/CubeCamera.js +66 -0
- package/src/cameras/OrthographicCamera.js +109 -0
- package/src/cameras/PerspectiveCamera.js +173 -34
- package/src/cameras/StereoCamera.js +48 -2
- package/src/constants.js +6 -6
- package/src/core/BufferAttribute.js +4 -9
- package/src/core/BufferGeometry.js +48 -8
- package/src/core/Clock.js +1 -1
- package/src/core/EventDispatcher.js +52 -8
- package/src/core/InterleavedBuffer.js +4 -13
- package/src/core/Object3D.js +573 -3
- package/src/core/RenderTarget.js +22 -4
- package/src/core/RenderTarget3D.js +22 -0
- package/src/core/RenderTargetArray.js +22 -0
- package/src/extras/Controls.js +104 -0
- package/src/extras/DataUtils.js +48 -8
- package/src/extras/Earcut.js +18 -7
- package/src/extras/ImageUtils.js +18 -11
- package/src/extras/PMREMGenerator.js +40 -9
- package/src/extras/ShapeUtils.js +24 -2
- package/src/extras/TextureUtils.js +96 -10
- package/src/extras/core/Curve.js +153 -53
- package/src/extras/core/CurvePath.js +63 -22
- package/src/extras/core/Interpolations.js +29 -3
- package/src/extras/core/Path.js +134 -1
- package/src/extras/core/Shape.js +66 -3
- package/src/extras/core/ShapePath.js +76 -0
- package/src/extras/curves/ArcCurve.js +22 -0
- package/src/extras/curves/CatmullRomCurve3.js +89 -18
- package/src/extras/curves/CubicBezierCurve.js +67 -0
- package/src/extras/curves/CubicBezierCurve3.js +50 -0
- package/src/extras/curves/EllipseCurve.js +102 -0
- package/src/extras/curves/LineCurve.js +36 -0
- package/src/extras/curves/LineCurve3.js +36 -0
- package/src/extras/curves/QuadraticBezierCurve.js +59 -0
- package/src/extras/curves/QuadraticBezierCurve3.js +43 -0
- package/src/extras/curves/SplineCurve.js +48 -0
- package/src/geometries/BoxGeometry.js +38 -0
- package/src/geometries/CapsuleGeometry.js +34 -0
- package/src/geometries/CircleGeometry.js +40 -0
- package/src/geometries/ConeGeometry.js +38 -0
- package/src/geometries/CylinderGeometry.js +50 -4
- package/src/geometries/DodecahedronGeometry.js +32 -0
- package/src/geometries/EdgesGeometry.js +30 -2
- package/src/geometries/ExtrudeGeometry.js +52 -0
- package/src/geometries/IcosahedronGeometry.js +32 -0
- package/src/geometries/LatheGeometry.js +43 -3
- package/src/geometries/OctahedronGeometry.js +32 -0
- package/src/geometries/PlaneGeometry.js +34 -0
- package/src/geometries/PolyhedronGeometry.js +29 -0
- package/src/geometries/RingGeometry.js +36 -0
- package/src/geometries/ShapeGeometry.js +37 -0
- package/src/geometries/SphereGeometry.js +37 -0
- package/src/geometries/TetrahedronGeometry.js +32 -0
- package/src/geometries/TorusGeometry.js +35 -0
- package/src/geometries/TorusKnotGeometry.js +38 -0
- package/src/geometries/TubeGeometry.js +49 -0
- package/src/geometries/WireframeGeometry.js +32 -0
- package/src/helpers/ArrowHelper.js +60 -3
- package/src/helpers/AxesHelper.js +28 -0
- package/src/helpers/Box3Helper.js +28 -0
- package/src/helpers/BoxHelper.js +43 -7
- package/src/helpers/CameraHelper.js +61 -18
- package/src/helpers/DirectionalLightHelper.js +52 -0
- package/src/helpers/GridHelper.js +26 -0
- package/src/helpers/HemisphereLightHelper.js +39 -0
- package/src/helpers/PlaneHelper.js +33 -0
- package/src/helpers/PointLightHelper.js +43 -0
- package/src/helpers/PolarGridHelper.js +30 -0
- package/src/helpers/SkeletonHelper.js +39 -2
- package/src/helpers/SpotLightHelper.js +40 -0
- package/src/lights/AmbientLight.js +25 -0
- package/src/lights/DirectionalLight.js +57 -0
- package/src/lights/DirectionalLightShadow.js +15 -0
- package/src/lights/HemisphereLight.js +32 -0
- package/src/lights/Light.js +36 -0
- package/src/lights/LightProbe.js +43 -0
- package/src/lights/LightShadow.js +159 -0
- package/src/lights/PointLight.js +59 -0
- package/src/lights/PointLightShadow.js +21 -0
- package/src/lights/RectAreaLight.js +59 -0
- package/src/lights/SpotLight.js +102 -0
- package/src/lights/SpotLightShadow.js +24 -2
- package/src/lights/webgpu/IESSpotLight.js +21 -0
- package/src/loaders/Loader.js +132 -0
- package/src/loaders/MaterialLoader.js +7 -1
- package/src/loaders/nodes/NodeLoader.js +189 -0
- package/src/loaders/nodes/NodeMaterialLoader.js +108 -0
- package/src/loaders/nodes/NodeObjectLoader.js +151 -0
- package/src/materials/LineDashedMaterial.js +0 -1
- package/src/materials/Material.js +469 -7
- package/src/materials/MeshPhongMaterial.js +1 -1
- package/src/materials/MeshPhysicalMaterial.js +2 -2
- package/src/materials/MeshStandardMaterial.js +2 -2
- package/src/{nodes/materials → materials/nodes}/Line2NodeMaterial.js +192 -82
- package/src/materials/nodes/LineBasicNodeMaterial.js +46 -0
- package/src/materials/nodes/LineDashedNodeMaterial.js +132 -0
- package/src/materials/nodes/MeshBasicNodeMaterial.js +133 -0
- package/src/materials/nodes/MeshLambertNodeMaterial.js +82 -0
- package/src/materials/nodes/MeshMatcapNodeMaterial.js +77 -0
- package/src/materials/nodes/MeshNormalNodeMaterial.js +67 -0
- package/src/materials/nodes/MeshPhongNodeMaterial.js +141 -0
- package/src/materials/nodes/MeshPhysicalNodeMaterial.js +517 -0
- package/src/materials/nodes/MeshSSSNodeMaterial.js +175 -0
- package/src/materials/nodes/MeshStandardNodeMaterial.js +186 -0
- package/src/materials/nodes/MeshToonNodeMaterial.js +66 -0
- package/src/materials/nodes/NodeMaterial.js +1180 -0
- package/src/{nodes/materials/Materials.js → materials/nodes/NodeMaterials.js} +3 -2
- package/src/materials/nodes/PointsNodeMaterial.js +153 -0
- package/src/materials/nodes/ShadowNodeMaterial.js +67 -0
- package/src/materials/nodes/SpriteNodeMaterial.js +198 -0
- package/src/materials/nodes/VolumeNodeMaterial.js +72 -0
- package/src/materials/nodes/manager/NodeMaterialObserver.js +509 -0
- package/src/math/Box2.js +177 -0
- package/src/math/Box3.js +243 -0
- package/src/math/Color.js +343 -0
- package/src/math/ColorManagement.js +143 -102
- package/src/math/Cylindrical.js +65 -6
- package/src/math/Euler.js +137 -4
- package/src/math/Frustum.js +83 -0
- package/src/math/Interpolant.js +87 -8
- package/src/math/Line3.js +96 -2
- package/src/math/MathUtils.js +182 -19
- package/src/math/Matrix2.js +70 -0
- package/src/math/Matrix3.js +229 -4
- package/src/math/Matrix4.js +368 -3
- package/src/math/Plane.js +164 -2
- package/src/math/Quaternion.js +265 -9
- package/src/math/Ray.js +160 -0
- package/src/math/Sphere.js +147 -0
- package/src/math/Spherical.js +73 -11
- package/src/math/SphericalHarmonics3.js +112 -14
- package/src/math/Triangle.js +230 -2
- package/src/math/Vector2.js +396 -10
- package/src/math/Vector3.js +550 -13
- package/src/math/Vector4.js +415 -9
- package/src/math/interpolants/CubicInterpolant.js +10 -1
- package/src/math/interpolants/DiscreteInterpolant.js +10 -2
- package/src/math/interpolants/LinearInterpolant.js +13 -0
- package/src/math/interpolants/QuaternionLinearInterpolant.js +10 -1
- package/src/nodes/Nodes.js +84 -166
- package/src/nodes/TSL.js +167 -0
- package/src/nodes/accessors/AccessorsUtils.js +39 -10
- package/src/nodes/accessors/Arrays.js +68 -0
- package/src/nodes/accessors/BatchNode.js +93 -26
- package/src/nodes/accessors/Bitangent.js +54 -0
- package/src/nodes/accessors/BufferAttributeNode.js +189 -11
- package/src/nodes/accessors/BufferNode.js +70 -5
- package/src/nodes/accessors/BuiltinNode.js +63 -0
- package/src/nodes/accessors/Camera.js +129 -0
- package/src/nodes/accessors/ClippingNode.js +152 -43
- package/src/nodes/accessors/CubeTextureNode.js +76 -13
- package/src/nodes/accessors/InstanceNode.js +118 -35
- package/src/nodes/accessors/InstancedMeshNode.js +50 -0
- package/src/nodes/accessors/Lights.js +129 -0
- package/src/nodes/accessors/MaterialNode.js +394 -58
- package/src/nodes/accessors/MaterialProperties.js +57 -1
- package/src/nodes/accessors/MaterialReferenceNode.js +60 -18
- package/src/nodes/accessors/ModelNode.js +159 -12
- package/src/nodes/accessors/ModelViewProjectionNode.js +10 -36
- package/src/nodes/accessors/MorphNode.js +60 -13
- package/src/nodes/accessors/Normal.js +156 -0
- package/src/nodes/accessors/Object3DNode.js +154 -35
- package/src/nodes/accessors/PointUVNode.js +35 -6
- package/src/nodes/accessors/Position.js +64 -0
- package/src/nodes/accessors/ReferenceBaseNode.js +357 -0
- package/src/nodes/accessors/ReferenceNode.js +243 -6
- package/src/nodes/accessors/ReflectVector.js +36 -0
- package/src/nodes/accessors/RendererReferenceNode.js +57 -7
- package/src/nodes/accessors/SceneNode.js +98 -6
- package/src/nodes/accessors/SkinningNode.js +214 -21
- package/src/nodes/accessors/StorageBufferNode.js +288 -28
- package/src/nodes/accessors/StorageTextureNode.js +139 -12
- package/src/nodes/accessors/Tangent.js +62 -0
- package/src/nodes/accessors/Texture3DNode.js +98 -12
- package/src/nodes/accessors/{TextureBicubicNode.js → TextureBicubic.js} +14 -34
- package/src/nodes/accessors/TextureNode.js +347 -34
- package/src/nodes/accessors/TextureSizeNode.js +51 -9
- package/src/nodes/accessors/UV.js +11 -0
- package/src/nodes/accessors/UniformArrayNode.js +241 -32
- package/src/nodes/accessors/UserDataNode.js +55 -7
- package/src/nodes/accessors/VelocityNode.js +223 -0
- package/src/nodes/accessors/VertexColorNode.js +45 -6
- package/src/nodes/code/CodeNode.js +108 -8
- package/src/nodes/code/ExpressionNode.js +38 -7
- package/src/nodes/code/FunctionCallNode.js +62 -11
- package/src/nodes/code/FunctionNode.js +54 -24
- package/src/nodes/code/ScriptableNode.js +241 -17
- package/src/nodes/code/ScriptableValueNode.js +93 -8
- package/src/nodes/core/ArrayNode.js +142 -0
- package/src/nodes/core/AssignNode.js +60 -12
- package/src/nodes/core/AttributeNode.js +55 -22
- package/src/nodes/core/BypassNode.js +59 -11
- package/src/nodes/core/CacheNode.js +64 -10
- package/src/nodes/core/ConstNode.js +38 -3
- package/src/nodes/core/ContextNode.js +87 -12
- package/src/nodes/core/IndexNode.js +102 -10
- package/src/nodes/core/InputNode.js +55 -3
- package/src/nodes/core/LightingModel.js +65 -5
- package/src/nodes/core/MRTNode.js +81 -7
- package/src/nodes/core/Node.js +368 -50
- package/src/nodes/core/NodeAttribute.js +38 -0
- package/src/nodes/core/NodeBuilder.js +1317 -83
- package/src/nodes/core/NodeCache.js +41 -2
- package/src/nodes/core/NodeCode.js +31 -0
- package/src/nodes/core/NodeFrame.js +123 -2
- package/src/nodes/core/NodeFunction.js +46 -0
- package/src/nodes/core/NodeFunctionInput.js +44 -0
- package/src/nodes/core/NodeParser.js +11 -0
- package/src/nodes/core/NodeUniform.js +52 -0
- package/src/nodes/core/NodeUtils.js +226 -6
- package/src/nodes/core/NodeVar.js +47 -1
- package/src/nodes/core/NodeVarying.js +28 -0
- package/src/nodes/core/OutputStructNode.js +61 -17
- package/src/nodes/core/ParameterNode.js +34 -4
- package/src/nodes/core/PropertyNode.js +296 -32
- package/src/nodes/core/StackNode.js +108 -8
- package/src/nodes/core/StructNode.js +120 -0
- package/src/nodes/core/StructType.js +13 -0
- package/src/nodes/core/StructTypeNode.js +116 -9
- package/src/nodes/core/TempNode.js +37 -7
- package/src/nodes/core/UniformGroupNode.js +98 -17
- package/src/nodes/core/UniformNode.js +72 -4
- package/src/nodes/core/VarNode.js +170 -13
- package/src/nodes/core/VaryingNode.js +109 -8
- package/src/nodes/core/constants.js +40 -0
- package/src/nodes/display/BlendModes.js +193 -0
- package/src/nodes/display/BumpMapNode.js +47 -10
- package/src/nodes/display/ColorAdjustment.js +141 -0
- package/src/nodes/display/ColorSpaceFunctions.js +54 -0
- package/src/nodes/display/ColorSpaceNode.js +147 -68
- package/src/nodes/display/FrontFacingNode.js +39 -6
- package/src/nodes/display/NormalMapNode.js +55 -13
- package/src/nodes/display/PassNode.js +420 -19
- package/src/nodes/display/PosterizeNode.js +40 -7
- package/src/nodes/display/RenderOutputNode.js +81 -13
- package/src/nodes/display/ScreenNode.js +286 -0
- package/src/nodes/display/ToneMappingFunctions.js +242 -0
- package/src/nodes/display/ToneMappingNode.js +68 -175
- package/src/nodes/display/ToonOutlinePassNode.js +183 -0
- package/src/nodes/display/ViewportDepthNode.js +210 -36
- package/src/nodes/display/ViewportDepthTextureNode.js +32 -9
- package/src/nodes/display/ViewportSharedTextureNode.js +32 -9
- package/src/nodes/display/ViewportTextureNode.js +68 -11
- package/src/nodes/fog/Fog.js +113 -0
- package/src/nodes/functions/BSDF/BRDF_GGX.js +4 -4
- package/src/nodes/functions/BSDF/BRDF_Lambert.js +2 -2
- package/src/nodes/functions/BSDF/BRDF_Sheen.js +6 -6
- package/src/nodes/functions/BSDF/DFGApprox.js +2 -2
- package/src/nodes/functions/BSDF/D_GGX.js +2 -2
- package/src/nodes/functions/BSDF/D_GGX_Anisotropic.js +3 -3
- package/src/nodes/functions/BSDF/EnvironmentBRDF.js +2 -2
- package/src/nodes/functions/BSDF/F_Schlick.js +2 -2
- package/src/nodes/functions/BSDF/LTC.js +50 -6
- package/src/nodes/functions/BSDF/Schlick_to_F0.js +2 -2
- package/src/nodes/functions/BSDF/V_GGX_SmithCorrelated.js +2 -2
- package/src/nodes/functions/BSDF/V_GGX_SmithCorrelated_Anisotropic.js +2 -2
- package/src/nodes/functions/BasicLightingModel.js +27 -6
- package/src/nodes/functions/PhongLightingModel.js +38 -8
- package/src/nodes/functions/PhysicalLightingModel.js +215 -51
- package/src/nodes/functions/ShadowMaskModel.js +24 -1
- package/src/nodes/functions/ToonLightingModel.js +24 -5
- package/src/nodes/functions/VolumetricLightingModel.js +183 -0
- package/src/nodes/functions/material/getAlphaHashThreshold.js +68 -0
- package/src/nodes/functions/material/getGeometryRoughness.js +10 -4
- package/src/nodes/functions/material/getParallaxCorrectNormal.js +37 -0
- package/src/nodes/functions/material/getRoughness.js +2 -2
- package/src/nodes/functions/material/getShIrradianceAt.js +28 -0
- package/src/nodes/geometry/RangeNode.js +62 -7
- package/src/nodes/gpgpu/AtomicFunctionNode.js +280 -0
- package/src/nodes/gpgpu/BarrierNode.js +89 -0
- package/src/nodes/gpgpu/ComputeBuiltinNode.js +227 -0
- package/src/nodes/gpgpu/ComputeNode.js +124 -9
- package/src/nodes/gpgpu/WorkgroupInfoNode.js +208 -0
- package/src/nodes/lighting/AONode.js +24 -3
- package/src/nodes/lighting/AmbientLightNode.js +16 -8
- package/src/nodes/lighting/AnalyticLightNode.js +151 -231
- package/src/nodes/lighting/BasicEnvironmentNode.js +25 -3
- package/src/nodes/lighting/BasicLightMapNode.js +25 -5
- package/src/nodes/lighting/DirectionalLightNode.js +19 -20
- package/src/nodes/lighting/EnvironmentNode.js +34 -17
- package/src/nodes/lighting/HemisphereLightNode.js +42 -11
- package/src/nodes/lighting/IESSpotLightNode.js +18 -9
- package/src/nodes/lighting/IrradianceNode.js +23 -3
- package/src/nodes/lighting/LightProbeNode.js +29 -36
- package/src/nodes/lighting/LightUtils.js +12 -4
- package/src/nodes/lighting/LightingContextNode.js +70 -21
- package/src/nodes/lighting/LightingNode.js +22 -9
- package/src/nodes/lighting/LightsNode.js +309 -86
- package/src/nodes/lighting/PointLightNode.js +66 -32
- package/src/nodes/lighting/PointShadowNode.js +306 -0
- package/src/nodes/lighting/RectAreaLightNode.js +61 -25
- package/src/nodes/lighting/ShadowBaseNode.js +92 -0
- package/src/nodes/lighting/ShadowNode.js +812 -0
- package/src/nodes/lighting/SpotLightNode.js +73 -31
- package/src/nodes/materialx/MaterialXNodes.js +2 -2
- package/src/nodes/materialx/lib/mx_hsv.js +27 -22
- package/src/nodes/materialx/lib/mx_noise.js +70 -70
- package/src/nodes/materialx/lib/mx_transform_color.js +2 -2
- package/src/nodes/math/ConditionalNode.js +230 -0
- package/src/nodes/math/Hash.js +21 -0
- package/src/nodes/math/MathNode.js +812 -131
- package/src/nodes/math/MathUtils.js +47 -8
- package/src/nodes/math/OperatorNode.js +410 -66
- package/src/nodes/math/TriNoise3D.js +32 -32
- package/src/nodes/parsers/GLSLNodeFunction.js +16 -0
- package/src/nodes/parsers/GLSLNodeParser.js +11 -0
- package/src/nodes/pmrem/PMREMNode.js +188 -28
- package/src/nodes/pmrem/PMREMUtils.js +24 -24
- package/src/nodes/procedural/Checker.js +22 -0
- package/src/nodes/shapes/Shapes.js +32 -0
- package/src/nodes/tsl/TSLBase.js +31 -0
- package/src/nodes/{shadernode/ShaderNode.js → tsl/TSLCore.js} +114 -98
- package/src/nodes/utils/ArrayElementNode.js +45 -5
- package/src/nodes/utils/ConvertNode.js +39 -4
- package/src/nodes/utils/CubeMapNode.js +88 -8
- package/src/nodes/utils/Discard.js +24 -0
- package/src/nodes/utils/EquirectUVNode.js +39 -7
- package/src/nodes/utils/FlipNode.js +106 -0
- package/src/nodes/utils/FunctionOverloadingNode.js +61 -6
- package/src/nodes/utils/JoinNode.js +31 -3
- package/src/nodes/utils/LoopNode.js +95 -9
- package/src/nodes/utils/MatcapUVNode.js +27 -8
- package/src/nodes/utils/MaxMipLevelNode.js +57 -6
- package/src/nodes/utils/MemberNode.js +68 -0
- package/src/nodes/utils/Oscillators.js +41 -0
- package/src/nodes/utils/Packing.js +21 -0
- package/src/nodes/utils/PostProcessingUtils.js +95 -0
- package/src/nodes/utils/RTTNode.js +141 -9
- package/src/nodes/utils/ReflectorNode.js +295 -21
- package/src/nodes/utils/RemapNode.js +93 -10
- package/src/nodes/utils/RotateNode.js +48 -13
- package/src/nodes/utils/SetNode.js +50 -4
- package/src/nodes/utils/SplitNode.js +62 -6
- package/src/nodes/utils/SpriteSheetUVNode.js +56 -7
- package/src/nodes/utils/SpriteUtils.js +21 -5
- package/src/nodes/utils/StorageArrayElementNode.js +64 -12
- package/src/nodes/utils/Timer.js +73 -0
- package/src/nodes/utils/TriplanarTexturesNode.js +96 -10
- package/src/nodes/utils/UVUtils.js +27 -9
- package/src/nodes/utils/ViewportUtils.js +16 -4
- package/src/objects/BatchedMesh.js +808 -281
- package/src/objects/Bone.js +24 -0
- package/src/objects/ClippingGroup.js +68 -0
- package/src/objects/Group.js +24 -0
- package/src/objects/InstancedMesh.js +120 -2
- package/src/objects/LOD.js +120 -5
- package/src/objects/Line.js +89 -6
- package/src/objects/LineLoop.js +20 -0
- package/src/objects/LineSegments.js +18 -0
- package/src/objects/Mesh.js +82 -23
- package/src/objects/Points.js +62 -0
- package/src/objects/Skeleton.js +107 -2
- package/src/objects/SkinnedMesh.js +99 -5
- package/src/objects/Sprite.js +54 -0
- package/src/renderers/WebGLRenderer.js +274 -157
- package/src/renderers/common/Animation.js +109 -12
- package/src/renderers/common/Attributes.js +40 -0
- package/src/renderers/common/Backend.js +504 -44
- package/src/renderers/common/Background.js +67 -9
- package/src/renderers/common/BindGroup.js +45 -1
- package/src/renderers/common/Binding.js +35 -0
- package/src/renderers/common/Bindings.js +136 -19
- package/src/renderers/common/Buffer.js +49 -0
- package/src/renderers/common/BufferUtils.js +25 -0
- package/src/renderers/common/BundleGroup.js +83 -0
- package/src/renderers/common/ChainMap.js +45 -6
- package/src/renderers/common/ClippingContext.js +175 -80
- package/src/renderers/common/Color4.js +40 -0
- package/src/renderers/common/ComputePipeline.js +24 -0
- package/src/renderers/common/Constants.js +2 -1
- package/src/renderers/common/CubeRenderTarget.js +22 -3
- package/src/renderers/common/DataMap.js +37 -1
- package/src/renderers/common/Geometries.js +111 -14
- package/src/renderers/common/IndirectStorageBufferAttribute.js +38 -0
- package/src/renderers/common/Info.js +78 -35
- package/src/renderers/common/Lighting.js +73 -0
- package/src/renderers/common/Pipeline.js +22 -0
- package/src/renderers/common/Pipelines.js +148 -5
- package/src/renderers/common/PostProcessing.js +112 -11
- package/src/renderers/common/ProgrammableStage.js +60 -2
- package/src/renderers/common/QuadMesh.js +56 -5
- package/src/renderers/common/RenderBundle.js +14 -8
- package/src/renderers/common/RenderBundles.js +39 -10
- package/src/renderers/common/RenderContext.js +205 -7
- package/src/renderers/common/RenderContexts.js +59 -6
- package/src/renderers/common/RenderList.js +230 -21
- package/src/renderers/common/RenderLists.js +45 -6
- package/src/renderers/common/RenderObject.js +552 -41
- package/src/renderers/common/RenderObjects.js +118 -9
- package/src/renderers/common/RenderPipeline.js +24 -0
- package/src/renderers/common/Renderer.js +1537 -239
- package/src/renderers/common/RendererUtils.js +191 -0
- package/src/renderers/common/SampledTexture.js +132 -3
- package/src/renderers/common/Sampler.js +30 -0
- package/src/renderers/common/StorageBuffer.js +24 -0
- package/src/renderers/common/StorageBufferAttribute.js +31 -2
- package/src/renderers/common/StorageInstancedBufferAttribute.js +31 -2
- package/src/renderers/common/StorageTexture.js +38 -0
- package/src/renderers/common/Textures.js +142 -32
- package/src/renderers/common/TimestampQueryPool.js +98 -0
- package/src/renderers/common/Uniform.js +225 -3
- package/src/renderers/common/UniformBuffer.js +19 -0
- package/src/renderers/common/UniformsGroup.js +157 -6
- package/src/renderers/common/XRManager.js +1185 -0
- package/src/renderers/common/XRRenderTarget.js +74 -0
- package/src/renderers/common/extras/PMREMGenerator.js +211 -53
- package/src/renderers/common/nodes/NodeBuilderState.js +100 -6
- package/src/renderers/common/nodes/NodeLibrary.js +194 -0
- package/src/renderers/common/nodes/NodeSampledTexture.js +92 -4
- package/src/renderers/common/nodes/NodeSampler.js +28 -0
- package/src/renderers/common/nodes/NodeStorageBuffer.js +37 -3
- package/src/renderers/common/nodes/NodeUniform.js +285 -2
- package/src/renderers/common/nodes/NodeUniformBuffer.js +29 -0
- package/src/renderers/common/nodes/NodeUniformsGroup.js +31 -18
- package/src/renderers/common/nodes/Nodes.js +390 -70
- package/src/renderers/shaders/ShaderChunk/colorspace_pars_fragment.glsl.js +4 -24
- package/src/renderers/shaders/ShaderChunk/emissivemap_fragment.glsl.js +8 -0
- package/src/renderers/shaders/ShaderChunk/lights_physical_pars_fragment.glsl.js +2 -2
- package/src/renderers/shaders/ShaderChunk/map_fragment.glsl.js +2 -2
- package/src/renderers/shaders/ShaderChunk/tonemapping_pars_fragment.glsl.js +2 -2
- package/src/renderers/shaders/ShaderChunk/transmission_pars_fragment.glsl.js +7 -7
- package/src/renderers/shaders/ShaderLib/sprite.glsl.js +2 -4
- package/src/renderers/webgl/WebGLAttributes.js +45 -14
- package/src/renderers/webgl/WebGLBackground.js +24 -1
- package/src/renderers/webgl/WebGLBufferRenderer.js +2 -6
- package/src/renderers/webgl/WebGLCapabilities.js +2 -0
- package/src/renderers/webgl/WebGLGeometries.js +0 -28
- package/src/renderers/webgl/WebGLIndexedBufferRenderer.js +2 -6
- package/src/renderers/webgl/WebGLProgram.js +27 -29
- package/src/renderers/webgl/WebGLPrograms.js +24 -16
- package/src/renderers/webgl/WebGLState.js +68 -11
- package/src/renderers/webgl/WebGLTextures.js +49 -10
- package/src/renderers/webgl-fallback/WebGLBackend.js +1055 -238
- package/src/renderers/webgl-fallback/WebGLBufferRenderer.js +5 -10
- package/src/renderers/webgl-fallback/nodes/GLSLNodeBuilder.js +425 -48
- package/src/renderers/webgl-fallback/utils/WebGLAttributeUtils.js +64 -1
- package/src/renderers/webgl-fallback/utils/WebGLCapabilities.js +28 -0
- package/src/renderers/webgl-fallback/utils/WebGLExtensions.js +45 -0
- package/src/renderers/webgl-fallback/utils/WebGLState.js +419 -14
- package/src/renderers/webgl-fallback/utils/WebGLTextureUtils.js +281 -59
- package/src/renderers/webgl-fallback/utils/WebGLTimestampQueryPool.js +367 -0
- package/src/renderers/webgl-fallback/utils/WebGLUtils.js +43 -0
- package/src/renderers/webgpu/WebGPUBackend.js +816 -236
- package/src/renderers/webgpu/WebGPURenderer.Nodes.js +78 -0
- package/src/renderers/webgpu/WebGPURenderer.js +45 -6
- package/src/renderers/webgpu/nodes/BasicNodeLibrary.js +63 -0
- package/src/renderers/webgpu/nodes/StandardNodeLibrary.js +97 -0
- package/src/renderers/webgpu/nodes/WGSLNodeBuilder.js +954 -147
- package/src/renderers/webgpu/nodes/WGSLNodeFunction.js +29 -4
- package/src/renderers/webgpu/nodes/WGSLNodeParser.js +11 -0
- package/src/renderers/webgpu/utils/WebGPUAttributeUtils.js +147 -31
- package/src/renderers/webgpu/utils/WebGPUBindingUtils.js +213 -31
- package/src/renderers/webgpu/utils/WebGPUPipelineUtils.js +146 -28
- package/src/renderers/webgpu/utils/WebGPUTexturePassUtils.js +161 -7
- package/src/renderers/webgpu/utils/WebGPUTextureUtils.js +333 -50
- package/src/renderers/webgpu/utils/WebGPUTimestampQueryPool.js +287 -0
- package/src/renderers/webgpu/utils/WebGPUUtils.js +131 -3
- package/src/renderers/webxr/WebXRDepthSensing.js +1 -1
- package/src/renderers/webxr/WebXRManager.js +54 -32
- package/src/scenes/Fog.js +60 -0
- package/src/scenes/FogExp2.js +51 -0
- package/src/scenes/Scene.js +87 -0
- package/src/textures/Data3DTexture.js +2 -2
- package/src/textures/DepthTexture.js +2 -0
- package/src/textures/Source.js +2 -2
- package/src/textures/Texture.js +368 -5
- package/src/textures/VideoFrameTexture.js +35 -0
- package/src/utils.js +33 -1
- package/examples/jsm/animation/MMDAnimationHelper.js +0 -1207
- package/examples/jsm/animation/MMDPhysics.js +0 -1406
- package/examples/jsm/cameras/CinematicCamera.js +0 -208
- package/examples/jsm/controls/Controls.js +0 -32
- package/examples/jsm/exporters/MMDExporter.js +0 -217
- package/examples/jsm/geometries/InstancedPointsGeometry.js +0 -174
- package/examples/jsm/geometries/SDFGeometryGenerator.js +0 -144
- package/examples/jsm/libs/mmdparser.module.js +0 -11530
- package/examples/jsm/loaders/LogLuvLoader.js +0 -606
- package/examples/jsm/loaders/MMDLoader.js +0 -2295
- package/examples/jsm/loaders/TiltLoader.js +0 -520
- package/examples/jsm/objects/InstancedPoints.js +0 -21
- package/examples/jsm/shaders/MMDToonShader.js +0 -134
- package/examples/jsm/utils/GPUStatsPanel.js +0 -95
- package/examples/jsm/utils/PackedPhongMaterial.js +0 -178
- package/src/nodes/accessors/BitangentNode.js +0 -13
- package/src/nodes/accessors/CameraNode.js +0 -19
- package/src/nodes/accessors/InstancedPointsMaterialNode.js +0 -21
- package/src/nodes/accessors/NormalNode.js +0 -14
- package/src/nodes/accessors/PositionNode.js +0 -10
- package/src/nodes/accessors/ReflectVectorNode.js +0 -10
- package/src/nodes/accessors/TangentNode.js +0 -23
- package/src/nodes/accessors/UVNode.js +0 -3
- package/src/nodes/core/NodeKeywords.js +0 -80
- package/src/nodes/core/UniformGroup.js +0 -13
- package/src/nodes/display/AfterImageNode.js +0 -152
- package/src/nodes/display/AnamorphicNode.js +0 -145
- package/src/nodes/display/BlendModeNode.js +0 -128
- package/src/nodes/display/ColorAdjustmentNode.js +0 -104
- package/src/nodes/display/DenoiseNode.js +0 -198
- package/src/nodes/display/DotScreenNode.js +0 -75
- package/src/nodes/display/FXAANode.js +0 -327
- package/src/nodes/display/FilmNode.js +0 -52
- package/src/nodes/display/GTAONode.js +0 -324
- package/src/nodes/display/GaussianBlurNode.js +0 -207
- package/src/nodes/display/Lut3DNode.js +0 -53
- package/src/nodes/display/RGBShiftNode.js +0 -49
- package/src/nodes/display/SepiaNode.js +0 -18
- package/src/nodes/display/TransitionNode.js +0 -76
- package/src/nodes/display/ViewportNode.js +0 -137
- package/src/nodes/fog/FogExp2Node.js +0 -34
- package/src/nodes/fog/FogNode.js +0 -48
- package/src/nodes/fog/FogRangeNode.js +0 -35
- package/src/nodes/lighting/LightNode.js +0 -57
- package/src/nodes/loaders/NodeLoader.js +0 -110
- package/src/nodes/loaders/NodeMaterialLoader.js +0 -60
- package/src/nodes/loaders/NodeObjectLoader.js +0 -71
- package/src/nodes/materials/InstancedPointsNodeMaterial.js +0 -162
- package/src/nodes/materials/LineBasicNodeMaterial.js +0 -28
- package/src/nodes/materials/LineDashedNodeMaterial.js +0 -55
- package/src/nodes/materials/MeshBasicNodeMaterial.js +0 -73
- package/src/nodes/materials/MeshLambertNodeMaterial.js +0 -43
- package/src/nodes/materials/MeshMatcapNodeMaterial.js +0 -53
- package/src/nodes/materials/MeshNormalNodeMaterial.js +0 -40
- package/src/nodes/materials/MeshPhongNodeMaterial.js +0 -74
- package/src/nodes/materials/MeshPhysicalNodeMaterial.js +0 -244
- package/src/nodes/materials/MeshSSSNodeMaterial.js +0 -84
- package/src/nodes/materials/MeshStandardNodeMaterial.js +0 -104
- package/src/nodes/materials/MeshToonNodeMaterial.js +0 -34
- package/src/nodes/materials/NodeMaterial.js +0 -680
- package/src/nodes/materials/PointsNodeMaterial.js +0 -39
- package/src/nodes/materials/ShadowNodeMaterial.js +0 -34
- package/src/nodes/materials/SpriteNodeMaterial.js +0 -90
- package/src/nodes/materials/VolumeNodeMaterial.js +0 -106
- package/src/nodes/math/CondNode.js +0 -139
- package/src/nodes/math/HashNode.js +0 -34
- package/src/nodes/procedural/CheckerNode.js +0 -42
- package/src/nodes/utils/DiscardNode.js +0 -28
- package/src/nodes/utils/OscNode.js +0 -81
- package/src/nodes/utils/PackingNode.js +0 -55
- package/src/nodes/utils/TimerNode.js +0 -94
|
@@ -13,19 +13,205 @@ import { WebGLBufferRenderer } from './WebGLBufferRenderer.js';
|
|
|
13
13
|
|
|
14
14
|
import { warnOnce } from '../../utils.js';
|
|
15
15
|
import { WebGLCoordinateSystem } from '../../constants.js';
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
16
|
+
import WebGLTimestampQueryPool from './utils/WebGLTimestampQueryPool.js';
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* A backend implementation targeting WebGL 2.
|
|
20
|
+
*
|
|
21
|
+
* @private
|
|
22
|
+
* @augments Backend
|
|
23
|
+
*/
|
|
19
24
|
class WebGLBackend extends Backend {
|
|
20
25
|
|
|
26
|
+
/**
|
|
27
|
+
* Constructs a new WebGPU backend.
|
|
28
|
+
*
|
|
29
|
+
* @param {Object} parameters - The configuration parameter.
|
|
30
|
+
* @param {boolean} [parameters.logarithmicDepthBuffer=false] - Whether logarithmic depth buffer is enabled or not.
|
|
31
|
+
* @param {boolean} [parameters.alpha=true] - Whether the default framebuffer (which represents the final contents of the canvas) should be transparent or opaque.
|
|
32
|
+
* @param {boolean} [parameters.depth=true] - Whether the default framebuffer should have a depth buffer or not.
|
|
33
|
+
* @param {boolean} [parameters.stencil=false] - Whether the default framebuffer should have a stencil buffer or not.
|
|
34
|
+
* @param {boolean} [parameters.antialias=false] - Whether MSAA as the default anti-aliasing should be enabled or not.
|
|
35
|
+
* @param {number} [parameters.samples=0] - When `antialias` is `true`, `4` samples are used by default. Set this parameter to any other integer value than 0 to overwrite the default.
|
|
36
|
+
* @param {boolean} [parameters.forceWebGL=false] - If set to `true`, the renderer uses a WebGL 2 backend no matter if WebGPU is supported or not.
|
|
37
|
+
* @param {WebGL2RenderingContext} [parameters.context=undefined] - A WebGL 2 rendering context.
|
|
38
|
+
*/
|
|
21
39
|
constructor( parameters = {} ) {
|
|
22
40
|
|
|
23
41
|
super( parameters );
|
|
24
42
|
|
|
43
|
+
/**
|
|
44
|
+
* This flag can be used for type testing.
|
|
45
|
+
*
|
|
46
|
+
* @type {boolean}
|
|
47
|
+
* @readonly
|
|
48
|
+
* @default true
|
|
49
|
+
*/
|
|
25
50
|
this.isWebGLBackend = true;
|
|
26
51
|
|
|
52
|
+
/**
|
|
53
|
+
* A reference to a backend module holding shader attribute-related
|
|
54
|
+
* utility functions.
|
|
55
|
+
*
|
|
56
|
+
* @type {?WebGLAttributeUtils}
|
|
57
|
+
* @default null
|
|
58
|
+
*/
|
|
59
|
+
this.attributeUtils = null;
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* A reference to a backend module holding extension-related
|
|
63
|
+
* utility functions.
|
|
64
|
+
*
|
|
65
|
+
* @type {?WebGLExtensions}
|
|
66
|
+
* @default null
|
|
67
|
+
*/
|
|
68
|
+
this.extensions = null;
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* A reference to a backend module holding capability-related
|
|
72
|
+
* utility functions.
|
|
73
|
+
*
|
|
74
|
+
* @type {?WebGLCapabilities}
|
|
75
|
+
* @default null
|
|
76
|
+
*/
|
|
77
|
+
this.capabilities = null;
|
|
78
|
+
|
|
79
|
+
/**
|
|
80
|
+
* A reference to a backend module holding texture-related
|
|
81
|
+
* utility functions.
|
|
82
|
+
*
|
|
83
|
+
* @type {?WebGLTextureUtils}
|
|
84
|
+
* @default null
|
|
85
|
+
*/
|
|
86
|
+
this.textureUtils = null;
|
|
87
|
+
|
|
88
|
+
/**
|
|
89
|
+
* A reference to a backend module holding renderer-related
|
|
90
|
+
* utility functions.
|
|
91
|
+
*
|
|
92
|
+
* @type {?WebGLBufferRenderer}
|
|
93
|
+
* @default null
|
|
94
|
+
*/
|
|
95
|
+
this.bufferRenderer = null;
|
|
96
|
+
|
|
97
|
+
/**
|
|
98
|
+
* A reference to the rendering context.
|
|
99
|
+
*
|
|
100
|
+
* @type {?WebGL2RenderingContext}
|
|
101
|
+
* @default null
|
|
102
|
+
*/
|
|
103
|
+
this.gl = null;
|
|
104
|
+
|
|
105
|
+
/**
|
|
106
|
+
* A reference to a backend module holding state-related
|
|
107
|
+
* utility functions.
|
|
108
|
+
*
|
|
109
|
+
* @type {?WebGLState}
|
|
110
|
+
* @default null
|
|
111
|
+
*/
|
|
112
|
+
this.state = null;
|
|
113
|
+
|
|
114
|
+
/**
|
|
115
|
+
* A reference to a backend module holding common
|
|
116
|
+
* utility functions.
|
|
117
|
+
*
|
|
118
|
+
* @type {?WebGLUtils}
|
|
119
|
+
* @default null
|
|
120
|
+
*/
|
|
121
|
+
this.utils = null;
|
|
122
|
+
|
|
123
|
+
/**
|
|
124
|
+
* Dictionary for caching VAOs.
|
|
125
|
+
*
|
|
126
|
+
* @type {Object<string,WebGLVertexArrayObject>}
|
|
127
|
+
*/
|
|
128
|
+
this.vaoCache = {};
|
|
129
|
+
|
|
130
|
+
/**
|
|
131
|
+
* Dictionary for caching transform feedback objects.
|
|
132
|
+
*
|
|
133
|
+
* @type {Object<string,WebGLTransformFeedback>}
|
|
134
|
+
*/
|
|
135
|
+
this.transformFeedbackCache = {};
|
|
136
|
+
|
|
137
|
+
/**
|
|
138
|
+
* Controls if `gl.RASTERIZER_DISCARD` should be enabled or not.
|
|
139
|
+
* Only relevant when using compute shaders.
|
|
140
|
+
*
|
|
141
|
+
* @type {boolean}
|
|
142
|
+
* @default false
|
|
143
|
+
*/
|
|
144
|
+
this.discard = false;
|
|
145
|
+
|
|
146
|
+
/**
|
|
147
|
+
* A reference to the `EXT_disjoint_timer_query_webgl2` extension. `null` if the
|
|
148
|
+
* device does not support the extension.
|
|
149
|
+
*
|
|
150
|
+
* @type {?EXTDisjointTimerQueryWebGL2}
|
|
151
|
+
* @default null
|
|
152
|
+
*/
|
|
153
|
+
this.disjoint = null;
|
|
154
|
+
|
|
155
|
+
/**
|
|
156
|
+
* A reference to the `KHR_parallel_shader_compile` extension. `null` if the
|
|
157
|
+
* device does not support the extension.
|
|
158
|
+
*
|
|
159
|
+
* @type {?KHRParallelShaderCompile}
|
|
160
|
+
* @default null
|
|
161
|
+
*/
|
|
162
|
+
this.parallel = null;
|
|
163
|
+
|
|
164
|
+
/**
|
|
165
|
+
* Whether to track timestamps with a Timestamp Query API or not.
|
|
166
|
+
*
|
|
167
|
+
* @type {boolean}
|
|
168
|
+
* @default false
|
|
169
|
+
*/
|
|
170
|
+
this.trackTimestamp = ( parameters.trackTimestamp === true );
|
|
171
|
+
|
|
172
|
+
/**
|
|
173
|
+
* A reference to the current render context.
|
|
174
|
+
*
|
|
175
|
+
* @private
|
|
176
|
+
* @type {RenderContext}
|
|
177
|
+
* @default null
|
|
178
|
+
*/
|
|
179
|
+
this._currentContext = null;
|
|
180
|
+
|
|
181
|
+
/**
|
|
182
|
+
* A unique collection of bindings.
|
|
183
|
+
*
|
|
184
|
+
* @private
|
|
185
|
+
* @type {WeakSet}
|
|
186
|
+
*/
|
|
187
|
+
this._knownBindings = new WeakSet();
|
|
188
|
+
|
|
189
|
+
|
|
190
|
+
/**
|
|
191
|
+
* Whether the device supports framebuffers invalidation or not.
|
|
192
|
+
*
|
|
193
|
+
* @private
|
|
194
|
+
* @type {boolean}
|
|
195
|
+
*/
|
|
196
|
+
this._supportsInvalidateFramebuffer = typeof navigator === 'undefined' ? false : /OculusBrowser/g.test( navigator.userAgent );
|
|
197
|
+
|
|
198
|
+
/**
|
|
199
|
+
* The target framebuffer when rendering with
|
|
200
|
+
* the WebXR device API.
|
|
201
|
+
*
|
|
202
|
+
* @private
|
|
203
|
+
* @type {WebGLFramebuffer}
|
|
204
|
+
* @default null
|
|
205
|
+
*/
|
|
206
|
+
this._xrFramebuffer = null;
|
|
207
|
+
|
|
27
208
|
}
|
|
28
209
|
|
|
210
|
+
/**
|
|
211
|
+
* Initializes the backend so it is ready for usage.
|
|
212
|
+
*
|
|
213
|
+
* @param {Renderer} renderer - The renderer.
|
|
214
|
+
*/
|
|
29
215
|
init( renderer ) {
|
|
30
216
|
|
|
31
217
|
super.init( renderer );
|
|
@@ -34,7 +220,33 @@ class WebGLBackend extends Backend {
|
|
|
34
220
|
|
|
35
221
|
const parameters = this.parameters;
|
|
36
222
|
|
|
37
|
-
const
|
|
223
|
+
const contextAttributes = {
|
|
224
|
+
antialias: renderer.samples > 0,
|
|
225
|
+
alpha: true, // always true for performance reasons
|
|
226
|
+
depth: renderer.depth,
|
|
227
|
+
stencil: renderer.stencil
|
|
228
|
+
};
|
|
229
|
+
|
|
230
|
+
const glContext = ( parameters.context !== undefined ) ? parameters.context : renderer.domElement.getContext( 'webgl2', contextAttributes );
|
|
231
|
+
|
|
232
|
+
function onContextLost( event ) {
|
|
233
|
+
|
|
234
|
+
event.preventDefault();
|
|
235
|
+
|
|
236
|
+
const contextLossInfo = {
|
|
237
|
+
api: 'WebGL',
|
|
238
|
+
message: event.statusMessage || 'Unknown reason',
|
|
239
|
+
reason: null,
|
|
240
|
+
originalEvent: event
|
|
241
|
+
};
|
|
242
|
+
|
|
243
|
+
renderer.onDeviceLost( contextLossInfo );
|
|
244
|
+
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
this._onContextLost = onContextLost;
|
|
248
|
+
|
|
249
|
+
renderer.domElement.addEventListener( 'webglcontextlost', onContextLost, false );
|
|
38
250
|
|
|
39
251
|
this.gl = glContext;
|
|
40
252
|
|
|
@@ -47,86 +259,114 @@ class WebGLBackend extends Backend {
|
|
|
47
259
|
this.state = new WebGLState( this );
|
|
48
260
|
this.utils = new WebGLUtils( this );
|
|
49
261
|
|
|
50
|
-
this.vaoCache = {};
|
|
51
|
-
this.transformFeedbackCache = {};
|
|
52
|
-
this.discard = false;
|
|
53
|
-
this.trackTimestamp = ( parameters.trackTimestamp === true );
|
|
54
|
-
|
|
55
262
|
this.extensions.get( 'EXT_color_buffer_float' );
|
|
263
|
+
this.extensions.get( 'WEBGL_clip_cull_distance' );
|
|
264
|
+
this.extensions.get( 'OES_texture_float_linear' );
|
|
265
|
+
this.extensions.get( 'EXT_color_buffer_half_float' );
|
|
266
|
+
this.extensions.get( 'WEBGL_multisampled_render_to_texture' );
|
|
267
|
+
this.extensions.get( 'WEBGL_render_shared_exponent' );
|
|
56
268
|
this.extensions.get( 'WEBGL_multi_draw' );
|
|
57
269
|
|
|
58
270
|
this.disjoint = this.extensions.get( 'EXT_disjoint_timer_query_webgl2' );
|
|
59
271
|
this.parallel = this.extensions.get( 'KHR_parallel_shader_compile' );
|
|
60
|
-
this._currentContext = null;
|
|
61
272
|
|
|
62
273
|
}
|
|
63
274
|
|
|
275
|
+
/**
|
|
276
|
+
* The coordinate system of the backend.
|
|
277
|
+
*
|
|
278
|
+
* @type {number}
|
|
279
|
+
* @readonly
|
|
280
|
+
*/
|
|
64
281
|
get coordinateSystem() {
|
|
65
282
|
|
|
66
283
|
return WebGLCoordinateSystem;
|
|
67
284
|
|
|
68
285
|
}
|
|
69
286
|
|
|
287
|
+
/**
|
|
288
|
+
* This method performs a readback operation by moving buffer data from
|
|
289
|
+
* a storage buffer attribute from the GPU to the CPU.
|
|
290
|
+
*
|
|
291
|
+
* @async
|
|
292
|
+
* @param {StorageBufferAttribute} attribute - The storage buffer attribute.
|
|
293
|
+
* @return {Promise<ArrayBuffer>} A promise that resolves with the buffer data when the data are ready.
|
|
294
|
+
*/
|
|
70
295
|
async getArrayBufferAsync( attribute ) {
|
|
71
296
|
|
|
72
297
|
return await this.attributeUtils.getArrayBufferAsync( attribute );
|
|
73
298
|
|
|
74
299
|
}
|
|
75
300
|
|
|
301
|
+
/**
|
|
302
|
+
* Can be used to synchronize CPU operations with GPU tasks. So when this method is called,
|
|
303
|
+
* the CPU waits for the GPU to complete its operation (e.g. a compute task).
|
|
304
|
+
*
|
|
305
|
+
* @async
|
|
306
|
+
* @return {Promise} A Promise that resolves when synchronization has been finished.
|
|
307
|
+
*/
|
|
308
|
+
async waitForGPU() {
|
|
76
309
|
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
if ( ! this.disjoint || ! this.trackTimestamp ) return;
|
|
310
|
+
await this.utils._clientWaitAsync();
|
|
80
311
|
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
if ( this.queryRunning ) {
|
|
312
|
+
}
|
|
84
313
|
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
314
|
+
/**
|
|
315
|
+
* Ensures the backend is XR compatible.
|
|
316
|
+
*
|
|
317
|
+
* @async
|
|
318
|
+
* @return {Promise} A Promise that resolve when the renderer is XR compatible.
|
|
319
|
+
*/
|
|
320
|
+
async makeXRCompatible() {
|
|
88
321
|
|
|
89
|
-
|
|
322
|
+
const attributes = this.gl.getContextAttributes();
|
|
90
323
|
|
|
91
|
-
if (
|
|
324
|
+
if ( attributes.xrCompatible !== true ) {
|
|
92
325
|
|
|
93
|
-
|
|
94
|
-
renderContextData.activeQuery = null;
|
|
326
|
+
await this.gl.makeXRCompatible();
|
|
95
327
|
|
|
96
328
|
}
|
|
97
329
|
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
330
|
+
}
|
|
331
|
+
/**
|
|
332
|
+
* Sets the XR rendering destination.
|
|
333
|
+
*
|
|
334
|
+
* @param {WebGLFramebuffer} xrFramebuffer - The XR framebuffer.
|
|
335
|
+
*/
|
|
336
|
+
setXRTarget( xrFramebuffer ) {
|
|
104
337
|
|
|
105
|
-
|
|
338
|
+
this._xrFramebuffer = xrFramebuffer;
|
|
106
339
|
|
|
107
340
|
}
|
|
108
341
|
|
|
109
|
-
|
|
342
|
+
/**
|
|
343
|
+
* Configures the given XR render target with external textures.
|
|
344
|
+
*
|
|
345
|
+
* This method is only relevant when using the WebXR Layers API.
|
|
346
|
+
*
|
|
347
|
+
* @param {XRRenderTarget} renderTarget - The XR render target.
|
|
348
|
+
* @param {WebGLTexture} colorTexture - A native color texture.
|
|
349
|
+
* @param {?WebGLTexture} [depthTexture=null] - A native depth texture.
|
|
350
|
+
*/
|
|
351
|
+
setXRRenderTargetTextures( renderTarget, colorTexture, depthTexture = null ) {
|
|
110
352
|
|
|
111
|
-
|
|
353
|
+
const gl = this.gl;
|
|
112
354
|
|
|
113
|
-
|
|
355
|
+
this.set( renderTarget.texture, { textureGPU: colorTexture, glInternalFormat: gl.RGBA8 } ); // see #24698 why RGBA8 and not SRGB8_ALPHA8 is used
|
|
114
356
|
|
|
115
|
-
|
|
357
|
+
if ( depthTexture !== null ) {
|
|
116
358
|
|
|
117
|
-
|
|
359
|
+
const glInternalFormat = renderTarget.stencilBuffer ? gl.DEPTH24_STENCIL8 : gl.DEPTH_COMPONENT24;
|
|
118
360
|
|
|
119
|
-
|
|
361
|
+
this.set( renderTarget.depthTexture, { textureGPU: depthTexture, glInternalFormat: glInternalFormat } );
|
|
120
362
|
|
|
121
|
-
|
|
122
|
-
renderContextData.gpuQueries.push( { query: renderContextData.activeQuery } );
|
|
123
|
-
renderContextData.activeQuery = null;
|
|
124
|
-
this.queryRunning = false;
|
|
363
|
+
renderTarget.autoAllocateDepthBuffer = false;
|
|
125
364
|
|
|
126
|
-
|
|
365
|
+
// The multisample_render_to_texture extension doesn't work properly if there
|
|
366
|
+
// are midframe flushes and an external depth texture.
|
|
367
|
+
if ( this.extensions.has( 'WEBGL_multisampled_render_to_texture' ) === true ) {
|
|
127
368
|
|
|
128
|
-
|
|
129
|
-
this.initTimestampQuery( nextRenderContext );
|
|
369
|
+
console.warn( 'THREE.WebGLBackend: Render-to-texture extension was disabled because an external texture was provided' );
|
|
130
370
|
|
|
131
371
|
}
|
|
132
372
|
|
|
@@ -134,67 +374,86 @@ class WebGLBackend extends Backend {
|
|
|
134
374
|
|
|
135
375
|
}
|
|
136
376
|
|
|
137
|
-
|
|
377
|
+
/**
|
|
378
|
+
* Inits a time stamp query for the given render context.
|
|
379
|
+
*
|
|
380
|
+
* @param {RenderContext} renderContext - The render context.
|
|
381
|
+
*/
|
|
382
|
+
initTimestampQuery( renderContext ) {
|
|
138
383
|
|
|
139
384
|
if ( ! this.disjoint || ! this.trackTimestamp ) return;
|
|
140
385
|
|
|
141
|
-
const
|
|
386
|
+
const type = renderContext.isComputeNode ? 'compute' : 'render';
|
|
142
387
|
|
|
143
|
-
if ( !
|
|
388
|
+
if ( ! this.timestampQueryPool[ type ] ) {
|
|
144
389
|
|
|
145
|
-
|
|
390
|
+
// TODO: Variable maxQueries?
|
|
391
|
+
this.timestampQueryPool[ type ] = new WebGLTimestampQueryPool( this.gl, type, 2048 );
|
|
146
392
|
|
|
147
|
-
|
|
148
|
-
const available = this.gl.getQueryParameter( queryInfo.query, this.gl.QUERY_RESULT_AVAILABLE );
|
|
149
|
-
const disjoint = this.gl.getParameter( this.disjoint.GPU_DISJOINT_EXT );
|
|
393
|
+
}
|
|
150
394
|
|
|
151
|
-
|
|
395
|
+
const timestampQueryPool = this.timestampQueryPool[ type ];
|
|
152
396
|
|
|
153
|
-
|
|
154
|
-
const duration = Number( elapsed ) / 1000000; // Convert nanoseconds to milliseconds
|
|
155
|
-
this.gl.deleteQuery( queryInfo.query );
|
|
156
|
-
renderContextData.gpuQueries.splice( i, 1 ); // Remove the processed query
|
|
157
|
-
i --;
|
|
158
|
-
this.renderer.info.updateTimestamp( type, duration );
|
|
397
|
+
const baseOffset = timestampQueryPool.allocateQueriesForContext( renderContext );
|
|
159
398
|
|
|
160
|
-
|
|
399
|
+
if ( baseOffset !== null ) {
|
|
400
|
+
|
|
401
|
+
timestampQueryPool.beginQuery( renderContext );
|
|
161
402
|
|
|
162
403
|
}
|
|
163
404
|
|
|
164
405
|
}
|
|
165
406
|
|
|
166
|
-
|
|
407
|
+
// timestamp utils
|
|
167
408
|
|
|
168
|
-
|
|
409
|
+
/**
|
|
410
|
+
* Prepares the timestamp buffer.
|
|
411
|
+
*
|
|
412
|
+
* @param {RenderContext} renderContext - The render context.
|
|
413
|
+
*/
|
|
414
|
+
prepareTimestampBuffer( renderContext ) {
|
|
169
415
|
|
|
170
|
-
|
|
416
|
+
if ( ! this.disjoint || ! this.trackTimestamp ) return;
|
|
171
417
|
|
|
172
|
-
|
|
418
|
+
const type = renderContext.isComputeNode ? 'compute' : 'render';
|
|
419
|
+
const timestampQueryPool = this.timestampQueryPool[ type ];
|
|
173
420
|
|
|
174
|
-
|
|
175
|
-
const renderContextData = this.get( renderContext );
|
|
421
|
+
timestampQueryPool.endQuery( renderContext );
|
|
176
422
|
|
|
177
|
-
|
|
423
|
+
}
|
|
178
424
|
|
|
179
|
-
//
|
|
180
425
|
|
|
181
|
-
|
|
426
|
+
/**
|
|
427
|
+
* Returns the backend's rendering context.
|
|
428
|
+
*
|
|
429
|
+
* @return {WebGL2RenderingContext} The rendering context.
|
|
430
|
+
*/
|
|
431
|
+
getContext() {
|
|
182
432
|
|
|
183
|
-
|
|
184
|
-
this._currentContext = renderContext;
|
|
433
|
+
return this.gl;
|
|
185
434
|
|
|
186
|
-
|
|
435
|
+
}
|
|
187
436
|
|
|
188
|
-
|
|
437
|
+
/**
|
|
438
|
+
* This method is executed at the beginning of a render call and prepares
|
|
439
|
+
* the WebGL state for upcoming render calls
|
|
440
|
+
*
|
|
441
|
+
* @param {RenderContext} renderContext - The render context.
|
|
442
|
+
*/
|
|
443
|
+
beginRender( renderContext ) {
|
|
444
|
+
|
|
445
|
+
const { state, gl } = this;
|
|
446
|
+
const renderContextData = this.get( renderContext );
|
|
189
447
|
|
|
190
448
|
//
|
|
449
|
+
|
|
191
450
|
if ( renderContext.viewport ) {
|
|
192
451
|
|
|
193
452
|
this.updateViewport( renderContext );
|
|
194
453
|
|
|
195
454
|
} else {
|
|
196
455
|
|
|
197
|
-
|
|
456
|
+
state.viewport( 0, 0, gl.drawingBufferWidth, gl.drawingBufferHeight );
|
|
198
457
|
|
|
199
458
|
}
|
|
200
459
|
|
|
@@ -202,10 +461,22 @@ class WebGLBackend extends Backend {
|
|
|
202
461
|
|
|
203
462
|
const { x, y, width, height } = renderContext.scissorValue;
|
|
204
463
|
|
|
205
|
-
|
|
464
|
+
state.scissor( x, renderContext.height - height - y, width, height );
|
|
206
465
|
|
|
207
466
|
}
|
|
208
467
|
|
|
468
|
+
//
|
|
469
|
+
|
|
470
|
+
this.initTimestampQuery( renderContext );
|
|
471
|
+
|
|
472
|
+
renderContextData.previousContext = this._currentContext;
|
|
473
|
+
this._currentContext = renderContext;
|
|
474
|
+
|
|
475
|
+
this._setFramebuffer( renderContext );
|
|
476
|
+
|
|
477
|
+
this.clear( renderContext.clearColor, renderContext.clearDepth, renderContext.clearStencil, renderContext, false );
|
|
478
|
+
|
|
479
|
+
|
|
209
480
|
const occlusionQueryCount = renderContext.occlusionQueryCount;
|
|
210
481
|
|
|
211
482
|
if ( occlusionQueryCount > 0 ) {
|
|
@@ -224,12 +495,34 @@ class WebGLBackend extends Backend {
|
|
|
224
495
|
|
|
225
496
|
}
|
|
226
497
|
|
|
498
|
+
/**
|
|
499
|
+
* This method is executed at the end of a render call and finalizes work
|
|
500
|
+
* after draw calls.
|
|
501
|
+
*
|
|
502
|
+
* @param {RenderContext} renderContext - The render context.
|
|
503
|
+
*/
|
|
227
504
|
finishRender( renderContext ) {
|
|
228
505
|
|
|
229
506
|
const { gl, state } = this;
|
|
230
507
|
const renderContextData = this.get( renderContext );
|
|
231
508
|
const previousContext = renderContextData.previousContext;
|
|
232
509
|
|
|
510
|
+
state.resetVertexState();
|
|
511
|
+
|
|
512
|
+
const occlusionQueryCount = renderContext.occlusionQueryCount;
|
|
513
|
+
|
|
514
|
+
if ( occlusionQueryCount > 0 ) {
|
|
515
|
+
|
|
516
|
+
if ( occlusionQueryCount > renderContextData.occlusionQueryIndex ) {
|
|
517
|
+
|
|
518
|
+
gl.endQuery( gl.ANY_SAMPLES_PASSED );
|
|
519
|
+
|
|
520
|
+
}
|
|
521
|
+
|
|
522
|
+
this.resolveOccludedAsync( renderContext );
|
|
523
|
+
|
|
524
|
+
}
|
|
525
|
+
|
|
233
526
|
const textures = renderContext.textures;
|
|
234
527
|
|
|
235
528
|
if ( textures !== null ) {
|
|
@@ -250,14 +543,13 @@ class WebGLBackend extends Backend {
|
|
|
250
543
|
|
|
251
544
|
this._currentContext = previousContext;
|
|
252
545
|
|
|
253
|
-
|
|
254
546
|
if ( renderContext.textures !== null && renderContext.renderTarget ) {
|
|
255
547
|
|
|
256
548
|
const renderTargetContextData = this.get( renderContext.renderTarget );
|
|
257
549
|
|
|
258
550
|
const { samples } = renderContext.renderTarget;
|
|
259
551
|
|
|
260
|
-
if ( samples > 0 ) {
|
|
552
|
+
if ( samples > 0 && this._useMultisampledRTT( renderContext.renderTarget ) === false ) {
|
|
261
553
|
|
|
262
554
|
const fb = renderTargetContextData.framebuffers[ renderContext.getCacheKey() ];
|
|
263
555
|
|
|
@@ -274,57 +566,66 @@ class WebGLBackend extends Backend {
|
|
|
274
566
|
|
|
275
567
|
// TODO Add support for MRT
|
|
276
568
|
|
|
277
|
-
|
|
569
|
+
if ( renderContext.scissor ) {
|
|
278
570
|
|
|
279
|
-
|
|
571
|
+
const { x, y, width, height } = renderContext.scissorValue;
|
|
280
572
|
|
|
281
|
-
|
|
573
|
+
const viewY = renderContext.height - height - y;
|
|
282
574
|
|
|
283
|
-
|
|
575
|
+
gl.blitFramebuffer( x, viewY, x + width, viewY + height, x, viewY, x + width, viewY + height, mask, gl.NEAREST );
|
|
284
576
|
|
|
577
|
+
if ( this._supportsInvalidateFramebuffer === true ) {
|
|
285
578
|
|
|
286
|
-
|
|
579
|
+
gl.invalidateSubFramebuffer( gl.READ_FRAMEBUFFER, renderTargetContextData.invalidationArray, x, viewY, width, height );
|
|
287
580
|
|
|
288
|
-
|
|
581
|
+
}
|
|
289
582
|
|
|
290
|
-
|
|
583
|
+
} else {
|
|
291
584
|
|
|
292
|
-
|
|
585
|
+
gl.blitFramebuffer( 0, 0, renderContext.width, renderContext.height, 0, 0, renderContext.width, renderContext.height, mask, gl.NEAREST );
|
|
293
586
|
|
|
294
|
-
|
|
587
|
+
if ( this._supportsInvalidateFramebuffer === true ) {
|
|
295
588
|
|
|
296
|
-
|
|
589
|
+
gl.invalidateFramebuffer( gl.READ_FRAMEBUFFER, renderTargetContextData.invalidationArray );
|
|
297
590
|
|
|
298
|
-
|
|
591
|
+
}
|
|
299
592
|
|
|
300
|
-
|
|
593
|
+
}
|
|
594
|
+
|
|
595
|
+
}
|
|
301
596
|
|
|
302
597
|
}
|
|
303
598
|
|
|
599
|
+
|
|
304
600
|
}
|
|
305
601
|
|
|
306
|
-
|
|
602
|
+
if ( previousContext !== null ) {
|
|
307
603
|
|
|
308
|
-
|
|
604
|
+
this._setFramebuffer( previousContext );
|
|
309
605
|
|
|
310
|
-
|
|
606
|
+
if ( previousContext.viewport ) {
|
|
311
607
|
|
|
312
|
-
|
|
608
|
+
this.updateViewport( previousContext );
|
|
313
609
|
|
|
314
|
-
|
|
610
|
+
} else {
|
|
315
611
|
|
|
316
|
-
|
|
612
|
+
state.viewport( 0, 0, gl.drawingBufferWidth, gl.drawingBufferHeight );
|
|
317
613
|
|
|
318
614
|
}
|
|
319
615
|
|
|
320
|
-
this.resolveOccludedAsync( renderContext );
|
|
321
|
-
|
|
322
616
|
}
|
|
323
617
|
|
|
324
618
|
this.prepareTimestampBuffer( renderContext );
|
|
325
619
|
|
|
326
620
|
}
|
|
327
621
|
|
|
622
|
+
/**
|
|
623
|
+
* This method processes the result of occlusion queries and writes it
|
|
624
|
+
* into render context data.
|
|
625
|
+
*
|
|
626
|
+
* @async
|
|
627
|
+
* @param {RenderContext} renderContext - The render context.
|
|
628
|
+
*/
|
|
328
629
|
resolveOccludedAsync( renderContext ) {
|
|
329
630
|
|
|
330
631
|
const renderContextData = this.get( renderContext );
|
|
@@ -354,7 +655,7 @@ class WebGLBackend extends Backend {
|
|
|
354
655
|
|
|
355
656
|
if ( gl.getQueryParameter( query, gl.QUERY_RESULT_AVAILABLE ) ) {
|
|
356
657
|
|
|
357
|
-
if ( gl.getQueryParameter( query, gl.QUERY_RESULT )
|
|
658
|
+
if ( gl.getQueryParameter( query, gl.QUERY_RESULT ) === 0 ) occluded.add( currentOcclusionQueryObjects[ i ] );
|
|
358
659
|
|
|
359
660
|
currentOcclusionQueries[ i ] = null;
|
|
360
661
|
gl.deleteQuery( query );
|
|
@@ -383,6 +684,14 @@ class WebGLBackend extends Backend {
|
|
|
383
684
|
|
|
384
685
|
}
|
|
385
686
|
|
|
687
|
+
/**
|
|
688
|
+
* Returns `true` if the given 3D object is fully occluded by other
|
|
689
|
+
* 3D objects in the scene.
|
|
690
|
+
*
|
|
691
|
+
* @param {RenderContext} renderContext - The render context.
|
|
692
|
+
* @param {Object3D} object - The 3D object to test.
|
|
693
|
+
* @return {boolean} Whether the 3D object is fully occluded or not.
|
|
694
|
+
*/
|
|
386
695
|
isOccluded( renderContext, object ) {
|
|
387
696
|
|
|
388
697
|
const renderContextData = this.get( renderContext );
|
|
@@ -391,40 +700,74 @@ class WebGLBackend extends Backend {
|
|
|
391
700
|
|
|
392
701
|
}
|
|
393
702
|
|
|
703
|
+
/**
|
|
704
|
+
* Updates the viewport with the values from the given render context.
|
|
705
|
+
*
|
|
706
|
+
* @param {RenderContext} renderContext - The render context.
|
|
707
|
+
*/
|
|
394
708
|
updateViewport( renderContext ) {
|
|
395
709
|
|
|
396
|
-
const
|
|
710
|
+
const { state } = this;
|
|
397
711
|
const { x, y, width, height } = renderContext.viewportValue;
|
|
398
712
|
|
|
399
|
-
|
|
713
|
+
state.viewport( x, renderContext.height - height - y, width, height );
|
|
400
714
|
|
|
401
715
|
}
|
|
402
716
|
|
|
717
|
+
/**
|
|
718
|
+
* Defines the scissor test.
|
|
719
|
+
*
|
|
720
|
+
* @param {boolean} boolean - Whether the scissor test should be enabled or not.
|
|
721
|
+
*/
|
|
403
722
|
setScissorTest( boolean ) {
|
|
404
723
|
|
|
405
|
-
const
|
|
724
|
+
const state = this.state;
|
|
406
725
|
|
|
407
|
-
|
|
726
|
+
state.setScissorTest( boolean );
|
|
408
727
|
|
|
409
|
-
|
|
728
|
+
}
|
|
410
729
|
|
|
411
|
-
|
|
730
|
+
/**
|
|
731
|
+
* Returns the clear color and alpha into a single
|
|
732
|
+
* color object.
|
|
733
|
+
*
|
|
734
|
+
* @return {Color4} The clear color.
|
|
735
|
+
*/
|
|
736
|
+
getClearColor() {
|
|
412
737
|
|
|
413
|
-
|
|
738
|
+
const clearColor = super.getClearColor();
|
|
414
739
|
|
|
415
|
-
|
|
740
|
+
// Since the canvas is always created with alpha: true,
|
|
741
|
+
// WebGL must always premultiply the clear color.
|
|
742
|
+
|
|
743
|
+
clearColor.r *= clearColor.a;
|
|
744
|
+
clearColor.g *= clearColor.a;
|
|
745
|
+
clearColor.b *= clearColor.a;
|
|
746
|
+
|
|
747
|
+
return clearColor;
|
|
416
748
|
|
|
417
749
|
}
|
|
418
750
|
|
|
751
|
+
/**
|
|
752
|
+
* Performs a clear operation.
|
|
753
|
+
*
|
|
754
|
+
* @param {boolean} color - Whether the color buffer should be cleared or not.
|
|
755
|
+
* @param {boolean} depth - Whether the depth buffer should be cleared or not.
|
|
756
|
+
* @param {boolean} stencil - Whether the stencil buffer should be cleared or not.
|
|
757
|
+
* @param {?Object} [descriptor=null] - The render context of the current set render target.
|
|
758
|
+
* @param {boolean} [setFrameBuffer=true] - TODO.
|
|
759
|
+
*/
|
|
419
760
|
clear( color, depth, stencil, descriptor = null, setFrameBuffer = true ) {
|
|
420
761
|
|
|
421
|
-
const { gl } = this;
|
|
762
|
+
const { gl, renderer } = this;
|
|
422
763
|
|
|
423
764
|
if ( descriptor === null ) {
|
|
424
765
|
|
|
766
|
+
const clearColor = this.getClearColor();
|
|
767
|
+
|
|
425
768
|
descriptor = {
|
|
426
769
|
textures: null,
|
|
427
|
-
clearColorValue:
|
|
770
|
+
clearColorValue: clearColor
|
|
428
771
|
};
|
|
429
772
|
|
|
430
773
|
}
|
|
@@ -439,7 +782,20 @@ class WebGLBackend extends Backend {
|
|
|
439
782
|
|
|
440
783
|
if ( clear !== 0 ) {
|
|
441
784
|
|
|
442
|
-
|
|
785
|
+
let clearColor;
|
|
786
|
+
|
|
787
|
+
if ( descriptor.clearColorValue ) {
|
|
788
|
+
|
|
789
|
+
clearColor = descriptor.clearColorValue;
|
|
790
|
+
|
|
791
|
+
} else {
|
|
792
|
+
|
|
793
|
+
clearColor = this.getClearColor();
|
|
794
|
+
|
|
795
|
+
}
|
|
796
|
+
|
|
797
|
+
const clearDepth = renderer.getClearDepth();
|
|
798
|
+
const clearStencil = renderer.getClearStencil();
|
|
443
799
|
|
|
444
800
|
if ( depth ) this.state.setDepthMask( true );
|
|
445
801
|
|
|
@@ -456,7 +812,15 @@ class WebGLBackend extends Backend {
|
|
|
456
812
|
|
|
457
813
|
for ( let i = 0; i < descriptor.textures.length; i ++ ) {
|
|
458
814
|
|
|
459
|
-
|
|
815
|
+
if ( i === 0 ) {
|
|
816
|
+
|
|
817
|
+
gl.clearBufferfv( gl.COLOR, i, [ clearColor.r, clearColor.g, clearColor.b, clearColor.a ] );
|
|
818
|
+
|
|
819
|
+
} else {
|
|
820
|
+
|
|
821
|
+
gl.clearBufferfv( gl.COLOR, i, [ 0, 0, 0, 1 ] );
|
|
822
|
+
|
|
823
|
+
}
|
|
460
824
|
|
|
461
825
|
}
|
|
462
826
|
|
|
@@ -464,15 +828,15 @@ class WebGLBackend extends Backend {
|
|
|
464
828
|
|
|
465
829
|
if ( depth && stencil ) {
|
|
466
830
|
|
|
467
|
-
gl.clearBufferfi( gl.DEPTH_STENCIL, 0,
|
|
831
|
+
gl.clearBufferfi( gl.DEPTH_STENCIL, 0, clearDepth, clearStencil );
|
|
468
832
|
|
|
469
833
|
} else if ( depth ) {
|
|
470
834
|
|
|
471
|
-
gl.clearBufferfv( gl.DEPTH, 0, [
|
|
835
|
+
gl.clearBufferfv( gl.DEPTH, 0, [ clearDepth ] );
|
|
472
836
|
|
|
473
837
|
} else if ( stencil ) {
|
|
474
838
|
|
|
475
|
-
gl.clearBufferiv( gl.STENCIL, 0, [
|
|
839
|
+
gl.clearBufferiv( gl.STENCIL, 0, [ clearStencil ] );
|
|
476
840
|
|
|
477
841
|
}
|
|
478
842
|
|
|
@@ -482,20 +846,34 @@ class WebGLBackend extends Backend {
|
|
|
482
846
|
|
|
483
847
|
}
|
|
484
848
|
|
|
849
|
+
/**
|
|
850
|
+
* This method is executed at the beginning of a compute call and
|
|
851
|
+
* prepares the state for upcoming compute tasks.
|
|
852
|
+
*
|
|
853
|
+
* @param {Node|Array<Node>} computeGroup - The compute node(s).
|
|
854
|
+
*/
|
|
485
855
|
beginCompute( computeGroup ) {
|
|
486
856
|
|
|
487
|
-
const gl = this
|
|
857
|
+
const { state, gl } = this;
|
|
488
858
|
|
|
489
|
-
|
|
859
|
+
state.bindFramebuffer( gl.FRAMEBUFFER, null );
|
|
490
860
|
this.initTimestampQuery( computeGroup );
|
|
491
861
|
|
|
492
862
|
}
|
|
493
863
|
|
|
864
|
+
/**
|
|
865
|
+
* Executes a compute command for the given compute node.
|
|
866
|
+
*
|
|
867
|
+
* @param {Node|Array<Node>} computeGroup - The group of compute nodes of a compute call. Can be a single compute node.
|
|
868
|
+
* @param {Node} computeNode - The compute node.
|
|
869
|
+
* @param {Array<BindGroup>} bindings - The bindings.
|
|
870
|
+
* @param {ComputePipeline} pipeline - The compute pipeline.
|
|
871
|
+
*/
|
|
494
872
|
compute( computeGroup, computeNode, bindings, pipeline ) {
|
|
495
873
|
|
|
496
|
-
const gl = this
|
|
874
|
+
const { state, gl } = this;
|
|
497
875
|
|
|
498
|
-
if (
|
|
876
|
+
if ( this.discard === false ) {
|
|
499
877
|
|
|
500
878
|
// required here to handle async behaviour of render.compute()
|
|
501
879
|
gl.enable( gl.RASTERIZER_DISCARD );
|
|
@@ -505,21 +883,21 @@ class WebGLBackend extends Backend {
|
|
|
505
883
|
|
|
506
884
|
const { programGPU, transformBuffers, attributes } = this.get( pipeline );
|
|
507
885
|
|
|
508
|
-
const vaoKey = this._getVaoKey(
|
|
886
|
+
const vaoKey = this._getVaoKey( attributes );
|
|
509
887
|
|
|
510
888
|
const vaoGPU = this.vaoCache[ vaoKey ];
|
|
511
889
|
|
|
512
890
|
if ( vaoGPU === undefined ) {
|
|
513
891
|
|
|
514
|
-
this._createVao(
|
|
892
|
+
this._createVao( attributes );
|
|
515
893
|
|
|
516
894
|
} else {
|
|
517
895
|
|
|
518
|
-
|
|
896
|
+
state.setVertexState( vaoGPU );
|
|
519
897
|
|
|
520
898
|
}
|
|
521
899
|
|
|
522
|
-
|
|
900
|
+
state.useProgram( programGPU );
|
|
523
901
|
|
|
524
902
|
this._bindUniforms( bindings );
|
|
525
903
|
|
|
@@ -560,6 +938,12 @@ class WebGLBackend extends Backend {
|
|
|
560
938
|
|
|
561
939
|
}
|
|
562
940
|
|
|
941
|
+
/**
|
|
942
|
+
* This method is executed at the end of a compute call and
|
|
943
|
+
* finalizes work after compute tasks.
|
|
944
|
+
*
|
|
945
|
+
* @param {Node|Array<Node>} computeGroup - The compute node(s).
|
|
946
|
+
*/
|
|
563
947
|
finishCompute( computeGroup ) {
|
|
564
948
|
|
|
565
949
|
const gl = this.gl;
|
|
@@ -570,34 +954,52 @@ class WebGLBackend extends Backend {
|
|
|
570
954
|
|
|
571
955
|
this.prepareTimestampBuffer( computeGroup );
|
|
572
956
|
|
|
957
|
+
if ( this._currentContext ) {
|
|
958
|
+
|
|
959
|
+
this._setFramebuffer( this._currentContext );
|
|
960
|
+
|
|
961
|
+
}
|
|
962
|
+
|
|
573
963
|
}
|
|
574
964
|
|
|
965
|
+
/**
|
|
966
|
+
* Executes a draw command for the given render object.
|
|
967
|
+
*
|
|
968
|
+
* @param {RenderObject} renderObject - The render object to draw.
|
|
969
|
+
* @param {Info} info - Holds a series of statistical information about the GPU memory and the rendering process.
|
|
970
|
+
*/
|
|
575
971
|
draw( renderObject/*, info*/ ) {
|
|
576
972
|
|
|
577
|
-
const { object, pipeline, material, context } = renderObject;
|
|
973
|
+
const { object, pipeline, material, context, hardwareClippingPlanes } = renderObject;
|
|
578
974
|
const { programGPU } = this.get( pipeline );
|
|
579
975
|
|
|
580
976
|
const { gl, state } = this;
|
|
581
977
|
|
|
582
978
|
const contextData = this.get( context );
|
|
583
979
|
|
|
980
|
+
const drawParams = renderObject.getDrawParameters();
|
|
981
|
+
|
|
982
|
+
if ( drawParams === null ) return;
|
|
983
|
+
|
|
584
984
|
//
|
|
585
985
|
|
|
586
986
|
this._bindUniforms( renderObject.getBindings() );
|
|
587
987
|
|
|
588
988
|
const frontFaceCW = ( object.isMesh && object.matrixWorld.determinant() < 0 );
|
|
589
989
|
|
|
590
|
-
state.setMaterial( material, frontFaceCW );
|
|
990
|
+
state.setMaterial( material, frontFaceCW, hardwareClippingPlanes );
|
|
591
991
|
|
|
592
|
-
|
|
992
|
+
state.useProgram( programGPU );
|
|
593
993
|
|
|
594
|
-
//
|
|
994
|
+
// vertex state
|
|
595
995
|
|
|
596
|
-
|
|
996
|
+
const renderObjectData = this.get( renderObject );
|
|
597
997
|
|
|
598
|
-
|
|
998
|
+
let vaoGPU = renderObjectData.staticVao;
|
|
999
|
+
|
|
1000
|
+
if ( vaoGPU === undefined || renderObjectData.geometryId !== renderObject.geometry.id ) {
|
|
599
1001
|
|
|
600
|
-
const vaoKey = this._getVaoKey( renderObject.
|
|
1002
|
+
const vaoKey = this._getVaoKey( renderObject.getAttributes() );
|
|
601
1003
|
|
|
602
1004
|
vaoGPU = this.vaoCache[ vaoKey ];
|
|
603
1005
|
|
|
@@ -605,23 +1007,23 @@ class WebGLBackend extends Backend {
|
|
|
605
1007
|
|
|
606
1008
|
let staticVao;
|
|
607
1009
|
|
|
608
|
-
( { vaoGPU, staticVao } = this._createVao( renderObject.
|
|
1010
|
+
( { vaoGPU, staticVao } = this._createVao( renderObject.getAttributes() ) );
|
|
609
1011
|
|
|
610
|
-
if ( staticVao )
|
|
1012
|
+
if ( staticVao ) {
|
|
611
1013
|
|
|
612
|
-
|
|
1014
|
+
renderObjectData.staticVao = vaoGPU;
|
|
1015
|
+
renderObjectData.geometryId = renderObject.geometry.id;
|
|
613
1016
|
|
|
614
|
-
|
|
1017
|
+
}
|
|
615
1018
|
|
|
616
|
-
|
|
1019
|
+
}
|
|
617
1020
|
|
|
618
|
-
|
|
1021
|
+
}
|
|
619
1022
|
|
|
620
1023
|
const index = renderObject.getIndex();
|
|
1024
|
+
const indexGPU = ( index !== null ) ? this.get( index ).bufferGPU : null;
|
|
621
1025
|
|
|
622
|
-
|
|
623
|
-
const drawRange = renderObject.drawRange;
|
|
624
|
-
const firstVertex = drawRange.start;
|
|
1026
|
+
state.setVertexState( vaoGPU, indexGPU );
|
|
625
1027
|
|
|
626
1028
|
//
|
|
627
1029
|
|
|
@@ -653,7 +1055,6 @@ class WebGLBackend extends Backend {
|
|
|
653
1055
|
}
|
|
654
1056
|
|
|
655
1057
|
//
|
|
656
|
-
|
|
657
1058
|
const renderer = this.bufferRenderer;
|
|
658
1059
|
|
|
659
1060
|
if ( object.isPoints ) renderer.mode = gl.POINTS;
|
|
@@ -677,125 +1078,254 @@ class WebGLBackend extends Backend {
|
|
|
677
1078
|
|
|
678
1079
|
//
|
|
679
1080
|
|
|
680
|
-
|
|
681
|
-
let
|
|
1081
|
+
const { vertexCount, instanceCount } = drawParams;
|
|
1082
|
+
let { firstVertex } = drawParams;
|
|
682
1083
|
|
|
683
1084
|
renderer.object = object;
|
|
684
1085
|
|
|
685
1086
|
if ( index !== null ) {
|
|
686
1087
|
|
|
1088
|
+
firstVertex *= index.array.BYTES_PER_ELEMENT;
|
|
1089
|
+
|
|
687
1090
|
const indexData = this.get( index );
|
|
688
|
-
const indexCount = ( drawRange.count !== Infinity ) ? drawRange.count : index.count;
|
|
689
1091
|
|
|
690
1092
|
renderer.index = index.count;
|
|
691
1093
|
renderer.type = indexData.type;
|
|
692
1094
|
|
|
693
|
-
count = indexCount;
|
|
694
|
-
|
|
695
1095
|
} else {
|
|
696
1096
|
|
|
697
1097
|
renderer.index = 0;
|
|
698
1098
|
|
|
699
|
-
|
|
1099
|
+
}
|
|
700
1100
|
|
|
701
|
-
|
|
1101
|
+
const draw = () => {
|
|
702
1102
|
|
|
703
|
-
|
|
1103
|
+
if ( object.isBatchedMesh ) {
|
|
704
1104
|
|
|
705
|
-
|
|
1105
|
+
if ( object._multiDrawInstances !== null ) {
|
|
706
1106
|
|
|
707
|
-
|
|
1107
|
+
// @deprecated, r174
|
|
1108
|
+
warnOnce( 'THREE.WebGLBackend: renderMultiDrawInstances has been deprecated and will be removed in r184. Append to renderMultiDraw arguments and use indirection.' );
|
|
1109
|
+
renderer.renderMultiDrawInstances( object._multiDrawStarts, object._multiDrawCounts, object._multiDrawCount, object._multiDrawInstances );
|
|
708
1110
|
|
|
709
|
-
|
|
1111
|
+
} else if ( ! this.hasFeature( 'WEBGL_multi_draw' ) ) {
|
|
710
1112
|
|
|
711
|
-
|
|
1113
|
+
warnOnce( 'THREE.WebGLRenderer: WEBGL_multi_draw not supported.' );
|
|
712
1114
|
|
|
713
|
-
|
|
1115
|
+
} else {
|
|
1116
|
+
|
|
1117
|
+
renderer.renderMultiDraw( object._multiDrawStarts, object._multiDrawCounts, object._multiDrawCount );
|
|
1118
|
+
|
|
1119
|
+
}
|
|
1120
|
+
|
|
1121
|
+
} else if ( instanceCount > 1 ) {
|
|
714
1122
|
|
|
715
|
-
|
|
1123
|
+
renderer.renderInstances( firstVertex, vertexCount, instanceCount );
|
|
716
1124
|
|
|
717
1125
|
} else {
|
|
718
1126
|
|
|
719
|
-
renderer.
|
|
1127
|
+
renderer.render( firstVertex, vertexCount );
|
|
720
1128
|
|
|
721
1129
|
}
|
|
722
1130
|
|
|
723
|
-
}
|
|
1131
|
+
};
|
|
1132
|
+
|
|
1133
|
+
if ( renderObject.camera.isArrayCamera && renderObject.camera.cameras.length > 0 ) {
|
|
1134
|
+
|
|
1135
|
+
const cameraData = this.get( renderObject.camera );
|
|
1136
|
+
const cameras = renderObject.camera.cameras;
|
|
1137
|
+
const cameraIndex = renderObject.getBindingGroup( 'cameraIndex' ).bindings[ 0 ];
|
|
1138
|
+
|
|
1139
|
+
if ( cameraData.indexesGPU === undefined || cameraData.indexesGPU.length !== cameras.length ) {
|
|
1140
|
+
|
|
1141
|
+
const data = new Uint32Array( [ 0, 0, 0, 0 ] );
|
|
1142
|
+
const indexesGPU = [];
|
|
1143
|
+
|
|
1144
|
+
for ( let i = 0, len = cameras.length; i < len; i ++ ) {
|
|
1145
|
+
|
|
1146
|
+
const bufferGPU = gl.createBuffer();
|
|
1147
|
+
|
|
1148
|
+
data[ 0 ] = i;
|
|
1149
|
+
|
|
1150
|
+
gl.bindBuffer( gl.UNIFORM_BUFFER, bufferGPU );
|
|
1151
|
+
gl.bufferData( gl.UNIFORM_BUFFER, data, gl.STATIC_DRAW );
|
|
1152
|
+
|
|
1153
|
+
indexesGPU.push( bufferGPU );
|
|
1154
|
+
|
|
1155
|
+
}
|
|
1156
|
+
|
|
1157
|
+
cameraData.indexesGPU = indexesGPU; // TODO: Create a global library for this
|
|
1158
|
+
|
|
1159
|
+
}
|
|
1160
|
+
|
|
1161
|
+
const cameraIndexData = this.get( cameraIndex );
|
|
1162
|
+
const pixelRatio = this.renderer.getPixelRatio();
|
|
1163
|
+
|
|
1164
|
+
for ( let i = 0, len = cameras.length; i < len; i ++ ) {
|
|
1165
|
+
|
|
1166
|
+
const subCamera = cameras[ i ];
|
|
1167
|
+
|
|
1168
|
+
if ( object.layers.test( subCamera.layers ) ) {
|
|
1169
|
+
|
|
1170
|
+
const vp = subCamera.viewport;
|
|
1171
|
+
|
|
1172
|
+
const x = vp.x * pixelRatio;
|
|
1173
|
+
const y = vp.y * pixelRatio;
|
|
1174
|
+
const width = vp.width * pixelRatio;
|
|
1175
|
+
const height = vp.height * pixelRatio;
|
|
1176
|
+
|
|
1177
|
+
state.viewport(
|
|
1178
|
+
Math.floor( x ),
|
|
1179
|
+
Math.floor( renderObject.context.height - height - y ),
|
|
1180
|
+
Math.floor( width ),
|
|
1181
|
+
Math.floor( height )
|
|
1182
|
+
);
|
|
1183
|
+
|
|
1184
|
+
state.bindBufferBase( gl.UNIFORM_BUFFER, cameraIndexData.index, cameraData.indexesGPU[ i ] );
|
|
1185
|
+
|
|
1186
|
+
draw();
|
|
1187
|
+
|
|
1188
|
+
}
|
|
724
1189
|
|
|
725
|
-
|
|
1190
|
+
}
|
|
726
1191
|
|
|
727
1192
|
} else {
|
|
728
1193
|
|
|
729
|
-
|
|
1194
|
+
draw();
|
|
730
1195
|
|
|
731
1196
|
}
|
|
732
|
-
//
|
|
733
|
-
|
|
734
|
-
gl.bindVertexArray( null );
|
|
735
1197
|
|
|
736
1198
|
}
|
|
737
1199
|
|
|
1200
|
+
/**
|
|
1201
|
+
* Explain why always null is returned.
|
|
1202
|
+
*
|
|
1203
|
+
* @param {RenderObject} renderObject - The render object.
|
|
1204
|
+
* @return {boolean} Whether the render pipeline requires an update or not.
|
|
1205
|
+
*/
|
|
738
1206
|
needsRenderUpdate( /*renderObject*/ ) {
|
|
739
1207
|
|
|
740
1208
|
return false;
|
|
741
1209
|
|
|
742
1210
|
}
|
|
743
1211
|
|
|
744
|
-
|
|
1212
|
+
/**
|
|
1213
|
+
* Explain why no cache key is computed.
|
|
1214
|
+
*
|
|
1215
|
+
* @param {RenderObject} renderObject - The render object.
|
|
1216
|
+
* @return {string} The cache key.
|
|
1217
|
+
*/
|
|
1218
|
+
getRenderCacheKey( /*renderObject*/ ) {
|
|
745
1219
|
|
|
746
|
-
return
|
|
1220
|
+
return '';
|
|
747
1221
|
|
|
748
1222
|
}
|
|
749
1223
|
|
|
750
1224
|
// textures
|
|
751
1225
|
|
|
1226
|
+
/**
|
|
1227
|
+
* Creates a default texture for the given texture that can be used
|
|
1228
|
+
* as a placeholder until the actual texture is ready for usage.
|
|
1229
|
+
*
|
|
1230
|
+
* @param {Texture} texture - The texture to create a default texture for.
|
|
1231
|
+
*/
|
|
752
1232
|
createDefaultTexture( texture ) {
|
|
753
1233
|
|
|
754
1234
|
this.textureUtils.createDefaultTexture( texture );
|
|
755
1235
|
|
|
756
1236
|
}
|
|
757
1237
|
|
|
1238
|
+
/**
|
|
1239
|
+
* Defines a texture on the GPU for the given texture object.
|
|
1240
|
+
*
|
|
1241
|
+
* @param {Texture} texture - The texture.
|
|
1242
|
+
* @param {Object} [options={}] - Optional configuration parameter.
|
|
1243
|
+
*/
|
|
758
1244
|
createTexture( texture, options ) {
|
|
759
1245
|
|
|
760
1246
|
this.textureUtils.createTexture( texture, options );
|
|
761
1247
|
|
|
762
1248
|
}
|
|
763
1249
|
|
|
1250
|
+
/**
|
|
1251
|
+
* Uploads the updated texture data to the GPU.
|
|
1252
|
+
*
|
|
1253
|
+
* @param {Texture} texture - The texture.
|
|
1254
|
+
* @param {Object} [options={}] - Optional configuration parameter.
|
|
1255
|
+
*/
|
|
764
1256
|
updateTexture( texture, options ) {
|
|
765
1257
|
|
|
766
1258
|
this.textureUtils.updateTexture( texture, options );
|
|
767
1259
|
|
|
768
1260
|
}
|
|
769
1261
|
|
|
1262
|
+
/**
|
|
1263
|
+
* Generates mipmaps for the given texture.
|
|
1264
|
+
*
|
|
1265
|
+
* @param {Texture} texture - The texture.
|
|
1266
|
+
*/
|
|
770
1267
|
generateMipmaps( texture ) {
|
|
771
1268
|
|
|
772
1269
|
this.textureUtils.generateMipmaps( texture );
|
|
773
1270
|
|
|
774
1271
|
}
|
|
775
1272
|
|
|
776
|
-
|
|
1273
|
+
/**
|
|
1274
|
+
* Destroys the GPU data for the given texture object.
|
|
1275
|
+
*
|
|
1276
|
+
* @param {Texture} texture - The texture.
|
|
1277
|
+
*/
|
|
777
1278
|
destroyTexture( texture ) {
|
|
778
1279
|
|
|
779
1280
|
this.textureUtils.destroyTexture( texture );
|
|
780
1281
|
|
|
781
1282
|
}
|
|
782
1283
|
|
|
783
|
-
|
|
784
|
-
|
|
785
|
-
|
|
1284
|
+
/**
|
|
1285
|
+
* Returns texture data as a typed array.
|
|
1286
|
+
*
|
|
1287
|
+
* @async
|
|
1288
|
+
* @param {Texture} texture - The texture to copy.
|
|
1289
|
+
* @param {number} x - The x coordinate of the copy origin.
|
|
1290
|
+
* @param {number} y - The y coordinate of the copy origin.
|
|
1291
|
+
* @param {number} width - The width of the copy.
|
|
1292
|
+
* @param {number} height - The height of the copy.
|
|
1293
|
+
* @param {number} faceIndex - The face index.
|
|
1294
|
+
* @return {Promise<TypedArray>} A Promise that resolves with a typed array when the copy operation has finished.
|
|
1295
|
+
*/
|
|
1296
|
+
async copyTextureToBuffer( texture, x, y, width, height, faceIndex ) {
|
|
1297
|
+
|
|
1298
|
+
return this.textureUtils.copyTextureToBuffer( texture, x, y, width, height, faceIndex );
|
|
786
1299
|
|
|
787
1300
|
}
|
|
788
1301
|
|
|
1302
|
+
/**
|
|
1303
|
+
* This method does nothing since WebGL 2 has no concept of samplers.
|
|
1304
|
+
*
|
|
1305
|
+
* @param {Texture} texture - The texture to create the sampler for.
|
|
1306
|
+
*/
|
|
789
1307
|
createSampler( /*texture*/ ) {
|
|
790
1308
|
|
|
791
1309
|
//console.warn( 'Abstract class.' );
|
|
792
1310
|
|
|
793
1311
|
}
|
|
794
1312
|
|
|
795
|
-
|
|
1313
|
+
/**
|
|
1314
|
+
* This method does nothing since WebGL 2 has no concept of samplers.
|
|
1315
|
+
*
|
|
1316
|
+
* @param {Texture} texture - The texture to destroy the sampler for.
|
|
1317
|
+
*/
|
|
1318
|
+
destroySampler( /*texture*/ ) {}
|
|
796
1319
|
|
|
797
1320
|
// node builder
|
|
798
1321
|
|
|
1322
|
+
/**
|
|
1323
|
+
* Returns a node builder for the given render object.
|
|
1324
|
+
*
|
|
1325
|
+
* @param {RenderObject} object - The render object.
|
|
1326
|
+
* @param {Renderer} renderer - The renderer.
|
|
1327
|
+
* @return {GLSLNodeBuilder} The node builder.
|
|
1328
|
+
*/
|
|
799
1329
|
createNodeBuilder( object, renderer ) {
|
|
800
1330
|
|
|
801
1331
|
return new GLSLNodeBuilder( object, renderer );
|
|
@@ -804,6 +1334,11 @@ class WebGLBackend extends Backend {
|
|
|
804
1334
|
|
|
805
1335
|
// program
|
|
806
1336
|
|
|
1337
|
+
/**
|
|
1338
|
+
* Creates a shader program from the given programmable stage.
|
|
1339
|
+
*
|
|
1340
|
+
* @param {ProgrammableStage} program - The programmable stage.
|
|
1341
|
+
*/
|
|
807
1342
|
createProgram( program ) {
|
|
808
1343
|
|
|
809
1344
|
const gl = this.gl;
|
|
@@ -820,12 +1355,23 @@ class WebGLBackend extends Backend {
|
|
|
820
1355
|
|
|
821
1356
|
}
|
|
822
1357
|
|
|
823
|
-
|
|
1358
|
+
/**
|
|
1359
|
+
* Destroys the shader program of the given programmable stage.
|
|
1360
|
+
*
|
|
1361
|
+
* @param {ProgrammableStage} program - The programmable stage.
|
|
1362
|
+
*/
|
|
1363
|
+
destroyProgram( program ) {
|
|
824
1364
|
|
|
825
|
-
|
|
1365
|
+
this.delete( program );
|
|
826
1366
|
|
|
827
1367
|
}
|
|
828
1368
|
|
|
1369
|
+
/**
|
|
1370
|
+
* Creates a render pipeline for the given render object.
|
|
1371
|
+
*
|
|
1372
|
+
* @param {RenderObject} renderObject - The render object.
|
|
1373
|
+
* @param {Array<Promise>} promises - An array of compilation promises which are used in `compileAsync()`.
|
|
1374
|
+
*/
|
|
829
1375
|
createRenderPipeline( renderObject, promises ) {
|
|
830
1376
|
|
|
831
1377
|
const gl = this.gl;
|
|
@@ -884,6 +1430,14 @@ class WebGLBackend extends Backend {
|
|
|
884
1430
|
|
|
885
1431
|
}
|
|
886
1432
|
|
|
1433
|
+
/**
|
|
1434
|
+
* Formats the source code of error messages.
|
|
1435
|
+
*
|
|
1436
|
+
* @private
|
|
1437
|
+
* @param {string} string - The code.
|
|
1438
|
+
* @param {number} errorLine - The error line.
|
|
1439
|
+
* @return {string} The formatted code.
|
|
1440
|
+
*/
|
|
887
1441
|
_handleSource( string, errorLine ) {
|
|
888
1442
|
|
|
889
1443
|
const lines = string.split( '\n' );
|
|
@@ -903,6 +1457,15 @@ class WebGLBackend extends Backend {
|
|
|
903
1457
|
|
|
904
1458
|
}
|
|
905
1459
|
|
|
1460
|
+
/**
|
|
1461
|
+
* Gets the shader compilation errors from the info log.
|
|
1462
|
+
*
|
|
1463
|
+
* @private
|
|
1464
|
+
* @param {WebGL2RenderingContext} gl - The rendering context.
|
|
1465
|
+
* @param {WebGLShader} shader - The WebGL shader object.
|
|
1466
|
+
* @param {string} type - The shader type.
|
|
1467
|
+
* @return {string} The shader errors.
|
|
1468
|
+
*/
|
|
906
1469
|
_getShaderErrors( gl, shader, type ) {
|
|
907
1470
|
|
|
908
1471
|
const status = gl.getShaderParameter( shader, gl.COMPILE_STATUS );
|
|
@@ -924,6 +1487,14 @@ class WebGLBackend extends Backend {
|
|
|
924
1487
|
|
|
925
1488
|
}
|
|
926
1489
|
|
|
1490
|
+
/**
|
|
1491
|
+
* Logs shader compilation errors.
|
|
1492
|
+
*
|
|
1493
|
+
* @private
|
|
1494
|
+
* @param {WebGLProgram} programGPU - The WebGL program.
|
|
1495
|
+
* @param {WebGLShader} glFragmentShader - The fragment shader as a native WebGL shader object.
|
|
1496
|
+
* @param {WebGLShader} glVertexShader - The vertex shader as a native WebGL shader object.
|
|
1497
|
+
*/
|
|
927
1498
|
_logProgramError( programGPU, glFragmentShader, glVertexShader ) {
|
|
928
1499
|
|
|
929
1500
|
if ( this.renderer.debug.checkShaderErrors ) {
|
|
@@ -966,9 +1537,16 @@ class WebGLBackend extends Backend {
|
|
|
966
1537
|
|
|
967
1538
|
}
|
|
968
1539
|
|
|
1540
|
+
/**
|
|
1541
|
+
* Completes the shader program setup for the given render object.
|
|
1542
|
+
*
|
|
1543
|
+
* @private
|
|
1544
|
+
* @param {RenderObject} renderObject - The render object.
|
|
1545
|
+
* @param {RenderPipeline} pipeline - The render pipeline.
|
|
1546
|
+
*/
|
|
969
1547
|
_completeCompile( renderObject, pipeline ) {
|
|
970
1548
|
|
|
971
|
-
const gl = this
|
|
1549
|
+
const { state, gl } = this;
|
|
972
1550
|
const pipelineData = this.get( pipeline );
|
|
973
1551
|
const { programGPU, fragmentShader, vertexShader } = pipelineData;
|
|
974
1552
|
|
|
@@ -978,7 +1556,7 @@ class WebGLBackend extends Backend {
|
|
|
978
1556
|
|
|
979
1557
|
}
|
|
980
1558
|
|
|
981
|
-
|
|
1559
|
+
state.useProgram( programGPU );
|
|
982
1560
|
|
|
983
1561
|
// Bindings
|
|
984
1562
|
|
|
@@ -994,9 +1572,15 @@ class WebGLBackend extends Backend {
|
|
|
994
1572
|
|
|
995
1573
|
}
|
|
996
1574
|
|
|
1575
|
+
/**
|
|
1576
|
+
* Creates a compute pipeline for the given compute node.
|
|
1577
|
+
*
|
|
1578
|
+
* @param {ComputePipeline} computePipeline - The compute pipeline.
|
|
1579
|
+
* @param {Array<BindGroup>} bindings - The bindings.
|
|
1580
|
+
*/
|
|
997
1581
|
createComputePipeline( computePipeline, bindings ) {
|
|
998
1582
|
|
|
999
|
-
const gl = this
|
|
1583
|
+
const { state, gl } = this;
|
|
1000
1584
|
|
|
1001
1585
|
// Program
|
|
1002
1586
|
|
|
@@ -1046,12 +1630,10 @@ class WebGLBackend extends Backend {
|
|
|
1046
1630
|
|
|
1047
1631
|
}
|
|
1048
1632
|
|
|
1049
|
-
|
|
1633
|
+
state.useProgram( programGPU );
|
|
1050
1634
|
|
|
1051
1635
|
// Bindings
|
|
1052
1636
|
|
|
1053
|
-
this.createBindings( null, bindings );
|
|
1054
|
-
|
|
1055
1637
|
this._setupBindings( bindings, programGPU );
|
|
1056
1638
|
|
|
1057
1639
|
const attributeNodes = computeProgram.attributes;
|
|
@@ -1090,48 +1672,86 @@ class WebGLBackend extends Backend {
|
|
|
1090
1672
|
|
|
1091
1673
|
}
|
|
1092
1674
|
|
|
1093
|
-
|
|
1675
|
+
/**
|
|
1676
|
+
* Creates bindings from the given bind group definition.
|
|
1677
|
+
*
|
|
1678
|
+
* @param {BindGroup} bindGroup - The bind group.
|
|
1679
|
+
* @param {Array<BindGroup>} bindings - Array of bind groups.
|
|
1680
|
+
* @param {number} cacheIndex - The cache index.
|
|
1681
|
+
* @param {number} version - The version.
|
|
1682
|
+
*/
|
|
1683
|
+
createBindings( bindGroup, bindings /*, cacheIndex, version*/ ) {
|
|
1684
|
+
|
|
1685
|
+
if ( this._knownBindings.has( bindings ) === false ) {
|
|
1686
|
+
|
|
1687
|
+
this._knownBindings.add( bindings );
|
|
1688
|
+
|
|
1689
|
+
let uniformBuffers = 0;
|
|
1690
|
+
let textures = 0;
|
|
1691
|
+
|
|
1692
|
+
for ( const bindGroup of bindings ) {
|
|
1693
|
+
|
|
1694
|
+
this.set( bindGroup, {
|
|
1695
|
+
textures: textures,
|
|
1696
|
+
uniformBuffers: uniformBuffers
|
|
1697
|
+
} );
|
|
1698
|
+
|
|
1699
|
+
for ( const binding of bindGroup.bindings ) {
|
|
1700
|
+
|
|
1701
|
+
if ( binding.isUniformBuffer ) uniformBuffers ++;
|
|
1702
|
+
if ( binding.isSampledTexture ) textures ++;
|
|
1703
|
+
|
|
1704
|
+
}
|
|
1705
|
+
|
|
1706
|
+
}
|
|
1707
|
+
|
|
1708
|
+
}
|
|
1094
1709
|
|
|
1095
1710
|
this.updateBindings( bindGroup, bindings );
|
|
1096
1711
|
|
|
1097
1712
|
}
|
|
1098
1713
|
|
|
1099
|
-
|
|
1714
|
+
/**
|
|
1715
|
+
* Updates the given bind group definition.
|
|
1716
|
+
*
|
|
1717
|
+
* @param {BindGroup} bindGroup - The bind group.
|
|
1718
|
+
* @param {Array<BindGroup>} bindings - Array of bind groups.
|
|
1719
|
+
* @param {number} cacheIndex - The cache index.
|
|
1720
|
+
* @param {number} version - The version.
|
|
1721
|
+
*/
|
|
1722
|
+
updateBindings( bindGroup /*, bindings, cacheIndex, version*/ ) {
|
|
1100
1723
|
|
|
1101
1724
|
const { gl } = this;
|
|
1102
1725
|
|
|
1103
|
-
|
|
1104
|
-
let textureIndex = 0;
|
|
1105
|
-
|
|
1106
|
-
for ( const bindGroup of bindings ) {
|
|
1726
|
+
const bindGroupData = this.get( bindGroup );
|
|
1107
1727
|
|
|
1108
|
-
|
|
1728
|
+
let i = bindGroupData.uniformBuffers;
|
|
1729
|
+
let t = bindGroupData.textures;
|
|
1109
1730
|
|
|
1110
|
-
|
|
1731
|
+
for ( const binding of bindGroup.bindings ) {
|
|
1111
1732
|
|
|
1112
|
-
|
|
1113
|
-
const data = binding.buffer;
|
|
1733
|
+
if ( binding.isUniformsGroup || binding.isUniformBuffer ) {
|
|
1114
1734
|
|
|
1115
|
-
|
|
1116
|
-
|
|
1117
|
-
gl.bindBufferBase( gl.UNIFORM_BUFFER, groupIndex, bufferGPU );
|
|
1735
|
+
const data = binding.buffer;
|
|
1736
|
+
const bufferGPU = gl.createBuffer();
|
|
1118
1737
|
|
|
1119
|
-
|
|
1120
|
-
|
|
1121
|
-
bufferGPU
|
|
1122
|
-
} );
|
|
1738
|
+
gl.bindBuffer( gl.UNIFORM_BUFFER, bufferGPU );
|
|
1739
|
+
gl.bufferData( gl.UNIFORM_BUFFER, data, gl.DYNAMIC_DRAW );
|
|
1123
1740
|
|
|
1124
|
-
|
|
1741
|
+
this.set( binding, {
|
|
1742
|
+
index: i ++,
|
|
1743
|
+
bufferGPU
|
|
1744
|
+
} );
|
|
1125
1745
|
|
|
1126
|
-
|
|
1746
|
+
} else if ( binding.isSampledTexture ) {
|
|
1127
1747
|
|
|
1128
|
-
|
|
1129
|
-
index: textureIndex ++,
|
|
1130
|
-
textureGPU,
|
|
1131
|
-
glTextureType
|
|
1132
|
-
} );
|
|
1748
|
+
const { textureGPU, glTextureType } = this.get( binding.texture );
|
|
1133
1749
|
|
|
1134
|
-
|
|
1750
|
+
this.set( binding, {
|
|
1751
|
+
index: t ++,
|
|
1752
|
+
textureGPU,
|
|
1753
|
+
glTextureType
|
|
1754
|
+
} );
|
|
1135
1755
|
|
|
1136
1756
|
}
|
|
1137
1757
|
|
|
@@ -1139,6 +1759,11 @@ class WebGLBackend extends Backend {
|
|
|
1139
1759
|
|
|
1140
1760
|
}
|
|
1141
1761
|
|
|
1762
|
+
/**
|
|
1763
|
+
* Updates a buffer binding.
|
|
1764
|
+
*
|
|
1765
|
+
* @param {Buffer} binding - The buffer binding to update.
|
|
1766
|
+
*/
|
|
1142
1767
|
updateBinding( binding ) {
|
|
1143
1768
|
|
|
1144
1769
|
const gl = this.gl;
|
|
@@ -1158,6 +1783,11 @@ class WebGLBackend extends Backend {
|
|
|
1158
1783
|
|
|
1159
1784
|
// attributes
|
|
1160
1785
|
|
|
1786
|
+
/**
|
|
1787
|
+
* Creates the GPU buffer of an indexed shader attribute.
|
|
1788
|
+
*
|
|
1789
|
+
* @param {BufferAttribute} attribute - The indexed buffer attribute.
|
|
1790
|
+
*/
|
|
1161
1791
|
createIndexAttribute( attribute ) {
|
|
1162
1792
|
|
|
1163
1793
|
const gl = this.gl;
|
|
@@ -1166,6 +1796,11 @@ class WebGLBackend extends Backend {
|
|
|
1166
1796
|
|
|
1167
1797
|
}
|
|
1168
1798
|
|
|
1799
|
+
/**
|
|
1800
|
+
* Creates the GPU buffer of a shader attribute.
|
|
1801
|
+
*
|
|
1802
|
+
* @param {BufferAttribute} attribute - The buffer attribute.
|
|
1803
|
+
*/
|
|
1169
1804
|
createAttribute( attribute ) {
|
|
1170
1805
|
|
|
1171
1806
|
if ( this.has( attribute ) ) return;
|
|
@@ -1176,6 +1811,11 @@ class WebGLBackend extends Backend {
|
|
|
1176
1811
|
|
|
1177
1812
|
}
|
|
1178
1813
|
|
|
1814
|
+
/**
|
|
1815
|
+
* Creates the GPU buffer of a storage attribute.
|
|
1816
|
+
*
|
|
1817
|
+
* @param {BufferAttribute} attribute - The buffer attribute.
|
|
1818
|
+
*/
|
|
1179
1819
|
createStorageAttribute( attribute ) {
|
|
1180
1820
|
|
|
1181
1821
|
if ( this.has( attribute ) ) return;
|
|
@@ -1186,24 +1826,34 @@ class WebGLBackend extends Backend {
|
|
|
1186
1826
|
|
|
1187
1827
|
}
|
|
1188
1828
|
|
|
1829
|
+
/**
|
|
1830
|
+
* Updates the GPU buffer of a shader attribute.
|
|
1831
|
+
*
|
|
1832
|
+
* @param {BufferAttribute} attribute - The buffer attribute to update.
|
|
1833
|
+
*/
|
|
1189
1834
|
updateAttribute( attribute ) {
|
|
1190
1835
|
|
|
1191
1836
|
this.attributeUtils.updateAttribute( attribute );
|
|
1192
1837
|
|
|
1193
1838
|
}
|
|
1194
1839
|
|
|
1840
|
+
/**
|
|
1841
|
+
* Destroys the GPU buffer of a shader attribute.
|
|
1842
|
+
*
|
|
1843
|
+
* @param {BufferAttribute} attribute - The buffer attribute to destroy.
|
|
1844
|
+
*/
|
|
1195
1845
|
destroyAttribute( attribute ) {
|
|
1196
1846
|
|
|
1197
1847
|
this.attributeUtils.destroyAttribute( attribute );
|
|
1198
1848
|
|
|
1199
1849
|
}
|
|
1200
1850
|
|
|
1201
|
-
|
|
1202
|
-
|
|
1203
|
-
|
|
1204
|
-
|
|
1205
|
-
|
|
1206
|
-
|
|
1851
|
+
/**
|
|
1852
|
+
* Checks if the given feature is supported by the backend.
|
|
1853
|
+
*
|
|
1854
|
+
* @param {string} name - The feature's name.
|
|
1855
|
+
* @return {boolean} Whether the feature is supported or not.
|
|
1856
|
+
*/
|
|
1207
1857
|
hasFeature( name ) {
|
|
1208
1858
|
|
|
1209
1859
|
const keysMatching = Object.keys( GLFeatureName ).filter( key => GLFeatureName[ key ] === name );
|
|
@@ -1220,24 +1870,51 @@ class WebGLBackend extends Backend {
|
|
|
1220
1870
|
|
|
1221
1871
|
}
|
|
1222
1872
|
|
|
1873
|
+
/**
|
|
1874
|
+
* Returns the maximum anisotropy texture filtering value.
|
|
1875
|
+
*
|
|
1876
|
+
* @return {number} The maximum anisotropy texture filtering value.
|
|
1877
|
+
*/
|
|
1223
1878
|
getMaxAnisotropy() {
|
|
1224
1879
|
|
|
1225
1880
|
return this.capabilities.getMaxAnisotropy();
|
|
1226
1881
|
|
|
1227
1882
|
}
|
|
1228
1883
|
|
|
1229
|
-
|
|
1884
|
+
/**
|
|
1885
|
+
* Copies data of the given source texture to the given destination texture.
|
|
1886
|
+
*
|
|
1887
|
+
* @param {Texture} srcTexture - The source texture.
|
|
1888
|
+
* @param {Texture} dstTexture - The destination texture.
|
|
1889
|
+
* @param {?Vector4} [srcRegion=null] - The region of the source texture to copy.
|
|
1890
|
+
* @param {?(Vector2|Vector3)} [dstPosition=null] - The destination position of the copy.
|
|
1891
|
+
* @param {number} [level=0] - The mip level to copy.
|
|
1892
|
+
*/
|
|
1893
|
+
copyTextureToTexture( srcTexture, dstTexture, srcRegion = null, dstPosition = null, level = 0 ) {
|
|
1230
1894
|
|
|
1231
|
-
this.textureUtils.copyTextureToTexture(
|
|
1895
|
+
this.textureUtils.copyTextureToTexture( srcTexture, dstTexture, srcRegion, dstPosition, level );
|
|
1232
1896
|
|
|
1233
1897
|
}
|
|
1234
1898
|
|
|
1235
|
-
|
|
1899
|
+
/**
|
|
1900
|
+
* Copies the current bound framebuffer to the given texture.
|
|
1901
|
+
*
|
|
1902
|
+
* @param {Texture} texture - The destination texture.
|
|
1903
|
+
* @param {RenderContext} renderContext - The render context.
|
|
1904
|
+
* @param {Vector4} rectangle - A four dimensional vector defining the origin and dimension of the copy.
|
|
1905
|
+
*/
|
|
1906
|
+
copyFramebufferToTexture( texture, renderContext, rectangle ) {
|
|
1236
1907
|
|
|
1237
|
-
this.textureUtils.copyFramebufferToTexture( texture, renderContext );
|
|
1908
|
+
this.textureUtils.copyFramebufferToTexture( texture, renderContext, rectangle );
|
|
1238
1909
|
|
|
1239
1910
|
}
|
|
1240
1911
|
|
|
1912
|
+
/**
|
|
1913
|
+
* Configures the active framebuffer from the given render context.
|
|
1914
|
+
*
|
|
1915
|
+
* @private
|
|
1916
|
+
* @param {RenderContext} descriptor - The render context.
|
|
1917
|
+
*/
|
|
1241
1918
|
_setFramebuffer( descriptor ) {
|
|
1242
1919
|
|
|
1243
1920
|
const { gl, state } = this;
|
|
@@ -1251,9 +1928,15 @@ class WebGLBackend extends Backend {
|
|
|
1251
1928
|
const { samples, depthBuffer, stencilBuffer } = renderTarget;
|
|
1252
1929
|
|
|
1253
1930
|
const isCube = renderTarget.isWebGLCubeRenderTarget === true;
|
|
1931
|
+
const isRenderTarget3D = renderTarget.isRenderTarget3D === true;
|
|
1932
|
+
const isRenderTargetArray = renderTarget.isRenderTargetArray === true;
|
|
1933
|
+
const isXRRenderTarget = renderTarget.isXRRenderTarget === true;
|
|
1934
|
+
const hasExternalTextures = ( isXRRenderTarget === true && renderTarget.hasExternalTextures === true );
|
|
1254
1935
|
|
|
1255
1936
|
let msaaFb = renderTargetContextData.msaaFrameBuffer;
|
|
1256
1937
|
let depthRenderbuffer = renderTargetContextData.depthRenderbuffer;
|
|
1938
|
+
const multisampledRTTExt = this.extensions.get( 'WEBGL_multisampled_render_to_texture' );
|
|
1939
|
+
const useMultisampledRTT = this._useMultisampledRTT( renderTarget );
|
|
1257
1940
|
|
|
1258
1941
|
const cacheKey = getCacheKey( descriptor );
|
|
1259
1942
|
|
|
@@ -1265,6 +1948,10 @@ class WebGLBackend extends Backend {
|
|
|
1265
1948
|
|
|
1266
1949
|
fb = renderTargetContextData.cubeFramebuffers[ cacheKey ];
|
|
1267
1950
|
|
|
1951
|
+
} else if ( isXRRenderTarget && hasExternalTextures === false ) {
|
|
1952
|
+
|
|
1953
|
+
fb = this._xrFramebuffer;
|
|
1954
|
+
|
|
1268
1955
|
} else {
|
|
1269
1956
|
|
|
1270
1957
|
renderTargetContextData.framebuffers || ( renderTargetContextData.framebuffers = {} );
|
|
@@ -1300,10 +1987,29 @@ class WebGLBackend extends Backend {
|
|
|
1300
1987
|
const texture = textures[ i ];
|
|
1301
1988
|
const textureData = this.get( texture );
|
|
1302
1989
|
textureData.renderTarget = descriptor.renderTarget;
|
|
1990
|
+
textureData.cacheKey = cacheKey; // required for copyTextureToTexture()
|
|
1303
1991
|
|
|
1304
1992
|
const attachment = gl.COLOR_ATTACHMENT0 + i;
|
|
1305
1993
|
|
|
1306
|
-
|
|
1994
|
+
if ( isRenderTarget3D || isRenderTargetArray ) {
|
|
1995
|
+
|
|
1996
|
+
const layer = this.renderer._activeCubeFace;
|
|
1997
|
+
|
|
1998
|
+
gl.framebufferTextureLayer( gl.FRAMEBUFFER, attachment, textureData.textureGPU, 0, layer );
|
|
1999
|
+
|
|
2000
|
+
} else {
|
|
2001
|
+
|
|
2002
|
+
if ( useMultisampledRTT ) {
|
|
2003
|
+
|
|
2004
|
+
multisampledRTTExt.framebufferTexture2DMultisampleEXT( gl.FRAMEBUFFER, attachment, gl.TEXTURE_2D, textureData.textureGPU, 0, samples );
|
|
2005
|
+
|
|
2006
|
+
} else {
|
|
2007
|
+
|
|
2008
|
+
gl.framebufferTexture2D( gl.FRAMEBUFFER, attachment, gl.TEXTURE_2D, textureData.textureGPU, 0 );
|
|
2009
|
+
|
|
2010
|
+
}
|
|
2011
|
+
|
|
2012
|
+
}
|
|
1307
2013
|
|
|
1308
2014
|
}
|
|
1309
2015
|
|
|
@@ -1311,18 +2017,88 @@ class WebGLBackend extends Backend {
|
|
|
1311
2017
|
|
|
1312
2018
|
}
|
|
1313
2019
|
|
|
1314
|
-
if (
|
|
2020
|
+
if ( renderTarget.isXRRenderTarget && renderTarget.autoAllocateDepthBuffer === true ) {
|
|
2021
|
+
|
|
2022
|
+
const renderbuffer = gl.createRenderbuffer();
|
|
2023
|
+
this.textureUtils.setupRenderBufferStorage( renderbuffer, descriptor, 0, useMultisampledRTT );
|
|
2024
|
+
renderTargetContextData.xrDepthRenderbuffer = renderbuffer;
|
|
2025
|
+
|
|
2026
|
+
} else {
|
|
2027
|
+
|
|
2028
|
+
if ( descriptor.depthTexture !== null ) {
|
|
2029
|
+
|
|
2030
|
+
const textureData = this.get( descriptor.depthTexture );
|
|
2031
|
+
const depthStyle = stencilBuffer ? gl.DEPTH_STENCIL_ATTACHMENT : gl.DEPTH_ATTACHMENT;
|
|
2032
|
+
textureData.renderTarget = descriptor.renderTarget;
|
|
2033
|
+
textureData.cacheKey = cacheKey; // required for copyTextureToTexture()
|
|
2034
|
+
|
|
2035
|
+
if ( useMultisampledRTT ) {
|
|
2036
|
+
|
|
2037
|
+
multisampledRTTExt.framebufferTexture2DMultisampleEXT( gl.FRAMEBUFFER, depthStyle, gl.TEXTURE_2D, textureData.textureGPU, 0, samples );
|
|
2038
|
+
|
|
2039
|
+
} else {
|
|
2040
|
+
|
|
2041
|
+
gl.framebufferTexture2D( gl.FRAMEBUFFER, depthStyle, gl.TEXTURE_2D, textureData.textureGPU, 0 );
|
|
2042
|
+
|
|
2043
|
+
}
|
|
2044
|
+
|
|
2045
|
+
}
|
|
2046
|
+
|
|
2047
|
+
}
|
|
2048
|
+
|
|
2049
|
+
} else {
|
|
2050
|
+
|
|
2051
|
+
// rebind external XR textures
|
|
2052
|
+
|
|
2053
|
+
if ( isXRRenderTarget && hasExternalTextures ) {
|
|
2054
|
+
|
|
2055
|
+
state.bindFramebuffer( gl.FRAMEBUFFER, fb );
|
|
2056
|
+
|
|
2057
|
+
// rebind color
|
|
2058
|
+
|
|
2059
|
+
const textureData = this.get( descriptor.textures[ 0 ] );
|
|
2060
|
+
|
|
2061
|
+
if ( useMultisampledRTT ) {
|
|
2062
|
+
|
|
2063
|
+
multisampledRTTExt.framebufferTexture2DMultisampleEXT( gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, textureData.textureGPU, 0, samples );
|
|
2064
|
+
|
|
2065
|
+
} else {
|
|
2066
|
+
|
|
2067
|
+
gl.framebufferTexture2D( gl.FRAMEBUFFER, gl.COLOR_ATTACHMENT0, gl.TEXTURE_2D, textureData.textureGPU, 0 );
|
|
2068
|
+
|
|
2069
|
+
}
|
|
2070
|
+
|
|
2071
|
+
// rebind depth
|
|
1315
2072
|
|
|
1316
|
-
const textureData = this.get( descriptor.depthTexture );
|
|
1317
2073
|
const depthStyle = stencilBuffer ? gl.DEPTH_STENCIL_ATTACHMENT : gl.DEPTH_ATTACHMENT;
|
|
1318
2074
|
|
|
1319
|
-
|
|
2075
|
+
if ( renderTarget.autoAllocateDepthBuffer === true ) {
|
|
2076
|
+
|
|
2077
|
+
const renderbuffer = renderTargetContextData.xrDepthRenderbuffer;
|
|
2078
|
+
gl.bindRenderbuffer( gl.RENDERBUFFER, renderbuffer );
|
|
2079
|
+
gl.framebufferRenderbuffer( gl.FRAMEBUFFER, depthStyle, gl.RENDERBUFFER, renderbuffer );
|
|
2080
|
+
|
|
2081
|
+
} else {
|
|
2082
|
+
|
|
2083
|
+
const textureData = this.get( descriptor.depthTexture );
|
|
2084
|
+
|
|
2085
|
+
if ( useMultisampledRTT ) {
|
|
2086
|
+
|
|
2087
|
+
multisampledRTTExt.framebufferTexture2DMultisampleEXT( gl.FRAMEBUFFER, depthStyle, gl.TEXTURE_2D, textureData.textureGPU, 0, samples );
|
|
2088
|
+
|
|
2089
|
+
} else {
|
|
2090
|
+
|
|
2091
|
+
gl.framebufferTexture2D( gl.FRAMEBUFFER, depthStyle, gl.TEXTURE_2D, textureData.textureGPU, 0 );
|
|
2092
|
+
|
|
2093
|
+
}
|
|
2094
|
+
|
|
2095
|
+
}
|
|
1320
2096
|
|
|
1321
2097
|
}
|
|
1322
2098
|
|
|
1323
2099
|
}
|
|
1324
2100
|
|
|
1325
|
-
if ( samples > 0 ) {
|
|
2101
|
+
if ( samples > 0 && useMultisampledRTT === false ) {
|
|
1326
2102
|
|
|
1327
2103
|
if ( msaaFb === undefined ) {
|
|
1328
2104
|
|
|
@@ -1366,7 +2142,7 @@ class WebGLBackend extends Backend {
|
|
|
1366
2142
|
if ( depthRenderbuffer === undefined ) {
|
|
1367
2143
|
|
|
1368
2144
|
depthRenderbuffer = gl.createRenderbuffer();
|
|
1369
|
-
this.textureUtils.setupRenderBufferStorage( depthRenderbuffer, descriptor );
|
|
2145
|
+
this.textureUtils.setupRenderBufferStorage( depthRenderbuffer, descriptor, samples );
|
|
1370
2146
|
|
|
1371
2147
|
renderTargetContextData.depthRenderbuffer = depthRenderbuffer;
|
|
1372
2148
|
|
|
@@ -1393,18 +2169,16 @@ class WebGLBackend extends Backend {
|
|
|
1393
2169
|
|
|
1394
2170
|
}
|
|
1395
2171
|
|
|
2172
|
+
/**
|
|
2173
|
+
* Computes the VAO key for the given index and attributes.
|
|
2174
|
+
*
|
|
2175
|
+
* @private
|
|
2176
|
+
* @param {Array<BufferAttribute>} attributes - An array of buffer attributes.
|
|
2177
|
+
* @return {string} The VAO key.
|
|
2178
|
+
*/
|
|
2179
|
+
_getVaoKey( attributes ) {
|
|
1396
2180
|
|
|
1397
|
-
|
|
1398
|
-
|
|
1399
|
-
let key = [];
|
|
1400
|
-
|
|
1401
|
-
if ( index !== null ) {
|
|
1402
|
-
|
|
1403
|
-
const indexData = this.get( index );
|
|
1404
|
-
|
|
1405
|
-
key += ':' + indexData.id;
|
|
1406
|
-
|
|
1407
|
-
}
|
|
2181
|
+
let key = '';
|
|
1408
2182
|
|
|
1409
2183
|
for ( let i = 0; i < attributes.length; i ++ ) {
|
|
1410
2184
|
|
|
@@ -1418,7 +2192,14 @@ class WebGLBackend extends Backend {
|
|
|
1418
2192
|
|
|
1419
2193
|
}
|
|
1420
2194
|
|
|
1421
|
-
|
|
2195
|
+
/**
|
|
2196
|
+
* Creates a VAO from the index and attributes.
|
|
2197
|
+
*
|
|
2198
|
+
* @private
|
|
2199
|
+
* @param {Array<BufferAttribute>} attributes - An array of buffer attributes.
|
|
2200
|
+
* @return {Object} The VAO data.
|
|
2201
|
+
*/
|
|
2202
|
+
_createVao( attributes ) {
|
|
1422
2203
|
|
|
1423
2204
|
const { gl } = this;
|
|
1424
2205
|
|
|
@@ -1429,16 +2210,6 @@ class WebGLBackend extends Backend {
|
|
|
1429
2210
|
|
|
1430
2211
|
gl.bindVertexArray( vaoGPU );
|
|
1431
2212
|
|
|
1432
|
-
if ( index !== null ) {
|
|
1433
|
-
|
|
1434
|
-
const indexData = this.get( index );
|
|
1435
|
-
|
|
1436
|
-
gl.bindBuffer( gl.ELEMENT_ARRAY_BUFFER, indexData.bufferGPU );
|
|
1437
|
-
|
|
1438
|
-
key += ':' + indexData.id;
|
|
1439
|
-
|
|
1440
|
-
}
|
|
1441
|
-
|
|
1442
2213
|
for ( let i = 0; i < attributes.length; i ++ ) {
|
|
1443
2214
|
|
|
1444
2215
|
const attribute = attributes[ i ];
|
|
@@ -1495,6 +2266,13 @@ class WebGLBackend extends Backend {
|
|
|
1495
2266
|
|
|
1496
2267
|
}
|
|
1497
2268
|
|
|
2269
|
+
/**
|
|
2270
|
+
* Creates a transform feedback from the given transform buffers.
|
|
2271
|
+
*
|
|
2272
|
+
* @private
|
|
2273
|
+
* @param {Array<DualAttributeData>} transformBuffers - The transform buffers.
|
|
2274
|
+
* @return {WebGLTransformFeedback} The transform feedback.
|
|
2275
|
+
*/
|
|
1498
2276
|
_getTransformFeedback( transformBuffers ) {
|
|
1499
2277
|
|
|
1500
2278
|
let key = '';
|
|
@@ -1513,7 +2291,7 @@ class WebGLBackend extends Backend {
|
|
|
1513
2291
|
|
|
1514
2292
|
}
|
|
1515
2293
|
|
|
1516
|
-
const gl = this
|
|
2294
|
+
const { gl } = this;
|
|
1517
2295
|
|
|
1518
2296
|
transformFeedbackGPU = gl.createTransformFeedback();
|
|
1519
2297
|
|
|
@@ -1535,7 +2313,13 @@ class WebGLBackend extends Backend {
|
|
|
1535
2313
|
|
|
1536
2314
|
}
|
|
1537
2315
|
|
|
1538
|
-
|
|
2316
|
+
/**
|
|
2317
|
+
* Setups the given bindings.
|
|
2318
|
+
*
|
|
2319
|
+
* @private
|
|
2320
|
+
* @param {Array<BindGroup>} bindings - The bindings.
|
|
2321
|
+
* @param {WebGLProgram} programGPU - The WebGL program.
|
|
2322
|
+
*/
|
|
1539
2323
|
_setupBindings( bindings, programGPU ) {
|
|
1540
2324
|
|
|
1541
2325
|
const gl = this.gl;
|
|
@@ -1565,6 +2349,12 @@ class WebGLBackend extends Backend {
|
|
|
1565
2349
|
|
|
1566
2350
|
}
|
|
1567
2351
|
|
|
2352
|
+
/**
|
|
2353
|
+
* Binds the given uniforms.
|
|
2354
|
+
*
|
|
2355
|
+
* @private
|
|
2356
|
+
* @param {Array<BindGroup>} bindings - The bindings.
|
|
2357
|
+
*/
|
|
1568
2358
|
_bindUniforms( bindings ) {
|
|
1569
2359
|
|
|
1570
2360
|
const { gl, state } = this;
|
|
@@ -1578,7 +2368,8 @@ class WebGLBackend extends Backend {
|
|
|
1578
2368
|
|
|
1579
2369
|
if ( binding.isUniformsGroup || binding.isUniformBuffer ) {
|
|
1580
2370
|
|
|
1581
|
-
|
|
2371
|
+
// TODO USE bindBufferRange to group multiple uniform buffers
|
|
2372
|
+
state.bindBufferBase( gl.UNIFORM_BUFFER, index, bindingData.bufferGPU );
|
|
1582
2373
|
|
|
1583
2374
|
} else if ( binding.isSampledTexture ) {
|
|
1584
2375
|
|
|
@@ -1592,6 +2383,32 @@ class WebGLBackend extends Backend {
|
|
|
1592
2383
|
|
|
1593
2384
|
}
|
|
1594
2385
|
|
|
2386
|
+
/**
|
|
2387
|
+
* Returns `true` if the `WEBGL_multisampled_render_to_texture` extension
|
|
2388
|
+
* should be used when MSAA is enabled.
|
|
2389
|
+
*
|
|
2390
|
+
* @private
|
|
2391
|
+
* @param {RenderTarget} renderTarget - The render target that should be multisampled.
|
|
2392
|
+
* @return {boolean} Whether to use the `WEBGL_multisampled_render_to_texture` extension for MSAA or not.
|
|
2393
|
+
*/
|
|
2394
|
+
_useMultisampledRTT( renderTarget ) {
|
|
2395
|
+
|
|
2396
|
+
return renderTarget.samples > 0 && this.extensions.has( 'WEBGL_multisampled_render_to_texture' ) === true && renderTarget.autoAllocateDepthBuffer !== false;
|
|
2397
|
+
|
|
2398
|
+
}
|
|
2399
|
+
|
|
2400
|
+
/**
|
|
2401
|
+
* Frees internal resources.
|
|
2402
|
+
*/
|
|
2403
|
+
dispose() {
|
|
2404
|
+
|
|
2405
|
+
const extension = this.extensions.get( 'WEBGL_lose_context' );
|
|
2406
|
+
if ( extension ) extension.loseContext();
|
|
2407
|
+
|
|
2408
|
+
this.renderer.domElement.removeEventListener( 'webglcontextlost', this._onContextLost );
|
|
2409
|
+
|
|
2410
|
+
}
|
|
2411
|
+
|
|
1595
2412
|
}
|
|
1596
2413
|
|
|
1597
2414
|
export default WebGLBackend;
|