浏览代码

temp

/main
Tim Cooper 7 年前
当前提交
0818f178
共有 12 个文件被更改,包括 477 次插入470 次删除
  1. 4
      MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/AbstractMaterialGraphEditWindow.cs
  2. 2
      MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/Inspector/GraphInspectorPresenter.cs
  3. 9
      MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/PreviewSystem.cs
  4. 2
      MaterialGraphProject/Assets/UnityShaderEditor/Editor/Importers/ShaderGraphImporter.cs
  5. 245
      MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/AbstractMaterialGraph.cs
  6. 211
      MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/MaterialGraph.cs
  7. 153
      MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Nodes/MasterNode.cs
  8. 278
      MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Util/ShaderGenerator.cs
  9. 22
      MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/ShaderGraphRequirements.cs
  10. 3
      MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/ShaderGraphRequirements.cs.meta
  11. 9
      MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/Inspector/Presenters.meta
  12. 9
      MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/Inspector/Views.meta

4
MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/AbstractMaterialGraphEditWindow.cs


if (graph == null)
return;
List<PropertyCollector.TextureInfo> configuredTextures;
graph.GetFullShader(GenerationMode.ForReals, Path.GetFileNameWithoutExtension(path), out configuredTextures);
List<PropertyCollector.TextureInfo> configuredTextures = new List<PropertyCollector.TextureInfo>();
// graph.GetPreviewShader(graph.masterNode, GenerationMode.ForReals, Path.GetFileNameWithoutExtension(path), out configuredTextures);
var shaderImporter = AssetImporter.GetAtPath(path) as ShaderImporter;
if (shaderImporter == null)

2
MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/Inspector/GraphInspectorPresenter.cs


