Explorar o código

Merge pull request #6439 from MarkusBillharz/Add-MeshMorph-Support-To-The-GeometryBufferRenderer

Add MeshMorph support to the GeometryBufferRenderer
David Catuhe %!s(int64=6) %!d(string=hai) anos
pai
achega
bf21a43647

+ 1 - 1
dist/preview release/what's new.md

@@ -19,7 +19,7 @@
 - Ability to set render camera on utility layer instead of using the latest active camera ([TrevorDev](https://github.com/TrevorDev))
 - Ability to set render camera on utility layer instead of using the latest active camera ([TrevorDev](https://github.com/TrevorDev))
 - Move normalizeToUnitCube to transformNode instead of abstract mesh and add predicate to exclude sub objects when scaling ([TrevorDev](https://github.com/TrevorDev))
 - Move normalizeToUnitCube to transformNode instead of abstract mesh and add predicate to exclude sub objects when scaling ([TrevorDev](https://github.com/TrevorDev))
 - Method to check if device orientation is available ([TrevorDev](https://github.com/TrevorDev))
 - Method to check if device orientation is available ([TrevorDev](https://github.com/TrevorDev))
-- Added MorphTarget support to the DepthRenderer ([MarkusBillharz](https://github.com/MarkusBillharz))
+- Added MorphTarget support to the DepthRenderer and GeometryBufferRenderer ([MarkusBillharz](https://github.com/MarkusBillharz))
 
 
 ### Engine
 ### Engine
 - Added preprocessors for shaders to improve how shaders are compiled for WebGL1/2 or WebGPU ([Deltakosh](https://github.com/deltakosh/))
 - Added preprocessors for shaders to improve how shaders are compiled for WebGL1/2 or WebGPU ([Deltakosh](https://github.com/deltakosh/))

+ 19 - 2
src/Rendering/geometryBufferRenderer.ts

@@ -227,6 +227,20 @@ export class GeometryBufferRenderer {
             defines.push("#define NUM_BONE_INFLUENCERS 0");
             defines.push("#define NUM_BONE_INFLUENCERS 0");
         }
         }
 
 
+        // Morph targets
+        const morphTargetManager = (mesh as Mesh).morphTargetManager;
+        let numMorphInfluencers = 0;
+        if (morphTargetManager) {
+            if (morphTargetManager.numInfluencers > 0) {
+                numMorphInfluencers = morphTargetManager.numInfluencers;
+
+                defines.push("#define MORPHTARGETS");
+                defines.push("#define NUM_MORPH_INFLUENCERS " + numMorphInfluencers);
+
+                MaterialHelper.PrepareAttributesForMorphTargets(attribs, mesh, { "NUM_MORPH_INFLUENCERS": numMorphInfluencers });
+            }
+        }
+
         // Instances
         // Instances
         if (useInstances) {
         if (useInstances) {
             defines.push("#define INSTANCES");
             defines.push("#define INSTANCES");
@@ -242,10 +256,10 @@ export class GeometryBufferRenderer {
             this._cachedDefines = join;
             this._cachedDefines = join;
             this._effect = this._scene.getEngine().createEffect("geometry",
             this._effect = this._scene.getEngine().createEffect("geometry",
                 attribs,
                 attribs,
-                ["world", "mBones", "viewProjection", "diffuseMatrix", "view", "previousWorld", "previousViewProjection", "mPreviousBones"],
+                ["world", "mBones", "viewProjection", "diffuseMatrix", "view", "previousWorld", "previousViewProjection", "mPreviousBones", "morphTargetInfluences"],
                 ["diffuseSampler"], join,
                 ["diffuseSampler"], join,
                 undefined, undefined, undefined,
                 undefined, undefined, undefined,
-                { buffersCount: this._enablePosition ? 3 : 2 });
+                { buffersCount: this._enablePosition ? 3 : 2, maxSimultaneousMorphTargets: numMorphInfluencers});
         }
         }
 
 
         return this._effect.isReady();
         return this._effect.isReady();
@@ -372,6 +386,9 @@ export class GeometryBufferRenderer {
                     }
                     }
                 }
                 }
 
 
+                // Morph targets
+                MaterialHelper.BindMorphTargetParameters(mesh, this._effect);
+
                 // Velocity
                 // Velocity
                 if (this._enableVelocity) {
                 if (this._enableVelocity) {
                     this._effect.setMatrix("previousWorld", this._previousTransformationMatrices[mesh.uniqueId].world);
                     this._effect.setMatrix("previousWorld", this._previousTransformationMatrices[mesh.uniqueId].world);

+ 17 - 9
src/Shaders/geometry.vertex.fx

@@ -2,6 +2,10 @@ precision highp float;
 precision highp int;
 precision highp int;
 
 
 #include<bonesDeclaration>
 #include<bonesDeclaration>
+
+#include<morphTargetsVertexGlobalDeclaration>
+#include<morphTargetsVertexDeclaration>[0..maxSimultaneousMorphTargets]
+
 #include<instancesDeclaration>
 #include<instancesDeclaration>
 
 
 attribute vec3 position;
 attribute vec3 position;
@@ -44,22 +48,26 @@ varying vec4 vPreviousPosition;
 
 
 void main(void)
 void main(void)
 {
 {
+vec3 positionUpdated = position;
+vec3 normalUpdated = normal;
+#include<morphTargetsVertex>[0..maxSimultaneousMorphTargets]
+
 #include<instancesVertex>
 #include<instancesVertex>
 
 
 	#if defined(VELOCITY) && !defined(BONES_VELOCITY_ENABLED)
 	#if defined(VELOCITY) && !defined(BONES_VELOCITY_ENABLED)
 	// Compute velocity before bones computation
 	// Compute velocity before bones computation
-	vCurrentPosition = viewProjection * finalWorld * vec4(position, 1.0);	
-	vPreviousPosition = previousViewProjection * previousWorld * vec4(position, 1.0);
+	vCurrentPosition = viewProjection * finalWorld * vec4(positionUpdated, 1.0);
+	vPreviousPosition = previousViewProjection * previousWorld * vec4(positionUpdated, 1.0);
 	#endif
 	#endif
 
 
 #include<bonesVertex>
 #include<bonesVertex>
-	vec4 pos = vec4(finalWorld * vec4(position, 1.0));
+	vec4 pos = vec4(finalWorld * vec4(positionUpdated, 1.0));
 
 
-	vNormalV = normalize(vec3((view * finalWorld) * vec4(normal, 0.0)));
+	vNormalV = normalize(vec3((view * finalWorld) * vec4(normalUpdated, 0.0)));
 	vViewPos = view * pos;
 	vViewPos = view * pos;
 
 
 	#if defined(VELOCITY) && defined(BONES_VELOCITY_ENABLED)
 	#if defined(VELOCITY) && defined(BONES_VELOCITY_ENABLED)
-		vCurrentPosition = viewProjection * finalWorld * vec4(position, 1.0);
+		vCurrentPosition = viewProjection * finalWorld * vec4(positionUpdated, 1.0);
 
 
 		#if NUM_BONE_INFLUENCERS > 0
 		#if NUM_BONE_INFLUENCERS > 0
 			mat4 previousInfluence;
 			mat4 previousInfluence;
@@ -87,9 +95,9 @@ void main(void)
 				previousInfluence += mPreviousBones[int(matricesIndicesExtra[3])] * matricesWeightsExtra[3];
 				previousInfluence += mPreviousBones[int(matricesIndicesExtra[3])] * matricesWeightsExtra[3];
 			#endif
 			#endif
 
 
-			vPreviousPosition = previousViewProjection * previousWorld * previousInfluence * vec4(position, 1.0);
+			vPreviousPosition = previousViewProjection * previousWorld * previousInfluence * vec4(positionUpdated, 1.0);
 		#else
 		#else
-			vPreviousPosition = previousViewProjection * previousWorld * vec4(position, 1.0);
+			vPreviousPosition = previousViewProjection * previousWorld * vec4(positionUpdated, 1.0);
 		#endif
 		#endif
 	#endif
 	#endif
 
 
@@ -97,7 +105,7 @@ void main(void)
 	vPosition = pos.xyz / pos.w;
 	vPosition = pos.xyz / pos.w;
 	#endif
 	#endif
 
 
-	gl_Position = viewProjection * finalWorld * vec4(position, 1.0);
+	gl_Position = viewProjection * finalWorld * vec4(positionUpdated, 1.0);
 
 
 #if defined(ALPHATEST) || defined(BASIC_RENDER)
 #if defined(ALPHATEST) || defined(BASIC_RENDER)
 #ifdef UV1
 #ifdef UV1
@@ -107,4 +115,4 @@ void main(void)
 	vUV = vec2(diffuseMatrix * vec4(uv2, 1.0, 0.0));
 	vUV = vec2(diffuseMatrix * vec4(uv2, 1.0, 0.0));
 #endif
 #endif
 #endif
 #endif
-}
+}