De duplicate imports when generating a shader from shader nodes
This commit is contained in:
		
							parent
							
								
									eb6ce4d4b4
								
							
						
					
					
						commit
						171007693b
					
				| @ -31,14 +31,15 @@ | |||||||
|  */ |  */ | ||||||
| package com.jme3.shader; | package com.jme3.shader; | ||||||
| 
 | 
 | ||||||
| import com.jme3.asset.AssetKey; |  | ||||||
| import com.jme3.asset.AssetManager; | import com.jme3.asset.AssetManager; | ||||||
| import com.jme3.material.ShaderGenerationInfo; | import com.jme3.material.ShaderGenerationInfo; | ||||||
| import com.jme3.material.Technique; |  | ||||||
| import com.jme3.material.TechniqueDef; | import com.jme3.material.TechniqueDef; | ||||||
| import com.jme3.shader.Shader.ShaderType; | import com.jme3.shader.Shader.ShaderType; | ||||||
| import java.util.List; | import com.jme3.shader.plugins.ShaderAssetKey; | ||||||
| import java.util.regex.*; | 
 | ||||||
|  | import java.util.*; | ||||||
|  | import java.util.regex.Matcher; | ||||||
|  | import java.util.regex.Pattern; | ||||||
| 
 | 
 | ||||||
| /** | /** | ||||||
|  * This class is the base for a shader generator using the ShaderNodes system, |  * This class is the base for a shader generator using the ShaderNodes system, | ||||||
| @ -66,6 +67,8 @@ public abstract class ShaderGenerator { | |||||||
|      */ |      */ | ||||||
|     Pattern extensions = Pattern.compile("(#extension.*\\s+)"); |     Pattern extensions = Pattern.compile("(#extension.*\\s+)"); | ||||||
| 
 | 
 | ||||||
|  |     private Map<String, String> imports = new LinkedHashMap<>(); | ||||||
|  | 
 | ||||||