public void Initialize(string assetName, PreviewSystem previewSystem, HelperMaterialGraphEditWindow window)
{
m_Owner = window;
var masterNode = graph.GetNodes<MasterNode>().FirstOrDefault();
if (masterNode != null)
{

m_Owner = window;
this.assetName = assetName;
selectedNodes = new List<INode>();

9
MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/PreviewSystem.cs


{
public class PreviewSystem : IDisposable
{
IGraph m_Graph;
AbstractMaterialGraph m_Graph;
Dictionary<Guid, PreviewData> m_Previews = new Dictionary<Guid, PreviewData>();
HashSet<Guid> m_DirtyPreviews = new HashSet<Guid>();
HashSet<Guid> m_DirtyShaders = new HashSet<Guid>();

MaterialGraphPreviewGenerator m_PreviewGenerator = new MaterialGraphPreviewGenerator();
Texture2D m_ErrorTexture;
public PreviewSystem(IGraph graph)
public PreviewSystem(AbstractMaterialGraph graph)
{
m_Graph = graph;
m_PreviewMaterial = new Material(Shader.Find("Unlit/Color")) { hideFlags = HideFlags.HideInHierarchy };

}
else
{
PreviewMode previewMode;
previewData.shaderString = ShaderGenerator.GeneratePreviewShader(node, out previewMode);
previewData.previewMode = previewMode;
List<PropertyCollector.TextureInfo> defaultTextures;
previewData.shaderString = m_Graph.GetPreviewShader(node);
}
// Debug output

2
MaterialGraphProject/Assets/UnityShaderEditor/Editor/Importers/ShaderGraphImporter.cs


var name = Path.GetFileNameWithoutExtension(path);
List<PropertyCollector.TextureInfo> configuredTextures;
var shaderString = graph.GetFullShader(GenerationMode.ForReals, string.Format("graphs/{0}", name), out configuredTextures);
var shaderString = graph.GetShader(string.Format("graphs/{0}", name), out configuredTextures);
Debug.Log(shaderString);
return shaderString;
}

245
MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/AbstractMaterialGraph.cs


using System;
using System.Collections.Generic;
using System.Linq;
using UnityEngine.XR.WSA.WebCam;
namespace UnityEngine.MaterialGraph
{

[NonSerialized]
private List<IShaderProperty> m_Properties = new List<IShaderProperty>();
[NonSerialized] private List<IShaderProperty> m_Properties = new List<IShaderProperty>();
[SerializeField]
private List<SerializationHelper.JSONSerializedElement> m_SerializedProperties = new List<SerializationHelper.JSONSerializedElement>();
[SerializeField] private List<SerializationHelper.JSONSerializedElement> m_SerializedProperties = new List<SerializationHelper.JSONSerializedElement>();
public IEnumerable<IShaderProperty> properties

public void CollectShaderProperties(PropertyCollector collector, GenerationMode generationMode)
{
foreach(var prop in properties)
foreach (var prop in properties)
collector.AddShaderProperty(prop);
}

// have to deserialize 'globals' before nodes
m_Properties = SerializationHelper.Deserialize<IShaderProperty>(m_SerializedProperties, null);
base.OnAfterDeserialize();
}
private static ShaderGraphRequirements GetRequierments(AbstractMaterialNode nodeForRequirements)
{
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, nodeForRequirements);
NeededCoordinateSpace requiresNormal = activeNodeList.OfType<IMayRequireNormal>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresNormal());
NeededCoordinateSpace requiresBitangent = activeNodeList.OfType<IMayRequireBitangent>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresBitangent());
NeededCoordinateSpace requiresTangent = activeNodeList.OfType<IMayRequireTangent>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresTangent());
NeededCoordinateSpace requiresViewDir = activeNodeList.OfType<IMayRequireViewDirection>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresViewDirection());
NeededCoordinateSpace requiresPosition = activeNodeList.OfType<IMayRequirePosition>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresPosition());
bool requiresScreenPosition = activeNodeList.OfType<IMayRequireScreenPosition>().Any(x => x.RequiresScreenPosition());
bool requiresVertexColor = activeNodeList.OfType<IMayRequireVertexColor>().Any(x => x.RequiresVertexColor());
// if anything needs tangentspace we have make
// sure to have our othonormal basis!
var compoundSpaces = requiresBitangent | requiresNormal | requiresPosition
| requiresTangent | requiresViewDir | requiresPosition
| requiresNormal;
var needsTangentSpace = (compoundSpaces & NeededCoordinateSpace.Tangent) > 0;
if (needsTangentSpace)
{
requiresBitangent |= NeededCoordinateSpace.Object;
requiresNormal |= NeededCoordinateSpace.Object;
requiresTangent |= NeededCoordinateSpace.Object;
}
var reqs = new ShaderGraphRequirements()
{
requiresNormal = requiresNormal,
requiresBitangent = requiresBitangent,
requiresTangent = requiresTangent,
requiresViewDir = requiresViewDir,
requiresPosition = requiresPosition,
requiresScreenPosition = requiresScreenPosition,
requiresVertexColor = requiresVertexColor
};
ListPool<INode>.Release(activeNodeList);
return reqs;
}
private static void GenerateSpaceTranslationSurfaceInputs(
NeededCoordinateSpace neededSpaces,
ShaderGenerator surfaceInputs,
string objectSpaceName,
string viewSpaceName,
string worldSpaceName,
string tangentSpaceName)
{
if ((neededSpaces & NeededCoordinateSpace.Object) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", objectSpaceName), false);
if ((neededSpaces & NeededCoordinateSpace.World) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", worldSpaceName), false);
if ((neededSpaces & NeededCoordinateSpace.View) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", viewSpaceName), false);
if ((neededSpaces & NeededCoordinateSpace.Tangent) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", tangentSpaceName), false);
}
public string GetPreviewShader(AbstractMaterialNode node)
{
List<PropertyCollector.TextureInfo> configuredTextures;
return GetShader(node, GenerationMode.Preview, string.Format("hidden/preview/{0}", node.GetVariableNameForNode()), out configuredTextures);
}
protected string GetShader(AbstractMaterialNode node, GenerationMode mode, string name, out List<PropertyCollector.TextureInfo> configuredTextures)
{
var vertexShader = new ShaderGenerator();
var pixelShader = new ShaderGenerator();
var surfaceDescription = new ShaderGenerator();
var shaderFunctionVisitor = new ShaderGenerator();
var surfaceInputs = new ShaderGenerator();
var graphVertexInput = @"
struct GraphVertexInput
{
float4 vertex : POSITION;
float3 normal : NORMAL;
float4 tangent : TANGENT;
float2 texcoord : TEXCOORD0;
float2 lightmapUV : TEXCOORD1;
UNITY_VERTEX_INPUT_INSTANCE_ID
};";
surfaceInputs.AddShaderChunk("struct SurfaceInputs{", false);
surfaceInputs.Indent();
var requirements = GetRequierments(node);
GenerateSpaceTranslationSurfaceInputs(requirements.requiresNormal, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceNormal, ShaderGeneratorNames.ViewSpaceNormal,
ShaderGeneratorNames.WorldSpaceNormal, ShaderGeneratorNames.TangentSpaceNormal);
GenerateSpaceTranslationSurfaceInputs(requirements.requiresTangent, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceTangent, ShaderGeneratorNames.ViewSpaceTangent,
ShaderGeneratorNames.WorldSpaceTangent, ShaderGeneratorNames.TangentSpaceTangent);
GenerateSpaceTranslationSurfaceInputs(requirements.requiresBitangent, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceBiTangent, ShaderGeneratorNames.ViewSpaceBiTangent,
ShaderGeneratorNames.WorldSpaceSpaceBiTangent, ShaderGeneratorNames.TangentSpaceBiTangent);
GenerateSpaceTranslationSurfaceInputs(requirements.requiresViewDir, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceViewDirection, ShaderGeneratorNames.ViewSpaceViewDirection,
ShaderGeneratorNames.WorldSpaceViewDirection, ShaderGeneratorNames.TangentSpaceViewDirection);
GenerateSpaceTranslationSurfaceInputs(requirements.requiresPosition, surfaceInputs,
ShaderGeneratorNames.ObjectSpacePosition, ShaderGeneratorNames.ViewSpacePosition,
ShaderGeneratorNames.WorldSpacePosition, ShaderGeneratorNames.TangentSpacePosition);
if (requirements.requiresVertexColor)
surfaceInputs.AddShaderChunk(string.Format("float4 {0};", ShaderGeneratorNames.VertexColor), false);
if (requirements.requiresScreenPosition)
surfaceInputs.AddShaderChunk(string.Format("float4 {0};", ShaderGeneratorNames.ScreenPosition), false);
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, node);
for (int uvIndex = 0; uvIndex < ShaderGeneratorNames.UVCount; ++uvIndex)
{
var channel = (UVChannel) uvIndex;
if (activeNodeList.OfType<IMayRequireMeshUV>().Any(x => x.RequiresMeshUV(channel)))
surfaceInputs.AddShaderChunk(string.Format("half4 meshUV{0};", uvIndex), false);
}
surfaceInputs.Deindent();
surfaceInputs.AddShaderChunk("};", false);
vertexShader.AddShaderChunk("GraphVertexInput PopulateVertexData(GraphVertexInput v){", false);
vertexShader.Indent();
vertexShader.AddShaderChunk("return v;", false);
vertexShader.Deindent();
vertexShader.AddShaderChunk("}", false);
surfaceDescription.AddShaderChunk("struct SurfaceDescription{", false);
surfaceDescription.Indent();
if (mode == GenerationMode.Preview)
{
foreach (var slot in node.GetOutputSlots<MaterialSlot>())
surfaceDescription.AddShaderChunk(AbstractMaterialNode.ConvertConcreteSlotValueTypeToString(AbstractMaterialNode.OutputPrecision.@float, slot.concreteValueType) + " " + node.GetVariableNameForSlot(slot.id) + ";", false);
}
else
{
foreach (var slot in node.GetInputSlots<MaterialSlot>())
surfaceDescription.AddShaderChunk(AbstractMaterialNode.ConvertConcreteSlotValueTypeToString(AbstractMaterialNode.OutputPrecision.@float, slot.concreteValueType) + " " + slot.shaderOutputName + ";", false);
}
surfaceDescription.Deindent();
surfaceDescription.AddShaderChunk("};", false);
pixelShader.AddShaderChunk("SurfaceDescription PopulateSurfaceData(SurfaceInputs IN) {", false);
pixelShader.Indent();
var generationMode = GenerationMode.ForReals;
var shaderProperties = new PropertyCollector();
CollectShaderProperties(shaderProperties, generationMode);
foreach (var activeNode in activeNodeList.OfType<AbstractMaterialNode>())
{
if (activeNode is IGeneratesFunction)
(activeNode as IGeneratesFunction).GenerateNodeFunction(shaderFunctionVisitor, generationMode);
if (activeNode is IGeneratesBodyCode)
(activeNode as IGeneratesBodyCode).GenerateNodeCode(pixelShader, generationMode);
activeNode.CollectShaderProperties(shaderProperties, generationMode);
}
pixelShader.AddShaderChunk("SurfaceDescription surface;", false);
if (mode == GenerationMode.Preview)
{
foreach (var slot in node.GetOutputSlots<MaterialSlot>())
pixelShader.AddShaderChunk(string.Format("surface.{0} = {0};", node.GetVariableNameForSlot(slot.id)), true);
}
else
{
foreach (var input in node.GetInputSlots<MaterialSlot>())
{
foreach (var edge in GetEdges(input.slotReference))
{
var outputRef = edge.outputSlot;
var fromNode = GetNodeFromGuid<AbstractMaterialNode>(outputRef.nodeGuid);
if (fromNode == null)
continue;
var remapper = fromNode as INodeGroupRemapper;
if (remapper != null && !remapper.IsValidSlotConnection(outputRef.slotId))
continue;
pixelShader.AddShaderChunk(string.Format("surface.{0} = {1};", input.shaderOutputName, fromNode.GetVariableNameForSlot(outputRef.slotId)), true);
}
}
}
pixelShader.AddShaderChunk("return surface;", false);
pixelShader.Deindent();
pixelShader.AddShaderChunk("}", false);
ListPool<INode>.Release(activeNodeList);
var finalShader = new ShaderGenerator();
finalShader.AddShaderChunk(string.Format(@"Shader ""{0}""", name), false);
finalShader.AddShaderChunk("{", false);
finalShader.Indent();
finalShader.AddShaderChunk("Properties", false);
finalShader.AddShaderChunk("{", false);
finalShader.Indent();
finalShader.AddShaderChunk(shaderProperties.GetPropertiesBlock(2), false);
finalShader.Deindent();
finalShader.AddShaderChunk("}", false);
finalShader.AddShaderChunk("CGINCLUDE", false);
finalShader.AddShaderChunk("#include \"UnityCG.cginc\"", false);
finalShader.AddShaderChunk(shaderFunctionVisitor.GetShaderString(2), false);
finalShader.AddShaderChunk(graphVertexInput, false);
finalShader.AddShaderChunk(surfaceInputs.GetShaderString(2), false);
finalShader.AddShaderChunk(surfaceDescription.GetShaderString(2), false);
finalShader.AddShaderChunk(shaderProperties.GetPropertiesDeclaration(2), false);
finalShader.AddShaderChunk(vertexShader.GetShaderString(2), false);
finalShader.AddShaderChunk(pixelShader.GetShaderString(2), false);
finalShader.AddShaderChunk("ENDCG", false);
if (generationMode == GenerationMode.Preview)
finalShader.AddShaderChunk(ShaderGenerator.GetPreviewSubShader(node, GetRequierments(node)), false);
else
{
var master = (MasterNode) node;
finalShader.AddShaderChunk(master.GetSubShader(requirements), false);
}
finalShader.Deindent();
finalShader.AddShaderChunk("}", false);
configuredTextures = shaderProperties.GetConfiguredTexutres();
return finalShader.GetShaderString(0);
}
}
}

211
MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/MaterialGraph.cs


get { return GetNodes<MasterNode>().FirstOrDefault(); }
}
protected MasterNode.Requirements GetRequierments()
public string GetShader(string name, out List<PropertyCollector.TextureInfo> configuredTextures)
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, masterNode);
NeededCoordinateSpace requiresNormal = activeNodeList.OfType<IMayRequireNormal>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresNormal());
NeededCoordinateSpace requiresBitangent = activeNodeList.OfType<IMayRequireBitangent>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresBitangent());
NeededCoordinateSpace requiresTangent = activeNodeList.OfType<IMayRequireTangent>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresTangent());
NeededCoordinateSpace requiresViewDir = activeNodeList.OfType<IMayRequireViewDirection>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresViewDirection());
NeededCoordinateSpace requiresPosition = activeNodeList.OfType<IMayRequirePosition>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresPosition());
bool requiresScreenPosition = activeNodeList.OfType<IMayRequireScreenPosition>().Any(x => x.RequiresScreenPosition());
bool requiresVertexColor = activeNodeList.OfType<IMayRequireVertexColor>().Any(x => x.RequiresVertexColor());
// if anything needs tangentspace we have make
// sure to have our othonormal basis!
var compoundSpaces = requiresBitangent | requiresNormal | requiresPosition
| requiresTangent | requiresViewDir | requiresPosition
| requiresNormal;
var needsTangentSpace = (compoundSpaces & NeededCoordinateSpace.Tangent) > 0;
if (needsTangentSpace)
{
requiresBitangent |= NeededCoordinateSpace.Object;
requiresNormal |= NeededCoordinateSpace.Object;
requiresTangent |= NeededCoordinateSpace.Object;
}
var reqs = new MasterNode.Requirements()
{
requiresNormal = requiresNormal,
requiresBitangent = requiresBitangent,
requiresTangent = requiresTangent,
requiresViewDir = requiresViewDir,
requiresPosition = requiresPosition,
requiresScreenPosition = requiresScreenPosition,
requiresVertexColor = requiresVertexColor
};
ListPool<INode>.Release(activeNodeList);
return reqs;
}
private static void GenerateSpaceTranslation(
NeededCoordinateSpace neededSpaces,
ShaderGenerator surfaceInputs,
string objectSpaceName,
string viewSpaceName,
string worldSpaceName,
string tangentSpaceName)
{
if ((neededSpaces & NeededCoordinateSpace.Object) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", objectSpaceName), false);
if ((neededSpaces & NeededCoordinateSpace.World) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", worldSpaceName), false);
if ((neededSpaces & NeededCoordinateSpace.View) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", viewSpaceName), false);
if ((neededSpaces & NeededCoordinateSpace.Tangent) > 0)
surfaceInputs.AddShaderChunk(string.Format("float3 {0};", tangentSpaceName), false);
return GetShader(masterNode, GenerationMode.ForReals, name, out configuredTextures);
public string GetFullShader(GenerationMode mode, string name, out List<PropertyCollector.TextureInfo> configuredTextures)
{
var vertexShader = new ShaderGenerator();
var pixelShader = new ShaderGenerator();
var surfaceDescription = new ShaderGenerator();
var shaderFunctionVisitor = new ShaderGenerator();
var surfaceInputs = new ShaderGenerator();
// always add color because why not.
var graphVertexInput = @"
struct GraphVertexInput
{
float4 vertex : POSITION;
float3 normal : NORMAL;
float4 tangent : TANGENT;
float2 texcoord : TEXCOORD0;
float2 lightmapUV : TEXCOORD1;
UNITY_VERTEX_INPUT_INSTANCE_ID
};";
surfaceInputs.AddShaderChunk("struct SurfaceInputs{", false);
surfaceInputs.Indent();
var requirements = GetRequierments();
GenerateSpaceTranslation(requirements.requiresNormal, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceNormal, ShaderGeneratorNames.ViewSpaceNormal,
ShaderGeneratorNames.WorldSpaceNormal, ShaderGeneratorNames.TangentSpaceNormal);
GenerateSpaceTranslation(requirements.requiresTangent, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceTangent, ShaderGeneratorNames.ViewSpaceTangent,
ShaderGeneratorNames.WorldSpaceTangent, ShaderGeneratorNames.TangentSpaceTangent);
GenerateSpaceTranslation(requirements.requiresBitangent, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceBiTangent, ShaderGeneratorNames.ViewSpaceBiTangent,
ShaderGeneratorNames.WorldSpaceSpaceBiTangent, ShaderGeneratorNames.TangentSpaceBiTangent);
GenerateSpaceTranslation(requirements.requiresViewDir, surfaceInputs,
ShaderGeneratorNames.ObjectSpaceViewDirection, ShaderGeneratorNames.ViewSpaceViewDirection,
ShaderGeneratorNames.WorldSpaceViewDirection, ShaderGeneratorNames.TangentSpaceViewDirection);
GenerateSpaceTranslation(requirements.requiresPosition, surfaceInputs,
ShaderGeneratorNames.ObjectSpacePosition, ShaderGeneratorNames.ViewSpacePosition,
ShaderGeneratorNames.WorldSpacePosition, ShaderGeneratorNames.TangentSpacePosition);
if (requirements.requiresVertexColor)
surfaceInputs.AddShaderChunk(string.Format("float4 {0};", ShaderGeneratorNames.VertexColor), false);
if (requirements.requiresScreenPosition)
surfaceInputs.AddShaderChunk(string.Format("float4 {0};", ShaderGeneratorNames.ScreenPosition), false);
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, masterNode);
for (int uvIndex = 0; uvIndex < ShaderGeneratorNames.UVCount; ++uvIndex)
{
var channel = (UVChannel)uvIndex;
if (activeNodeList.OfType<IMayRequireMeshUV>().Any(x => x.RequiresMeshUV(channel)))
surfaceInputs.AddShaderChunk(string.Format("half4 meshUV{0};", uvIndex), false);
}
surfaceInputs.Deindent();
surfaceInputs.AddShaderChunk("};", false);
vertexShader.AddShaderChunk("GraphVertexInput PopulateVertexData(GraphVertexInput v){", false);
vertexShader.Indent();
vertexShader.AddShaderChunk("return v;", false);
vertexShader.Deindent();
vertexShader.AddShaderChunk("}", false);
surfaceDescription.AddShaderChunk("struct SurfaceDescription{", false);
surfaceDescription.Indent();
foreach (var input in masterNode.GetInputSlots<MaterialSlot>())
{
surfaceDescription.AddShaderChunk(AbstractMaterialNode.ConvertConcreteSlotValueTypeToString(AbstractMaterialNode.OutputPrecision.@float, input.concreteValueType) + " " + input.shaderOutputName + ";", false);
}
surfaceDescription.Deindent();
surfaceDescription.AddShaderChunk("};", false);
pixelShader.AddShaderChunk("SurfaceDescription PopulateSurfaceData(SurfaceInputs IN) {", false);
pixelShader.Indent();
var generationMode = GenerationMode.ForReals;
var shaderProperties = new PropertyCollector();
CollectShaderProperties(shaderProperties, generationMode);
foreach (var activeNode in activeNodeList.OfType<AbstractMaterialNode>())
{
if (activeNode is IGeneratesFunction)
(activeNode as IGeneratesFunction).GenerateNodeFunction(shaderFunctionVisitor, generationMode);
if (activeNode is IGeneratesBodyCode)
(activeNode as IGeneratesBodyCode).GenerateNodeCode(pixelShader, generationMode);
activeNode.CollectShaderProperties(shaderProperties, generationMode);
}
pixelShader.AddShaderChunk("SurfaceDescription surface;", false);
foreach (var input in masterNode.GetInputSlots<MaterialSlot>())
{
foreach (var edge in GetEdges(input.slotReference))
{
var outputRef = edge.outputSlot;
var fromNode = GetNodeFromGuid<AbstractMaterialNode>(outputRef.nodeGuid);
if (fromNode == null)
continue;
var remapper = fromNode as INodeGroupRemapper;
if (remapper != null && !remapper.IsValidSlotConnection(outputRef.slotId))
continue;
pixelShader.AddShaderChunk(string.Format("surface.{0} = {1};", input.shaderOutputName, fromNode.GetVariableNameForSlot(outputRef.slotId)), true);
}
}
pixelShader.AddShaderChunk("return surface;", false);
pixelShader.Deindent();
pixelShader.AddShaderChunk("}", false);
ListPool<INode>.Release(activeNodeList);
var finalShader = new ShaderGenerator();
finalShader.AddShaderChunk(string.Format(@"Shader ""{0}""", name), false);
finalShader.AddShaderChunk("{", false);
finalShader.Indent();
finalShader.AddShaderChunk("Properties", false);
finalShader.AddShaderChunk("{", false);
finalShader.Indent();
finalShader.AddShaderChunk(shaderProperties.GetPropertiesBlock(2), false);
finalShader.Deindent();
finalShader.AddShaderChunk("}", false);
finalShader.AddShaderChunk("CGINCLUDE", false);
finalShader.AddShaderChunk("#include \"UnityCG.cginc\"", false);
finalShader.AddShaderChunk(shaderFunctionVisitor.GetShaderString(2), false);
finalShader.AddShaderChunk(graphVertexInput, false);
finalShader.AddShaderChunk(surfaceInputs.GetShaderString(2), false);
finalShader.AddShaderChunk(surfaceDescription.GetShaderString(2), false);
finalShader.AddShaderChunk(shaderProperties.GetPropertiesDeclaration(2), false);
finalShader.AddShaderChunk(vertexShader.GetShaderString(2), false);
finalShader.AddShaderChunk(pixelShader.GetShaderString(2), false);
finalShader.AddShaderChunk("ENDCG", false);
finalShader.AddShaderChunk(masterNode.GetSubShader(GetRequierments()), false);
finalShader.Deindent();
finalShader.AddShaderChunk("}", false);
configuredTextures = shaderProperties.GetConfiguredTexutres();
return finalShader.GetShaderString(0);
}
}
}

153
MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Nodes/MasterNode.cs


return true;
}
private string subShaderTemplate = @"
SubShader
{
Tags { ""RenderType""=""Opaque"" }
LOD 100
Pass
{
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include ""UnityCG.cginc""
struct GraphVertexOutput
{
float4 position : POSITION;
{0}
};
GraphVertexOutput vert (GraphVertexInput v)
{
v = PopulateVertexData(v);
GraphVertexOutput o;
o.position = UnityObjectToClipPos(v.vertex);
{1}
return o;
}
fixed4 frag (GraphVertexOutput IN) : SV_Target
{
SurfaceInputs surfaceInput;
{2}
SurfaceDescription surf = PopulateSurfaceData(surfaceInput);
{3}
}
ENDCG
}
}";
public struct Requirements
{
public NeededCoordinateSpace requiresNormal;
public NeededCoordinateSpace requiresBitangent;
public NeededCoordinateSpace requiresTangent;
public NeededCoordinateSpace requiresViewDir;
public NeededCoordinateSpace requiresPosition;
public bool requiresScreenPosition;
public bool requiresVertexColor;
public bool NeedsTangentSpace()
{
var compoundSpaces = requiresBitangent | requiresNormal | requiresPosition
| requiresTangent | requiresViewDir | requiresPosition
| requiresNormal;
return (compoundSpaces & NeededCoordinateSpace.Tangent) > 0;
}
}
public string GetSubShader(Requirements requirements)
public string GetSubShader(ShaderGraphRequirements shaderGraphRequirements)
{
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, this);

