Browse Source

fix merge conflict

gero3 5 years ago
parent
commit
5f080a887c
41 changed files with 735 additions and 499 deletions
  1. 106 41
      build/three.js
  2. 283 289
      build/three.min.js
  3. 97 41
      build/three.module.js
  4. 10 0
      docs/api/en/audio/Audio.html
  5. 9 13
      docs/api/en/core/BufferAttribute.html
  6. 8 9
      docs/api/en/core/InterleavedBuffer.html
  7. 10 0
      docs/api/zh/audio/Audio.html
  8. 9 12
      docs/api/zh/core/BufferAttribute.html
  9. 8 9
      docs/api/zh/core/InterleavedBuffer.html
  10. 3 3
      examples/js/geometries/LightningStrike.js
  11. 2 2
      examples/js/shaders/VolumeShader.js
  12. 4 3
      examples/jsm/geometries/LightningStrike.js
  13. 15 1
      examples/jsm/misc/MD2Character.d.ts
  14. 2 2
      examples/jsm/shaders/VolumeShader.js
  15. 1 1
      examples/webgl_buffergeometry_custom_attributes_particles.html
  16. 3 3
      examples/webgl_buffergeometry_drawrange.html
  17. 1 1
      examples/webgl_buffergeometry_instancing_dynamic.html
  18. 1 1
      examples/webgl_buffergeometry_instancing_interleaved_dynamic.html
  19. 1 1
      examples/webgl_geometry_dynamic.html
  20. 1 1
      examples/webgl_points_dynamic.html
  21. 1 1
      examples/webgl_simple_gi.html
  22. 3 3
      examples/webvr_paint.html
  23. 3 3
      examples/webvr_vive_paint.html
  24. 52 15
      src/Three.Legacy.js
  25. 3 1
      src/audio/Audio.d.ts
  26. 20 0
      src/audio/Audio.js
  27. 2 1
      src/cameras/CubeCamera.d.ts
  28. 12 0
      src/constants.d.ts
  29. 10 0
      src/constants.js
  30. 6 2
      src/core/BufferAttribute.d.ts
  31. 5 4
      src/core/BufferAttribute.js
  32. 3 2
      src/core/InterleavedBuffer.d.ts
  33. 5 4
      src/core/InterleavedBuffer.js
  34. 2 2
      src/renderers/WebGLRenderer.js
  35. 3 1
      src/renderers/shaders/ShaderChunk/logdepthbuf_fragment.glsl.js
  36. 2 10
      src/renderers/webgl/WebGLAttributes.js
  37. 4 5
      src/renderers/webgl/WebGLProgram.js
  38. 5 1
      src/renderers/webgl/WebGLPrograms.js
  39. 3 2
      src/renderers/webgl/WebGLProperties.d.ts
  40. 8 4
      test/unit/src/core/BufferAttribute.tests.js
  41. 9 5
      test/unit/src/core/InterleavedBuffer.tests.js

+ 106 - 41
build/three.js

@@ -266,6 +266,16 @@
 	var GreaterEqualStencilFunc = 518;
 	var GreaterEqualStencilFunc = 518;
 	var AlwaysStencilFunc = 519;
 	var AlwaysStencilFunc = 519;
 
 
+	var StaticDrawUsage = 35044;
+	var DynamicDrawUsage = 35048;
+	var StreamDrawUsage = 35040;
+	var StaticReadUsage = 35045;
+	var DynamicReadUsage = 35049;
+	var StreamReadUsage = 35041;
+	var StaticCopyUsage = 35046;
+	var DynamicCopyUsage = 35050;
+	var StreamCopyUsage = 35042;
+
 	/**
 	/**
 	 * https://github.com/mrdoob/eventdispatcher.js/
 	 * https://github.com/mrdoob/eventdispatcher.js/
 	 */
 	 */
@@ -8858,7 +8868,7 @@
 		this.count = array !== undefined ? array.length / itemSize : 0;
 		this.count = array !== undefined ? array.length / itemSize : 0;
 		this.normalized = normalized === true;
 		this.normalized = normalized === true;
 
 
-		this.dynamic = false;
+		this.usage = StaticDrawUsage;
 		this.updateRange = { offset: 0, count: - 1 };
 		this.updateRange = { offset: 0, count: - 1 };
 
 
 		this.version = 0;
 		this.version = 0;
@@ -8881,9 +8891,9 @@
 
 
 		onUploadCallback: function () {},
 		onUploadCallback: function () {},
 
 
