瀏覽代碼

Implement support for morphTargetsRelative in WebGL

The shader code is now a bit simpler and relies on the precomputed base
influence value; JS code sets it up appropriately.
Arseny Kapoulkine 5 年之前
父節點
當前提交
a3a79e2a76

+ 5 - 4
src/renderers/shaders/ShaderChunk/morphnormal_vertex.glsl.js

@@ -1,10 +1,11 @@
 export default /* glsl */`
 #ifdef USE_MORPHNORMALS
 
-	objectNormal += ( morphNormal0 - normal ) * morphTargetInfluences[ 0 ];
-	objectNormal += ( morphNormal1 - normal ) * morphTargetInfluences[ 1 ];
-	objectNormal += ( morphNormal2 - normal ) * morphTargetInfluences[ 2 ];
-	objectNormal += ( morphNormal3 - normal ) * morphTargetInfluences[ 3 ];
+	objectNormal *= morphTargetBaseInfluence;
+	objectNormal += morphNormal0 * morphTargetInfluences[ 0 ];
+	objectNormal += morphNormal1 * morphTargetInfluences[ 1 ];
+	objectNormal += morphNormal2 * morphTargetInfluences[ 2 ];
+	objectNormal += morphNormal3 * morphTargetInfluences[ 3 ];
 
 #endif
 `;

+ 2 - 0
src/renderers/shaders/ShaderChunk/morphtarget_pars_vertex.glsl.js

@@ -1,6 +1,8 @@
 export default /* glsl */`
 #ifdef USE_MORPHTARGETS
 
+	uniform float morphTargetBaseInfluence;
+
 	#ifndef USE_MORPHNORMALS
 
 	uniform float morphTargetInfluences[ 8 ];

+ 9 - 8
src/renderers/shaders/ShaderChunk/morphtarget_vertex.glsl.js

@@ -1,17 +1,18 @@
 export default /* glsl */`
 #ifdef USE_MORPHTARGETS
 
-	transformed += ( morphTarget0 - position ) * morphTargetInfluences[ 0 ];
-	transformed += ( morphTarget1 - position ) * morphTargetInfluences[ 1 ];
-	transformed += ( morphTarget2 - position ) * morphTargetInfluences[ 2 ];
-	transformed += ( morphTarget3 - position ) * morphTargetInfluences[ 3 ];
+	transformed *= morphTargetBaseInfluence;
+	transformed += morphTarget0 * morphTargetInfluences[ 0 ];
+	transformed += morphTarget1 * morphTargetInfluences[ 1 ];
+	transformed += morphTarget2 * morphTargetInfluences[ 2 ];
+	transformed += morphTarget3 * morphTargetInfluences[ 3 ];
 
 	#ifndef USE_MORPHNORMALS
 
-	transformed += ( morphTarget4 - position ) * morphTargetInfluences[ 4 ];
-	transformed += ( morphTarget5 - position ) * morphTargetInfluences[ 5 ];
-	transformed += ( morphTarget6 - position ) * morphTargetInfluences[ 6 ];
-	transformed += ( morphTarget7 - position ) * morphTargetInfluences[ 7 ];
+	transformed += morphTarget4 * morphTargetInfluences[ 4 ];
+	transformed += morphTarget5 * morphTargetInfluences[ 5 ];
+	transformed += morphTarget6 * morphTargetInfluences[ 6 ];
+	transformed += morphTarget7 * morphTargetInfluences[ 7 ];
 
 	#endif
 

+ 6 - 0
src/renderers/webgl/WebGLMorphtargets.js

@@ -70,6 +70,8 @@ function WebGLMorphtargets( gl ) {
 
 		// Add morphAttributes
 
+		var morphInfluencesSum = 0;
+
 		for ( var i = 0; i < 8; i ++ ) {
 
 			var influence = influences[ i ];
@@ -85,6 +87,7 @@ function WebGLMorphtargets( gl ) {
 					if ( morphNormals ) geometry.addAttribute( 'morphNormal' + i, morphNormals[ index ] );
 
 					morphInfluences[ i ] = value;
+					morphInfluencesSum += value;
 					continue;
 
 				}
@@ -95,6 +98,9 @@ function WebGLMorphtargets( gl ) {
 
 		}
 
+		var morphBaseInfluence = geometry.morphTargetsRelative ? 1 : Math.max(0, 1 - morphInfluencesSum);
+
+		program.getUniforms().setValue( gl, 'morphTargetBaseInfluence', morphBaseInfluence );
 		program.getUniforms().setValue( gl, 'morphTargetInfluences', morphInfluences );
 
 	}