var pixelShader = new ShaderGenerator();
// var surfaceInputs = new ShaderGenerator();
if (requirements.requiresNormal > 0 || requirements.requiresBitangent > 0)
if (shaderGraphRequirements.requiresNormal > 0 || shaderGraphRequirements.requiresBitangent > 0)
{
interpolators.AddShaderChunk(string.Format("float3 {0} : NORMAL;", ShaderGeneratorNames.ObjectSpaceNormal), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = v.normal;", ShaderGeneratorNames.ObjectSpaceNormal), false);

if (requirements.requiresTangent > 0 || requirements.requiresBitangent > 0)
if (shaderGraphRequirements.requiresTangent > 0 || shaderGraphRequirements.requiresBitangent > 0)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TANGENT;", ShaderGeneratorNames.ObjectSpaceTangent), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = v.tangent;", ShaderGeneratorNames.ObjectSpaceTangent), false);

}
int interpolatorIndex = 0;
if (requirements.requiresViewDir > 0)
if (shaderGraphRequirements.requiresViewDir > 0)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TEXCOORD{1};", ShaderGeneratorNames.ObjectSpaceViewDirection, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = ObjSpaceViewDir(v.vertex);", ShaderGeneratorNames.ObjectSpaceViewDirection), false);

if (requirements.requiresPosition > 0)
if (shaderGraphRequirements.requiresPosition > 0)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TEXCOORD{1};", ShaderGeneratorNames.ObjectSpacePosition, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = v.vertex;", ShaderGeneratorNames.ObjectSpacePosition), false);