-		setDynamic: function ( value ) {
+		setUsage: function ( value ) {
 
 
-			this.dynamic = value;
+			this.usage = value;
 
 
 			return this;
 			return this;
 
 
@@ -8897,7 +8907,7 @@
 			this.count = source.count;
 			this.count = source.count;
 			this.normalized = source.normalized;
 			this.normalized = source.normalized;
 
 
-			this.dynamic = source.dynamic;
+			this.usage = source.usage;
 
 
 			return this;
 			return this;
 
 
@@ -14120,7 +14130,7 @@
 
 
 	var lights_fragment_end = "#if defined( RE_IndirectDiffuse )\n\tRE_IndirectDiffuse( irradiance, geometry, material, reflectedLight );\n#endif\n#if defined( RE_IndirectSpecular )\n\tRE_IndirectSpecular( radiance, iblIrradiance, clearcoatRadiance, geometry, material, reflectedLight );\n#endif";
 	var lights_fragment_end = "#if defined( RE_IndirectDiffuse )\n\tRE_IndirectDiffuse( irradiance, geometry, material, reflectedLight );\n#endif\n#if defined( RE_IndirectSpecular )\n\tRE_IndirectSpecular( radiance, iblIrradiance, clearcoatRadiance, geometry, material, reflectedLight );\n#endif";
 
 
-	var logdepthbuf_fragment = "#if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )\n\tgl_FragDepthEXT = vIsPerspective == 1.0 ? log2( vFragDepth ) * logDepthBufFC * 0.5 : gl_FragCoord.z;\n#endif";
+	var logdepthbuf_fragment = "#if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )\n\tgl_FragDepthEXT = vIsPerspective == 0.0 ? gl_FragCoord.z : log2( vFragDepth ) * logDepthBufFC * 0.5;\n#endif";
 
 
 	var logdepthbuf_pars_fragment = "#if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )\n\tuniform float logDepthBufFC;\n\tvarying float vFragDepth;\n\tvarying float vIsPerspective;\n#endif";
 	var logdepthbuf_pars_fragment = "#if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )\n\tuniform float logDepthBufFC;\n\tvarying float vFragDepth;\n\tvarying float vIsPerspective;\n#endif";
 
 
@@ -14940,7 +14950,7 @@
 		function createBuffer( attribute, bufferType ) {
 		function createBuffer( attribute, bufferType ) {
 
 
 			var array = attribute.array;
 			var array = attribute.array;
-			var usage = attribute.dynamic ? 35048 : 35044;
+			var usage = attribute.usage;
 
 
 			var buffer = gl.createBuffer();
 			var buffer = gl.createBuffer();
 
 
@@ -15001,20 +15011,12 @@
 
 
 			gl.bindBuffer( bufferType, buffer );
 			gl.bindBuffer( bufferType, buffer );
 
 
-			if ( attribute.dynamic === false ) {
-
-				gl.bufferData( bufferType, array, 35044 );
-
-			} else if ( updateRange.count === - 1 ) {
+			if ( updateRange.count === - 1 ) {
 
 
 				// Not using update ranges
 				// Not using update ranges
 
 
 				gl.bufferSubData( bufferType, 0, array );
 				gl.bufferSubData( bufferType, 0, array );
 
 
-			} else if ( updateRange.count === 0 ) {
-
-				console.error( 'THREE.WebGLObjects.updateBuffer: dynamic THREE.BufferAttribute marked as needsUpdate but updateRange.count is 0, ensure you are using set methods or updating manually.' );
-
 			} else {
 			} else {
 
 
 				gl.bufferSubData( bufferType, updateRange.offset * array.BYTES_PER_ELEMENT,
 				gl.bufferSubData( bufferType, updateRange.offset * array.BYTES_PER_ELEMENT,
@@ -17643,13 +17645,13 @@
 
 
 	}
 	}
 
 
-	function generateEnvMapBlendingDefine( parameters, material ) {
+	function generateEnvMapBlendingDefine( parameters ) {
 
 
 		var envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
 		var envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
 
 
 		if ( parameters.envMap ) {
 		if ( parameters.envMap ) {
 
 
-			switch ( material.combine ) {
+			switch ( parameters.combine ) {
 
 
 				case MultiplyOperation:
 				case MultiplyOperation:
 					envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
 					envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
@@ -17682,7 +17684,7 @@
 		var shadowMapTypeDefine = generateShadowMapTypeDefine( parameters );
 		var shadowMapTypeDefine = generateShadowMapTypeDefine( parameters );
 		var envMapTypeDefine = generateEnvMapTypeDefine( parameters );
 		var envMapTypeDefine = generateEnvMapTypeDefine( parameters );
 		var envMapModeDefine = generateEnvMapModeDefine( parameters );
 		var envMapModeDefine = generateEnvMapModeDefine( parameters );
-		var envMapBlendingDefine = generateEnvMapBlendingDefine( parameters, material );
+		var envMapBlendingDefine = generateEnvMapBlendingDefine( parameters );
 
 
 
 
 		var gammaFactorDefine = ( renderer.gammaFactor > 0 ) ? renderer.gammaFactor : 1.0;
 		var gammaFactorDefine = ( renderer.gammaFactor > 0 ) ? renderer.gammaFactor : 1.0;
@@ -17695,8 +17697,7 @@
 
 
 		var prefixVertex, prefixFragment;
 		var prefixVertex, prefixFragment;
 
 
-		var renderTarget = renderer.getRenderTarget();
-		var numMultiviewViews = renderTarget && renderTarget.isWebGLMultiviewRenderTarget ? renderTarget.numViews : 0;
+		var numMultiviewViews = parameters.numMultiviewViews;
 
 
 		if ( material.isRawShaderMaterial ) {
 		if ( material.isRawShaderMaterial ) {
 
 
@@ -18224,7 +18225,7 @@
 		};
 		};
 
 
 		var parameterNames = [
 		var parameterNames = [
-			"precision", "supportsVertexTextures", "instancing",
+			"precision", "supportsVertexTextures", "instancing", "numMultiviewViews",
 			"map", "mapEncoding", "matcap", "matcapEncoding", "envMap", "envMapMode", "envMapEncoding",
 			"map", "mapEncoding", "matcap", "matcapEncoding", "envMap", "envMapMode", "envMapEncoding",
 			"lightMap", "aoMap", "emissiveMap", "emissiveMapEncoding", "bumpMap", "normalMap", "objectSpaceNormalMap", "tangentSpaceNormalMap", "clearcoatNormalMap", "displacementMap", "specularMap",
 			"lightMap", "aoMap", "emissiveMap", "emissiveMapEncoding", "bumpMap", "normalMap", "objectSpaceNormalMap", "tangentSpaceNormalMap", "clearcoatNormalMap", "displacementMap", "specularMap",
 			"roughnessMap", "metalnessMap", "gradientMap",
 			"roughnessMap", "metalnessMap", "gradientMap",
@@ -18327,6 +18328,7 @@
 			}
 			}
 
 
 			var currentRenderTarget = renderer.getRenderTarget();
 			var currentRenderTarget = renderer.getRenderTarget();
+			var numMultiviewViews = currentRenderTarget && currentRenderTarget.isWebGLMultiviewRenderTarget ? currentRenderTarget.numViews : 0;
 
 
 			var parameters = {
 			var parameters = {
 
 
@@ -18339,6 +18341,7 @@
 				instancing: object.isInstancedMesh === true,
 				instancing: object.isInstancedMesh === true,
 
 
 				supportsVertexTextures: vertexTextures,
 				supportsVertexTextures: vertexTextures,
+				numMultiviewViews: numMultiviewViews,
 				outputEncoding: getTextureEncodingFromMap( ( ! currentRenderTarget ) ? null : currentRenderTarget.texture, renderer.gammaOutput ),
 				outputEncoding: getTextureEncodingFromMap( ( ! currentRenderTarget ) ? null : currentRenderTarget.texture, renderer.gammaOutput ),
 				map: !! material.map,
 				map: !! material.map,
 				mapEncoding: getTextureEncodingFromMap( material.map, renderer.gammaInput ),
 				mapEncoding: getTextureEncodingFromMap( material.map, renderer.gammaInput ),
@@ -25338,7 +25341,7 @@
 
 
 				if ( material.isShaderMaterial ) {
 				if ( material.isShaderMaterial ) {
 
 
-					material.uniformsNeedUpdate = false;
+					material.uniformsNeedUpdate = false; // #15581
 
 
 				}
 				}
 
 
@@ -25846,7 +25849,7 @@
 		//
 		//
 		this.setFramebuffer = function ( value ) {
 		this.setFramebuffer = function ( value ) {
 
 
-			if ( _framebuffer !== value ) { _gl.bindFramebuffer( 36160, value ); }
+			if ( _framebuffer !== value && _currentRenderTarget === null ) { _gl.bindFramebuffer( 36160, value ); }
 
 
 			_framebuffer = value;
 			_framebuffer = value;
 
 
@@ -26143,7 +26146,7 @@
 		this.stride = stride;
 		this.stride = stride;
 		this.count = array !== undefined ? array.length / stride : 0;
 		this.count = array !== undefined ? array.length / stride : 0;
 
 
-		this.dynamic = false;
+		this.usage = StaticDrawUsage;
 		this.updateRange = { offset: 0, count: - 1 };
 		this.updateRange = { offset: 0, count: - 1 };
 
 
 		this.version = 0;
 		this.version = 0;
@@ -26166,9 +26169,9 @@
 
 
 		onUploadCallback: function () {},
 		onUploadCallback: function () {},
 
 
-		setDynamic: function ( value ) {
+		setUsage: function ( value ) {
 
 
-			this.dynamic = value;
+			this.usage = value;
 
 
 			return this;
 			return this;
 
 
@@ -26179,7 +26182,7 @@
 			this.array = new source.array.constructor( source.array );
 			this.array = new source.array.constructor( source.array );
 			this.count = source.count;
 			this.count = source.count;
 			this.stride = source.stride;
 			this.stride = source.stride;
-			this.dynamic = source.dynamic;
+			this.usage = source.usage;
 
 
 			return this;
 			return this;
 
 
@@ -41587,6 +41590,8 @@
 		this.buffer = null;
 		this.buffer = null;
 		this.detune = 0;
 		this.detune = 0;
 		this.loop = false;
 		this.loop = false;
+		this.loopStart = 0;
+		this.loopEnd = 0;
 		this.startTime = 0;
 		this.startTime = 0;
 		this.offset = 0;
 		this.offset = 0;
 		this.duration = undefined;
 		this.duration = undefined;
@@ -41673,6 +41678,8 @@
 
 
 			source.buffer = this.buffer;
 			source.buffer = this.buffer;
 			source.loop = this.loop;
 			source.loop = this.loop;
+			source.loopStart = this.loopStart;
+			source.loopEnd = this.loopEnd;
 			source.onended = this.onEnded.bind( this );
 			source.onended = this.onEnded.bind( this );
 			this.startTime = this.context.currentTime;
 			this.startTime = this.context.currentTime;
 			source.start( this.startTime, this.offset, this.duration );
 			source.start( this.startTime, this.offset, this.duration );
@@ -41903,6 +41910,22 @@
 
 
 		},
 		},
 
 
+		setLoopStart: function ( value ) {
+
+			this.loopStart = value;
+
+			return this;
+
+		},
+
+		setLoopEnd: function ( value ) {
+
+			this.loopEnd = value;
+
+			return this;
+
+		},
+
 		getVolume: function () {
 		getVolume: function () {
 
 
 			return this.gain.gain.value;
 			return this.gain.gain.value;
@@ -48368,29 +48391,43 @@
 				console.warn( 'THREE.BufferAttribute: .length has been deprecated. Use .count instead.' );
 				console.warn( 'THREE.BufferAttribute: .length has been deprecated. Use .count instead.' );
 				return this.array.length;
 				return this.array.length;
 
 
+			}
+		},
+		dynamic: {
+			get: function () {
+
+				console.warn( 'THREE.BufferAttribute: .dynamic has been deprecated. Use .usage instead.' );
+				return this.usage === DynamicDrawUsage;
+
+			},
+			set: function ( value ) {
+
+				console.warn( 'THREE.BufferAttribute: .dynamic has been deprecated. Use .usage instead.' );
+				this.setUsage( value );
+
 			}
 			}
 		}
 		}
 
 
 	} );
 	} );
 
 
 	Object.assign( BufferAttribute.prototype, {
 	Object.assign( BufferAttribute.prototype, {
+		setDynamic: function ( value ) {
+
+			console.warn( 'THREE.BufferAttribute: .setDynamic() has been deprecated. Use .setUsage() instead.' );
+			this.setUsage( value === true ? DynamicDrawUsage : StaticDrawUsage );
+			return this;
 
 
+		},
 		copyIndicesArray: function ( /* indices */ ) {
 		copyIndicesArray: function ( /* indices */ ) {
 
 
 			console.error( 'THREE.BufferAttribute: .copyIndicesArray() has been removed.' );
 			console.error( 'THREE.BufferAttribute: .copyIndicesArray() has been removed.' );
 
 
 		},
 		},
-		setArray: function ( array ) {
-
-			console.warn( 'THREE.BufferAttribute: .setArray has been deprecated. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
-
-			this.count = array !== undefined ? array.length / this.itemSize : 0;
-			this.array = array;
+		setArray: function ( /* array */ ) {
 
 
-			return this;
+			console.error( 'THREE.BufferAttribute: .setArray has been removed. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
 
 
 		}
 		}
-
 	} );
 	} );
 
 
 	Object.assign( BufferGeometry.prototype, {
 	Object.assign( BufferGeometry.prototype, {
@@ -48452,21 +48489,40 @@
 
 
 	} );
 	} );
 
 
-	Object.assign( InterleavedBuffer.prototype, {
+	Object.defineProperties( InterleavedBuffer.prototype, {
 
 
-		setArray: function ( array ) {
+		dynamic: {
+			get: function () {
 
 
-			console.warn( 'THREE.InterleavedBuffer: .setArray has been deprecated. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
+				console.warn( 'THREE.InterleavedBuffer: .length has been deprecated. Use .usage instead.' );
+				return this.usage === DynamicDrawUsage;
 
 
-			this.count = array !== undefined ? array.length / this.stride : 0;
-			this.array = array;
+			},
+			set: function ( value ) {
 
 
-			return this;
+				console.warn( 'THREE.InterleavedBuffer: .length has been deprecated. Use .usage instead.' );
+				this.setUsage( value );
 
 
+			}
 		}
 		}
 
 
 	} );
 	} );
 
 
+	Object.assign( InterleavedBuffer.prototype, {
+		setDynamic: function ( value ) {
+
+			console.warn( 'THREE.InterleavedBuffer: .setDynamic() has been deprecated. Use .setUsage() instead.' );
+			this.setUsage( value === true ? DynamicDrawUsage : StaticDrawUsage );
+			return this;
+
+		},
+		setArray: function ( /* array */ ) {
+
+			console.error( 'THREE.InterleavedBuffer: .setArray has been removed. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
+
+		}
+	} );
+
 	//
 	//
 
 
 	Object.assign( ExtrudeBufferGeometry.prototype, {
 	Object.assign( ExtrudeBufferGeometry.prototype, {
@@ -49319,6 +49375,9 @@
 	exports.DstAlphaFactor = DstAlphaFactor;
 	exports.DstAlphaFactor = DstAlphaFactor;
 	exports.DstColorFactor = DstColorFactor;
 	exports.DstColorFactor = DstColorFactor;
 	exports.DynamicBufferAttribute = DynamicBufferAttribute;
 	exports.DynamicBufferAttribute = DynamicBufferAttribute;
+	exports.DynamicCopyUsage = DynamicCopyUsage;
+	exports.DynamicDrawUsage = DynamicDrawUsage;
+	exports.DynamicReadUsage = DynamicReadUsage;
 	exports.EdgesGeometry = EdgesGeometry;
 	exports.EdgesGeometry = EdgesGeometry;
 	exports.EdgesHelper = EdgesHelper;
 	exports.EdgesHelper = EdgesHelper;
 	exports.EllipseCurve = EllipseCurve;
 	exports.EllipseCurve = EllipseCurve;
@@ -49590,7 +49649,13 @@
 	exports.SrcAlphaFactor = SrcAlphaFactor;
 	exports.SrcAlphaFactor = SrcAlphaFactor;
 	exports.SrcAlphaSaturateFactor = SrcAlphaSaturateFactor;
 	exports.SrcAlphaSaturateFactor = SrcAlphaSaturateFactor;
 	exports.SrcColorFactor = SrcColorFactor;
 	exports.SrcColorFactor = SrcColorFactor;
+	exports.StaticCopyUsage = StaticCopyUsage;
+	exports.StaticDrawUsage = StaticDrawUsage;
+	exports.StaticReadUsage = StaticReadUsage;
 	exports.StereoCamera = StereoCamera;
 	exports.StereoCamera = StereoCamera;
+	exports.StreamCopyUsage = StreamCopyUsage;
+	exports.StreamDrawUsage = StreamDrawUsage;
+	exports.StreamReadUsage = StreamReadUsage;
 	exports.StringKeyframeTrack = StringKeyframeTrack;
 	exports.StringKeyframeTrack = StringKeyframeTrack;
 	exports.SubtractEquation = SubtractEquation;
 	exports.SubtractEquation = SubtractEquation;
 	exports.SubtractiveBlending = SubtractiveBlending;
 	exports.SubtractiveBlending = SubtractiveBlending;

File diff suppressed because it is too large
+ 283 - 289
build/three.min.js


File diff suppressed because it is too large
+ 97 - 41
build/three.module.js


+ 10 - 0
docs/api/en/audio/Audio.html

@@ -188,6 +188,16 @@
 		(whether playback should loop).
 		(whether playback should loop).
 		</p>
 		</p>
 
 
+		<h3>[method:Audio setLoopStart]( [param:Float value] )</h3>
+		<p>
+		Set [link:https://developer.mozilla.org/en-US/docs/Web/API/AudioBufferSourceNode/loopStart source.loopStart] to *value*.
+		</p>
+
+		<h3>[method:Audio setLoopEnd]( [param:Float value] )</h3>
+		<p>
+		Set [link:https://developer.mozilla.org/en-US/docs/Web/API/AudioBufferSourceNode/loopEnd source.loopEnd] to *value*.
+		</p>
+
 		<h3>[method:Audio setMediaElementSource]( mediaElement )</h3>
 		<h3>[method:Audio setMediaElementSource]( mediaElement )</h3>
 		<p>
 		<p>
 		Applies the given object of type [link:https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement HTMLMediaElement] as the source of this audio.<br />
 		Applies the given object of type [link:https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement HTMLMediaElement] as the source of this audio.<br />

+ 9 - 13
docs/api/en/core/BufferAttribute.html

@@ -58,16 +58,6 @@
 		then this will count the number of such vectors stored.
 		then this will count the number of such vectors stored.
 		</p>
 		</p>
 
 
-		<h3>[property:Boolean dynamic]</h3>
-		<p>
-			Whether the buffer is dynamic or not. Default is *false*.<br />
-
-			If false, the GPU is informed that contents of the buffer are likely to be used often and not change often.
-			This corresponds to the  [link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData gl.STATIC_DRAW] flag.<br />
-			if true, the GPU is informed that contents of the buffer are likely to be used often and change often.
-			This corresponds to the  [link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData gl.DYNAMIC_DRAW] flag.
-		</p>
-
 		<h3>[property:Boolean isBufferAttribute]</h3>
 		<h3>[property:Boolean isBufferAttribute]</h3>
 		<p>
 		<p>
 			Used to check whether this or derived classes are BufferAttributes. Default is *true*.<br /><br />
 			Used to check whether this or derived classes are BufferAttributes. Default is *true*.<br /><br />
@@ -111,10 +101,16 @@
 			related to color).
 			related to color).
 		</p>
 		</p>
 
 
+		<h3>[property:Usage usage]</h3>
+		<p>
+			Defines the intended usage pattern of the data store for optimization purposes. Corresponds to the *usage* parameter of
+			[link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData WebGLRenderingContext.bufferData]().
+			Default is *THREE.StaticDrawUsage*.
+		</p>
+
 		<h3>[property:Integer version]</h3>
 		<h3>[property:Integer version]</h3>
 		<p>A version number, incremented every time the [page:BufferAttribute.needsUpdate needsUpdate] property is set to true.</p>
 		<p>A version number, incremented every time the [page:BufferAttribute.needsUpdate needsUpdate] property is set to true.</p>
 
 
-
 		<h2>Methods</h2>
 		<h2>Methods</h2>
 
 
 		<h3>[method:BufferAttribute clone]() </h3>
 		<h3>[method:BufferAttribute clone]() </h3>
@@ -178,8 +174,8 @@
 		being a [page:TypedArray].
 		being a [page:TypedArray].
 		</p>
 		</p>
 
 
-		<h3>[method:BufferAttribute setDynamic] ( [param:Boolean value] ) </h3>
-		<p>Set [page:BufferAttribute.dynamic dynamic] to value.</p>
+		<h3>[method:BufferAttribute setUsage] ( [param:Usage value] ) </h3>
+		<p>Set [page:BufferAttribute.usage usage] to value.</p>
 
 
 		<h3>[method:BufferAttribute setX]( [param:Integer index], [param:Float x] ) </h3>
 		<h3>[method:BufferAttribute setX]( [param:Integer index], [param:Float x] ) </h3>
 		<p>Sets the x component of the vector at the given index.</p>
 		<p>Sets the x component of the vector at the given index.</p>

+ 8 - 9
docs/api/en/core/InterleavedBuffer.html

@@ -44,11 +44,6 @@
 		Gives the total number of elements in the array.
 		Gives the total number of elements in the array.
 		</p>
 		</p>
 
 
-		<h3>[property:Boolean dynamic]</h3>
-		<p>
-		Default is *false*.
-		</p>
-
 		<h3>[property:Object updateRange]</h3>
 		<h3>[property:Object updateRange]</h3>
 		<p>
 		<p>
 		Object containing offset and count.
 		Object containing offset and count.
@@ -79,13 +74,14 @@
 		Default is *false*. Setting this to true increments [page:InterleavedBuffer.version version].
 		Default is *false*. Setting this to true increments [page:InterleavedBuffer.version version].
 		</p>
 		</p>
 
 
-		<h2>Methods</h2>
-
-		<h3>[method:InterleavedBuffer setDynamic] ( [param:Boolean value] ) </h3>
+		<h3>[property:Usage usage]</h3>
 		<p>
 		<p>
-			Set [page:InterleavedBuffer.dynamic dynamic] to value.
+			Defines the intended usage pattern of the data store for optimization purposes. Corresponds to the *usage* parameter of
+			[link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData WebGLRenderingContext.bufferData]().
 		</p>
 		</p>
 
 
+		<h2>Methods</h2>
+
 		<h3>[method:InterleavedBuffer copy]( [param:InterleavedBuffer source] ) </h3>
 		<h3>[method:InterleavedBuffer copy]( [param:InterleavedBuffer source] ) </h3>
 		<p>
 		<p>
 		 Copies another [name] to this [name].
 		 Copies another [name] to this [name].
@@ -107,6 +103,9 @@
 			Creates a clone of this [name].
 			Creates a clone of this [name].
 		</p>
 		</p>
 
 
+		<h3>[method:BufferAttribute setUsage] ( [param:Usage value] ) </h3>
+		<p>Set [page:BufferAttribute.usage usage] to value.</p>
+
 		<h2>Source</h2>
 		<h2>Source</h2>
 
 
 		<p>
 		<p>

+ 10 - 0
docs/api/zh/audio/Audio.html

@@ -184,6 +184,16 @@
 		(是否循环播放).
 		(是否循环播放).
 		</p>
 		</p>
 
 
+		<h3>[method:Audio setLoopStart]( [param:Float value] )</h3>
+		<p>
+		Set [link:https://developer.mozilla.org/en-US/docs/Web/API/AudioBufferSourceNode/loopStart source.loopStart] to *value*.
+		</p>
+
+		<h3>[method:Audio setLoopEnd]( [param:Float value] )</h3>
+		<p>
+		Set [link:https://developer.mozilla.org/en-US/docs/Web/API/AudioBufferSourceNode/loopEnd source.loopEnd] to *value*.
+		</p>
+
 		<h3>[method:Audio setMediaElementSource]( mediaElement )</h3>
 		<h3>[method:Audio setMediaElementSource]( mediaElement )</h3>
 		<p>
 		<p>
 		应用[link:https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement HTMLMediaElement]类型对象作为音源.<br />
 		应用[link:https://developer.mozilla.org/en-US/docs/Web/API/HTMLMediaElement HTMLMediaElement]类型对象作为音源.<br />

+ 9 - 12
docs/api/zh/core/BufferAttribute.html

@@ -52,16 +52,6 @@
 			若缓存存储三元组(例如顶点位置、法向量、颜色值),则该值应等于队列中三元组的个数。
 			若缓存存储三元组(例如顶点位置、法向量、颜色值),则该值应等于队列中三元组的个数。
 		</p>
 		</p>
 
 
-		<h3>[property:Boolean dynamic]</h3>
-		<p>
-			不论缓存是否是动态的,默认值都将是 *false*<br />
-
-			如果该值为 false,即告知 GPU 缓存中的数据会经常使用但不经常变化。
-			该值与 [link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData gl.STATIC_DRAW] 标志位相一致。<br />
-			如果该值为 true,即告知 GPU 缓存中的数据会经常使用且经常变化。
-			该值与 [link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData gl.DYNAMIC_DRAW] 标志位相一致。
-		</p>
-
 		<h3>[property:Boolean isBufferAttribute]</h3>
 		<h3>[property:Boolean isBufferAttribute]</h3>
 		<p>
 		<p>
 			指示当前类或派生类是 BufferAttributes. 默认值为 *true*.<br /><br />
 			指示当前类或派生类是 BufferAttributes. 默认值为 *true*.<br /><br />
@@ -101,6 +91,13 @@
 			该值只可以被用于更新某些矢量数据(例如,颜色相关数据)。
 			该值只可以被用于更新某些矢量数据(例如,颜色相关数据)。
 		</p>
 		</p>
 
 
+		<h3>[property:Usage usage]</h3>
+		<p>
+			Defines the intended usage pattern of the data store for optimization purposes. Corresponds to the *usage* parameter of
+			[link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData WebGLRenderingContext.bufferData]().
+			Default is *THREE.StaticDrawUsage*.
+		</p>
+
 		<h3>[property:Integer version]</h3>
 		<h3>[property:Integer version]</h3>
 		<p>版本号,当 [page:BufferAttribute.needsUpdate needsUpdate] 被设置为 true 时,该值会自增。</p>
 		<p>版本号,当 [page:BufferAttribute.needsUpdate needsUpdate] 被设置为 true 时,该值会自增。</p>
 
 
@@ -158,8 +155,8 @@
 		特别的, 对将 [page:Array value] 转为  [page:TypedArray] 的要求详见上述链接。
 		特别的, 对将 [page:Array value] 转为  [page:TypedArray] 的要求详见上述链接。
 		</p>
 		</p>
 
 
-		<h3>[method:BufferAttribute setDynamic] ( [param:Boolean value] ) </h3>
-		<p>将 [page:BufferAttribute.dynamic dynamic] 设置为 value.</p>
+		<h3>[method:BufferAttribute setUsage] ( [param:Usage value] ) </h3>
+		<p>Set [page:BufferAttribute.usage usage] to value.</p>
 
 
 		<h3>[method:BufferAttribute setX]( [param:Integer index], [param:Float x] ) </h3>
 		<h3>[method:BufferAttribute setX]( [param:Integer index], [param:Float x] ) </h3>
 		<p>设置给定索引的矢量的第一维数据(设置 X 值)。</p>
 		<p>设置给定索引的矢量的第一维数据(设置 X 值)。</p>

+ 8 - 9
docs/api/zh/core/InterleavedBuffer.html

@@ -44,11 +44,6 @@
 			类型化队列中,所有元素的数目。
 			类型化队列中,所有元素的数目。
 		</p>
 		</p>
 
 
-		<h3>[property:Boolean dynamic]</h3>
-		<p>
-			默认值为 *false*。
-		</p>
-
 		<h3>[property:Object updateRange]</h3>
 		<h3>[property:Object updateRange]</h3>
 		<p>
 		<p>
 			对象存储着需要更新的数据的偏移量和数量。
 			对象存储着需要更新的数据的偏移量和数量。
@@ -79,13 +74,14 @@
 			默认值为 *false*。该值被设置为 true 时,会导致 [page:InterleavedBuffer.version version] 增加。
 			默认值为 *false*。该值被设置为 true 时,会导致 [page:InterleavedBuffer.version version] 增加。
 		</p>
 		</p>
 
 
-		<h2>方法</h2>
-
-		<h3>[method:InterleavedBuffer setDynamic] ( [param:Boolean value] ) </h3>
+		<h3>[property:Usage usage]</h3>
 		<p>
 		<p>
-			根据输入参数设置 [page:InterleavedBuffer.dynamic dynamic] 的值。
+			Defines the intended usage pattern of the data store for optimization purposes. Corresponds to the *usage* parameter of
+			[link:https://developer.mozilla.org/en-US/docs/Web/API/WebGLRenderingContext/bufferData WebGLRenderingContext.bufferData]().
 		</p>
 		</p>
 
 
+		<h2>方法</h2>
+
 		<h3>[method:InterleavedBuffer copy]( [param:InterleavedBuffer source] ) </h3>
 		<h3>[method:InterleavedBuffer copy]( [param:InterleavedBuffer source] ) </h3>
 		<p>
 		<p>
 			将参数指定的 [name] 拷贝到当前 [name]。
 			将参数指定的 [name] 拷贝到当前 [name]。
@@ -107,6 +103,9 @@
 			克隆当前 [name]。
 			克隆当前 [name]。
 		</p>
 		</p>
 
 
+		<h3>[method:BufferAttribute setUsage] ( [param:Usage value] ) </h3>
+		<p>Set [page:BufferAttribute.usage usage] to value.</p>
+
 		<h2>源代码</h2>
 		<h2>源代码</h2>
 
 
 		<p>
 		<p>

+ 3 - 3
examples/js/geometries/LightningStrike.js

@@ -430,11 +430,11 @@ THREE.LightningStrike.prototype.createMesh = function () {
 
 
 	if ( ! this.isStatic ) {
 	if ( ! this.isStatic ) {
 
 
-		this.index.dynamic = true;
-		this.positionAttribute.dynamic = true;
+		this.index.usage = THREE.DynamicDrawUsage;
+		this.positionAttribute.usage = THREE.DynamicDrawUsage;
 		if ( this.generateUVs ) {
 		if ( this.generateUVs ) {
 
 
-			this.uvsAttribute.dynamic = true;
+			this.uvsAttribute.usage = THREE.DynamicDrawUsage;
 
 
 		}
 		}
 
 

+ 2 - 2
examples/js/shaders/VolumeShader.js

@@ -67,8 +67,8 @@ THREE.VolumeRenderShader1 = {
 		"		void main() {",
 		"		void main() {",
 		// Prepare transforms to map to "camera view". See also:
 		// Prepare transforms to map to "camera view". See also:
 		// https://threejs.org/docs/#api/renderers/webgl/WebGLProgram
 		// https://threejs.org/docs/#api/renderers/webgl/WebGLProgram
-		"				mat4 viewtransformf = viewMatrix;",
-		"				mat4 viewtransformi = inversemat(viewMatrix);",
+		"				mat4 viewtransformf = modelViewMatrix;",
+		"				mat4 viewtransformi = inversemat(modelViewMatrix);",
 
 
 		// Project local vertex coordinate to camera position. Then do a step
 		// Project local vertex coordinate to camera position. Then do a step
 		// backward (in cam coords) to the near clipping plane, and project back. Do
 		// backward (in cam coords) to the near clipping plane, and project back. Do

+ 4 - 3
examples/jsm/geometries/LightningStrike.js

@@ -103,6 +103,7 @@
 
 
 import {
 import {
 	BufferGeometry,
 	BufferGeometry,
+	DynamicDrawUsage,
 	Float32BufferAttribute,
 	Float32BufferAttribute,
 	Math as _Math,
 	Math as _Math,
 	Uint32BufferAttribute,
 	Uint32BufferAttribute,
@@ -439,11 +440,11 @@ LightningStrike.prototype.createMesh = function () {
 
 
 	if ( ! this.isStatic ) {
 	if ( ! this.isStatic ) {
 
 
-		this.index.dynamic = true;
-		this.positionAttribute.dynamic = true;
+		this.index.usage = DynamicDrawUsage;
+		this.positionAttribute.usage = DynamicDrawUsage;
 		if ( this.generateUVs ) {
 		if ( this.generateUVs ) {
 
 
-			this.uvsAttribute.dynamic = true;
+			this.uvsAttribute.usage = DynamicDrawUsage;
 
 
 		}
 		}
 
 

+ 15 - 1
examples/jsm/misc/MD2Character.d.ts

@@ -1,9 +1,17 @@
 import {
 import {
 	Object3D,
 	Object3D,
 	Mesh,
 	Mesh,
-	Texture
+	Texture,
+	AnimationMixer
 } from '../../../src/Three';
 } from '../../../src/Three';
 
 
+export interface MD2PartsConfig {
+	baseUrl: string,
+	body: string,
+	skins: string[],
+	weapons: [string, string][],
+}
+
 export class MD2Character {
 export class MD2Character {
 
 
 	constructor();
 	constructor();
@@ -14,7 +22,13 @@ export class MD2Character {
 	meshWeapon: Mesh | null;
 	meshWeapon: Mesh | null;
 	skinsBody: Texture[];
 	skinsBody: Texture[];
 	skinsWeapon: Texture[];
 	skinsWeapon: Texture[];
+	weapons: Mesh[];
+	activeAnimation: string | null;
+	mixer: AnimationMixer | null;
+	loadCounter: number;
 
 
+	onLoadComplete(): void;
+	loadParts( config: MD2PartsConfig ): void;
 	setPlaybackRate( rate: number ): void;
 	setPlaybackRate( rate: number ): void;
 	setWireframe( wireframeEnabled: boolean ): void;
 	setWireframe( wireframeEnabled: boolean ): void;
 	setSkin( index: number ): void;
 	setSkin( index: number ): void;

+ 2 - 2
examples/jsm/shaders/VolumeShader.js

@@ -72,8 +72,8 @@ var VolumeRenderShader1 = {
 		"		void main() {",
 		"		void main() {",
 		// Prepare transforms to map to "camera view". See also:
 		// Prepare transforms to map to "camera view". See also:
 		// https://threejs.org/docs/#api/renderers/webgl/WebGLProgram
 		// https://threejs.org/docs/#api/renderers/webgl/WebGLProgram
-		"				mat4 viewtransformf = viewMatrix;",
-		"				mat4 viewtransformi = inversemat(viewMatrix);",
+		"				mat4 viewtransformf = modelViewMatrix;",
+		"				mat4 viewtransformi = inversemat(modelViewMatrix);",
 
 
 		// Project local vertex coordinate to camera position. Then do a step
 		// Project local vertex coordinate to camera position. Then do a step
 		// backward (in cam coords) to the near clipping plane, and project back. Do
 		// backward (in cam coords) to the near clipping plane, and project back. Do

+ 1 - 1
examples/webgl_buffergeometry_custom_attributes_particles.html

@@ -114,7 +114,7 @@
 
 
 				geometry.addAttribute( 'position', new THREE.Float32BufferAttribute( positions, 3 ) );
 				geometry.addAttribute( 'position', new THREE.Float32BufferAttribute( positions, 3 ) );
 				geometry.addAttribute( 'color', new THREE.Float32BufferAttribute( colors, 3 ) );
 				geometry.addAttribute( 'color', new THREE.Float32BufferAttribute( colors, 3 ) );
-				geometry.addAttribute( 'size', new THREE.Float32BufferAttribute( sizes, 1 ).setDynamic( true ) );
+				geometry.addAttribute( 'size', new THREE.Float32BufferAttribute( sizes, 1 ).setUsage( THREE.DynamicDrawUsage ) );
 
 
 				particleSystem = new THREE.Points( geometry, shaderMaterial );
 				particleSystem = new THREE.Points( geometry, shaderMaterial );
 
 

+ 3 - 3
examples/webgl_buffergeometry_drawrange.html

@@ -139,7 +139,7 @@
 				}
 				}
 
 
 				particles.setDrawRange( 0, particleCount );
 				particles.setDrawRange( 0, particleCount );
-				particles.addAttribute( 'position', new THREE.BufferAttribute( particlePositions, 3 ).setDynamic( true ) );
+				particles.addAttribute( 'position', new THREE.BufferAttribute( particlePositions, 3 ).setUsage( THREE.DynamicDrawUsage ) );
 
 
 				// create the particle system
 				// create the particle system
 				pointCloud = new THREE.Points( particles, pMaterial );
 				pointCloud = new THREE.Points( particles, pMaterial );
@@ -147,8 +147,8 @@
 
 
 				var geometry = new THREE.BufferGeometry();
 				var geometry = new THREE.BufferGeometry();
 
 
-				geometry.addAttribute( 'position', new THREE.BufferAttribute( positions, 3 ).setDynamic( true ) );
-				geometry.addAttribute( 'color', new THREE.BufferAttribute( colors, 3 ).setDynamic( true ) );
+				geometry.addAttribute( 'position', new THREE.BufferAttribute( positions, 3 ).setUsage( THREE.DynamicDrawUsage ) );
+				geometry.addAttribute( 'color', new THREE.BufferAttribute( colors, 3 ).setUsage( THREE.DynamicDrawUsage ) );
 
 
 				geometry.computeBoundingSphere();
 				geometry.computeBoundingSphere();
 
 

+ 1 - 1
examples/webgl_buffergeometry_instancing_dynamic.html

@@ -147,7 +147,7 @@
 			}
 			}
 
 
 			offsetAttribute = new THREE.InstancedBufferAttribute( new Float32Array( offsets ), 3 );
 			offsetAttribute = new THREE.InstancedBufferAttribute( new Float32Array( offsets ), 3 );
-			orientationAttribute = new THREE.InstancedBufferAttribute( new Float32Array( orientations ), 4 ).setDynamic( true );
+			orientationAttribute = new THREE.InstancedBufferAttribute( new Float32Array( orientations ), 4 ).setUsage( THREE.DynamicDrawUsage );
 
 
 			geometry.addAttribute( 'offset', offsetAttribute );
 			geometry.addAttribute( 'offset', offsetAttribute );
 			geometry.addAttribute( 'orientation', orientationAttribute );
 			geometry.addAttribute( 'orientation', orientationAttribute );

+ 1 - 1
examples/webgl_buffergeometry_instancing_interleaved_dynamic.html

@@ -162,7 +162,7 @@
 			geometry.setIndex( new THREE.BufferAttribute( indices, 1 ) );
 			geometry.setIndex( new THREE.BufferAttribute( indices, 1 ) );
 
 
 			// per instance data
 			// per instance data
-			instanceBuffer = new THREE.InstancedInterleavedBuffer( new Float32Array( instances * 8 ), 8, 1 ).setDynamic( true );
+			instanceBuffer = new THREE.InstancedInterleavedBuffer( new Float32Array( instances * 8 ), 8, 1 ).setUsage( THREE.DynamicDrawUsage );
 			var offsets = new THREE.InterleavedBufferAttribute( instanceBuffer, 3, 0 );
 			var offsets = new THREE.InterleavedBufferAttribute( instanceBuffer, 3, 0 );
 
 
 			var vector = new THREE.Vector4();
 			var vector = new THREE.Vector4();

+ 1 - 1
examples/webgl_geometry_dynamic.html

@@ -58,7 +58,7 @@
 				geometry.rotateX( - Math.PI / 2 );
 				geometry.rotateX( - Math.PI / 2 );
 
 
 				var position = geometry.attributes.position;
 				var position = geometry.attributes.position;
-				position.dynamic = true;
+				position.usage = THREE.DynamicDrawUsage;
 
 
 				for ( var i = 0; i < position.count; i ++ ) {
 				for ( var i = 0; i < position.count; i ++ ) {
 
 

+ 1 - 1
examples/webgl_points_dynamic.html

@@ -180,7 +180,7 @@
 				geometry.addAttribute( 'position', positions.clone() );
 				geometry.addAttribute( 'position', positions.clone() );
 				geometry.addAttribute( 'initialPosition', positions.clone() );
 				geometry.addAttribute( 'initialPosition', positions.clone() );
 
 
-				geometry.attributes.position.setDynamic( true );
+				geometry.attributes.position.setUsage( THREE.DynamicDrawUsage );
 
 
 				var clones = [
 				var clones = [
 
 

+ 1 - 1
examples/webgl_simple_gi.html

@@ -73,7 +73,7 @@
 					if ( attributes.color === undefined ) {
 					if ( attributes.color === undefined ) {
 
 
 						var colors = new Float32Array( positions.length );
 						var colors = new Float32Array( positions.length );
-						geometry.addAttribute( 'color', new THREE.BufferAttribute( colors, 3 ).setDynamic( true ) );
+						geometry.addAttribute( 'color', new THREE.BufferAttribute( colors, 3 ).setUsage( THREE.DynamicDrawUsage ) );
 
 
 					}
 					}
 
 

+ 3 - 3
examples/webvr_paint.html

@@ -146,15 +146,15 @@
 				var geometry = new THREE.BufferGeometry();
 				var geometry = new THREE.BufferGeometry();
 
 
 				var positions = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
 				var positions = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
-				positions.dynamic = true;
+				positions.usage = THREE.DynamicDrawUsage;
 				geometry.addAttribute( 'position', positions );
 				geometry.addAttribute( 'position', positions );
 
 
 				var normals = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
 				var normals = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
-				normals.dynamic = true;
+				normals.usage = THREE.DynamicDrawUsage;
 				geometry.addAttribute( 'normal', normals );
 				geometry.addAttribute( 'normal', normals );
 
 
 				var colors = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
 				var colors = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
-				colors.dynamic = true;
+				colors.usage = THREE.DynamicDrawUsage;
 				geometry.addAttribute( 'color', colors );
 				geometry.addAttribute( 'color', colors );
 
 
 				geometry.drawRange.count = 0;
 				geometry.drawRange.count = 0;

+ 3 - 3
examples/webvr_vive_paint.html

@@ -169,15 +169,15 @@
 				var geometry = new THREE.BufferGeometry();
 				var geometry = new THREE.BufferGeometry();
 
 
 				var positions = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
 				var positions = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
-				positions.dynamic = true;
+				positions.usage = THREE.DynamicDrawUsage;
 				geometry.addAttribute( 'position', positions );
 				geometry.addAttribute( 'position', positions );
 
 
 				var normals = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
 				var normals = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
-				normals.dynamic = true;
+				normals.usage = THREE.DynamicDrawUsage;
 				geometry.addAttribute( 'normal', normals );
 				geometry.addAttribute( 'normal', normals );
 
 
 				var colors = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
 				var colors = new THREE.BufferAttribute( new Float32Array( 1000000 * 3 ), 3 );
-				colors.dynamic = true;
+				colors.usage = THREE.DynamicDrawUsage;
 				geometry.addAttribute( 'color', colors );
 				geometry.addAttribute( 'color', colors );
 
 
 				geometry.drawRange.count = 0;
 				geometry.drawRange.count = 0;

+ 52 - 15
src/Three.Legacy.js

@@ -5,7 +5,11 @@
 import { Audio } from './audio/Audio.js';
 import { Audio } from './audio/Audio.js';
 import { AudioAnalyser } from './audio/AudioAnalyser.js';
 import { AudioAnalyser } from './audio/AudioAnalyser.js';
 import { PerspectiveCamera } from './cameras/PerspectiveCamera.js';
 import { PerspectiveCamera } from './cameras/PerspectiveCamera.js';
-import { FlatShading } from './constants.js';
+import {
+	FlatShading,
+	StaticDrawUsage,
+	DynamicDrawUsage
+} from './constants.js';
 import {
 import {
 	Float64BufferAttribute,
 	Float64BufferAttribute,
 	Float32BufferAttribute,
 	Float32BufferAttribute,
@@ -1163,29 +1167,43 @@ Object.defineProperties( BufferAttribute.prototype, {
 			console.warn( 'THREE.BufferAttribute: .length has been deprecated. Use .count instead.' );
 			console.warn( 'THREE.BufferAttribute: .length has been deprecated. Use .count instead.' );
 			return this.array.length;
 			return this.array.length;
 
 
+		}
+	},
+	dynamic: {
+		get: function () {
+
+			console.warn( 'THREE.BufferAttribute: .dynamic has been deprecated. Use .usage instead.' );
+			return this.usage === DynamicDrawUsage;
+
+		},
+		set: function ( value ) {
+
+			console.warn( 'THREE.BufferAttribute: .dynamic has been deprecated. Use .usage instead.' );
+			this.setUsage( value );
+
 		}
 		}
 	}
 	}
 
 
 } );
 } );
 
 
 Object.assign( BufferAttribute.prototype, {
 Object.assign( BufferAttribute.prototype, {
+	setDynamic: function ( value ) {
 
 
+		console.warn( 'THREE.BufferAttribute: .setDynamic() has been deprecated. Use .setUsage() instead.' );
+		this.setUsage( value === true ? DynamicDrawUsage : StaticDrawUsage );
+		return this;
+
+	},
 	copyIndicesArray: function ( /* indices */ ) {
 	copyIndicesArray: function ( /* indices */ ) {
 
 
 		console.error( 'THREE.BufferAttribute: .copyIndicesArray() has been removed.' );
 		console.error( 'THREE.BufferAttribute: .copyIndicesArray() has been removed.' );
 
 
 	},
 	},
-	setArray: function ( array ) {
+	setArray: function ( /* array */ ) {
 
 
-		console.warn( 'THREE.BufferAttribute: .setArray has been deprecated. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
-
-		this.count = array !== undefined ? array.length / this.itemSize : 0;
-		this.array = array;
-
-		return this;
+		console.error( 'THREE.BufferAttribute: .setArray has been removed. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
 
 
 	}
 	}
-
 } );
 } );
 
 
 Object.assign( BufferGeometry.prototype, {
 Object.assign( BufferGeometry.prototype, {
@@ -1247,21 +1265,40 @@ Object.defineProperties( BufferGeometry.prototype, {
 
 
 } );
 } );
 
 
-Object.assign( InterleavedBuffer.prototype, {
+Object.defineProperties( InterleavedBuffer.prototype, {
 
 
-	setArray: function ( array ) {
+	dynamic: {
+		get: function () {
 
 
-		console.warn( 'THREE.InterleavedBuffer: .setArray has been deprecated. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
+			console.warn( 'THREE.InterleavedBuffer: .length has been deprecated. Use .usage instead.' );
+			return this.usage === DynamicDrawUsage;
 
 
-		this.count = array !== undefined ? array.length / this.stride : 0;
-		this.array = array;
+		},
+		set: function ( value ) {
 
 
-		return this;
+			console.warn( 'THREE.InterleavedBuffer: .length has been deprecated. Use .usage instead.' );
+			this.setUsage( value );
 
 
+		}
 	}
 	}
 
 
 } );
 } );
 
 
+Object.assign( InterleavedBuffer.prototype, {
+	setDynamic: function ( value ) {
+
+		console.warn( 'THREE.InterleavedBuffer: .setDynamic() has been deprecated. Use .setUsage() instead.' );
+		this.setUsage( value === true ? DynamicDrawUsage : StaticDrawUsage );
+		return this;
+
+	},
+	setArray: function ( /* array */ ) {
+
+		console.error( 'THREE.InterleavedBuffer: .setArray has been removed. Use BufferGeometry .setAttribute to replace/resize attribute buffers' );
+
+	}
+} );
+
 //
 //
 
 
 Object.assign( ExtrudeBufferGeometry.prototype, {
 Object.assign( ExtrudeBufferGeometry.prototype, {

+ 3 - 1
src/audio/Audio.d.ts

@@ -45,7 +45,9 @@ export class Audio extends Object3D {
 	setPlaybackRate( value: number ): this;
 	setPlaybackRate( value: number ): this;
 	getPlaybackRate(): number;
 	getPlaybackRate(): number;
 	getLoop(): boolean;
 	getLoop(): boolean;
-	setLoop( value: boolean ): void;
+	setLoop( value: boolean ): this;
+	setLoopStart( value: number ): this;
+	setLoopEnd( value: number ): this;
 	getVolume(): number;
 	getVolume(): number;
 	setVolume( value: number ): this;
 	setVolume( value: number ): this;
 	/**
 	/**

+ 20 - 0
src/audio/Audio.js

@@ -22,6 +22,8 @@ function Audio( listener ) {
 	this.buffer = null;
 	this.buffer = null;
 	this.detune = 0;
 	this.detune = 0;
 	this.loop = false;
 	this.loop = false;
+	this.loopStart = 0;
+	this.loopEnd = 0;
 	this.startTime = 0;
 	this.startTime = 0;
 	this.offset = 0;
 	this.offset = 0;
 	this.duration = undefined;
 	this.duration = undefined;
@@ -108,6 +110,8 @@ Audio.prototype = Object.assign( Object.create( Object3D.prototype ), {
 
 
 		source.buffer = this.buffer;
 		source.buffer = this.buffer;
 		source.loop = this.loop;
 		source.loop = this.loop;
+		source.loopStart = this.loopStart;
+		source.loopEnd = this.loopEnd;
 		source.onended = this.onEnded.bind( this );
 		source.onended = this.onEnded.bind( this );
 		this.startTime = this.context.currentTime;
 		this.startTime = this.context.currentTime;
 		source.start( this.startTime, this.offset, this.duration );
 		source.start( this.startTime, this.offset, this.duration );
@@ -338,6 +342,22 @@ Audio.prototype = Object.assign( Object.create( Object3D.prototype ), {
 
 
 	},
 	},
 
 
+	setLoopStart: function ( value ) {
+
+		this.loopStart = value;
+
+		return this;
+
+	},
+
+	setLoopEnd: function ( value ) {
+
+		this.loopEnd = value;
+
+		return this;
+
+	},
+
 	getVolume: function () {
 	getVolume: function () {
 
 
 		return this.gain.gain.value;
 		return this.gain.gain.value;

+ 2 - 1
src/cameras/CubeCamera.d.ts

@@ -1,11 +1,12 @@
 import { WebGLRenderTargetCube } from './../renderers/WebGLRenderTargetCube';
 import { WebGLRenderTargetCube } from './../renderers/WebGLRenderTargetCube';
+import { WebGLRenderTargetOptions } from './../renderers/WebGLRenderTarget';
 import { Scene } from './../scenes/Scene';
 import { Scene } from './../scenes/Scene';
 import { WebGLRenderer } from './../renderers/WebGLRenderer';
 import { WebGLRenderer } from './../renderers/WebGLRenderer';
 import { Object3D } from './../core/Object3D';
 import { Object3D } from './../core/Object3D';
 
 
 export class CubeCamera extends Object3D {
 export class CubeCamera extends Object3D {
 
 
-	constructor( near?: number, far?: number, cubeResolution?: number );
+	constructor( near?: number, far?: number, cubeResolution?: number, options?: WebGLRenderTargetOptions );
 
 
 	type: 'CubeCamera';
 	type: 'CubeCamera';
 
 

+ 12 - 0
src/constants.d.ts

@@ -275,3 +275,15 @@ export const GreaterStencilFunc: StencilFunc;
 export const NotEqualStencilFunc: StencilFunc;
 export const NotEqualStencilFunc: StencilFunc;
 export const GreaterEqualStencilFunc: StencilFunc;
 export const GreaterEqualStencilFunc: StencilFunc;
 export const AlwaysStencilFunc: StencilFunc;
 export const AlwaysStencilFunc: StencilFunc;
+
+// usage types
+export enum Usage {}
+export const StaticDrawUsage: Usage;
+export const DynamicDrawUsage: Usage;
+export const StreamDrawUsage: Usage;
+export const StaticReadUsage: Usage;
+export const DynamicReadUsage: Usage;
+export const StreamReadUsage: Usage;
+export const StaticCopyUsage: Usage;
+export const DynamicCopyUsage: Usage;
+export const StreamCopyUsage: Usage;

+ 10 - 0
src/constants.js

@@ -166,3 +166,13 @@ export var GreaterStencilFunc = 516;
 export var NotEqualStencilFunc = 517;
 export var NotEqualStencilFunc = 517;
 export var GreaterEqualStencilFunc = 518;
 export var GreaterEqualStencilFunc = 518;
 export var AlwaysStencilFunc = 519;
 export var AlwaysStencilFunc = 519;
+
+export var StaticDrawUsage = 35044;
+export var DynamicDrawUsage = 35048;
+export var StreamDrawUsage = 35040;
+export var StaticReadUsage = 35045;
+export var DynamicReadUsage = 35049;
+export var StreamReadUsage = 35041;
+export var StaticCopyUsage = 35046;
+export var DynamicCopyUsage = 35050;
+export var StreamCopyUsage = 35042;

+ 6 - 2
src/core/BufferAttribute.d.ts

@@ -1,3 +1,7 @@
+import {
+	Usage
+} from '../constants';
+
 /**
 /**
  * @see <a href="https://github.com/mrdoob/three.js/blob/master/src/core/BufferAttribute.js">src/core/BufferAttribute.js</a>
  * @see <a href="https://github.com/mrdoob/three.js/blob/master/src/core/BufferAttribute.js">src/core/BufferAttribute.js</a>
  */
  */
@@ -8,7 +12,7 @@ export class BufferAttribute {
 	name: string;
 	name: string;
 	array: ArrayLike<number>;
 	array: ArrayLike<number>;
 	itemSize: number;
 	itemSize: number;
-	dynamic: boolean;
+	usage: Usage;
 	updateRange: { offset: number; count: number };
 	updateRange: { offset: number; count: number };
 	version: number;
 	version: number;
 	normalized: boolean;
 	normalized: boolean;
@@ -16,7 +20,7 @@ export class BufferAttribute {
 	count: number;
 	count: number;
 	onUpload: Function;
 	onUpload: Function;
 
 
-	setDynamic( dynamic: boolean ): BufferAttribute;
+	setUsage( usage: Usage ): BufferAttribute;
 	clone(): this;
 	clone(): this;
 	copy( source: BufferAttribute ): this;
 	copy( source: BufferAttribute ): this;
 	copyAt(
 	copyAt(

+ 5 - 4
src/core/BufferAttribute.js

@@ -2,6 +2,7 @@ import { Vector4 } from '../math/Vector4.js';
 import { Vector3 } from '../math/Vector3.js';
 import { Vector3 } from '../math/Vector3.js';
 import { Vector2 } from '../math/Vector2.js';
 import { Vector2 } from '../math/Vector2.js';
 import { Color } from '../math/Color.js';
 import { Color } from '../math/Color.js';
+import { StaticDrawUsage } from '../constants.js';
 
 
 /**
 /**
  * @author mrdoob / http://mrdoob.com/
  * @author mrdoob / http://mrdoob.com/
@@ -22,7 +23,7 @@ function BufferAttribute( array, itemSize, normalized ) {
 	this.count = array !== undefined ? array.length / itemSize : 0;
 	this.count = array !== undefined ? array.length / itemSize : 0;
 	this.normalized = normalized === true;
 	this.normalized = normalized === true;
 
 
-	this.dynamic = false;
+	this.usage = StaticDrawUsage;
 	this.updateRange = { offset: 0, count: - 1 };
 	this.updateRange = { offset: 0, count: - 1 };
 
 
 	this.version = 0;
 	this.version = 0;
@@ -45,9 +46,9 @@ Object.assign( BufferAttribute.prototype, {
 
 
 	onUploadCallback: function () {},
 	onUploadCallback: function () {},
 
 
-	setDynamic: function ( value ) {
+	setUsage: function ( value ) {
 
 
-		this.dynamic = value;
+		this.usage = value;
 
 
 		return this;
 		return this;
 
 
@@ -61,7 +62,7 @@ Object.assign( BufferAttribute.prototype, {
 		this.count = source.count;
 		this.count = source.count;
 		this.normalized = source.normalized;
 		this.normalized = source.normalized;
 
 
-		this.dynamic = source.dynamic;
+		this.usage = source.usage;
 
 
 		return this;
 		return this;
 
 

+ 3 - 2
src/core/InterleavedBuffer.d.ts

@@ -1,4 +1,5 @@
 import { InterleavedBufferAttribute } from './InterleavedBufferAttribute';
 import { InterleavedBufferAttribute } from './InterleavedBufferAttribute';
+import { Usage } from '../constants';
 
 
 /**
 /**
  * @see <a href="https://github.com/mrdoob/three.js/blob/master/src/core/InterleavedBuffer.js">src/core/InterleavedBuffer.js</a>
  * @see <a href="https://github.com/mrdoob/three.js/blob/master/src/core/InterleavedBuffer.js">src/core/InterleavedBuffer.js</a>
@@ -9,14 +10,14 @@ export class InterleavedBuffer {
 
 
 	array: ArrayLike<number>;
 	array: ArrayLike<number>;
 	stride: number;
 	stride: number;
-	dynamic: boolean;
+	usage: Usage;
 	updateRange: { offset: number; count: number };
 	updateRange: { offset: number; count: number };
 	version: number;
 	version: number;
 	length: number;
 	length: number;
 	count: number;
 	count: number;
 	needsUpdate: boolean;
 	needsUpdate: boolean;
 
 
-	setDynamic( dynamic: boolean ): InterleavedBuffer;
+	setUsage( usage: Usage ): InterleavedBuffer;
 	clone(): this;
 	clone(): this;
 	copy( source: InterleavedBuffer ): this;
 	copy( source: InterleavedBuffer ): this;
 	copyAt(
 	copyAt(

+ 5 - 4
src/core/InterleavedBuffer.js

@@ -1,3 +1,4 @@
+import { StaticDrawUsage } from '../constants.js';
 
 
 /**
 /**
  * @author benaadams / https://twitter.com/ben_a_adams
  * @author benaadams / https://twitter.com/ben_a_adams
@@ -9,7 +10,7 @@ function InterleavedBuffer( array, stride ) {
 	this.stride = stride;
 	this.stride = stride;
 	this.count = array !== undefined ? array.length / stride : 0;
 	this.count = array !== undefined ? array.length / stride : 0;
 
 
-	this.dynamic = false;
+	this.usage = StaticDrawUsage;
 	this.updateRange = { offset: 0, count: - 1 };
 	this.updateRange = { offset: 0, count: - 1 };
 
 
 	this.version = 0;
 	this.version = 0;
@@ -32,9 +33,9 @@ Object.assign( InterleavedBuffer.prototype, {
 
 
 	onUploadCallback: function () {},
 	onUploadCallback: function () {},
 
 
-	setDynamic: function ( value ) {
+	setUsage: function ( value ) {
 
 
-		this.dynamic = value;
+		this.usage = value;
 
 
 		return this;
 		return this;
 
 
@@ -45,7 +46,7 @@ Object.assign( InterleavedBuffer.prototype, {
 		this.array = new source.array.constructor( source.array );
 		this.array = new source.array.constructor( source.array );
 		this.count = source.count;
 		this.count = source.count;
 		this.stride = source.stride;
 		this.stride = source.stride;
-		this.dynamic = source.dynamic;
+		this.usage = source.usage;
 
 
 		return this;
 		return this;
 
 

+ 2 - 2
src/renderers/WebGLRenderer.js

@@ -1985,7 +1985,7 @@ function WebGLRenderer( parameters ) {
 
 
 			if ( material.isShaderMaterial ) {
 			if ( material.isShaderMaterial ) {
 
 
-				material.uniformsNeedUpdate = false;
+				material.uniformsNeedUpdate = false; // #15581
 
 
 			}
 			}
 
 
@@ -2493,7 +2493,7 @@ function WebGLRenderer( parameters ) {
 	//
 	//
 	this.setFramebuffer = function ( value ) {
 	this.setFramebuffer = function ( value ) {
 
 
-		if ( _framebuffer !== value ) _gl.bindFramebuffer( _gl.FRAMEBUFFER, value );
+		if ( _framebuffer !== value && _currentRenderTarget === null ) _gl.bindFramebuffer( _gl.FRAMEBUFFER, value );
 
 
 		_framebuffer = value;
 		_framebuffer = value;
 
 

+ 3 - 1
src/renderers/shaders/ShaderChunk/logdepthbuf_fragment.glsl.js

@@ -1,7 +1,9 @@
 export default /* glsl */`
 export default /* glsl */`
 #if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )
 #if defined( USE_LOGDEPTHBUF ) && defined( USE_LOGDEPTHBUF_EXT )
 
 
-	gl_FragDepthEXT = vIsPerspective == 1.0 ? log2( vFragDepth ) * logDepthBufFC * 0.5 : gl_FragCoord.z;
+	// Doing a strict comparison with == 1.0 can cause noise artifacts
+	// on some platforms. See issue #17623.
+	gl_FragDepthEXT = vIsPerspective == 0.0 ? gl_FragCoord.z : log2( vFragDepth ) * logDepthBufFC * 0.5;
 
 
 #endif
 #endif
 `;
 `;

+ 2 - 10
src/renderers/webgl/WebGLAttributes.js

@@ -9,7 +9,7 @@ function WebGLAttributes( gl ) {
 	function createBuffer( attribute, bufferType ) {
 	function createBuffer( attribute, bufferType ) {
 
 
 		var array = attribute.array;
 		var array = attribute.array;
-		var usage = attribute.dynamic ? gl.DYNAMIC_DRAW : gl.STATIC_DRAW;
+		var usage = attribute.usage;
 
 
 		var buffer = gl.createBuffer();
 		var buffer = gl.createBuffer();
 
 
@@ -70,20 +70,12 @@ function WebGLAttributes( gl ) {
 
 
 		gl.bindBuffer( bufferType, buffer );
 		gl.bindBuffer( bufferType, buffer );
 
 
-		if ( attribute.dynamic === false ) {
-
-			gl.bufferData( bufferType, array, gl.STATIC_DRAW );
-
-		} else if ( updateRange.count === - 1 ) {
+		if ( updateRange.count === - 1 ) {
 
 
 			// Not using update ranges
 			// Not using update ranges
 
 
 			gl.bufferSubData( bufferType, 0, array );
 			gl.bufferSubData( bufferType, 0, array );
 
 
-		} else if ( updateRange.count === 0 ) {
-
-			console.error( 'THREE.WebGLObjects.updateBuffer: dynamic THREE.BufferAttribute marked as needsUpdate but updateRange.count is 0, ensure you are using set methods or updating manually.' );
-
 		} else {
 		} else {
 
 
 			gl.bufferSubData( bufferType, updateRange.offset * array.BYTES_PER_ELEMENT,
 			gl.bufferSubData( bufferType, updateRange.offset * array.BYTES_PER_ELEMENT,

+ 4 - 5
src/renderers/webgl/WebGLProgram.js

@@ -349,13 +349,13 @@ function generateEnvMapModeDefine( parameters ) {
 
 
 }
 }
 
 
-function generateEnvMapBlendingDefine( parameters, material ) {
+function generateEnvMapBlendingDefine( parameters ) {
 
 
 	var envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
 	var envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
 
 
 	if ( parameters.envMap ) {
 	if ( parameters.envMap ) {
 
 
-		switch ( material.combine ) {
+		switch ( parameters.combine ) {
 
 
 			case MultiplyOperation:
 			case MultiplyOperation:
 				envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
 				envMapBlendingDefine = 'ENVMAP_BLENDING_MULTIPLY';
@@ -388,7 +388,7 @@ function WebGLProgram( renderer, extensions, code, material, shader, parameters
 	var shadowMapTypeDefine = generateShadowMapTypeDefine( parameters );
 	var shadowMapTypeDefine = generateShadowMapTypeDefine( parameters );
 	var envMapTypeDefine = generateEnvMapTypeDefine( parameters );
 	var envMapTypeDefine = generateEnvMapTypeDefine( parameters );
 	var envMapModeDefine = generateEnvMapModeDefine( parameters );
 	var envMapModeDefine = generateEnvMapModeDefine( parameters );
-	var envMapBlendingDefine = generateEnvMapBlendingDefine( parameters, material );
+	var envMapBlendingDefine = generateEnvMapBlendingDefine( parameters );
 
 
 
 
 	var gammaFactorDefine = ( renderer.gammaFactor > 0 ) ? renderer.gammaFactor : 1.0;
 	var gammaFactorDefine = ( renderer.gammaFactor > 0 ) ? renderer.gammaFactor : 1.0;
@@ -401,8 +401,7 @@ function WebGLProgram( renderer, extensions, code, material, shader, parameters
 
 
 	var prefixVertex, prefixFragment;
 	var prefixVertex, prefixFragment;
 
 
-	var renderTarget = renderer.getRenderTarget();
-	var numMultiviewViews = renderTarget && renderTarget.isWebGLMultiviewRenderTarget ? renderTarget.numViews : 0;
+	var numMultiviewViews = parameters.numMultiviewViews;
 
 
 	if ( material.isRawShaderMaterial ) {
 	if ( material.isRawShaderMaterial ) {
 
 

+ 5 - 1
src/renderers/webgl/WebGLPrograms.js

@@ -35,8 +35,10 @@ function WebGLPrograms( renderer, extensions, capabilities ) {
 	};
 	};
 
 
 	var parameterNames = [
 	var parameterNames = [
-		"precision", "isWebGL2", "supportsVertexTextures", "outputEncoding", "instancing",
+
+		"precision", "isWebGL2", "supportsVertexTextures", "outputEncoding", "instancing", "numMultiviewViews",
 		"map", "mapEncoding", "matcap", "matcapEncoding", "envMap", "envMapMode", "envMapEncoding", "envMapCubeUV",
 		"map", "mapEncoding", "matcap", "matcapEncoding", "envMap", "envMapMode", "envMapEncoding", "envMapCubeUV",
+
 		"lightMap", "aoMap", "emissiveMap", "emissiveMapEncoding", "bumpMap", "normalMap", "objectSpaceNormalMap", "tangentSpaceNormalMap", "clearcoatNormalMap", "displacementMap", "specularMap",
 		"lightMap", "aoMap", "emissiveMap", "emissiveMapEncoding", "bumpMap", "normalMap", "objectSpaceNormalMap", "tangentSpaceNormalMap", "clearcoatNormalMap", "displacementMap", "specularMap",
 		"roughnessMap", "metalnessMap", "gradientMap",
 		"roughnessMap", "metalnessMap", "gradientMap",
 		"alphaMap", "combine", "vertexColors", "vertexTangents", "vertexUvs", "fog", "useFog", "fogExp2",
 		"alphaMap", "combine", "vertexColors", "vertexTangents", "vertexUvs", "fog", "useFog", "fogExp2",
@@ -139,6 +141,7 @@ function WebGLPrograms( renderer, extensions, capabilities ) {
 		}
 		}
 
 
 		var currentRenderTarget = renderer.getRenderTarget();
 		var currentRenderTarget = renderer.getRenderTarget();
+		var numMultiviewViews = currentRenderTarget && currentRenderTarget.isWebGLMultiviewRenderTarget ? currentRenderTarget.numViews : 0;
 
 
 		var parameters = {
 		var parameters = {
 
 
@@ -151,6 +154,7 @@ function WebGLPrograms( renderer, extensions, capabilities ) {
 			instancing: object.isInstancedMesh === true,
 			instancing: object.isInstancedMesh === true,
 
 
 			supportsVertexTextures: vertexTextures,
 			supportsVertexTextures: vertexTextures,
+			numMultiviewViews: numMultiviewViews,
 			outputEncoding: getTextureEncodingFromMap( ( ! currentRenderTarget ) ? null : currentRenderTarget.texture, renderer.gammaOutput ),
 			outputEncoding: getTextureEncodingFromMap( ( ! currentRenderTarget ) ? null : currentRenderTarget.texture, renderer.gammaOutput ),
 			map: !! material.map,
 			map: !! material.map,
 			mapEncoding: getTextureEncodingFromMap( material.map, renderer.gammaInput ),
 			mapEncoding: getTextureEncodingFromMap( material.map, renderer.gammaInput ),

+ 3 - 2
src/renderers/webgl/WebGLProperties.d.ts

@@ -3,7 +3,8 @@ export class WebGLProperties {
 	constructor();
 	constructor();
 
 
 	get( object: any ): any;
 	get( object: any ): any;
-	delete( object: any ): void;
-	clear(): void;
+	remove( object: any ): void;
+	update( object: any, key: any, value: any ): any;
+	dispose(): void;
 
 
 }
 }

+ 8 - 4
test/unit/src/core/BufferAttribute.tests.js

@@ -8,6 +8,7 @@ import { Color } from '../../../../src/math/Color';
 import { Vector2 } from '../../../../src/math/Vector2';
 import { Vector2 } from '../../../../src/math/Vector2';
 import { Vector3 } from '../../../../src/math/Vector3';
 import { Vector3 } from '../../../../src/math/Vector3';
 import { Vector4 } from '../../../../src/math/Vector4';
 import { Vector4 } from '../../../../src/math/Vector4';
+import { DynamicDrawUsage } from '../../../../src/constants';
 
 
 export default QUnit.module( 'Core', () => {
 export default QUnit.module( 'Core', () => {
 
 
@@ -42,23 +43,26 @@ export default QUnit.module( 'Core', () => {
 
 
 		} );
 		} );
 
 
-		QUnit.todo( "setDynamic", ( assert ) => {
+		QUnit.test( "setUsage", ( assert ) => {
 
 
-			assert.ok( false, "everything's gonna be alright" );
+			var attr = new BufferAttribute();
+			attr.setUsage( DynamicDrawUsage );
+
+			assert.strictEqual( attr.usage, DynamicDrawUsage, "Usage was set" );
 
 
 		} );
 		} );
 
 
 		QUnit.test( "copy", ( assert ) => {
 		QUnit.test( "copy", ( assert ) => {
 
 
 			var attr = new BufferAttribute( new Float32Array( [ 1, 2, 3, 4, 5, 6 ] ), 3 );
 			var attr = new BufferAttribute( new Float32Array( [ 1, 2, 3, 4, 5, 6 ] ), 3 );
-			attr.setDynamic( true );
+			attr.setUsage( DynamicDrawUsage );
 			attr.needsUpdate = true;
 			attr.needsUpdate = true;
 
 
 			var attrCopy = new BufferAttribute().copy( attr );
 			var attrCopy = new BufferAttribute().copy( attr );
 
 
 			assert.ok( attr.count === attrCopy.count, 'count is equal' );
 			assert.ok( attr.count === attrCopy.count, 'count is equal' );
 			assert.ok( attr.itemSize === attrCopy.itemSize, 'itemSize is equal' );
 			assert.ok( attr.itemSize === attrCopy.itemSize, 'itemSize is equal' );
-			assert.ok( attr.dynamic === attrCopy.dynamic, 'dynamic is equal' );
+			assert.ok( attr.usage === attrCopy.usage, 'usage is equal' );
 			assert.ok( attr.array.length === attrCopy.array.length, 'array length is equal' );
 			assert.ok( attr.array.length === attrCopy.array.length, 'array length is equal' );
 			assert.ok( attr.version === 1 && attrCopy.version === 0, 'version is not copied which is good' );
 			assert.ok( attr.version === 1 && attrCopy.version === 0, 'version is not copied which is good' );
 
 

+ 9 - 5
test/unit/src/core/InterleavedBuffer.tests.js

@@ -4,6 +4,7 @@
 /* global QUnit */
 /* global QUnit */
 
 
 import { InterleavedBuffer } from '../../../../src/core/InterleavedBuffer';
 import { InterleavedBuffer } from '../../../../src/core/InterleavedBuffer';
+import { DynamicDrawUsage } from '../../../../src/constants';
 
 
 export default QUnit.module( 'Core', () => {
 export default QUnit.module( 'Core', () => {
 
 
@@ -20,7 +21,7 @@ export default QUnit.module( 'Core', () => {
 			}
 			}
 
 
 			assert.ok( copiedInstance.stride === instance.stride, "stride was copied" );
 			assert.ok( copiedInstance.stride === instance.stride, "stride was copied" );
-			assert.ok( copiedInstance.dynamic === true, "dynamic was copied" );
+			assert.ok( copiedInstance.usage === DynamicDrawUsage, "usage was copied" );
 
 
 		}
 		}
 
 
@@ -49,9 +50,12 @@ export default QUnit.module( 'Core', () => {
 
 
 		} );
 		} );
 
 
-		QUnit.todo( "setDynamic", ( assert ) => {
+		QUnit.test( "setUsage", ( assert ) => {
 
 
-			assert.ok( false, "everything's gonna be alright" );
+			var instance = new InterleavedBuffer();
+			instance.setUsage( DynamicDrawUsage );
+
+			assert.strictEqual( instance.usage, DynamicDrawUsage, "Usage was set" );
 
 
 		} );
 		} );
 
 
@@ -59,7 +63,7 @@ export default QUnit.module( 'Core', () => {
 
 
 			var array = new Float32Array( [ 1, 2, 3, 7, 8, 9 ] );
 			var array = new Float32Array( [ 1, 2, 3, 7, 8, 9 ] );
 			var instance = new InterleavedBuffer( array, 3 );
 			var instance = new InterleavedBuffer( array, 3 );
-			instance.setDynamic( true );
+			instance.setUsage( DynamicDrawUsage );
 
 
 			checkInstanceAgainstCopy( instance, instance.copy( instance ), assert );
 			checkInstanceAgainstCopy( instance, instance.copy( instance ), assert );
 
 
@@ -92,7 +96,7 @@ export default QUnit.module( 'Core', () => {
 
 
 			var array = new Float32Array( [ 1, 2, 3, 7, 8, 9 ] );
 			var array = new Float32Array( [ 1, 2, 3, 7, 8, 9 ] );
 			var instance = new InterleavedBuffer( array, 3 );
 			var instance = new InterleavedBuffer( array, 3 );
-			instance.setDynamic( true );
+			instance.setUsage( DynamicDrawUsage );
 
 
 			checkInstanceAgainstCopy( instance, instance.clone(), assert );
 			checkInstanceAgainstCopy( instance, instance.clone(), assert );
 
 

Some files were not shown because too many files changed in this diff