Browse Source

Merge pull request #9175 from Popov72/fix-shadow-nodematerial

Fix texture loop when using a node material on a shadow caster+receiver
David Catuhe 4 years ago
parent
commit
7921ec8e89
2 changed files with 68 additions and 11 deletions
  1. 18 0
      src/Materials/effect.ts
  2. 50 11
      src/Materials/shadowDepthWrapper.ts

+ 18 - 0
src/Materials/effect.ts

@@ -172,6 +172,8 @@ export class Effect implements IDisposable {
     private _vertexSourceCodeOverride: string = "";
     private _fragmentSourceCodeOverride: string = "";
     private _transformFeedbackVaryings: Nullable<string[]> = null;
+    private _rawVertexSourceCode: string = "";
+    private _rawFragmentSourceCode: string = "";
     /**
      * Compiled shader to webGL program.
      * @hidden
@@ -286,7 +288,9 @@ export class Effect implements IDisposable {
         };
 
         this._loadShader(vertexSource, "Vertex", "", (vertexCode) => {
+            this._rawVertexSourceCode = vertexCode;
             this._loadShader(fragmentSource, "Fragment", "Pixel", (fragmentCode) => {
+                this._rawFragmentSourceCode = fragmentCode;
                 ShaderProcessor.Process(vertexCode, processorOptions, (migratedVertexCode) => {
                     if (processFinalCode) {
                         migratedVertexCode = processFinalCode("vertex", migratedVertexCode);
@@ -560,6 +564,20 @@ export class Effect implements IDisposable {
     }
 
     /**
+     * Gets the vertex shader source code before it has been processed by the preprocessor
+     */
+    public get rawVertexSourceCode(): string {
+        return this._rawVertexSourceCode;
+    }
+
+    /**
+     * Gets the fragment shader source code before it has been processed by the preprocessor
+     */
+    public get rawFragmentSourceCode(): string {
+        return this._rawFragmentSourceCode;
+    }
+
+    /**
      * Recompiles the webGL program
      * @param vertexSourceCode The source code for the vertex shader.
      * @param fragmentSourceCode The source code for the fragment shader.

+ 50 - 11
src/Materials/shadowDepthWrapper.ts

@@ -9,6 +9,8 @@ import { AbstractMesh } from '../Meshes/abstractMesh';
 import { Node } from '../node';
 import { ShadowGenerator } from '../Lights/Shadows/shadowGenerator';
 import { GUID } from '../Misc/guid';
+import { NodeMaterial } from './Node/nodeMaterial';
+import { NodeMaterialSystemValues } from './Node/Enums/nodeMaterialSystemValues';
 
 /**
  * Options to be used when creating a shadow depth material
@@ -93,14 +95,51 @@ export class ShadowDepthWrapper {
 
         const prefix = baseMaterial.getClassName() === "NodeMaterial" ? "u_" : "";
 
-        this._matriceNames = {
-            "world": prefix + "world",
-            "view": prefix + "view",
-            "projection": prefix + "projection",
-            "viewProjection": prefix + "viewProjection",
-            "worldView": prefix + "worldView",
-            "worldViewProjection": prefix + "worldViewProjection",
-        };
+        if (prefix) {
+            this._matriceNames = {
+                "world": prefix + "World",
+                "view": prefix + "View",
+                "projection": prefix + "Projection",
+                "viewProjection": prefix + "ViewProjection",
+                "worldView": prefix + "WorldxView",
+                "worldViewProjection": prefix + "WorldxViewxProjection",
+            };
+
+            const nodeMat = baseMaterial as NodeMaterial;
+            const inputBlocks = nodeMat.getInputBlocks();
+
+            for (let i = 0; i < inputBlocks.length; ++i) {
+                switch (inputBlocks[i]._systemValue) {
+                    case NodeMaterialSystemValues.World:
+                        this._matriceNames["world"] = inputBlocks[i].associatedVariableName;
+                        break;
+                    case NodeMaterialSystemValues.View:
+                        this._matriceNames["view"] = inputBlocks[i].associatedVariableName;
+                        break;
+                    case NodeMaterialSystemValues.Projection:
+                        this._matriceNames["projection"] = inputBlocks[i].associatedVariableName;
+                        break;
+                    case NodeMaterialSystemValues.ViewProjection:
+                        this._matriceNames["viewProjection"] = inputBlocks[i].associatedVariableName;
+                        break;
+                    case NodeMaterialSystemValues.WorldView:
+                        this._matriceNames["worldView"] = inputBlocks[i].associatedVariableName;
+                        break;
+                    case NodeMaterialSystemValues.WorldViewProjection:
+                        this._matriceNames["worldViewProjection"] = inputBlocks[i].associatedVariableName;
+                        break;
+                }
+            }
+        } else {
+            this._matriceNames = {
+                "world": prefix + "world",
+                "view": prefix + "view",
+                "projection": prefix + "projection",
+                "viewProjection": prefix + "viewProjection",
+                "worldView": prefix + "worldView",
+                "worldViewProjection": prefix + "worldViewProjection",
+            };
+        }
 
         // Register for onEffectCreated to store the effect of the base material when it is (re)generated. This effect will be used
         // to create the depth effect later on
@@ -199,8 +238,8 @@ export class ShadowDepthWrapper {
         params.depthDefines = join;
 
         // the depth effect is either out of date or has not been created yet
-        let vertexCode = origEffect.vertexSourceCode,
-            fragmentCode = origEffect.fragmentSourceCode;
+        let vertexCode = origEffect.rawVertexSourceCode,
+            fragmentCode = origEffect.rawFragmentSourceCode;
 
         // vertex code
         const vertexNormalBiasCode = this._options && this._options.remappedVariables ? `#include<shadowMapVertexNormalBias>(${this._options.remappedVariables.join(",")})` : Effect.IncludesShadersStore["shadowMapVertexNormalBias"],
@@ -257,7 +296,7 @@ export class ShadowDepthWrapper {
             uniformsNames: uniforms,
             uniformBuffersNames: origEffect.getUniformBuffersNames(),
             samplers: origEffect.getSamplers(),
-            defines: join + "\n" + origEffect.defines,
+            defines: join + "\n" + origEffect.defines.replace("#define SHADOWS", "").replace(/#define SHADOW\d/g, ""),
             indexParameters: origEffect.getIndexParameters(),
         }, this._scene.getEngine());