if (requirements.NeedsTangentSpace())
if (shaderGraphRequirements.NeedsTangentSpace())
GenerateSpaceTranslation(requirements.requiresNormal, pixelShader,
ShaderGenerator.GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresNormal, pixelShader,
GenerateSpaceTranslation(requirements.requiresTangent, pixelShader,
ShaderGenerator.GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresTangent, pixelShader,
GenerateSpaceTranslation(requirements.requiresBitangent, pixelShader,
ShaderGenerator.GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresBitangent, pixelShader,
GenerateSpaceTranslation(requirements.requiresViewDir, pixelShader,
ShaderGenerator.GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresViewDir, pixelShader,
GenerateSpaceTranslation(requirements.requiresPosition, pixelShader,
ShaderGenerator.GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresPosition, pixelShader,
if (requirements.requiresVertexColor)
if (shaderGraphRequirements.requiresVertexColor)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : COLOR;", ShaderGeneratorNames.VertexColor), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = color", ShaderGeneratorNames.VertexColor), false);

if (requirements.requiresScreenPosition)
if (shaderGraphRequirements.requiresScreenPosition)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TEXCOORD{1};;", ShaderGeneratorNames.ScreenPosition, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = ComputeScreenPos(UnityObjectToClipPos(v.vertex)", ShaderGeneratorNames.ScreenPosition), false);

res = res.Replace("{2}", pixelShader.GetShaderString(0));
res = res.Replace("{3}", outputs.GetShaderString(0));
return res;
private static void GenerateSpaceTranslation(
NeededCoordinateSpace neededSpaces,
ShaderGenerator pixelShader,
string objectSpaceName,
string viewSpaceName,
string worldSpaceName,
string tangentSpaceName,
bool isNormal = false)
private const string subShaderTemplate = @"
SubShader
{
Tags { ""RenderType""=""Opaque"" }
LOD 100
Pass
{
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include ""UnityCG.cginc""
struct GraphVertexOutput
if ((neededSpaces & NeededCoordinateSpace.Object) > 0)
{
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = IN.{0};", objectSpaceName), false);
}
float4 position : POSITION;
{0}
};
if ((neededSpaces & NeededCoordinateSpace.World) > 0)
{
if (isNormal)
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = UnityObjectToWorldNormal(IN.{1});", worldSpaceName, objectSpaceName), false);
else
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = UnityObjectToWorldDir(IN.{1});", worldSpaceName, objectSpaceName), false);
}
GraphVertexOutput vert (GraphVertexInput v)
{
v = PopulateVertexData(v);
if ((neededSpaces & NeededCoordinateSpace.View) > 0)
{
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = UnityObjectToViewPos(IN.{1});", viewSpaceName, objectSpaceName), false);
}
GraphVertexOutput o;
o.position = UnityObjectToClipPos(v.vertex);
{1}
return o;
}
fixed4 frag (GraphVertexOutput IN) : SV_Target
{
SurfaceInputs surfaceInput;
{2}
if ((neededSpaces & NeededCoordinateSpace.Tangent) > 0)
{
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = mul(tangentSpaceTransform, IN.{1})", tangentSpaceName, objectSpaceName), false);
}
SurfaceDescription surf = PopulateSurfaceData(surfaceInput);
{3}
ENDCG
}
}";
}
}