|     /** |     /** | ||||||
|      * Build a shaderGenerator |      * Build a shaderGenerator | ||||||
|      * |      * | ||||||
| @ -127,6 +130,8 @@ public abstract class ShaderGenerator { | |||||||
|             return null; |             return null; | ||||||
|         } |         } | ||||||
| 
 | 
 | ||||||
|  |         imports.clear(); | ||||||
|  | 
 | ||||||
|         indent = 0; |         indent = 0; | ||||||
| 
 | 
 | ||||||
|         StringBuilder sourceDeclaration = new StringBuilder(); |         StringBuilder sourceDeclaration = new StringBuilder(); | ||||||
| @ -145,6 +150,12 @@ public abstract class ShaderGenerator { | |||||||
| 
 | 
 | ||||||
|         generateEndOfMainSection(source, info, type); |         generateEndOfMainSection(source, info, type); | ||||||
| 
 | 
 | ||||||
|  |         //insert imports backward | ||||||
|  |         int insertIndex = sourceDeclaration.length(); | ||||||
|  |         for (String importSource : imports.values()) { | ||||||
|  |             sourceDeclaration.insert(insertIndex, importSource); | ||||||
|  |         } | ||||||
|  | 
 | ||||||
|         sourceDeclaration.append(source); |         sourceDeclaration.append(source); | ||||||
| 
 | 
 | ||||||
|         return moveExtensionsUp(sourceDeclaration); |         return moveExtensionsUp(sourceDeclaration); | ||||||
| @ -186,7 +197,13 @@ public abstract class ShaderGenerator { | |||||||
|             if (shaderNode.getDefinition().getType() == type) { |             if (shaderNode.getDefinition().getType() == type) { | ||||||
|                 int index = findShaderIndexFromVersion(shaderNode, type); |                 int index = findShaderIndexFromVersion(shaderNode, type); | ||||||
|                 String shaderPath = shaderNode.getDefinition().getShadersPath().get(index); |                 String shaderPath = shaderNode.getDefinition().getShadersPath().get(index); | ||||||
|                 String loadedSource = (String) assetManager.loadAsset(new AssetKey(shaderPath)); |                 Map<String, String> sources = (Map<String, String>) assetManager.loadAsset(new ShaderAssetKey(shaderPath, false)); | ||||||
|  |                 String loadedSource = sources.get("[main]"); | ||||||
|  |                 for (String name : sources.keySet()) { | ||||||
|  |                     if (!name.equals("[main]")) { | ||||||
|  |                         imports.put(name, sources.get(name)); | ||||||
|  |                     } | ||||||
|  |                 } | ||||||
|                 appendNodeDeclarationAndMain(loadedSource, sourceDeclaration, source, shaderNode, info, shaderPath); |                 appendNodeDeclarationAndMain(loadedSource, sourceDeclaration, source, shaderNode, info, shaderPath); | ||||||
|             } |             } | ||||||
|         } |         } | ||||||
|  | |||||||
| @ -34,10 +34,7 @@ package com.jme3.shader.plugins; | |||||||
| import com.jme3.asset.*; | import com.jme3.asset.*; | ||||||
| import com.jme3.asset.cache.AssetCache; | import com.jme3.asset.cache.AssetCache; | ||||||
| 
 | 
 | ||||||
| import java.io.BufferedReader; | import java.io.*; | ||||||
| import java.io.IOException; |  | ||||||
| import java.io.InputStreamReader; |  | ||||||
| import java.io.Reader; |  | ||||||
| import java.util.*; | import java.util.*; | ||||||
| 
 | 
 | ||||||
| /** | /** | ||||||
| @ -148,7 +145,7 @@ public class GLSLLoader implements AssetLoader { | |||||||
|         throw new IOException("Circular dependency."); |         throw new IOException("Circular dependency."); | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
|     private String resolveDependencies(ShaderDependencyNode node, Set<ShaderDependencyNode> alreadyInjectedSet, StringBuilder extensions) { |     private String resolveDependencies(ShaderDependencyNode node, Set<ShaderDependencyNode> alreadyInjectedSet, StringBuilder extensions, boolean injectDependencies) { | ||||||
|         if (alreadyInjectedSet.contains(node)) { |         if (alreadyInjectedSet.contains(node)) { | ||||||
|             return "// " + node.getName() + " was already injected at the top.\n"; |             return "// " + node.getName() + " was already injected at the top.\n"; | ||||||
|         } else { |         } else { | ||||||
| @ -160,18 +157,27 @@ public class GLSLLoader implements AssetLoader { | |||||||
|         if (node.getDependencies().isEmpty()) { |         if (node.getDependencies().isEmpty()) { | ||||||
|             return node.getSource(); |             return node.getSource(); | ||||||
|         } else { |         } else { | ||||||
|             StringBuilder sb = new StringBuilder(node.getSource()); |             if (injectDependencies) { | ||||||
|             List<String> resolvedShaderNodes = new ArrayList<>(); |                 StringBuilder sb = new StringBuilder(node.getSource()); | ||||||
|  |                 List<String> resolvedShaderNodes = new ArrayList<>(); | ||||||
| 
 | 
 | ||||||
|             for (ShaderDependencyNode dependencyNode : node.getDependencies()) { |                 for (ShaderDependencyNode dependencyNode : node.getDependencies()) { | ||||||
|                 resolvedShaderNodes.add(resolveDependencies(dependencyNode, alreadyInjectedSet, extensions)); |                     resolvedShaderNodes.add(resolveDependencies(dependencyNode, alreadyInjectedSet, extensions, injectDependencies)); | ||||||
|  |                 } | ||||||
|  | 
 | ||||||
|  |                 List<Integer> injectIndices = node.getDependencyInjectIndices(); | ||||||
|  |                 for (int i = resolvedShaderNodes.size() - 1; i >= 0; i--) { | ||||||
|  |                     // Must insert them backwards .. | ||||||
|  |                     sb.insert(injectIndices.get(i), resolvedShaderNodes.get(i)); | ||||||
|  |                 } | ||||||
|  |                 return sb.toString(); | ||||||
|  |             } else { | ||||||
|  |                 for (ShaderDependencyNode dependencyNode : node.getDependencies()) { | ||||||
|  |                     resolveDependencies(dependencyNode, alreadyInjectedSet, extensions, injectDependencies); | ||||||
|  |                 } | ||||||
|  |                 return null; | ||||||
|             } |             } | ||||||
|             List<Integer> injectIndices = node.getDependencyInjectIndices(); | 
 | ||||||
|             for (int i = resolvedShaderNodes.size() - 1; i >= 0; i--) { |  | ||||||
|                 // Must insert them backwards .. |  | ||||||
|                 sb.insert(injectIndices.get(i), resolvedShaderNodes.get(i)); |  | ||||||
|             } |  | ||||||
|             return sb.toString(); |  | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| 
 | 
 | ||||||
| @ -181,6 +187,10 @@ public class GLSLLoader implements AssetLoader { | |||||||
|         // to retrieve the fragment shader, use the content manager |         // to retrieve the fragment shader, use the content manager | ||||||
|         this.assetManager = info.getManager(); |         this.assetManager = info.getManager(); | ||||||
|         Reader reader = new InputStreamReader(info.openStream()); |         Reader reader = new InputStreamReader(info.openStream()); | ||||||
|  |         boolean injectDependencies = true; | ||||||
|  |         if (info.getKey() instanceof ShaderAssetKey) { | ||||||
|  |             injectDependencies = ((ShaderAssetKey) info.getKey()).isInjectDependencies(); | ||||||
|  |         } | ||||||
|         if (info.getKey().getExtension().equals("glsllib")) { |         if (info.getKey().getExtension().equals("glsllib")) { | ||||||
|             // NOTE: Loopback, GLSLLIB is loaded by this loader |             // NOTE: Loopback, GLSLLIB is loaded by this loader | ||||||
|             // and needs data as InputStream |             // and needs data as InputStream | ||||||
| @ -188,10 +198,25 @@ public class GLSLLoader implements AssetLoader { | |||||||
|         } else { |         } else { | ||||||
|             ShaderDependencyNode rootNode = loadNode(reader, "[main]"); |             ShaderDependencyNode rootNode = loadNode(reader, "[main]"); | ||||||
|             StringBuilder extensions = new StringBuilder(); |             StringBuilder extensions = new StringBuilder(); | ||||||
|             String code = resolveDependencies(rootNode, new HashSet<ShaderDependencyNode>(), extensions); |             if (injectDependencies) { | ||||||
|             extensions.append(code); |                 String code = resolveDependencies(rootNode, new HashSet<ShaderDependencyNode>(), extensions, injectDependencies); | ||||||
|             dependCache.clear(); |                 extensions.append(code); | ||||||
|             return extensions.toString(); |                 dependCache.clear(); | ||||||
|  |                 return extensions.toString(); | ||||||
|  |             } else { | ||||||
|  |                 Map<String, String> files = new LinkedHashMap<>(); | ||||||
|  |                 HashSet<ShaderDependencyNode> dependencies = new HashSet<>(); | ||||||
|  |                 String code = resolveDependencies(rootNode, dependencies, extensions, injectDependencies); | ||||||
|  |                 extensions.append(code); | ||||||
|  |                 files.put("[main]", extensions.toString()); | ||||||
|  | 
 | ||||||
|  |                 for (ShaderDependencyNode dependency : dependencies) { | ||||||
|  |                     files.put(dependency.getName(), dependency.getSource()); | ||||||
|  |                 } | ||||||
|  | 
 | ||||||
|  |                 dependCache.clear(); | ||||||
|  |                 return files; | ||||||
|  |             } | ||||||
|         } |         } | ||||||
|     } |     } | ||||||
| } | } | ||||||
|  | |||||||
| @ -0,0 +1,24 @@ | |||||||
|  | package com.jme3.shader.plugins; | ||||||
|  | 
 | ||||||
|  | import com.jme3.asset.AssetKey; | ||||||
|  | 
 | ||||||
|  | /** | ||||||
|  |  * Created by Nehon on 28/10/2017. | ||||||
|  |  */ | ||||||
|  | public class ShaderAssetKey extends AssetKey { | ||||||
|  | 
 | ||||||
|  |     private boolean injectDependencies = false; | ||||||
|  | 
 | ||||||
|  |     public ShaderAssetKey(String name, boolean injectDependencies) { | ||||||
|  |         super(name); | ||||||
|  |         this.injectDependencies = injectDependencies; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     public boolean isInjectDependencies() { | ||||||
|  |         return injectDependencies; | ||||||
|  |     } | ||||||
|  | 
 | ||||||
|  |     public void setInjectDependencies(boolean injectDependencies) { | ||||||
|  |         this.injectDependencies = injectDependencies; | ||||||
|  |     } | ||||||
|  | } | ||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user