278
MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Util/ShaderGenerator.cs


public static string GetUVName(this UVChannel channel)
{
return UV[(int)channel];
return UV[(int) channel];
}
}

get { return m_ShaderChunks.Count; }
}
public static string GeneratePreviewShader(AbstractMaterialNode node, out PreviewMode generatedShaderMode)
public static void GenerateSpaceTranslationPixelShader(
NeededCoordinateSpace neededSpaces,
ShaderGenerator pixelShader,
string objectSpaceName,
string viewSpaceName,
string worldSpaceName,
string tangentSpaceName,
bool isNormal = false)
generatedShaderMode = PreviewMode.Preview2D;
return string.Empty;
if ((neededSpaces & NeededCoordinateSpace.Object) > 0)
{
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = IN.{0};", objectSpaceName), false);
}
if ((neededSpaces & NeededCoordinateSpace.World) > 0)
{
if (isNormal)
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = UnityObjectToWorldNormal(IN.{1});", worldSpaceName, objectSpaceName), false);
else
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = UnityObjectToWorldDir(IN.{1});", worldSpaceName, objectSpaceName), false);
}
if ((neededSpaces & NeededCoordinateSpace.View) > 0)
{
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = UnityObjectToViewPos(IN.{1});", viewSpaceName, objectSpaceName), false);
}
if ((neededSpaces & NeededCoordinateSpace.Tangent) > 0)
{
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = mul(tangentSpaceTransform, IN.{1})", tangentSpaceName, objectSpaceName), false);
}
/*
if (!node.GetOutputSlots<MaterialSlot>().Any())
public static string GetPreviewSubShader(AbstractMaterialNode node, ShaderGraphRequirements shaderGraphRequirements)
generatedShaderMode = PreviewMode.Preview2D;
return string.Empty;
}
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, node);
// figure out what kind of preview we want!
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, node);
generatedShaderMode = PreviewMode.Preview2D;
var interpolators = new ShaderGenerator();
var vertexShader = new ShaderGenerator();
var pixelShader = new ShaderGenerator();
if (activeNodeList.OfType<AbstractMaterialNode>().Any(x => x.previewMode == PreviewMode.Preview3D))
generatedShaderMode = PreviewMode.Preview3D;
// bitangent needs normal for x product
if (shaderGraphRequirements.requiresNormal > 0 || shaderGraphRequirements.requiresBitangent > 0)
{
interpolators.AddShaderChunk(string.Format("float3 {0} : NORMAL;", ShaderGeneratorNames.ObjectSpaceNormal), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = v.normal;", ShaderGeneratorNames.ObjectSpaceNormal), false);
pixelShader.AddShaderChunk(string.Format("float3 {0} = normalize(IN.{0});", ShaderGeneratorNames.ObjectSpaceNormal), false);
}
string templateLocation = GetTemplatePath("2DPreview.template");
if (!File.Exists(templateLocation))
return null;
if (shaderGraphRequirements.requiresTangent > 0 || shaderGraphRequirements.requiresBitangent > 0)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TANGENT;", ShaderGeneratorNames.ObjectSpaceTangent), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = v.tangent;", ShaderGeneratorNames.ObjectSpaceTangent), false);
pixelShader.AddShaderChunk(string.Format("float4 {0} = IN.{0};", ShaderGeneratorNames.ObjectSpaceTangent), false);
pixelShader.AddShaderChunk(string.Format("float4 {0} = normalize(cross(normalize(IN.{1}), normalize(IN.{2}.xyz)) * IN.{2}.w);",
ShaderGeneratorNames.ObjectSpaceBiTangent,
ShaderGeneratorNames.ObjectSpaceTangent,
ShaderGeneratorNames.ObjectSpaceNormal), false);
}
string template = File.ReadAllText(templateLocation);
int interpolatorIndex = 0;
if (shaderGraphRequirements.requiresViewDir > 0)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TEXCOORD{1};", ShaderGeneratorNames.ObjectSpaceViewDirection, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = ObjSpaceViewDir(v.vertex);", ShaderGeneratorNames.ObjectSpaceViewDirection), false);
pixelShader.AddShaderChunk(string.Format("float4 {0} = normalize(IN.{0});", ShaderGeneratorNames.ObjectSpaceViewDirection), false);
interpolatorIndex++;
}
var shaderBodyVisitor = new ShaderGenerator();
var shaderFunctionVisitor = new ShaderGenerator();
var shaderPropertiesVisitor = new PropertyCollector();
if (shaderGraphRequirements.requiresPosition > 0)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TEXCOORD{1};", ShaderGeneratorNames.ObjectSpacePosition, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = v.vertex;", ShaderGeneratorNames.ObjectSpacePosition), false);
pixelShader.AddShaderChunk(string.Format("float4 {0} = IN.{0};", ShaderGeneratorNames.ObjectSpacePosition), false);
interpolatorIndex++;
}
var shaderName = "Hidden/PreviewShader/" + node.GetVariableNameForSlot(node.GetOutputSlots<MaterialSlot>().First().id);
if (shaderGraphRequirements.NeedsTangentSpace())
{
pixelShader.AddShaderChunk(string.Format("float3x3 tangentSpaceTransform = float3x3({0},{1},{2});",
ShaderGeneratorNames.ObjectSpaceTangent, ShaderGeneratorNames.ObjectSpaceBiTangent, ShaderGeneratorNames.ObjectSpaceNormal), false);
}
var owner = node.owner as AbstractMaterialGraph;
if (owner != null)
owner.CollectShaderProperties(shaderPropertiesVisitor, GenerationMode.Preview);
GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresNormal, pixelShader,
ShaderGeneratorNames.ObjectSpaceNormal, ShaderGeneratorNames.ViewSpaceNormal,
ShaderGeneratorNames.WorldSpaceNormal, ShaderGeneratorNames.TangentSpaceNormal);
var shaderInputVisitor = new ShaderGenerator();
var vertexShaderBlock = new ShaderGenerator();
GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresTangent, pixelShader,
ShaderGeneratorNames.ObjectSpaceTangent, ShaderGeneratorNames.ViewSpaceTangent,
ShaderGeneratorNames.WorldSpaceTangent, ShaderGeneratorNames.TangentSpaceTangent);
// always add color because why not.
shaderInputVisitor.AddShaderChunk("float4 color : COLOR;", true);
GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresBitangent, pixelShader,
ShaderGeneratorNames.ObjectSpaceBiTangent, ShaderGeneratorNames.ViewSpaceBiTangent,
ShaderGeneratorNames.WorldSpaceSpaceBiTangent, ShaderGeneratorNames.TangentSpaceBiTangent);
vertexShaderBlock.AddShaderChunk("float3 worldPos = mul(unity_ObjectToWorld, v.vertex).xyz;", true);
vertexShaderBlock.AddShaderChunk("float3 viewDir = UnityWorldSpaceViewDir(worldPos);", true);
vertexShaderBlock.AddShaderChunk("float4 screenPos = ComputeScreenPos(UnityObjectToClipPos(v.vertex));", true);
vertexShaderBlock.AddShaderChunk("float3 worldNormal = UnityObjectToWorldNormal(v.normal);", true);
GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresViewDir, pixelShader,
ShaderGeneratorNames.ObjectSpaceViewDirection, ShaderGeneratorNames.ViewSpaceViewDirection,
ShaderGeneratorNames.WorldSpaceViewDirection, ShaderGeneratorNames.TangentSpaceViewDirection);
bool requiresBitangent = activeNodeList.OfType<IMayRequireBitangent>().Any(x => x.RequiresBitangent());
bool requiresTangent = activeNodeList.OfType<IMayRequireTangent>().Any(x => x.RequiresTangent());
bool requiresViewDirTangentSpace = activeNodeList.OfType<IMayRequireViewDirectionTangentSpace>().Any(x => x.RequiresViewDirectionTangentSpace());
bool requiresViewDir = activeNodeList.OfType<IMayRequireViewDirection>().Any(x => x.RequiresViewDirection());
bool requiresWorldPos = activeNodeList.OfType<IMayRequireWorldPosition>().Any(x => x.RequiresWorldPosition());
bool requiresNormal = activeNodeList.OfType<IMayRequireNormal>().Any(x => x.RequiresNormal());
bool requiresScreenPosition = activeNodeList.OfType<IMayRequireScreenPosition>().Any(x => x.RequiresScreenPosition());
bool requiresVertexColor = activeNodeList.OfType<IMayRequireVertexColor>().Any(x => x.RequiresVertexColor());
GenerateSpaceTranslationPixelShader(shaderGraphRequirements.requiresPosition, pixelShader,
ShaderGeneratorNames.ObjectSpacePosition, ShaderGeneratorNames.ViewSpacePosition,
ShaderGeneratorNames.WorldSpacePosition, ShaderGeneratorNames.TangentSpacePosition);
// view directions calculated from world position
if (requiresWorldPos || requiresViewDir || requiresViewDirTangentSpace)
{
shaderInputVisitor.AddShaderChunk("float3 worldPos : TEXCOORD0;", true);
vertexShaderBlock.AddShaderChunk("o.worldPos = worldPos;", true);
shaderBodyVisitor.AddShaderChunk("float3 " + ShaderGeneratorNames.Position + " = IN.worldPos;", true);
}
/*
if (requiresBitangent || requiresNormal || requiresViewDirTangentSpace)
{
shaderInputVisitor.AddShaderChunk("float3 worldNormal : TEXCOORD1;", true);
vertexShaderBlock.AddShaderChunk("o.worldNormal = worldNormal;", true);
shaderBodyVisitor.AddShaderChunk("float3 " + ShaderGeneratorNames.Normal + " = normalize(IN.worldNormal);", true);
}*
if (shaderGraphRequirements.requiresVertexColor)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : COLOR;", ShaderGeneratorNames.VertexColor), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = color", ShaderGeneratorNames.VertexColor), false);
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = IN.{0};", ShaderGeneratorNames.VertexColor), false);
}
if (shaderGraphRequirements.requiresScreenPosition)
{
interpolators.AddShaderChunk(string.Format("float4 {0} : TEXCOORD{1};;", ShaderGeneratorNames.ScreenPosition, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.{0} = ComputeScreenPos(UnityObjectToClipPos(v.vertex)", ShaderGeneratorNames.ScreenPosition), false);
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = IN.{0};", ShaderGeneratorNames.ScreenPosition), false);
interpolatorIndex++;
}
for (int uvIndex = 0; uvIndex < ShaderGeneratorNames.UVCount; ++uvIndex)
{
var channel = (UVChannel)uvIndex;
if (activeNodeList.OfType<IMayRequireMeshUV>().Any(x => x.RequiresMeshUV(channel)))
for (int uvIndex = 0; uvIndex < ShaderGeneratorNames.UVCount; ++uvIndex)
shaderInputVisitor.AddShaderChunk(string.Format("half4 meshUV{0} : TEXCOORD{1};", uvIndex, (uvIndex + 5)), true);
vertexShaderBlock.AddShaderChunk(string.Format("o.meshUV{0} = v.texcoord{1};", uvIndex, uvIndex == 0 ? "" : uvIndex.ToString()), true);
shaderBodyVisitor.AddShaderChunk(string.Format("half4 {0} = IN.meshUV{1};", channel.GetUVName(), uvIndex), true);
var channel = (UVChannel) uvIndex;
if (activeNodeList.OfType<IMayRequireMeshUV>().Any(x => x.RequiresMeshUV(channel)))
{
interpolators.AddShaderChunk(string.Format("half4 meshUV{0} : TEXCOORD{1};", uvIndex, interpolatorIndex), false);
vertexShader.AddShaderChunk(string.Format("o.meshUV{0} = v.texcoord{1};", uvIndex, uvIndex == 0 ? "" : uvIndex.ToString()), false);
pixelShader.AddShaderChunk(string.Format("surfaceInput.{0} = IN.meshUV{1};", channel.GetUVName(), uvIndex), false);
interpolatorIndex++;
}
}
if (requiresViewDir || requiresViewDirTangentSpace)
{
shaderBodyVisitor.AddShaderChunk(
"float3 "
+ ShaderGeneratorNames.WorldSpaceViewDirection
+ " = normalize(UnityWorldSpaceViewDir("
+ ShaderGeneratorNames.Position
+ "));", true);
}
var outputs = new ShaderGenerator();
var outputSlot = node.GetOutputSlots<MaterialSlot>().FirstOrDefault();
if (outputSlot != null)
outputs.AddShaderChunk(string.Format("return surf.{0};", node.GetVariableNameForSlot(outputSlot.id)), true);
else
outputs.AddShaderChunk("return 0;", true);
if (requiresScreenPosition)
{
shaderInputVisitor.AddShaderChunk("float4 screenPos : TEXCOORD3;", true);
vertexShaderBlock.AddShaderChunk("o.screenPos = screenPos;", true);
shaderBodyVisitor.AddShaderChunk("half4 " + ShaderGeneratorNames.ScreenPosition + " = IN.screenPos;", true);
var res = subShaderTemplate.Replace("{0}", interpolators.GetShaderString(0));
res = res.Replace("{1}", vertexShader.GetShaderString(0));
res = res.Replace("{2}", pixelShader.GetShaderString(0));
res = res.Replace("{3}", outputs.GetShaderString(0));
return res;
/* if (requiresBitangent || requiresViewDirTangentSpace || requiresTangent)
{
shaderInputVisitor.AddShaderChunk("float4 worldTangent : TEXCOORD4;", true);
vertexShaderBlock.AddShaderChunk("o.worldTangent = float4(UnityObjectToWorldDir(v.tangent.xyz), v.tangent.w);", true);
shaderBodyVisitor.AddShaderChunk("float3 " + ShaderGeneratorNames.Tangent + " = normalize(IN.worldTangent.xyz);", true);
}*
private const string subShaderTemplate = @"
SubShader
{
Tags { ""RenderType""=""Opaque"" }
LOD 100
if (requiresBitangent || requiresViewDirTangentSpace)
{
shaderBodyVisitor.AddShaderChunk(string.Format("float3 {0} = cross({1}, {2}) * IN.worldTangent.w;", ShaderGeneratorNames.BiTangent, ShaderGeneratorNames.Normal, ShaderGeneratorNames.Tangent), true);
}
Pass
{
CGPROGRAM
#pragma vertex vert
#pragma fragment frag
#include ""UnityCG.cginc""
if (requiresVertexColor)
struct GraphVertexOutput
vertexShaderBlock.AddShaderChunk("o.color = v.color;", true);
shaderBodyVisitor.AddShaderChunk("float4 " + ShaderGeneratorNames.VertexColor + " = IN.color;", true);
}
float4 position : POSITION;
{0}
};
var generationMode = GenerationMode.Preview;
foreach (var activeNode in activeNodeList.OfType<AbstractMaterialNode>())
GraphVertexOutput vert (GraphVertexInput v)
if (activeNode is IGeneratesFunction)
(activeNode as IGeneratesFunction).GenerateNodeFunction(shaderFunctionVisitor, generationMode);
if (activeNode is IGeneratesBodyCode)
(activeNode as IGeneratesBodyCode).GenerateNodeCode(shaderBodyVisitor, generationMode);
v = PopulateVertexData(v);
activeNode.CollectShaderProperties(shaderPropertiesVisitor, generationMode);
GraphVertexOutput o;
o.position = UnityObjectToClipPos(v.vertex);
{1}
return o;
shaderBodyVisitor.AddShaderChunk("return " + AdaptNodeOutputForPreview(node, node.GetOutputSlots<MaterialSlot>().First().id) + ";", true);
ListPool<INode>.Release(activeNodeList);
template = template.Replace("${ShaderName}", shaderName);
template = template.Replace("${ShaderPropertiesHeader}", shaderPropertiesVisitor.GetPropertiesBlock(2));
template = template.Replace("${ShaderPropertyUsages}", shaderPropertiesVisitor.GetPropertiesDeclaration(3));
template = template.Replace("${ShaderInputs}", shaderInputVisitor.GetShaderString(4));
template = template.Replace("${ShaderFunctions}", shaderFunctionVisitor.GetShaderString(3));
template = template.Replace("${VertexShaderBody}", vertexShaderBlock.GetShaderString(4));
template = template.Replace("${PixelShaderBody}", shaderBodyVisitor.GetShaderString(4));
string vertexShaderBody = vertexShaderBlock.GetShaderString(4);
if (vertexShaderBody.Length > 0)
{
template = template.Replace("${VertexShaderDecl}", "vertex:vert");
template = template.Replace("${VertexShaderBody}", vertexShaderBody);
}
else
fixed4 frag (GraphVertexOutput IN) : SV_Target
template = template.Replace("${VertexShaderDecl}", "");
template = template.Replace("${VertexShaderBody}", vertexShaderBody);
SurfaceInputs surfaceInput;
{2}
SurfaceDescription surf = PopulateSurfaceData(surfaceInput);
{3}
return Regex.Replace(template, @"\r\n|\n\r|\n|\r", Environment.NewLine);
}*/
ENDCG
}
}";
}
}

22
MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/ShaderGraphRequirements.cs


namespace UnityEngine.MaterialGraph
{
public struct ShaderGraphRequirements
{
public NeededCoordinateSpace requiresNormal;
public NeededCoordinateSpace requiresBitangent;
public NeededCoordinateSpace requiresTangent;
public NeededCoordinateSpace requiresViewDir;
public NeededCoordinateSpace requiresPosition;
public bool requiresScreenPosition;
public bool requiresVertexColor;
public bool NeedsTangentSpace()
{
var compoundSpaces = requiresBitangent | requiresNormal | requiresPosition
| requiresTangent | requiresViewDir | requiresPosition
| requiresNormal;
return (compoundSpaces & NeededCoordinateSpace.Tangent) > 0;
}
}
}

3
MaterialGraphProject/Assets/UnityShaderEditor/Runtime/Graphs/ShaderGraphRequirements.cs.meta


fileFormatVersion: 2
guid: b80c0c5cd7f940d7bc0f37b22c454d40
timeCreated: 1505698038

9
MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/Inspector/Presenters.meta


fileFormatVersion: 2
guid: 2d08dfb360644031a5e64558d4a93263
folderAsset: yes
timeCreated: 1503663071
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

9
MaterialGraphProject/Assets/UnityShaderEditor/Editor/Drawing/Inspector/Views.meta


fileFormatVersion: 2
guid: 0969ff891b874694aa732e1240ee159b
folderAsset: yes
timeCreated: 1503663067
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:
正在加载...
取消
保存