浏览代码

Merge branch 'master' into StackLit2

/main
Stephane Laroche 7 年前
当前提交
7933fd8d
共有 79 个文件被更改,包括 2003 次插入834 次删除
  1. 61
      TestProjects/GraphicsTests/Packages/manifest.json
  2. 49
      TestProjects/LWGraphicsTest/Packages/manifest.json
  3. 57
      TestProjects/ShaderGraph/Packages/manifest.json
  4. 13
      com.unity.render-pipelines.core/CoreRP/Debugging/MousePositionDebug.cs
  5. 205
      com.unity.render-pipelines.core/CoreRP/Editor/CoreEditorUtils.cs
  6. 13
      com.unity.render-pipelines.core/CoreRP/Utilities/CoreUtils.cs
  7. 1
      com.unity.render-pipelines.high-definition/CHANGELOG.md
  8. 103
      com.unity.render-pipelines.high-definition/HDRP/Editor/BuildProcessors/HDRPreprocessShaders.cs
  9. 14
      com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/HDEditorUtils.cs
  10. 16
      com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/HDRenderPipelineMenuItems.cs
  11. 22
      com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/Settings/RenderPipelineSettingsUI.cs
  12. 3
      com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/Settings/SerializedRenderPipelineSettings.cs
  13. 92
      com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDPBRPass.template
  14. 342
      com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDPBRSubShader.cs
  15. 226
      com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDSubShaderUtilities.cs
  16. 79
      com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDUnlitPassForward.template
  17. 262
      com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDUnlitSubShader.cs
  18. 13
      com.unity.render-pipelines.high-definition/HDRP/Editor/Upgraders/HDRPVersion.cs
  19. 14
      com.unity.render-pipelines.high-definition/HDRP/Editor/Upgraders/UpgradeMenuItem.cs
  20. 2
      com.unity.render-pipelines.high-definition/HDRP/Material/LayeredLit/LayeredLit.shader
  21. 2
      com.unity.render-pipelines.high-definition/HDRP/Material/LayeredLit/LayeredLitTessellation.shader
  22. 2
      com.unity.render-pipelines.high-definition/HDRP/Material/Lit/Lit.shader
  23. 2
      com.unity.render-pipelines.high-definition/HDRP/Material/Lit/LitTessellation.shader
  24. 23
      com.unity.render-pipelines.high-definition/HDRP/Material/StackLit/StackLit.shader
  25. 4
      com.unity.render-pipelines.high-definition/HDRP/Material/StackLit/StackLitProperties.hlsl
  26. 2
      com.unity.render-pipelines.high-definition/HDRP/Material/Unlit/Unlit.shader
  27. 1
      com.unity.render-pipelines.high-definition/HDRP/RenderPipeline/Settings/RenderPipelineSettings.cs
  28. 12
      com.unity.render-pipelines.high-definition/HDRP/ShaderPass/ShaderPassVelocity.hlsl
  29. 4
      com.unity.render-pipelines.high-definition/HDRP/ShaderPass/VertMesh.hlsl
  30. 58
      com.unity.render-pipelines.lightweight/LWRP/Editor/LightweightLightEditor.cs
  31. 16
      com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/LightWeightPBRSubShader.cs
  32. 16
      com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/LightWeightUnlitSubShader.cs
  33. 2
      com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/lightweightPBRForwardPass.template
  34. 2
      com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/lightweightUnlitPass.template
  35. 38
      com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderPreprocessor.cs
  36. 22
      com.unity.render-pipelines.lightweight/LWRP/LightweightForwardRenderer.cs
  37. 4
      com.unity.render-pipelines.lightweight/LWRP/LightweightPipeline.cs
  38. 30
      com.unity.render-pipelines.lightweight/LWRP/LightweightPipelineCore.cs
  39. 3
      com.unity.render-pipelines.lightweight/LWRP/Passes/DepthOnlyPass.cs
  40. 3
      com.unity.render-pipelines.lightweight/LWRP/Passes/DirectionalShadowsPass.cs
  41. 49
      com.unity.render-pipelines.lightweight/LWRP/Passes/ForwardLitPass.cs
  42. 3
      com.unity.render-pipelines.lightweight/LWRP/Passes/LocalShadowsPass.cs
  43. 11
      com.unity.render-pipelines.lightweight/LWRP/Passes/ScreenSpaceShadowResolvePass.cs
  44. 4
      com.unity.render-pipelines.lightweight/LWRP/Passes/ScriptableRenderPass.cs
  45. 30
      com.unity.shadergraph/CHANGELOG.md
  46. 55
      com.unity.shadergraph/Editor/Data/Graphs/PreviewProperty.cs
  47. 8
      com.unity.shadergraph/Editor/Data/Graphs/ShaderGraphRequirements.cs
  48. 14
      com.unity.shadergraph/Editor/Data/Nodes/Procedural/CheckerboardNode.cs
  49. 69
      com.unity.shadergraph/Editor/Data/Util/GraphUtil.cs
  50. 16
      com.unity.shadergraph/Editor/Data/Util/ShaderGenerator.cs
  51. 1
      com.unity.shadergraph/Editor/Data/Util/ShaderGeneratorNames.cs
  52. 1
      com.unity.shadergraph/Editor/Drawing/Views/MaterialNodeView.cs
  53. 52
      com.unity.shadergraph/Editor/Importers/ShaderGraphImporter.cs
  54. 8
      com.unity.render-pipelines.core/CoreRP/Editor/Shadow.meta
  55. 77
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/BaseShaderPreprocessor.cs
  56. 11
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/BaseShaderPreprocessor.cs.meta
  57. 69
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Lit/LitShaderPreprocessor.cs
  58. 11
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Lit/LitShaderPreprocessor.cs.meta
  59. 23
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/StackLit/StackLitShaderPreprocessor.cs
  60. 11
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/StackLit/StackLitShaderPreprocessor.cs.meta
  61. 23
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Unlit/UnlitShaderPreprocessor.cs
  62. 11
      com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Unlit/UnlitShaderPreprocessor.cs.meta
  63. 3
      com.unity.shadergraph/.data/face_sign.png
  64. 3
      com.unity.shadergraph/.data/hd_render_pipeline.png
  65. 3
      com.unity.shadergraph/.data/texture_2d_lod_node.PNG
  66. 3
      com.unity.shadergraph/.data/texture_nodes.png
  67. 3
      com.unity.shadergraph/.data/vertex_position.png
  68. 18
      com.unity.shadergraph/Editor/Data/Interfaces/IMayRequireFaceSign.cs
  69. 3
      com.unity.shadergraph/Editor/Data/Interfaces/IMayRequireFaceSign.cs.meta
  70. 120
      com.unity.shadergraph/Editor/Data/Nodes/Input/Texture/SampleTexture2DLODNode.cs
  71. 11
      com.unity.shadergraph/Editor/Data/Nodes/Input/Texture/SampleTexture2DLODNode.cs.meta
  72. 41
      com.unity.shadergraph/Editor/Data/Nodes/Utility/Logic/IsFrontFaceNode.cs
  73. 11
      com.unity.shadergraph/Editor/Data/Nodes/Utility/Logic/IsFrontFaceNode.cs.meta
  74. 214
      com.unity.render-pipelines.core/CoreRP/Editor/Shadow/ShadowCascadeSplitGUI.cs
  75. 11
      com.unity.render-pipelines.core/CoreRP/Editor/Shadow/ShadowCascadeSplitGUI.cs.meta
  76. 1
      TestProjects/GraphicsTests/ProjectSettings/ProjectVersion.txt
  77. 1
      TestProjects/LWGraphicsTest/ProjectSettings/ProjectVersion.txt
  78. 1
      TestProjects/ShaderGraph/ProjectSettings/ProjectVersion.txt

61
TestProjects/GraphicsTests/Packages/manifest.json


{
"dependencies": {
"com.unity.postprocessing": "file:../../../com.unity.postprocessing",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
"com.unity.render-pipelines.high-definition": "file:../../../com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.lightweight": "file:../../../com.unity.render-pipelines.lightweight"
},
"testables": [
"com.unity.render-pipelines.core",
"com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.lightweight"
]
"dependencies": {
"com.unity.ads": "2.0.8",
"com.unity.analytics": "2.0.16",
"com.unity.collab-proxy": "1.2.4-preview",
"com.unity.package-manager-ui": "2.0.0-preview.2",
"com.unity.postprocessing": "file:../../../com.unity.postprocessing",
"com.unity.purchasing": "2.0.1",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.render-pipelines.high-definition": "file:../../../com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.lightweight": "file:../../../com.unity.render-pipelines.lightweight",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
"com.unity.standardevents": "1.0.13",
"com.unity.textmeshpro": "1.2.1",
"com.unity.modules.ai": "1.0.0",
"com.unity.modules.animation": "1.0.0",
"com.unity.modules.assetbundle": "1.0.0",
"com.unity.modules.audio": "1.0.0",
"com.unity.modules.cloth": "1.0.0",
"com.unity.modules.director": "1.0.0",
"com.unity.modules.imageconversion": "1.0.0",
"com.unity.modules.imgui": "1.0.0",
"com.unity.modules.jsonserialize": "1.0.0",
"com.unity.modules.particlesystem": "1.0.0",
"com.unity.modules.physics": "1.0.0",
"com.unity.modules.physics2d": "1.0.0",
"com.unity.modules.screencapture": "1.0.0",
"com.unity.modules.terrain": "1.0.0",
"com.unity.modules.terrainphysics": "1.0.0",
"com.unity.modules.tilemap": "1.0.0",
"com.unity.modules.ui": "1.0.0",
"com.unity.modules.uielements": "1.0.0",
"com.unity.modules.umbra": "1.0.0",
"com.unity.modules.unityanalytics": "1.0.0",
"com.unity.modules.unitywebrequest": "1.0.0",
"com.unity.modules.unitywebrequestassetbundle": "1.0.0",
"com.unity.modules.unitywebrequestaudio": "1.0.0",
"com.unity.modules.unitywebrequesttexture": "1.0.0",
"com.unity.modules.unitywebrequestwww": "1.0.0",
"com.unity.modules.vehicles": "1.0.0",
"com.unity.modules.video": "1.0.0",
"com.unity.modules.vr": "1.0.0",
"com.unity.modules.wind": "1.0.0",
"com.unity.modules.xr": "1.0.0"
},
"testables": [
"com.unity.render-pipelines.core",
"com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.lightweight"
]
}

49
TestProjects/LWGraphicsTest/Packages/manifest.json


{
"dependencies": {
"com.unity.postprocessing": "file:../../../com.unity.postprocessing",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
"com.unity.render-pipelines.lightweight": "file:../../../com.unity.render-pipelines.lightweight"
}
"dependencies": {
"com.unity.ads": "2.0.8",
"com.unity.analytics": "2.0.16",
"com.unity.collab-proxy": "1.2.4-preview",
"com.unity.package-manager-ui": "2.0.0-preview.2",
"com.unity.postprocessing": "file:../../../com.unity.postprocessing",
"com.unity.purchasing": "2.0.1",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.render-pipelines.lightweight": "file:../../../com.unity.render-pipelines.lightweight",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
"com.unity.standardevents": "1.0.13",
"com.unity.textmeshpro": "1.2.1",
"com.unity.modules.ai": "1.0.0",
"com.unity.modules.animation": "1.0.0",
"com.unity.modules.assetbundle": "1.0.0",
"com.unity.modules.audio": "1.0.0",
"com.unity.modules.cloth": "1.0.0",
"com.unity.modules.director": "1.0.0",
"com.unity.modules.imageconversion": "1.0.0",
"com.unity.modules.imgui": "1.0.0",
"com.unity.modules.jsonserialize": "1.0.0",
"com.unity.modules.particlesystem": "1.0.0",
"com.unity.modules.physics": "1.0.0",
"com.unity.modules.physics2d": "1.0.0",
"com.unity.modules.screencapture": "1.0.0",
"com.unity.modules.terrain": "1.0.0",
"com.unity.modules.terrainphysics": "1.0.0",
"com.unity.modules.tilemap": "1.0.0",
"com.unity.modules.ui": "1.0.0",
"com.unity.modules.uielements": "1.0.0",
"com.unity.modules.umbra": "1.0.0",
"com.unity.modules.unityanalytics": "1.0.0",
"com.unity.modules.unitywebrequest": "1.0.0",
"com.unity.modules.unitywebrequestassetbundle": "1.0.0",
"com.unity.modules.unitywebrequestaudio": "1.0.0",
"com.unity.modules.unitywebrequesttexture": "1.0.0",
"com.unity.modules.unitywebrequestwww": "1.0.0",
"com.unity.modules.vehicles": "1.0.0",
"com.unity.modules.video": "1.0.0",
"com.unity.modules.vr": "1.0.0",
"com.unity.modules.wind": "1.0.0",
"com.unity.modules.xr": "1.0.0"
}
}

57
TestProjects/ShaderGraph/Packages/manifest.json


{
"dependencies": {
"com.unity.postprocessing": "file:../../../com.unity.postprocessing",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
"com.unity.render-pipelines.high-definition": "file:../../../com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.lightweight": "file:../../../com.unity.render-pipelines.lightweight"
},
"testables": [
"com.unity.render-pipelines.shadergraph"
]
"dependencies": {
"com.unity.ads": "2.0.8",
"com.unity.analytics": "2.0.16",
"com.unity.collab-proxy": "1.2.4-preview",
"com.unity.package-manager-ui": "2.0.0-preview.2",
"com.unity.postprocessing": "file:../../../com.unity.postprocessing",
"com.unity.purchasing": "2.0.1",
"com.unity.render-pipelines.core": "file:../../../com.unity.render-pipelines.core",
"com.unity.render-pipelines.high-definition": "file:../../../com.unity.render-pipelines.high-definition",
"com.unity.render-pipelines.lightweight": "file:../../../com.unity.render-pipelines.lightweight",
"com.unity.shadergraph": "file:../../../com.unity.shadergraph",
"com.unity.standardevents": "1.0.13",
"com.unity.textmeshpro": "1.2.1",
"com.unity.modules.ai": "1.0.0",
"com.unity.modules.animation": "1.0.0",
"com.unity.modules.assetbundle": "1.0.0",
"com.unity.modules.audio": "1.0.0",
"com.unity.modules.cloth": "1.0.0",
"com.unity.modules.director": "1.0.0",
"com.unity.modules.imageconversion": "1.0.0",
"com.unity.modules.imgui": "1.0.0",
"com.unity.modules.jsonserialize": "1.0.0",
"com.unity.modules.particlesystem": "1.0.0",
"com.unity.modules.physics": "1.0.0",
"com.unity.modules.physics2d": "1.0.0",
"com.unity.modules.screencapture": "1.0.0",
"com.unity.modules.terrain": "1.0.0",
"com.unity.modules.terrainphysics": "1.0.0",
"com.unity.modules.tilemap": "1.0.0",
"com.unity.modules.ui": "1.0.0",
"com.unity.modules.uielements": "1.0.0",
"com.unity.modules.umbra": "1.0.0",
"com.unity.modules.unityanalytics": "1.0.0",
"com.unity.modules.unitywebrequest": "1.0.0",
"com.unity.modules.unitywebrequestassetbundle": "1.0.0",
"com.unity.modules.unitywebrequestaudio": "1.0.0",
"com.unity.modules.unitywebrequesttexture": "1.0.0",
"com.unity.modules.unitywebrequestwww": "1.0.0",
"com.unity.modules.vehicles": "1.0.0",
"com.unity.modules.video": "1.0.0",
"com.unity.modules.vr": "1.0.0",
"com.unity.modules.wind": "1.0.0",
"com.unity.modules.xr": "1.0.0"
},
"testables": [
"com.unity.render-pipelines.shadergraph"
]
}

13
com.unity.render-pipelines.core/CoreRP/Debugging/MousePositionDebug.cs


public static void Cleanup()
{
if (s_Instance != null)
DestroyImmediate(s_Instance.gameObject);
{
// Either we call DestroyImmediate or Destroy we get an error :(
// GameViewEventCatcher is only use for SSR debugging currently so comment this code and uncomment it if you want to debug SSR
//DestroyImmediate(s_Instance.gameObject);
//Destroy(s_Instance.gameObject);
}
}
public static void Build()

#if UNITY_EDITOR
UnityEditor.SceneView.onSceneGUIDelegate -= OnSceneGUI;
UnityEditor.SceneView.onSceneGUIDelegate += OnSceneGUI;
GameViewEventCatcher.Build();
// Disabled as it cause error: GameViewEventCatcher is only use for SSR debugging currently so comment this code and uncomment it if you want to debug SSR
//GameViewEventCatcher.Build();
#endif
}

UnityEditor.SceneView.onSceneGUIDelegate -= OnSceneGUI;
GameViewEventCatcher.Cleanup();
// Disabled as it cause error: GameViewEventCatcher is only use for SSR debugging currently so comment this code and uncomment it if you want to debug SSR
//GameViewEventCatcher.Cleanup();
#endif
}

205
com.unity.render-pipelines.core/CoreRP/Editor/CoreEditorUtils.cs


namespace UnityEditor.Experimental.Rendering
{
using UnityObject = UnityEngine.Object;
public static class CoreEditorUtils
{
// GUIContent cache utilities

mode = EditorGUILayout.Popup(label, mode, options);
if (EditorGUI.EndChangeCheck())
{
Undo.RecordObject(property.objectReferenceValue, property.name);
}
}
public static void DrawCascadeSplitGUI<T>(ref SerializedProperty shadowCascadeSplit)

string[] versionText = readText[0].Split(' ');
return versionText[1];
}
}
static class ShadowCascadeSplitGUI
{
private const int kSliderbarTopMargin = 2;
private const int kSliderbarHeight = 24;
private const int kSliderbarBottomMargin = 2;
private const int kPartitionHandleWidth = 2;
private const int kPartitionHandleExtraHitAreaWidth = 2;
private static readonly Color[] kCascadeColors =
{
new Color(0.5f, 0.5f, 0.6f, 1.0f),
new Color(0.5f, 0.6f, 0.5f, 1.0f),
new Color(0.6f, 0.6f, 0.5f, 1.0f),
new Color(0.6f, 0.5f, 0.5f, 1.0f),
};
// using a LODGroup skin
private static readonly GUIStyle s_CascadeSliderBG = "LODSliderRange";
private static readonly GUIStyle s_TextCenteredStyle = new GUIStyle(EditorStyles.whiteMiniLabel)
{
alignment = TextAnchor.MiddleCenter
};
// Internal struct to bundle drag information
private class DragCache
{
public int m_ActivePartition; // the cascade partition that we are currently dragging/resizing
public float m_NormalizedPartitionSize; // the normalized size of the partition (0.0f < size < 1.0f)
public Vector2 m_LastCachedMousePosition; // mouse position the last time we registered a drag or mouse down.
public DragCache(int activePartition, float normalizedPartitionSize, Vector2 currentMousePos)
{
m_ActivePartition = activePartition;
m_NormalizedPartitionSize = normalizedPartitionSize;
m_LastCachedMousePosition = currentMousePos;
}
};
private static DragCache s_DragCache;
private static readonly int s_CascadeSliderId = "s_CascadeSliderId".GetHashCode();
private static SceneView s_RestoreSceneView;
private static SceneView.CameraMode s_OldSceneDrawMode;
private static bool s_OldSceneLightingMode;
/**
* Static function to handle the GUI and User input related to the cascade slider.
*
* @param normalizedCascadePartition The array of partition sizes in the range 0.0f - 1.0f; expects ONE entry if cascades = 2, and THREE if cascades=4
* The last entry will be automatically determined by summing up the array, and doing 1.0f - sum
*/
public static void HandleCascadeSliderGUI(ref float[] normalizedCascadePartitions)
static public void CheckOutFile(bool VCSEnabled, UnityObject mat)
EditorGUILayout.LabelField("Cascade splits");
// get the inspector width since we need it while drawing the partition rects.
// Only way currently is to reserve the block in the layout using GetRect(), and then immediately drawing the empty box
// to match the call to GetRect.
// From this point on, we move to non-layout based code.
var sliderRect = GUILayoutUtility.GetRect(GUIContent.none
, s_CascadeSliderBG
, GUILayout.Height(kSliderbarTopMargin + kSliderbarHeight + kSliderbarBottomMargin)
, GUILayout.ExpandWidth(true));
GUI.Box(sliderRect, GUIContent.none);
float currentX = sliderRect.x;
float cascadeBoxStartY = sliderRect.y + kSliderbarTopMargin;
float cascadeSliderWidth = sliderRect.width - (normalizedCascadePartitions.Length * kPartitionHandleWidth);
Color origTextColor = GUI.color;
Color origBackgroundColor = GUI.backgroundColor;
int colorIndex = -1;
// setup the array locally with the last partition
float[] adjustedCascadePartitions = new float[normalizedCascadePartitions.Length + 1];
System.Array.Copy(normalizedCascadePartitions, adjustedCascadePartitions, normalizedCascadePartitions.Length);
adjustedCascadePartitions[adjustedCascadePartitions.Length - 1] = 1.0f - normalizedCascadePartitions.Sum();
// check for user input on any of the partition handles
// this mechanism gets the current event in the queue... make sure that the mouse is over our control before consuming the event
int sliderControlId = GUIUtility.GetControlID(s_CascadeSliderId, FocusType.Passive);
Event currentEvent = Event.current;
int hotPartitionHandleIndex = -1; // the index of any partition handle that we are hovering over or dragging
// draw each cascade partition
for (int i = 0; i < adjustedCascadePartitions.Length; ++i)
if (VCSEnabled)
float currentPartition = adjustedCascadePartitions[i];
colorIndex = (colorIndex + 1) % kCascadeColors.Length;
GUI.backgroundColor = kCascadeColors[colorIndex];
float boxLength = (cascadeSliderWidth * currentPartition);
UnityEditor.VersionControl.Task task = UnityEditor.VersionControl.Provider.Checkout(mat, UnityEditor.VersionControl.CheckoutMode.Both);
// main cascade box
Rect partitionRect = new Rect(currentX, cascadeBoxStartY, boxLength, kSliderbarHeight);
GUI.Box(partitionRect, GUIContent.none, s_CascadeSliderBG);
currentX += boxLength;
// cascade box percentage text
GUI.color = Color.white;
Rect textRect = partitionRect;
var cascadeText = string.Format("{0}\n{1:F1}%", i, currentPartition * 100.0f);
GUI.Label(textRect, cascadeText, s_TextCenteredStyle);
// no need to draw the partition handle for last box
if (i == adjustedCascadePartitions.Length - 1)
break;
// partition handle
GUI.backgroundColor = Color.black;
Rect handleRect = partitionRect;
handleRect.x = currentX;
handleRect.width = kPartitionHandleWidth;
GUI.Box(handleRect, GUIContent.none, s_CascadeSliderBG);
// we want a thin handle visually (since wide black bar looks bad), but a slightly larger
// hit area for easier manipulation
Rect handleHitRect = handleRect;
handleHitRect.xMin -= kPartitionHandleExtraHitAreaWidth;
handleHitRect.xMax += kPartitionHandleExtraHitAreaWidth;
if (handleHitRect.Contains(currentEvent.mousePosition))
hotPartitionHandleIndex = i;
// add regions to slider where the cursor changes to Resize-Horizontal
if (s_DragCache == null)
if (!task.success)
EditorGUIUtility.AddCursorRect(handleHitRect, MouseCursor.ResizeHorizontal, sliderControlId);
Debug.Log(task.text + " " + task.resultCode);
currentX += kPartitionHandleWidth;
}
GUI.color = origTextColor;
GUI.backgroundColor = origBackgroundColor;
EventType eventType = currentEvent.GetTypeForControl(sliderControlId);
switch (eventType)
{
case EventType.MouseDown:
if (hotPartitionHandleIndex >= 0)
{
s_DragCache = new DragCache(hotPartitionHandleIndex, normalizedCascadePartitions[hotPartitionHandleIndex], currentEvent.mousePosition);
if (GUIUtility.hotControl == 0)
GUIUtility.hotControl = sliderControlId;
currentEvent.Use();
// Switch active scene view into shadow cascades visualization mode, once we start
// tweaking cascade splits.
if (s_RestoreSceneView == null)
{
s_RestoreSceneView = SceneView.lastActiveSceneView;
if (s_RestoreSceneView != null)
{
s_OldSceneDrawMode = s_RestoreSceneView.cameraMode;
s_OldSceneLightingMode = s_RestoreSceneView.m_SceneLighting;
s_RestoreSceneView.cameraMode = SceneView.GetBuiltinCameraMode(DrawCameraMode.ShadowCascades);
}
}
}
break;
case EventType.MouseUp:
// mouseUp event anywhere should release the hotcontrol (if it belongs to us), drags (if any)
if (GUIUtility.hotControl == sliderControlId)
{
GUIUtility.hotControl = 0;
currentEvent.Use();
}
s_DragCache = null;
// Restore previous scene view drawing mode once we stop tweaking cascade splits.
if (s_RestoreSceneView != null)
{
s_RestoreSceneView.cameraMode = s_OldSceneDrawMode;
s_RestoreSceneView.m_SceneLighting = s_OldSceneLightingMode;
s_RestoreSceneView = null;
}
break;
case EventType.MouseDrag:
if (GUIUtility.hotControl != sliderControlId)
break;
// convert the mouse movement to normalized cascade width. Make sure that we are safe to apply the delta before using it.
float delta = (currentEvent.mousePosition - s_DragCache.m_LastCachedMousePosition).x / cascadeSliderWidth;
bool isLeftPartitionHappy = ((adjustedCascadePartitions[s_DragCache.m_ActivePartition] + delta) > 0.0f);
bool isRightPartitionHappy = ((adjustedCascadePartitions[s_DragCache.m_ActivePartition + 1] - delta) > 0.0f);
if (isLeftPartitionHappy && isRightPartitionHappy)
{
s_DragCache.m_NormalizedPartitionSize += delta;
normalizedCascadePartitions[s_DragCache.m_ActivePartition] = s_DragCache.m_NormalizedPartitionSize;
if (s_DragCache.m_ActivePartition < normalizedCascadePartitions.Length - 1)
normalizedCascadePartitions[s_DragCache.m_ActivePartition + 1] -= delta;
GUI.changed = true;
}
s_DragCache.m_LastCachedMousePosition = currentEvent.mousePosition;
currentEvent.Use();
break;
}
}
}

13
com.unity.render-pipelines.core/CoreRP/Utilities/CoreUtils.cs


return fogEnable;
}
static public void CheckOutFile(bool VSCEnabled, UnityObject mat)
{
if (VSCEnabled)
{
UnityEditor.VersionControl.Task task = UnityEditor.VersionControl.Provider.Checkout(mat, UnityEditor.VersionControl.CheckoutMode.Both);
if (!task.success)
{
Debug.Log(task.text + " " + task.resultCode);
}
}
}
}
}

1
com.unity.render-pipelines.high-definition/CHANGELOG.md


- Add a DefaultHDMirrorMaterial material for PlanarReflection
- Added a script to be able to upgrade material to newer version of HDRP
- Removed useless duplication of ForwardError passes.
- Add option to not compile any DEBUG_DISPLAY shader in the player (Faster build) call Support Runtime Debug display
### Changed, Removals and deprecations
- Removed GlobalLightLoopSettings.maxPlanarReflectionProbes and instead use value of GlobalLightLoopSettings.planarReflectionProbeCacheSize

103
com.unity.render-pipelines.high-definition/HDRP/Editor/BuildProcessors/HDRPreprocessShaders.cs


{
class HDRPreprocessShaders : IPreprocessShaders
{
// returns true if the variant should be stripped.
delegate bool VariantStrippingFunc(Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData);
ShaderKeyword m_ShadowMask;
ShaderKeyword m_Transparent;
ShaderKeyword m_DebugDisplay;
ShaderKeyword m_TileLighting;
ShaderKeyword m_ClusterLighting;
//ShaderKeyword m_FeatureSSS;
public HDRPreprocessShaders()
{
// TODO: Grab correct configuration/quality asset.

m_StripperFuncs = new Dictionary<string, VariantStrippingFunc>();
m_StripperFuncs.Add("HDRenderPipeline/Lit", LitShaderStripper);
m_StripperFuncs.Add("HDRenderPipeline/LitTessellation", LitShaderStripper);
m_StripperFuncs.Add("HDRenderPipeline/LayeredLit", LitShaderStripper);
m_StripperFuncs.Add("HDRenderPipeline/LayeredLitTessellation", LitShaderStripper);
m_StripperFuncs.Add("HDRenderPipeline/Unlit", UnlitShaderStripper);
m_Transparent = new ShaderKeyword("_SURFACE_TYPE_TRANSPARENT");
m_DebugDisplay = new ShaderKeyword("DEBUG_DISPLAY");
m_TileLighting = new ShaderKeyword("USE_FPTL_LIGHTLIST");
m_ClusterLighting = new ShaderKeyword("USE_CLUSTERED_LIGHTLIST");
//m_FeatureSSS = new ShaderKeyword("_MATERIAL_FEATURE_SUBSURFACE_SCATTERING");
}
bool UnlitShaderStripper(Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData)
{
bool isSceneSelectionPass = snippet.passName == "SceneSelectionPass";
if (isSceneSelectionPass)
return true;
return false;
}
bool LitShaderStripper(Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData)
{
bool isSceneSelectionPass = snippet.passName == "SceneSelectionPass";
if (isSceneSelectionPass)
return true;
List<BaseShaderPreprocessor> materialList = HDEditorUtils.GetBaseShaderPreprocessorList();
bool isGBufferPass = snippet.passName == "GBuffer";
bool isForwardPass = snippet.passName == "Forward";
bool isTransparentForwardPass = snippet.passName == "TransparentDepthPostpass" || snippet.passName == "TransparentBackface" || snippet.passName == "TransparentDepthPrepass";
bool isMotionPass = snippet.passName == "Motion Vectors";
// NOTE: All these keyword should be automatically stripped so there's no need to handle them ourselves.
// LIGHTMAP_ON, DIRLIGHTMAP_COMBINED, DYNAMICLIGHTMAP_ON, LIGHTMAP_SHADOW_MIXING, SHADOWS_SHADOWMASK
// FOG_LINEAR, FOG_EXP, FOG_EXP2
// STEREO_INSTANCING_ON, STEREO_MULTIVIEW_ON, STEREO_CUBEMAP_RENDER_ON, UNITY_SINGLE_PASS_STEREO
// INSTANCING_ON
if (!m_CurrentHDRPAsset.renderPipelineSettings.supportMotionVectors && isMotionPass)
return true;
// When using forward only, we never need GBuffer pass (only Forward)
if (m_CurrentHDRPAsset.renderPipelineSettings.supportOnlyForward && isGBufferPass)
return true;
if (inputData.shaderKeywordSet.IsEnabled(m_Transparent))
// Fill the dictionary with material to handle
foreach (BaseShaderPreprocessor material in materialList)
// If transparent, we never need GBuffer pass.
if (isGBufferPass)
return true;
// We will also use cluster instead of tile
if (inputData.shaderKeywordSet.IsEnabled(m_TileLighting))
return true;
material.AddStripperFuncs(m_StripperFuncs);
else // Opaque
{
// If opaque, we never need transparent specific passes (even in forward only mode)
if (isTransparentForwardPass)
return true;
if (!m_CurrentHDRPAsset.renderPipelineSettings.supportOnlyForward && inputData.shaderKeywordSet.IsEnabled(m_ClusterLighting))
return true;
if (!m_CurrentHDRPAsset.renderPipelineSettings.supportOnlyForward)
{
// If opaque and not forward only, then we only need the forward debug pass.
if (isForwardPass && !inputData.shaderKeywordSet.IsEnabled(m_DebugDisplay))
return true;
}
}
// TODO: Expose development build flag.
//if (developmentBuild && inputData.shaderKeywordSet.IsEnabled(m_DebugDisplay))
// return true;
// TODO: Tests for later
// We need to find a way to strip useless shader features for passes/shader stages that don't need them (example, vertex shaders won't ever need SSS Feature flag)
// This causes several problems:
// - Runtime code that "finds" shader variants based on feature flags might not find them anymore... thus fall backing to the "let's give a score to variant" code path that may find the wrong variant.
// - Another issue is that if a feature is declared without a "_" fall-back, if we strip the other variants, none may be left to use! This needs to be changed on our side.
//if (snippet.shaderType == ShaderType.Vertex && inputData.shaderKeywordSet.IsEnabled(m_FeatureSSS))
// return true;
return false;
}
public int callbackOrder { get { return 0; } }

for (int i = 0; i < inputData.Count; ++i)
{
ShaderCompilerData input = inputData[i];
if (stripperFunc(shader, snippet, input))
if (stripperFunc(m_CurrentHDRPAsset, shader, snippet, input))
{
inputData.RemoveAt(i);
i--;

// Currently if a certain snippet is completely stripped (for example if you remove a whole pass) other passes might get broken
// To work around that, we make sure that we always have at least one variant.
// TODO: Remove this one it is fixed
if (inputData.Count == 0)
inputData.Add(workaround);
}

14
com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/HDEditorUtils.cs


}
return false;
}
public static List<BaseShaderPreprocessor> GetBaseShaderPreprocessorList()
{
var baseType = typeof(BaseShaderPreprocessor);
var assembly = baseType.Assembly;
var types = assembly.GetTypes()
.Where(t => t.IsSubclassOf(baseType))
.Select(Activator.CreateInstance)
.Cast<BaseShaderPreprocessor>()
.ToList();
return types;
}
}
}

16
com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/HDRenderPipelineMenuItems.cs


{
var materials = Resources.FindObjectsOfTypeAll<Material>();
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
CoreUtils.CheckOutFile(VSCEnabled, mat);
CoreEditorUtils.CheckOutFile(VCSEnabled, mat);
LayeredLitGUI.SynchronizeAllLayers(mat);
EditorUtility.SetDirty(mat);
}

for (var i = 0; i < openedScenes.Length; ++i)
openedScenes[i] = SceneManager.GetSceneAt(i).path;
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
try
{

{
var scenePath = AssetDatabase.GUIDToAssetPath(scenes[i]);
var sceneAsset = AssetDatabase.LoadAssetAtPath<SceneAsset>(scenePath);
CoreUtils.CheckOutFile(VSCEnabled, sceneAsset);
CoreEditorUtils.CheckOutFile(VCSEnabled, sceneAsset);
EditorSceneManager.OpenScene(scenePath);
var sceneName = Path.GetFileNameWithoutExtension(scenePath);

{
var matIds = AssetDatabase.FindAssets("t:Material");
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
for (int i = 0, length = matIds.Length; i < length; i++)
{

string.Format("{0} / {1} materials cleaned.", i, length),
(i / (float)(length - 1)) * progressScale + progressOffset);
CoreUtils.CheckOutFile(VSCEnabled, mat);
CoreEditorUtils.CheckOutFile(VCSEnabled, mat);
var h = Debug.unityLogger.logHandler;
Debug.unityLogger.logHandler = new UnityContextualLogHandler(mat);
HDEditorUtils.ResetMaterialKeywords(mat);

{
var materials = Resources.FindObjectsOfTypeAll<Material>();
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool anyMaterialDirty = false; // Will be true if any material is dirty.

string.Format("{0}{1} / {2} materials cleaned.", descriptionPrefix, i, length),
(i / (float)(length - 1)) * progressScale + progressOffset);
CoreUtils.CheckOutFile(VSCEnabled, materials[i]);
CoreEditorUtils.CheckOutFile(VCSEnabled, materials[i]);
if (HDEditorUtils.ResetMaterialKeywords(materials[i]))
{

22
com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/Settings/RenderPipelineSettingsUI.cs


{
EditorGUILayout.LabelField(_.GetContent("Render Pipeline Settings"), EditorStyles.boldLabel);
++EditorGUI.indentLevel;
EditorGUILayout.PropertyField(d.supportShadowMask, _.GetContent("Support Shadow Mask"));
EditorGUILayout.PropertyField(d.supportSSR, _.GetContent("Support SSR"));
EditorGUILayout.PropertyField(d.supportSSAO, _.GetContent("Support SSAO"));
EditorGUILayout.PropertyField(d.supportDBuffer, _.GetContent("Support Decal Buffer"));
EditorGUILayout.PropertyField(d.supportMSAA, _.GetContent("Support Multi Sampling Anti-Aliasing"));
EditorGUILayout.PropertyField(d.MSAASampleCount, _.GetContent("MSAA Sample Count"));
EditorGUILayout.PropertyField(d.supportShadowMask, _.GetContent("Support Shadow Mask|Enable memory (Extra Gbuffer in deferred) and shader variant for shadow mask."));
EditorGUILayout.PropertyField(d.supportSSR, _.GetContent("Support SSR|Enable memory use by SSR effect."));
EditorGUILayout.PropertyField(d.supportSSAO, _.GetContent("Support SSAO|Enable memory use by SSAO effect."));
EditorGUILayout.PropertyField(d.supportDBuffer, _.GetContent("Support Decal Buffer|Enable memory and variant of decal buffer."));
EditorGUILayout.PropertyField(d.supportMSAA, _.GetContent("Support Multi Sampling Anti-Aliasing|This feature doesn't work currently."));
EditorGUILayout.PropertyField(d.MSAASampleCount, _.GetContent("MSAA Sample Count|Allow to select the level of MSAA."));
EditorGUILayout.PropertyField(d.supportOnlyForward, _.GetContent("Support Only Forward"));
EditorGUILayout.PropertyField(d.supportMotionVectors, _.GetContent("Support Motion Vectors"));
EditorGUILayout.PropertyField(d.supportOnlyForward, _.GetContent("Support Only Forward|Remove all the memory and shader variant of GBuffer. The renderer can be switch to deferred anymore."));
EditorGUILayout.PropertyField(d.supportMotionVectors, _.GetContent("Support Motion Vectors|Motion vector are use for Motion Blur, TAA, temporal re-projection of various effect like SSR."));
EditorGUILayout.PropertyField(d.enableUltraQualitySSS, _.GetContent("Increase SSS Sample Count"));
EditorGUILayout.PropertyField(d.supportVolumetric, _.GetContent("Support volumetric"));
EditorGUILayout.PropertyField(d.enableUltraQualitySSS, _.GetContent("Increase SSS Sample Count|This allow better SSS quality. Warning: Slow feature, don't use for game."));
EditorGUILayout.PropertyField(d.supportVolumetric, _.GetContent("Support volumetric|Enable memory and shader variant for volumetric."));
EditorGUILayout.PropertyField(d.supportRuntimeDebugDisplay, _.GetContent("Support runtime debug display|Remove all debug display shader variant only in the player. Allow faster build."));
--EditorGUI.indentLevel;
}
}

3
com.unity.render-pipelines.high-definition/HDRP/Editor/RenderPipeline/Settings/SerializedRenderPipelineSettings.cs


public SerializedProperty supportStereo;
public SerializedProperty enableUltraQualitySSS;
public SerializedProperty supportVolumetric;
public SerializedProperty supportRuntimeDebugDisplay;
public SerializedGlobalLightLoopSettings lightLoopSettings;
public SerializedShadowInitParameters shadowInitParams;

supportStereo = root.Find((RenderPipelineSettings s) => s.supportStereo);
enableUltraQualitySSS = root.Find((RenderPipelineSettings s) => s.enableUltraQualitySSS);
supportVolumetric = root.Find((RenderPipelineSettings s) => s.supportVolumetric);
supportRuntimeDebugDisplay = root.Find((RenderPipelineSettings s) => s.supportRuntimeDebugDisplay);
lightLoopSettings = new SerializedGlobalLightLoopSettings(root.Find((RenderPipelineSettings s) => s.lightLoopSettings));
shadowInitParams = new SerializedShadowInitParameters(root.Find((RenderPipelineSettings s) => s.shadowInitParams));

92
com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDPBRPass.template


//#pragma enable_d3d11_debug_symbols
//-------------------------------------------------------------------------------------
// Variant Definitions
// Variant Definitions (active field translations to HDRP defines)
${VariantDefines}
$AlphaTest: #define _ALPHATEST_ON 1
$Material.SubsurfaceScattering: #define _MATERIAL_FEATURE_SUBSURFACE_SCATTERING 1
$Material.Transmission: #define _MATERIAL_FEATURE_TRANSMISSION 1
$Material.Anisotropy: #define _MATERIAL_FEATURE_ANISOTROPY 1
$Material.ClearCoat: #define _MATERIAL_FEATURE_CLEAR_COAT 1
$Material.Iridescence: #define _MATERIAL_FEATURE_IRIDESCENCE 1
$Material.SpecularColor: #define _MATERIAL_FEATURE_SPECULAR_COLOR 1
$SurfaceType.Transparent: #define _SURFACE_TYPE_TRANSPARENT 1
$BlendMode.Alpha: #define _BLENDMODE_ALPHA 1
$BlendMode.Add: #define _BLENDMODE_ADD 1
//-------------------------------------------------------------------------------------
// End Variant
//-------------------------------------------------------------------------------------

// Use surface gradient normal mapping as it handle correctly triplanar normal mapping and multiple UVSet
// this modifies the normal calculation
// #define SURFACE_GRADIENT
// This shader support vertex modification (or not)
// TODO - move to PBR shader control
// #define HAVE_VERTEX_MODIFICATION
// If we use subsurface scattering, enable output split lighting (for forward pass)
#if defined(_MATID_SSS) && !defined(_SURFACE_TYPE_TRANSPARENT)

$VaryingsMeshToPS.texCoord3: #define VARYINGS_NEED_TEXCOORD3
$VaryingsMeshToPS.color: #define VARYINGS_NEED_COLOR
$VaryingsMeshToPS.cullFace: #define VARYINGS_NEED_CULLFACE
$features.modifyMesh: #define HAVE_MESH_MODIFICATION
#include "ShaderGraphLibrary/Functions.hlsl"
#include "HDRP/ShaderVariables.hlsl"
#ifdef DEBUG_DISPLAY
#include "HDRP/Debug/DebugDisplay.hlsl"

// End graph generated code
//-------------------------------------------------------------------------------------
// TODO: Do we want to build include functionality for sharing these preprocessed functions across templates?
#ifdef HAVE_MESH_MODIFICATION
// TODO: we should share this between template files somehow
VertexDescriptionInputs AttributesMeshToVertexDescriptionInputs(AttributesMesh input)
{
VertexDescriptionInputs output;
ZERO_INITIALIZE(VertexDescriptionInputs, output);
$VertexDescriptionInputs.ObjectSpaceNormal: output.ObjectSpaceNormal = input.normalOS;
$VertexDescriptionInputs.WorldSpaceNormal: output.WorldSpaceNormal = TransformObjectToWorldNormal(input.normalOS);
$VertexDescriptionInputs.ViewSpaceNormal: output.ViewSpaceNormal = TransformWorldToViewDir(output.WorldSpaceNormal);
$VertexDescriptionInputs.TangentSpaceNormal: output.TangentSpaceNormal = float3(0.0f, 0.0f, 1.0f);
$VertexDescriptionInputs.ObjectSpaceTangent: output.ObjectSpaceTangent = input.tangentOS;
$VertexDescriptionInputs.WorldSpaceTangent: output.WorldSpaceTangent = TransformObjectToWorldDir(input.tangentOS.xyz);
$VertexDescriptionInputs.ViewSpaceTangent: output.ViewSpaceTangent = TransformWorldToViewDir(output.WorldSpaceTangent);
$VertexDescriptionInputs.TangentSpaceTangent: output.TangentSpaceTangent = float3(1.0f, 0.0f, 0.0f);
$VertexDescriptionInputs.ObjectSpaceBiTangent: output.ObjectSpaceBiTangent = normalize(cross(input.normalOS, input.tangentOS) * (input.tangentOS.w > 0.0f ? 1.0f : -1.0f) * GetOddNegativeScale());
$VertexDescriptionInputs.WorldSpaceBiTangent: output.WorldSpaceBiTangent = TransformObjectToWorldDir(output.ObjectSpaceBiTangent);
$VertexDescriptionInputs.ViewSpaceBiTangent: output.ViewSpaceBiTangent = TransformWorldToViewDir(output.WorldSpaceBiTangent);
$VertexDescriptionInputs.TangentSpaceBiTangent: output.TangentSpaceBiTangent = float3(0.0f, 1.0f, 0.0f);
$VertexDescriptionInputs.ObjectSpacePosition: output.ObjectSpacePosition = input.positionOS;
$VertexDescriptionInputs.WorldSpacePosition: output.WorldSpacePosition = TransformObjectToWorld(input.positionOS);
$VertexDescriptionInputs.ViewSpacePosition: output.ViewSpacePosition = TransformWorldToView(output.WorldSpacePosition);
$VertexDescriptionInputs.TangentSpacePosition: output.TangentSpacePosition = float3(0.0f, 0.0f, 0.0f);
$VertexDescriptionInputs.WorldSpaceViewDirection: output.WorldSpaceViewDirection = GetWorldSpaceNormalizeViewDir(output.WorldSpacePosition);
$VertexDescriptionInputs.ObjectSpaceViewDirection: output.ObjectSpaceViewDirection = TransformWorldToObjectDir(output.WorldSpaceViewDirection);
$VertexDescriptionInputs.ViewSpaceViewDirection: output.ViewSpaceViewDirection = TransformWorldToViewDir(output.WorldSpaceViewDirection);
$VertexDescriptionInputs.TangentSpaceViewDirection: float3x3 tangentSpaceTransform = float3x3(output.WorldSpaceTangent,output.WorldSpaceBiTangent,output.WorldSpaceNormal);
$VertexDescriptionInputs.TangentSpaceViewDirection: output.TangentSpaceViewDirection = mul(tangentSpaceTransform, output.WorldSpaceViewDirection);
$VertexDescriptionInputs.ScreenPosition: output.ScreenPosition = ComputeScreenPos(TransformWorldToHClip(output.WorldSpacePosition), _ProjectionParams.x);
$VertexDescriptionInputs.uv0: output.uv0 = float4(input.uv0, 0.0f, 0.0f);
$VertexDescriptionInputs.uv1: output.uv1 = float4(input.uv1, 0.0f, 0.0f);
$VertexDescriptionInputs.uv2: output.uv2 = float4(input.uv2, 0.0f, 0.0f);
$VertexDescriptionInputs.uv3: output.uv3 = float4(input.uv3, 0.0f, 0.0f);
$VertexDescriptionInputs.VertexColor: output.VertexColor = input.color;
return output;
}
AttributesMesh ApplyMeshModification(AttributesMesh input)
{
// build graph inputs
VertexDescriptionInputs vertexDescriptionInputs = AttributesMeshToVertexDescriptionInputs(input);
// evaluate vertex graph
VertexDescription vertexDescription = VertexDescriptionFunction(vertexDescriptionInputs);
// copy graph output to the results
$VertexDescription.Position: input.positionOS = vertexDescription.Position;
return input;
}
#endif // HAVE_MESH_MODIFICATION
// TODO: Do we want to build include functionality for sharing these preprocessed functions across templates?
FragInputs BuildFragInputs(VaryingsMeshToPS input)
{
FragInputs output;

$SurfaceDescriptionInputs.ViewSpaceNormal: output.ViewSpaceNormal = mul(output.WorldSpaceNormal, (float3x3) UNITY_MATRIX_I_V); // transposed multiplication by inverse matrix to handle normal scale
$SurfaceDescriptionInputs.TangentSpaceNormal: output.TangentSpaceNormal = float3(0.0f, 0.0f, 1.0f);
$SurfaceDescriptionInputs.WorldSpaceTangent: output.WorldSpaceTangent = input.worldToTangent[0].xyz;
$SurfaceDescriptionInputs.WorldSpaceTangent: output.WorldSpaceTangent = input.worldToTangent[0].xyz;
$SurfaceDescriptionInputs.ObjectSpaceTangent: output.ObjectSpaceTangent = mul((float3x3) unity_WorldToObject, output.WorldSpaceTangent);
$SurfaceDescriptionInputs.ViewSpaceTangent: output.ViewSpaceTangent = mul((float3x3) UNITY_MATRIX_V, output.WorldSpaceTangent);
$SurfaceDescriptionInputs.TangentSpaceTangent: output.TangentSpaceTangent = float3(1.0f, 0.0f, 0.0f);

$SurfaceDescriptionInputs.TangentSpacePosition: output.TangentSpacePosition = float3(0.0f, 0.0f, 0.0f);
// TODO: positionSS is SV_Position, graph input expects screenPosition to be 0..1 across the active viewport (?)
$SurfaceDescriptionInputs.screenPosition: output.screenPosition = input.positionSS;
$SurfaceDescriptionInputs.ScreenPosition: output.ScreenPosition = ComputeScreenPos(TransformWorldToHClip(input.positionWS), _ProjectionParams.x);
$SurfaceDescriptionInputs.uv0: output.uv0 = float4(input.texCoord0, 0.0f, 0.0f);
$SurfaceDescriptionInputs.uv1: output.uv1 = float4(input.texCoord1, 0.0f, 0.0f);

$SurfaceDescriptionInputs.vertexColor: output.vertexColor = input.color;
$SurfaceDescriptionInputs.VertexColor: output.VertexColor = input.color;
$SurfaceDescriptionInputs.FaceSign: output.FaceSign = input.isFrontFace;
return output;
}

// Perform alpha test very early to save performance (a killed pixel will not sample textures)
// TODO: split graph evaluation to grab just alpha dependencies first? tricky..
#ifdef _ALPHATEST_ON
DoAlphaTest(surfaceDescription.Alpha, surfaceDescription.AlphaClipThreshold);
#endif
$AlphaTest: DoAlphaTest(surfaceDescription.Alpha, surfaceDescription.AlphaClipThreshold);
BuildSurfaceData(fragInputs, surfaceDescription, V, surfaceData);

342
com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDPBRSubShader.cs


using System.Collections.Generic;
using System.Collections;
using System.IO;
using System.Linq;
using UnityEditor.Graphing;

PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};
Pass m_PassGBufferWithPrepass = new Pass()

PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};
Pass m_PassMETA = new Pass()

"AttributesMesh.uv1",
"AttributesMesh.color",
"AttributesMesh.uv2", // SHADERPASS_LIGHT_TRANSPORT always uses uv2
// "FragInputs.worldToTangent",
// "FragInputs.positionWS",
},
PixelShaderSlots = new List<int>()
{

PBRMasterNode.OcclusionSlotId,
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
// VertexShaderSlots = new List<int>()
// {
// PBRMasterNode.PositionSlotId
// }
};
Pass m_PassShadowCaster = new Pass()

{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};

{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};

{
"FragInputs.positionWS",
},
PixelShaderSlots = new List<int>()
{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
},
StencilOverride = new List<string>()
{
"// If velocity pass (motion vectors) is enabled we tag the stencil so it don't perform CameraMotionVelocity",

" Comp Always",
" Pass Replace",
"}"
}
},
PixelShaderSlots = new List<int>()
{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
};
Pass m_PassDistortion = new Pass()

{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
};
Pass m_PassTransparentDepthPrepass = new Pass()

{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
};
Pass m_PassTransparentBackface = new Pass()

PBRMasterNode.OcclusionSlotId,
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
};
Pass m_PassForward = new Pass()

PBRMasterNode.OcclusionSlotId,
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
};
Pass m_PassTransparentDepthPostpass = new Pass()

{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
private static string GetVariantDefines(PBRMasterNode masterNode)
private static HashSet<string> GetActiveFieldsFromMasterNode(INode iMasterNode, Pass pass)
ShaderGenerator defines = new ShaderGenerator();
HashSet<string> activeFields = new HashSet<string>();
PBRMasterNode masterNode = iMasterNode as PBRMasterNode;
if (masterNode == null)
{
return activeFields;
}
// TODO:
// _MATERIAL_FEATURE_SUBSURFACE_SCATTERING
// _MATERIAL_FEATURE_TRANSMISSION
// _MATERIAL_FEATURE_ANISOTROPY
// _MATERIAL_FEATURE_CLEAR_COAT
// _MATERIAL_FEATURE_IRIDESCENCE
if (masterNode.twoSided.isOn)
{
activeFields.Add("DoubleSided");
if (pass.ShaderPassName != "SHADERPASS_VELOCITY") // HACK to get around lack of a good interpolator dependency system
{ // we need to be able to build interpolators using multiple input structs
// also: should only require isFrontFace if Normals are required...
activeFields.Add("DoubleSided.Mirror"); // TODO: change this depending on what kind of normal flip you want..
activeFields.Add("FragInputs.isFrontFace"); // will need this for determining normal flip mode
}
}
switch (masterNode.model)
{

defines.AddShaderChunk("#define _MATERIAL_FEATURE_SPECULAR_COLOR 1", true);
activeFields.Add("Material.SpecularColor");
break;
default:
// TODO: error!

// #pragma shader_feature _ALPHATEST_ON
defines.AddShaderChunk("#define _ALPHATEST_ON 1", true);
activeFields.Add("AlphaTest");
}
// if (kTesselationMode != TessellationMode.None)

// #pragma shader_feature _ _MAPPING_PLANAR _MAPPING_TRIPLANAR // MOVE to a node
// #pragma shader_feature _NORMALMAP_TANGENT_SPACE
// #pragma shader_feature _ _REQUIRE_UV2 _REQUIRE_UV3
//
// #pragma shader_feature _NORMALMAP
if (masterNode.IsSlotConnected(PBRMasterNode.NormalSlotId))
{
defines.AddShaderChunk("#define _NORMALMAP 1", true);
}
// #pragma shader_feature _MASKMAP
// #pragma shader_feature _BENTNORMALMAP

// #pragma shader_feature _TANGENTMAP
// #pragma shader_feature _ANISOTROPYMAP
// #pragma shader_feature _DETAIL_MAP // MOVE to a node
// #pragma shader_feature _SUBSURFACE_RADIUS_MAP
// #pragma shader_feature _THICKNESSMAP
// #pragma shader_feature _SPECULARCOLORMAP

if (masterNode.surfaceType != SurfaceType.Opaque)
{
// transparent-only defines
defines.AddShaderChunk("#define _SURFACE_TYPE_TRANSPARENT 1", true);
activeFields.Add("SurfaceType.Transparent");
defines.AddShaderChunk("#define _BLENDMODE_ALPHA 1", true);
activeFields.Add("BlendMode.Alpha");
defines.AddShaderChunk("#define _BLENDMODE_ADD 1", true);
activeFields.Add("BlendMode.Add");
}
// else if (masterNode.alphaMode == PBRMasterNode.AlphaMode.PremultiplyAlpha) // TODO
// {

{
// opaque-only defines
}
// MaterialId are used as shader feature to allow compiler to optimize properly
// Note _MATID_STANDARD is not define as there is always the default case "_". We assign default as _MATID_STANDARD, so we never test _MATID_STANDARD
// #pragma shader_feature _ _MATID_SSS _MATID_ANISO _MATID_SPECULAR _MATID_CLEARCOAT
// enable dithering LOD crossfade
// #pragma multi_compile _ LOD_FADE_CROSSFADE

return defines.GetShaderString(2);
return activeFields;
private static bool GenerateShaderPass(PBRMasterNode masterNode, Pass pass, GenerationMode mode, SurfaceMaterialOptions materialOptions, ShaderGenerator result, List<string> sourceAssetDependencyPaths)
private static bool GenerateShaderPassLit(AbstractMaterialNode masterNode, Pass pass, GenerationMode mode, SurfaceMaterialOptions materialOptions, ShaderGenerator result, List<string> sourceAssetDependencyPaths)
{
var templateLocation = Path.Combine(Path.Combine(Path.Combine(HDEditorUtils.GetHDRenderPipelinePath(), "Editor"), "ShaderGraph"), pass.TemplateName);
if (!File.Exists(templateLocation))

if (sourceAssetDependencyPaths != null)
sourceAssetDependencyPaths.Add(templateLocation);
// grab all of the active nodes
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, masterNode, NodeUtils.IncludeSelf.Include, pass.PixelShaderSlots);
// grab all of the active nodes (for pixel and vertex graphs)
var vertexNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(vertexNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.VertexShaderSlots);
var pixelNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(pixelNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.PixelShaderSlots);
var graphRequirements = ShaderGraphRequirements.FromNodes(activeNodeList, ShaderStageCapability.Fragment);
var pixelRequirements = ShaderGraphRequirements.FromNodes(pixelNodes, ShaderStageCapability.Fragment, false); // TODO: is ShaderStageCapability.Fragment correct?
var vertexRequirements = ShaderGraphRequirements.FromNodes(vertexNodes, ShaderStageCapability.Vertex, false);
// Function Registry tracks functions to remove duplicates, it wraps a string builder that stores the combined function string
// TODO: this can be a shared function for all HDRP master nodes -- From here through GraphUtil.GenerateSurfaceDescription(..)
// TODO: this can be a shared function -- From here through GraphUtil.GenerateSurfaceDescription(..)
var activeSlots = new List<MaterialSlot>();
foreach (var id in pass.PixelShaderSlots)
{
MaterialSlot slot = masterNode.FindSlot<MaterialSlot>(id);
if (slot != null)
{
activeSlots.Add(slot);
}
}
var pixelSlots = HDSubShaderUtilities.FindMaterialSlotsOnNode(pass.PixelShaderSlots, masterNode);
var vertexSlots = HDSubShaderUtilities.FindMaterialSlotsOnNode(pass.VertexShaderSlots, masterNode);
// properties used by either pixel and vertex shader
PropertyCollector sharedProperties = new PropertyCollector();
string graphInputStructName = "SurfaceDescriptionInputs";
string graphOutputStructName = "SurfaceDescription";
string graphEvalFunctionName = "SurfaceDescriptionFunction";
ShaderStringBuilder graphEvalFunction = new ShaderStringBuilder();
ShaderStringBuilder graphOutputs = new ShaderStringBuilder();
PropertyCollector graphProperties = new PropertyCollector();
string pixelGraphInputStructName = "SurfaceDescriptionInputs";
string pixelGraphOutputStructName = "SurfaceDescription";
string pixelGraphEvalFunctionName = "SurfaceDescriptionFunction";
ShaderStringBuilder pixelGraphEvalFunction = new ShaderStringBuilder();
ShaderStringBuilder pixelGraphOutputs = new ShaderStringBuilder();
// dependency tracker -- set of active fields
HashSet<string> activeFields = GetActiveFieldsFromMasterNode(masterNode, pass);
// build initial requirements
HDRPShaderStructs.AddActiveFieldsFromPixelGraphRequirements(activeFields, pixelRequirements);
HashSet<string> activeFields = new HashSet<string>();
GraphUtil.GenerateSurfaceDescriptionStruct(graphOutputs, activeSlots, true);
//GraphUtil.GenerateSurfaceDescriptionStruct(graphOutputs, activeSlots, true, graphOutputStructName, activeFields);
GraphUtil.GenerateSurfaceDescriptionStruct(pixelGraphOutputs, pixelSlots, true, pixelGraphOutputStructName, activeFields);
activeNodeList,
pixelNodes,
graphEvalFunction,
pixelGraphEvalFunction,
graphProperties,
graphRequirements, // TODO : REMOVE UNUSED
sharedProperties,
pixelRequirements, // TODO : REMOVE UNUSED
graphEvalFunctionName,
graphOutputStructName,
pixelGraphEvalFunctionName,
pixelGraphOutputStructName,
activeSlots,
graphInputStructName);
pixelSlots,
pixelGraphInputStructName);
string vertexGraphInputStructName = "VertexDescriptionInputs";
string vertexGraphOutputStructName = "VertexDescription";
string vertexGraphEvalFunctionName = "VertexDescriptionFunction";
ShaderStringBuilder vertexGraphEvalFunction = new ShaderStringBuilder();
ShaderStringBuilder vertexGraphOutputs = new ShaderStringBuilder();
// check for vertex animation -- enables HAVE_VERTEX_MODIFICATION
bool vertexActive = false;
if (masterNode.IsSlotConnected(PBRMasterNode.PositionSlotId))
{
vertexActive = true;
activeFields.Add("features.modifyMesh");
HDRPShaderStructs.AddActiveFieldsFromVertexGraphRequirements(activeFields, vertexRequirements);
// -------------------------------------
// Generate Output structure for Vertex Description function
GraphUtil.GenerateVertexDescriptionStruct(vertexGraphOutputs, vertexSlots, vertexGraphOutputStructName, activeFields);
// -------------------------------------
// Generate Vertex Description function
GraphUtil.GenerateVertexDescriptionFunction(
masterNode.owner as AbstractMaterialGraph,
vertexGraphEvalFunction,
functionRegistry,
sharedProperties,
mode,
vertexNodes,
vertexSlots,
vertexGraphInputStructName,
vertexGraphEvalFunctionName,
vertexGraphOutputStructName);
}
var blendCode = new ShaderStringBuilder();
var cullCode = new ShaderStringBuilder();

var colorMaskCode = new ShaderStringBuilder();
HDSubShaderUtilities.BuildRenderStatesFromPassAndMaterialOptions(pass, materialOptions, blendCode, cullCode, zTestCode, zWriteCode, stencilCode, colorMaskCode);
if (masterNode.twoSided.isOn)
{
activeFields.Add("DoubleSided");
if (pass.ShaderPassName != "SHADERPASS_VELOCITY") // HACK to get around lack of a good interpolator dependency system
{ // we need to be able to build interpolators using multiple input structs
// also: should only require isFrontFace if Normals are required...
activeFields.Add("DoubleSided.Mirror"); // TODO: change this depending on what kind of normal flip you want..
activeFields.Add("FragInputs.isFrontFace"); // will need this for determining normal flip mode
}
}
HDRPShaderStructs.AddRequiredFields(pass.RequiredFields, activeFields);
if (pass.PixelShaderSlots != null)
{
foreach (var slotId in pass.PixelShaderSlots)
{
var slot = masterNode.FindSlot<MaterialSlot>(slotId);
if (slot != null)
{
var rawSlotName = slot.RawDisplayName().ToString();
var descriptionVar = string.Format("{0}.{1}", graphOutputStructName, rawSlotName);
activeFields.Add(descriptionVar);
}
}
}
// apply dependencies to the active fields, and build interpolators (TODO: split this function)
var graphInputs = new ShaderGenerator();
graphInputs,
graphRequirements,
pass.RequiredFields,
CoordinateSpace.World,
activeFields);
// debug output all active fields

}
}
// build graph inputs structures
ShaderGenerator pixelGraphInputs = new ShaderGenerator();
ShaderSpliceUtil.BuildType(typeof(HDRPShaderStructs.SurfaceDescriptionInputs), activeFields, pixelGraphInputs);
ShaderGenerator vertexGraphInputs = new ShaderGenerator();
ShaderSpliceUtil.BuildType(typeof(HDRPShaderStructs.VertexDescriptionInputs), activeFields, vertexGraphInputs);
ShaderGenerator defines = new ShaderGenerator();
{
defines.AddShaderChunk(string.Format("#define SHADERPASS {0}", pass.ShaderPassName), true);

// build graph code
var graph = new ShaderGenerator();
graph.AddShaderChunk("// Graph Inputs");
graph.Indent();
graph.AddGenerator(graphInputs);
graph.Deindent();
graph.AddShaderChunk("// Graph Outputs");
graph.Indent();
graph.AddShaderChunk(graphOutputs.ToString());
//graph.AddGenerator(graphOutputs);
graph.Deindent();
graph.AddShaderChunk("// Graph Properties (uniform inputs)");
graph.AddShaderChunk(graphProperties.GetPropertiesDeclaration(1));
graph.AddShaderChunk("// Graph Node Functions");
graph.AddShaderChunk(graphNodeFunctions.ToString());
graph.AddShaderChunk("// Graph Evaluation");
graph.Indent();
graph.AddShaderChunk(graphEvalFunction.ToString());
//graph.AddGenerator(graphEvalFunction);
graph.Deindent();
{
graph.AddShaderChunk("// Shared Graph Properties (uniform inputs)");
graph.AddShaderChunk(sharedProperties.GetPropertiesDeclaration(1));
if (vertexActive)
{
graph.AddShaderChunk("// Vertex Graph Inputs");
graph.Indent();
graph.AddGenerator(vertexGraphInputs);
graph.Deindent();
graph.AddShaderChunk("// Vertex Graph Outputs");
graph.Indent();
graph.AddShaderChunk(vertexGraphOutputs.ToString());
graph.Deindent();
}
graph.AddShaderChunk("// Pixel Graph Inputs");
graph.Indent();
graph.AddGenerator(pixelGraphInputs);
graph.Deindent();
graph.AddShaderChunk("// Pixel Graph Outputs");
graph.Indent();
graph.AddShaderChunk(pixelGraphOutputs.ToString());
graph.Deindent();
graph.AddShaderChunk("// Shared Graph Node Functions");
graph.AddShaderChunk(graphNodeFunctions.ToString());
if (vertexActive)
{
graph.AddShaderChunk("// Vertex Graph Evaluation");
graph.Indent();
graph.AddShaderChunk(vertexGraphEvalFunction.ToString());
graph.Deindent();
}
graph.AddShaderChunk("// Pixel Graph Evaluation");
graph.Indent();
graph.AddShaderChunk(pixelGraphEvalFunction.ToString());
graph.Deindent();
}
// build the hash table of all named fragments TODO: could make this Dictionary<string, ShaderGenerator / string> ?
Dictionary<string, string> namedFragments = new Dictionary<string, string>();

namedFragments.Add("${Stencil}", stencilCode.ToString());
namedFragments.Add("${ColorMask}", colorMaskCode.ToString());
namedFragments.Add("${LOD}", materialOptions.lod.ToString());
namedFragments.Add("${VariantDefines}", GetVariantDefines(masterNode));
// process the template to generate the shader code for this pass TODO: could make this a shared function
string[] templateLines = File.ReadAllLines(templateLocation);

if (opaque)
{
GenerateShaderPass(masterNode, m_PassGBuffer, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassGBufferWithPrepass, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassGBuffer, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassGBufferWithPrepass, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassMETA, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassShadowCaster, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassMETA, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassShadowCaster, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassDepthOnly, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassMotionVectors, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassDepthOnly, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassMotionVectors, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassDistortion, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassDistortion, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassTransparentDepthPrepass, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassTransparentDepthPrepass, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassTransparentBackface, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassTransparentBackface, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassForward, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassForward, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassTransparentDepthPostpass, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassLit(masterNode, m_PassTransparentDepthPostpass, mode, materialOptions, subShader, sourceAssetDependencyPaths);
}
}
subShader.Deindent();

226
com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDSubShaderUtilities.cs


};
};
struct SurfaceDescriptionInputs
// this describes the input to the pixel shader graph eval
public struct SurfaceDescriptionInputs
{
[Optional] Vector3 ObjectSpaceNormal;
[Optional] Vector3 ViewSpaceNormal;

[Optional] Vector3 WorldSpacePosition;
[Optional] Vector3 TangentSpacePosition;
[Optional] Vector4 screenPosition;
[Optional] Vector4 ScreenPosition;
[Optional] Vector4 vertexColor;
[Optional] Vector4 VertexColor;
[Optional] float FaceSign;
public static Dependency[] dependencies = new Dependency[]
{

new Dependency("SurfaceDescriptionInputs.TangentSpaceViewDirection", "SurfaceDescriptionInputs.WorldSpaceBiTangent"),
new Dependency("SurfaceDescriptionInputs.TangentSpaceViewDirection", "SurfaceDescriptionInputs.WorldSpaceNormal"),
new Dependency("SurfaceDescriptionInputs.screenPosition", "FragInputs.positionSS"),
new Dependency("SurfaceDescriptionInputs.ScreenPosition", "SurfaceDescriptionInputs.WorldSpacePosition"),
new Dependency("SurfaceDescriptionInputs.vertexColor", "FragInputs.color"),
new Dependency("SurfaceDescriptionInputs.VertexColor", "FragInputs.color"),
new Dependency("SurfaceDescriptionInputs.FaceSign", "FragInputs.isFrontFace"),
};
};
// this describes the input to the pixel shader graph eval
public struct VertexDescriptionInputs
{
[Optional] Vector3 ObjectSpaceNormal;
[Optional] Vector3 ViewSpaceNormal;
[Optional] Vector3 WorldSpaceNormal;
[Optional] Vector3 TangentSpaceNormal;
[Optional] Vector3 ObjectSpaceTangent;
[Optional] Vector3 ViewSpaceTangent;
[Optional] Vector3 WorldSpaceTangent;
[Optional] Vector3 TangentSpaceTangent;
[Optional] Vector3 ObjectSpaceBiTangent;
[Optional] Vector3 ViewSpaceBiTangent;
[Optional] Vector3 WorldSpaceBiTangent;
[Optional] Vector3 TangentSpaceBiTangent;
[Optional] Vector3 ObjectSpaceViewDirection;
[Optional] Vector3 ViewSpaceViewDirection;
[Optional] Vector3 WorldSpaceViewDirection;
[Optional] Vector3 TangentSpaceViewDirection;
[Optional] Vector3 ObjectSpacePosition;
[Optional] Vector3 ViewSpacePosition;
[Optional] Vector3 WorldSpacePosition;
[Optional] Vector3 TangentSpacePosition;
[Optional] Vector4 ScreenPosition;
[Optional] Vector4 uv0;
[Optional] Vector4 uv1;
[Optional] Vector4 uv2;
[Optional] Vector4 uv3;
[Optional] Vector4 VertexColor;
public static Dependency[] dependencies = new Dependency[]
{ // TODO: NOCHECKIN: these dependencies are not correct for vertex pass
new Dependency("VertexDescriptionInputs.ObjectSpaceNormal", "AttributesMesh.normalOS"),
new Dependency("VertexDescriptionInputs.WorldSpaceNormal", "AttributesMesh.normalOS"),
new Dependency("VertexDescriptionInputs.ViewSpaceNormal", "VertexDescriptionInputs.WorldSpaceNormal"),
new Dependency("VertexDescriptionInputs.ObjectSpaceTangent", "AttributesMesh.tangentOS"),
new Dependency("VertexDescriptionInputs.WorldSpaceTangent", "AttributesMesh.tangentOS"),
new Dependency("VertexDescriptionInputs.ViewSpaceTangent", "VertexDescriptionInputs.WorldSpaceTangent"),
new Dependency("VertexDescriptionInputs.ObjectSpaceBiTangent", "AttributesMesh.normalOS"),
new Dependency("VertexDescriptionInputs.ObjectSpaceBiTangent", "AttributesMesh.tangentOS"),
new Dependency("VertexDescriptionInputs.WorldSpaceBiTangent", "VertexDescriptionInputs.ObjectSpaceBiTangent"),
new Dependency("VertexDescriptionInputs.ViewSpaceBiTangent", "VertexDescriptionInputs.WorldSpaceBiTangent"),
new Dependency("VertexDescriptionInputs.ObjectSpacePosition", "AttributesMesh.positionOS"),
new Dependency("VertexDescriptionInputs.WorldSpacePosition", "AttributesMesh.positionOS"),
new Dependency("VertexDescriptionInputs.ViewSpacePosition", "VertexDescriptionInputs.WorldSpacePosition"),
new Dependency("VertexDescriptionInputs.WorldSpaceViewDirection", "VertexDescriptionInputs.WorldSpacePosition"),
new Dependency("VertexDescriptionInputs.ObjectSpaceViewDirection", "VertexDescriptionInputs.WorldSpaceViewDirection"),
new Dependency("VertexDescriptionInputs.ViewSpaceViewDirection", "VertexDescriptionInputs.WorldSpaceViewDirection"),
new Dependency("VertexDescriptionInputs.TangentSpaceViewDirection", "VertexDescriptionInputs.WorldSpaceViewDirection"),
new Dependency("VertexDescriptionInputs.TangentSpaceViewDirection", "VertexDescriptionInputs.WorldSpaceTangent"),
new Dependency("VertexDescriptionInputs.TangentSpaceViewDirection", "VertexDescriptionInputs.WorldSpaceBiTangent"),
new Dependency("VertexDescriptionInputs.TangentSpaceViewDirection", "VertexDescriptionInputs.WorldSpaceNormal"),
new Dependency("VertexDescriptionInputs.ScreenPosition", "VertexDescriptionInputs.WorldSpacePosition"),
new Dependency("VertexDescriptionInputs.uv0", "AttributesMesh.uv0"),
new Dependency("VertexDescriptionInputs.uv1", "AttributesMesh.uv1"),
new Dependency("VertexDescriptionInputs.uv2", "AttributesMesh.uv2"),
new Dependency("VertexDescriptionInputs.uv3", "AttributesMesh.uv3"),
new Dependency("VertexDescriptionInputs.VertexColor", "AttributesMesh.color"),
static void AddActiveFieldsFromGraphRequirements(HashSet<string> activeFields, ShaderGraphRequirements requirements)
// TODO: move this out of HDRPShaderStructs
static public void AddActiveFieldsFromVertexGraphRequirements(HashSet<string> activeFields, ShaderGraphRequirements requirements)
activeFields.Add("SurfaceDescriptionInputs.screenPosition");
activeFields.Add("VertexDescriptionInputs.ScreenPosition");
activeFields.Add("SurfaceDescriptionInputs.vertexColor");
activeFields.Add("VertexDescriptionInputs.VertexColor");
}
if (requirements.requiresNormal != 0)
{
if ((requirements.requiresNormal & NeededCoordinateSpace.Object) > 0)
activeFields.Add("VertexDescriptionInputs.ObjectSpaceNormal");
if ((requirements.requiresNormal & NeededCoordinateSpace.View) > 0)
activeFields.Add("VertexDescriptionInputs.ViewSpaceNormal");
if ((requirements.requiresNormal & NeededCoordinateSpace.World) > 0)
activeFields.Add("VertexDescriptionInputs.WorldSpaceNormal");
if ((requirements.requiresNormal & NeededCoordinateSpace.Tangent) > 0)
activeFields.Add("VertexDescriptionInputs.TangentSpaceNormal");
}
if (requirements.requiresTangent != 0)
{
if ((requirements.requiresTangent & NeededCoordinateSpace.Object) > 0)
activeFields.Add("VertexDescriptionInputs.ObjectSpaceTangent");
if ((requirements.requiresTangent & NeededCoordinateSpace.View) > 0)
activeFields.Add("VertexDescriptionInputs.ViewSpaceTangent");
if ((requirements.requiresTangent & NeededCoordinateSpace.World) > 0)
activeFields.Add("VertexDescriptionInputs.WorldSpaceTangent");
if ((requirements.requiresTangent & NeededCoordinateSpace.Tangent) > 0)
activeFields.Add("VertexDescriptionInputs.TangentSpaceTangent");
}
if (requirements.requiresBitangent != 0)
{
if ((requirements.requiresBitangent & NeededCoordinateSpace.Object) > 0)
activeFields.Add("VertexDescriptionInputs.ObjectSpaceBiTangent");
if ((requirements.requiresBitangent & NeededCoordinateSpace.View) > 0)
activeFields.Add("VertexDescriptionInputs.ViewSpaceBiTangent");
if ((requirements.requiresBitangent & NeededCoordinateSpace.World) > 0)
activeFields.Add("VertexDescriptionInputs.WorldSpaceBiTangent");
if ((requirements.requiresBitangent & NeededCoordinateSpace.Tangent) > 0)
activeFields.Add("VertexDescriptionInputs.TangentSpaceBiTangent");
}
if (requirements.requiresViewDir != 0)
{
if ((requirements.requiresViewDir & NeededCoordinateSpace.Object) > 0)
activeFields.Add("VertexDescriptionInputs.ObjectSpaceViewDirection");
if ((requirements.requiresViewDir & NeededCoordinateSpace.View) > 0)
activeFields.Add("VertexDescriptionInputs.ViewSpaceViewDirection");
if ((requirements.requiresViewDir & NeededCoordinateSpace.World) > 0)
activeFields.Add("VertexDescriptionInputs.WorldSpaceViewDirection");
if ((requirements.requiresViewDir & NeededCoordinateSpace.Tangent) > 0)
activeFields.Add("VertexDescriptionInputs.TangentSpaceViewDirection");
}
if (requirements.requiresPosition != 0)
{
if ((requirements.requiresPosition & NeededCoordinateSpace.Object) > 0)
activeFields.Add("VertexDescriptionInputs.ObjectSpacePosition");
if ((requirements.requiresPosition & NeededCoordinateSpace.View) > 0)
activeFields.Add("VertexDescriptionInputs.ViewSpacePosition");
if ((requirements.requiresPosition & NeededCoordinateSpace.World) > 0)
activeFields.Add("VertexDescriptionInputs.WorldSpacePosition");
if ((requirements.requiresPosition & NeededCoordinateSpace.Tangent) > 0)
activeFields.Add("VertexDescriptionInputs.TangentSpacePosition");
}
foreach (var channel in requirements.requiresMeshUVs.Distinct())
{
activeFields.Add("VertexDescriptionInputs." + channel.GetUVName());
}
}
// TODO: move this out of HDRPShaderStructs
static public void AddActiveFieldsFromPixelGraphRequirements(HashSet<string> activeFields, ShaderGraphRequirements requirements)
{
if (requirements.requiresScreenPosition)
{
activeFields.Add("SurfaceDescriptionInputs.ScreenPosition");
}
if (requirements.requiresVertexColor)
{
activeFields.Add("SurfaceDescriptionInputs.VertexColor");
}
if (requirements.requiresFaceSign)
{
activeFields.Add("SurfaceDescriptionInputs.FaceSign");
}
if (requirements.requiresNormal != 0)

}
}
// TODO : split this function into buildActiveFields and buildHLSLTypeDeclaration functions
public static void Generate(
ShaderGenerator codeResult,
ShaderGenerator graphInputsResult,
ShaderGraphRequirements graphRequirements,
public static void AddRequiredFields(
CoordinateSpace preferedCoordinateSpace,
if (preferedCoordinateSpace == CoordinateSpace.Tangent)
preferedCoordinateSpace = CoordinateSpace.World;
// build initial requirements
AddActiveFieldsFromGraphRequirements(activeFields, graphRequirements);
if (passRequiredFields != null)
{
foreach (var requiredField in passRequiredFields)

}
}
public static void Generate(
ShaderGenerator codeResult,
HashSet<string> activeFields)
{
// propagate requirements using dependencies
{
ShaderSpliceUtil.ApplyDependencies(

FragInputs.dependencies,
VaryingsMeshToPS.standardDependencies,
SurfaceDescriptionInputs.dependencies,
VertexDescriptionInputs.dependencies
});
}

ShaderSpliceUtil.BuildType(typeof(VaryingsMeshToDS), activeFields, codeResult);
ShaderSpliceUtil.BuildPackedType(typeof(VaryingsMeshToPS), activeFields, codeResult);
ShaderSpliceUtil.BuildPackedType(typeof(VaryingsMeshToDS), activeFields, codeResult);
ShaderSpliceUtil.BuildType(typeof(SurfaceDescriptionInputs), activeFields, graphInputsResult);
}
};

public static class HDSubShaderUtilities
{
public static List<MaterialSlot> FindMaterialSlotsOnNode(IEnumerable<int> slots, AbstractMaterialNode node)
{
var activeSlots = new List<MaterialSlot>();
if (slots != null)
{
foreach (var id in slots)
{
MaterialSlot slot = node.FindSlot<MaterialSlot>(id);
if (slot != null)
{
activeSlots.Add(slot);
}
}
}
return activeSlots;
}
public static void BuildRenderStatesFromPassAndMaterialOptions(
Pass pass,
SurfaceMaterialOptions materialOptions,

79
com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDUnlitPassForward.template


#define UNITY_MATERIAL_UNLIT // Need to be define before including Material.hlsl
#include "CoreRP/ShaderLibrary/Common.hlsl"
// #include "CoreRP/ShaderLibrary/Wind.hlsl"
#include "CoreRP/ShaderLibrary/Wind.hlsl"
#include "ShaderGraphLibrary/Functions.hlsl"

$VaryingsMeshToPS.texCoord3: #define VARYINGS_NEED_TEXCOORD3
$VaryingsMeshToPS.color: #define VARYINGS_NEED_COLOR
$VaryingsMeshToPS.cullFace: #define VARYINGS_NEED_CULLFACE
$features.modifyMesh: #define HAVE_MESH_MODIFICATION
#include "ShaderGraphLibrary/Functions.hlsl"
#include "HDRP/ShaderVariables.hlsl"
#ifdef DEBUG_DISPLAY
#include "HDRP/Debug/DebugDisplay.hlsl"

// End graph generated code
//-------------------------------------------------------------------------------------
// TODO: Do we want to build include functionality for sharing these preprocessed functions across templates?
#ifdef HAVE_MESH_MODIFICATION
// TODO: we should share this between template files somehow
VertexDescriptionInputs AttributesMeshToVertexDescriptionInputs(AttributesMesh input)
{
VertexDescriptionInputs output;
ZERO_INITIALIZE(VertexDescriptionInputs, output);
$VertexDescriptionInputs.ObjectSpaceNormal: output.ObjectSpaceNormal = input.normalOS;
$VertexDescriptionInputs.WorldSpaceNormal: output.WorldSpaceNormal = TransformObjectToWorldNormal(input.normalOS);
$VertexDescriptionInputs.ViewSpaceNormal: output.ViewSpaceNormal = TransformWorldToViewDir(output.WorldSpaceNormal);
$VertexDescriptionInputs.TangentSpaceNormal: output.TangentSpaceNormal = float3(0.0f, 0.0f, 1.0f);
$VertexDescriptionInputs.ObjectSpaceTangent: output.ObjectSpaceTangent = input.tangentOS;
$VertexDescriptionInputs.WorldSpaceTangent: output.WorldSpaceTangent = TransformObjectToWorldDir(input.tangentOS.xyz);
$VertexDescriptionInputs.ViewSpaceTangent: output.ViewSpaceTangent = TransformWorldToViewDir(output.WorldSpaceTangent);
$VertexDescriptionInputs.TangentSpaceTangent: output.TangentSpaceTangent = float3(1.0f, 0.0f, 0.0f);
$VertexDescriptionInputs.ObjectSpaceBiTangent: output.ObjectSpaceBiTangent = normalize(cross(input.normalOS, input.tangentOS) * (input.tangentOS.w > 0.0f ? 1.0f : -1.0f) * GetOddNegativeScale());
$VertexDescriptionInputs.WorldSpaceBiTangent: output.WorldSpaceBiTangent = TransformObjectToWorldDir(output.ObjectSpaceBiTangent);
$VertexDescriptionInputs.ViewSpaceBiTangent: output.ViewSpaceBiTangent = TransformWorldToViewDir(output.WorldSpaceBiTangent);
$VertexDescriptionInputs.TangentSpaceBiTangent: output.TangentSpaceBiTangent = float3(0.0f, 1.0f, 0.0f);
$VertexDescriptionInputs.ObjectSpacePosition: output.ObjectSpacePosition = input.positionOS;
$VertexDescriptionInputs.WorldSpacePosition: output.WorldSpacePosition = TransformObjectToWorld(input.positionOS);
$VertexDescriptionInputs.ViewSpacePosition: output.ViewSpacePosition = TransformWorldToView(output.WorldSpacePosition);
$VertexDescriptionInputs.TangentSpacePosition: output.TangentSpacePosition = float3(0.0f, 0.0f, 0.0f);
$VertexDescriptionInputs.WorldSpaceViewDirection: output.WorldSpaceViewDirection = GetWorldSpaceNormalizeViewDir(output.WorldSpacePosition);
$VertexDescriptionInputs.ObjectSpaceViewDirection: output.ObjectSpaceViewDirection = TransformWorldToObjectDir(output.WorldSpaceViewDirection);
$VertexDescriptionInputs.ViewSpaceViewDirection: output.ViewSpaceViewDirection = TransformWorldToViewDir(output.WorldSpaceViewDirection);
$VertexDescriptionInputs.TangentSpaceViewDirection: float3x3 tangentSpaceTransform = float3x3(output.WorldSpaceTangent,output.WorldSpaceBiTangent,output.WorldSpaceNormal);
$VertexDescriptionInputs.TangentSpaceViewDirection: output.TangentSpaceViewDirection = mul(tangentSpaceTransform, output.WorldSpaceViewDirection);
$VertexDescriptionInputs.ScreenPosition: output.ScreenPosition = ComputeScreenPos(TransformWorldToHClip(output.WorldSpacePosition), _ProjectionParams.x);
$VertexDescriptionInputs.uv0: output.uv0 = float4(input.uv0, 0.0f, 0.0f);
$VertexDescriptionInputs.uv1: output.uv1 = float4(input.uv1, 0.0f, 0.0f);
$VertexDescriptionInputs.uv2: output.uv2 = float4(input.uv2, 0.0f, 0.0f);
$VertexDescriptionInputs.uv3: output.uv3 = float4(input.uv3, 0.0f, 0.0f);
$VertexDescriptionInputs.VertexColor: output.VertexColor = input.color;
return output;
}
AttributesMesh ApplyMeshModification(AttributesMesh input)
{
// build graph inputs
VertexDescriptionInputs vertexDescriptionInputs = AttributesMeshToVertexDescriptionInputs(input);
// evaluate vertex graph
VertexDescription vertexDescription = VertexDescriptionFunction(vertexDescriptionInputs);
// copy graph output to the results
$VertexDescription.Position: input.positionOS = vertexDescription.Position;
return input;
}
#endif // HAVE_MESH_MODIFICATION
// TODO: Do we want to build include functionality for sharing these preprocessed functions across templates?
FragInputs BuildFragInputs(VaryingsMeshToPS input)
{
FragInputs output;

$SurfaceDescriptionInputs.ViewSpaceNormal: output.ViewSpaceNormal = mul(output.WorldSpaceNormal, (float3x3) UNITY_MATRIX_I_V); // transposed multiplication by inverse matrix to handle normal scale
$SurfaceDescriptionInputs.TangentSpaceNormal: output.TangentSpaceNormal = float3(0.0f, 0.0f, 1.0f);
$SurfaceDescriptionInputs.WorldSpaceTangent: output.WorldSpaceTangent = input.worldToTangent[0].xyz;
$SurfaceDescriptionInputs.WorldSpaceTangent: output.WorldSpaceTangent = input.worldToTangent[0].xyz;
$SurfaceDescriptionInputs.ObjectSpaceTangent: output.ObjectSpaceTangent = mul((float3x3) unity_WorldToObject, output.WorldSpaceTangent);
$SurfaceDescriptionInputs.ViewSpaceTangent: output.ViewSpaceTangent = mul((float3x3) UNITY_MATRIX_V, output.WorldSpaceTangent);
$SurfaceDescriptionInputs.TangentSpaceTangent: output.TangentSpaceTangent = float3(1.0f, 0.0f, 0.0f);

$SurfaceDescriptionInputs.TangentSpaceViewDirection: output.TangentSpaceViewDirection = mul(tangentSpaceTransform, output.WorldSpaceViewDirection);
// TODO: FragInputs.positionWS is badly named -- it's camera relative, not in world space
// we have to fix it up here to match graph input expectations
$SurfaceDescriptionInputs.WorldSpacePosition: output.WorldSpacePosition = input.positionWS + _WorldSpaceCameraPos;
$SurfaceDescriptionInputs.ObjectSpacePosition: output.ObjectSpacePosition = mul(unity_WorldToObject, float4(input.positionWS + _WorldSpaceCameraPos, 1.0f)).xyz;
$SurfaceDescriptionInputs.ViewSpacePosition: float4 posViewSpace = mul(UNITY_MATRIX_V, float4(input.positionWS, 1.0f));

$SurfaceDescriptionInputs.screenPosition: output.screenPosition = input.positionSS;
// TODO: positionSS is SV_Position, graph input expects screenPosition to be 0..1 across the active viewport (?)
$SurfaceDescriptionInputs.ScreenPosition: output.ScreenPosition = ComputeScreenPos(TransformWorldToHClip(input.positionWS), _ProjectionParams.x);
$SurfaceDescriptionInputs.uv0: output.uv0 = float4(input.texCoord0, 0.0f, 0.0f);
$SurfaceDescriptionInputs.uv1: output.uv1 = float4(input.texCoord1, 0.0f, 0.0f);

$SurfaceDescriptionInputs.vertexColor: output.vertexColor = input.color;
$SurfaceDescriptionInputs.VertexColor: output.VertexColor = input.color;
$SurfaceDescriptionInputs.FaceSign: output.FaceSign = input.isFrontFace;
return output;
}

// Perform alpha test very early to save performance (a killed pixel will not sample textures)
// TODO: split graph evaluation to grab just alpha dependencies first? tricky..
#ifdef _ALPHATEST_ON
DoAlphaTest(surfaceDescription.Alpha, surfaceDescription.AlphaClipThreshold);
#endif
$AlphaTest: DoAlphaTest(surfaceDescription.Alpha, surfaceDescription.AlphaClipThreshold);
BuildSurfaceData(fragInputs, surfaceDescription, V, surfaceData);

262
com.unity.render-pipelines.high-definition/HDRP/Editor/ShaderGraph/HDUnlitSubShader.cs


using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;

namespace UnityEditor.Experimental.Rendering.HDPipeline
{
// [Serializable] ??
public class HDUnlitSubShader : IUnlitSubShader
{
Pass m_PassDepthOnly = new Pass()

{
UnlitMasterNode.AlphaSlotId,
UnlitMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};

UnlitMasterNode.ColorSlotId,
UnlitMasterNode.AlphaSlotId,
UnlitMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};

UnlitMasterNode.ColorSlotId,
UnlitMasterNode.AlphaSlotId,
UnlitMasterNode.AlphaThresholdSlotId
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
}
};

{
PBRMasterNode.AlphaSlotId,
PBRMasterNode.AlphaThresholdSlotId
}
},
VertexShaderSlots = new List<int>()
{
PBRMasterNode.PositionSlotId
},
private static string GetVariantDefines(UnlitMasterNode masterNode)
private static HashSet<string> GetActiveFieldsFromMasterNode(INode iMasterNode, Pass pass)
ShaderGenerator defines = new ShaderGenerator();
HashSet<string> activeFields = new HashSet<string>();
// #pragma shader_feature _ALPHATEST_ON
UnlitMasterNode masterNode = iMasterNode as UnlitMasterNode;
if (masterNode == null)
{
return null;
}
if (masterNode.twoSided.isOn)
{
activeFields.Add("DoubleSided");
if (pass.ShaderPassName != "SHADERPASS_VELOCITY") // HACK to get around lack of a good interpolator dependency system
{ // we need to be able to build interpolators using multiple input structs
// also: should only require isFrontFace if Normals are required...
activeFields.Add("DoubleSided.Mirror"); // TODO: change this depending on what kind of normal flip you want..
activeFields.Add("FragInputs.isFrontFace"); // will need this for determining normal flip mode
}
}
defines.AddShaderChunk("#define _ALPHATEST_ON 1", true);
activeFields.Add("AlphaTest");
}
// if (kTesselationMode != TessellationMode.None)

// #pragma shader_feature _HEIGHTMAP
// #pragma shader_feature _TANGENTMAP
// #pragma shader_feature _ANISOTROPYMAP
// #pragma shader_feature _DETAIL_MAP // MOVE to a node
// #pragma shader_feature _SUBSURFACE_RADIUS_MAP
// #pragma shader_feature _THICKNESSMAP
// #pragma shader_feature _SPECULARCOLORMAP

if (masterNode.surfaceType != SurfaceType.Opaque)
{
// transparent-only defines
defines.AddShaderChunk("#define _SURFACE_TYPE_TRANSPARENT 1", true);
activeFields.Add("SurfaceType.Transparent");
defines.AddShaderChunk("#define _BLENDMODE_ALPHA 1", true);
activeFields.Add("BlendMode.Alpha");
defines.AddShaderChunk("#define _BLENDMODE_ADD 1", true);
activeFields.Add("BlendMode.Add");
}
// else if (masterNode.alphaMode == PBRMasterNode.AlphaMode.PremultiplyAlpha) // TODO
// {

// TODO: We should have this keyword only if VelocityInGBuffer is enable, how to do that ?
//#pragma multi_compile VELOCITYOUTPUT_OFF VELOCITYOUTPUT_ON
return defines.GetShaderString(2);
return activeFields;
private static bool GenerateShaderPass(UnlitMasterNode masterNode, Pass pass, GenerationMode mode, SurfaceMaterialOptions materialOptions, ShaderGenerator result, List<string> sourceAssetDependencyPaths)
private static bool GenerateShaderPassUnlit(AbstractMaterialNode masterNode, Pass pass, GenerationMode mode, SurfaceMaterialOptions materialOptions, ShaderGenerator result, List<string> sourceAssetDependencyPaths)
{
var templateLocation = Path.Combine(Path.Combine(Path.Combine(HDEditorUtils.GetHDRenderPipelinePath(), "Editor"), "ShaderGraph"), pass.TemplateName);
if (!File.Exists(templateLocation))

}
sourceAssetDependencyPaths.Add(templateLocation);
if (sourceAssetDependencyPaths != null)
sourceAssetDependencyPaths.Add(templateLocation);
// grab all of the active nodes (for pixel and vertex graphs)
var vertexNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(vertexNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.VertexShaderSlots);
// grab all of the active nodes
var activeNodeList = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(activeNodeList, masterNode, NodeUtils.IncludeSelf.Include, pass.PixelShaderSlots);
var pixelNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(pixelNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.PixelShaderSlots);
var graphRequirements = ShaderGraphRequirements.FromNodes(activeNodeList, ShaderStageCapability.All, true, true);
var pixelRequirements = ShaderGraphRequirements.FromNodes(pixelNodes, ShaderStageCapability.Fragment, false); // TODO: is ShaderStageCapability.Fragment correct?
var vertexRequirements = ShaderGraphRequirements.FromNodes(vertexNodes, ShaderStageCapability.Vertex, false);
// Function Registry tracks functions to remove duplicates, it wraps a string builder that stores the combined function string
// TODO: this can be a shared function for all HDRP master nodes -- From here through GraphUtil.GenerateSurfaceDescription(..)
// TODO: this can be a shared function -- From here through GraphUtil.GenerateSurfaceDescription(..)
var activeSlots = new List<MaterialSlot>();
foreach (var id in pass.PixelShaderSlots)
{
MaterialSlot slot = masterNode.FindSlot<MaterialSlot>(id);
if (slot != null)
{
activeSlots.Add(slot);
}
}
var pixelSlots = HDSubShaderUtilities.FindMaterialSlotsOnNode(pass.PixelShaderSlots, masterNode);
var vertexSlots = HDSubShaderUtilities.FindMaterialSlotsOnNode(pass.VertexShaderSlots, masterNode);
// properties used by either pixel and vertex shader
PropertyCollector sharedProperties = new PropertyCollector();
string graphInputStructName = "SurfaceDescriptionInputs";
string graphOutputStructName = "SurfaceDescription";
string graphEvalFunctionName = "SurfaceDescriptionFunction";
var graphEvalFunction = new ShaderStringBuilder();
var graphOutputs = new ShaderStringBuilder();
PropertyCollector graphProperties = new PropertyCollector();
string pixelGraphInputStructName = "SurfaceDescriptionInputs";
string pixelGraphOutputStructName = "SurfaceDescription";
string pixelGraphEvalFunctionName = "SurfaceDescriptionFunction";
ShaderStringBuilder pixelGraphEvalFunction = new ShaderStringBuilder();
ShaderStringBuilder pixelGraphOutputs = new ShaderStringBuilder();
// dependency tracker -- set of active fields
HashSet<string> activeFields = GetActiveFieldsFromMasterNode(masterNode, pass);
// build initial requirements
HDRPShaderStructs.AddActiveFieldsFromPixelGraphRequirements(activeFields, pixelRequirements);
HashSet<string> activeFields = new HashSet<string>();
GraphUtil.GenerateSurfaceDescriptionStruct(graphOutputs, activeSlots, true);
GraphUtil.GenerateSurfaceDescriptionStruct(pixelGraphOutputs, pixelSlots, true, pixelGraphOutputStructName, activeFields);
activeNodeList,
pixelNodes,
graphEvalFunction,
pixelGraphEvalFunction,
graphProperties,
graphRequirements, // TODO : REMOVE UNUSED
sharedProperties,
pixelRequirements, // TODO : REMOVE UNUSED
graphEvalFunctionName,
graphOutputStructName,
pixelGraphEvalFunctionName,
pixelGraphOutputStructName,
activeSlots,
graphInputStructName);
pixelSlots,
pixelGraphInputStructName);
string vertexGraphInputStructName = "VertexDescriptionInputs";
string vertexGraphOutputStructName = "VertexDescription";
string vertexGraphEvalFunctionName = "VertexDescriptionFunction";
ShaderStringBuilder vertexGraphEvalFunction = new ShaderStringBuilder();
ShaderStringBuilder vertexGraphOutputs = new ShaderStringBuilder();
// check for vertex animation -- enables HAVE_VERTEX_MODIFICATION
bool vertexActive = false;
if (masterNode.IsSlotConnected(PBRMasterNode.PositionSlotId))
{
vertexActive = true;
activeFields.Add("features.modifyMesh");
HDRPShaderStructs.AddActiveFieldsFromVertexGraphRequirements(activeFields, vertexRequirements);
// -------------------------------------
// Generate Output structure for Vertex Description function
GraphUtil.GenerateVertexDescriptionStruct(vertexGraphOutputs, vertexSlots, vertexGraphOutputStructName, activeFields);
// -------------------------------------
// Generate Vertex Description function
GraphUtil.GenerateVertexDescriptionFunction(
masterNode.owner as AbstractMaterialGraph,
vertexGraphEvalFunction,
functionRegistry,
sharedProperties,
mode,
vertexNodes,
vertexSlots,
vertexGraphInputStructName,
vertexGraphEvalFunctionName,
vertexGraphOutputStructName);
}
var blendCode = new ShaderStringBuilder();
var cullCode = new ShaderStringBuilder();

var colorMaskCode = new ShaderStringBuilder();
HDSubShaderUtilities.BuildRenderStatesFromPassAndMaterialOptions(pass, materialOptions, blendCode, cullCode, zTestCode, zWriteCode, stencilCode, colorMaskCode);
if (masterNode.twoSided.isOn)
{
activeFields.Add("DoubleSided");
if (pass.ShaderPassName != "SHADERPASS_VELOCITY") // HACK to get around lack of a good interpolator dependency system
{ // we need to be able to build interpolators using multiple input structs
// also: should only require isFrontFace if Normals are required...
activeFields.Add("DoubleSided.Mirror"); // TODO: change this depending on what kind of normal flip you want..
activeFields.Add("FragInputs.isFrontFace"); // will need this for determining normal flip mode
}
}
HDRPShaderStructs.AddRequiredFields(pass.RequiredFields, activeFields);
if (pass.PixelShaderSlots != null)
{
foreach (var slotId in pass.PixelShaderSlots)
{
var slot = masterNode.FindSlot<MaterialSlot>(slotId);
if (slot != null)
{
var rawSlotName = slot.RawDisplayName().ToString();
var descriptionVar = string.Format("{0}.{1}", graphOutputStructName, rawSlotName);
activeFields.Add(descriptionVar);
}
}
}
// apply dependencies to the active fields, and build interpolators (TODO: split this function)
var graphInputs = new ShaderGenerator();
graphInputs,
graphRequirements,
pass.RequiredFields,
CoordinateSpace.World,
activeFields);
// debug output all active fields

}
}
// build graph inputs structures
ShaderGenerator pixelGraphInputs = new ShaderGenerator();
ShaderSpliceUtil.BuildType(typeof(HDRPShaderStructs.SurfaceDescriptionInputs), activeFields, pixelGraphInputs);
ShaderGenerator vertexGraphInputs = new ShaderGenerator();
ShaderSpliceUtil.BuildType(typeof(HDRPShaderStructs.VertexDescriptionInputs), activeFields, vertexGraphInputs);
ShaderGenerator defines = new ShaderGenerator();
{
defines.AddShaderChunk(string.Format("#define SHADERPASS {0}", pass.ShaderPassName), true);

// build graph code
var graph = new ShaderGenerator();
graph.AddShaderChunk("// Graph Inputs");
graph.Indent();
graph.AddGenerator(graphInputs);
graph.Deindent();
graph.AddShaderChunk("// Graph Outputs");
graph.Indent();
graph.AddShaderChunk(graphOutputs.ToString());
//graph.AddGenerator(graphOutputs);
graph.Deindent();
graph.AddShaderChunk("// Graph Properties (uniform inputs)");
graph.AddShaderChunk(graphProperties.GetPropertiesDeclaration(1));
graph.AddShaderChunk("// Graph Node Functions");
graph.AddShaderChunk(graphNodeFunctions.ToString());
graph.AddShaderChunk("// Graph Evaluation");
graph.Indent();
graph.AddShaderChunk(graphEvalFunction.ToString());
//graph.AddGenerator(graphEvalFunction);
graph.Deindent();
{
graph.AddShaderChunk("// Shared Graph Properties (uniform inputs)");
graph.AddShaderChunk(sharedProperties.GetPropertiesDeclaration(1));
if (vertexActive)
{
graph.AddShaderChunk("// Vertex Graph Inputs");
graph.Indent();
graph.AddGenerator(vertexGraphInputs);
graph.Deindent();
graph.AddShaderChunk("// Vertex Graph Outputs");
graph.Indent();
graph.AddShaderChunk(vertexGraphOutputs.ToString());
graph.Deindent();
}
graph.AddShaderChunk("// Pixel Graph Inputs");
graph.Indent();
graph.AddGenerator(pixelGraphInputs);
graph.Deindent();
graph.AddShaderChunk("// Pixel Graph Outputs");
graph.Indent();
graph.AddShaderChunk(pixelGraphOutputs.ToString());
graph.Deindent();
graph.AddShaderChunk("// Shared Graph Node Functions");
graph.AddShaderChunk(graphNodeFunctions.ToString());
if (vertexActive)
{
graph.AddShaderChunk("// Vertex Graph Evaluation");
graph.Indent();
graph.AddShaderChunk(vertexGraphEvalFunction.ToString());
graph.Deindent();
}
graph.AddShaderChunk("// Pixel Graph Evaluation");
graph.Indent();
graph.AddShaderChunk(pixelGraphEvalFunction.ToString());
graph.Deindent();
}
// build the hash table of all named fragments TODO: could make this Dictionary<string, ShaderGenerator / string> ?
Dictionary<string, string> namedFragments = new Dictionary<string, string>();

namedFragments.Add("${Stencil}", stencilCode.ToString());
namedFragments.Add("${ColorMask}", colorMaskCode.ToString());
namedFragments.Add("${LOD}", materialOptions.lod.ToString());
namedFragments.Add("${VariantDefines}", GetVariantDefines(masterNode));
// process the template to generate the shader code for this pass TODO: could make this a shared function
string[] templateLines = File.ReadAllLines(templateLocation);

// bool transparent = (masterNode.surfaceType != SurfaceType.Opaque);
bool distortionActive = false;
GenerateShaderPass(masterNode, m_PassDepthOnly, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassForward, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassMETA, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassUnlit(masterNode, m_PassDepthOnly, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassUnlit(masterNode, m_PassForward, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassUnlit(masterNode, m_PassMETA, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPass(masterNode, m_PassDistortion, mode, materialOptions, subShader, sourceAssetDependencyPaths);
GenerateShaderPassUnlit(masterNode, m_PassDistortion, mode, materialOptions, subShader, sourceAssetDependencyPaths);
}
}
subShader.Deindent();

13
com.unity.render-pipelines.high-definition/HDRP/Editor/Upgraders/HDRPVersion.cs


[InitializeOnLoad]
public class HDRPVersion
{
static public float hdrpVersion = 1.0f;
static public int hdrpVersion = 1;
static public float GetCurrentHDRPProjectVersion()
static public int GetCurrentHDRPProjectVersion()
version[0] = "0.9"; // Note: When we don't know what a project is, assume worst case
try
{

{
Debug.LogWarning("Unable to read from ProjectSettings/HDRPProjectVersion.txt - Assign default version value");
// Don't display warning
//Debug.LogWarning("Unable to read from ProjectSettings/HDRPProjectVersion.txt - Assign default version value");
// When we don't find HDRPProjectVersion file we return the current value. Because this happen when you create new project.
return hdrpVersion;
return float.Parse(version[0]);
return int.Parse(version[0]);
}
static public void WriteCurrentHDRPProjectVersion()

14
com.unity.render-pipelines.high-definition/HDRP/Editor/Upgraders/UpgradeMenuItem.cs


string.Format("{0} / {1} materials subsurface updated.", i, length),
i / (float)(length - 1));
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
if (mat.shader.name == "HDRenderPipeline/LitTessellation" ||
mat.shader.name == "HDRenderPipeline/Lit" ||

if (mat.HasProperty("_SSSAndTransmissionType"))
{
CoreUtils.CheckOutFile(VSCEnabled, mat);
CoreEditorUtils.CheckOutFile(VCSEnabled, mat);
int materialSSSAndTransmissionID = mat.GetInt("_SSSAndTransmissionType");

string.Format("{0} / {1} materials updated.", i, length),
i / (float)(length - 1));
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
if (mat.shader.name == "HDRenderPipeline/LitTessellation" ||
mat.shader.name == "HDRenderPipeline/Lit")

{
CoreUtils.CheckOutFile(VSCEnabled, mat);
CoreEditorUtils.CheckOutFile(VCSEnabled, mat);
float valueMax = mat.GetFloat("_HeightMax");
float valueMin = mat.GetFloat("_HeightMin");

if (mat.HasProperty("_HeightPoMAmplitude0"))
{
CoreUtils.CheckOutFile(VSCEnabled, mat);
CoreEditorUtils.CheckOutFile(VCSEnabled, mat);
for (int x = 0; x < numLayer; ++x)
{

static void UpdateMaterialToNewerVersion(string caption, UpdateMaterial updateMaterial, UpdateMaterialFile updateMaterialFile = null)
{
bool VSCEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
bool VCSEnabled = (UnityEditor.VersionControl.Provider.enabled && UnityEditor.VersionControl.Provider.isActive);
var matIds = AssetDatabase.FindAssets("t:Material");
List<string> materialFiles = new List<string>(); // Contain the list dirty files

if (dirty)
{
// Checkout the file and tag it as dirty
CoreUtils.CheckOutFile(VSCEnabled, mat);
CoreEditorUtils.CheckOutFile(VCSEnabled, mat);
EditorUtility.SetDirty(mat);
materialFiles.Add(path);
}

2
com.unity.render-pipelines.high-definition/HDRP/Material/LayeredLit/LayeredLit.shader


HLSLPROGRAM
// Note: Require _ObjectId and _PassValue variables
#define SHADERPASS SHADERPASS_DEPTH_ONLY
#define SCENESELECTIONPASS // This will drive the output of the scene selection shader
#include "../../ShaderVariables.hlsl"

2
com.unity.render-pipelines.high-definition/HDRP/Material/LayeredLit/LayeredLitTessellation.shader


HLSLPROGRAM
// Note: Require _ObjectId and _PassValue variables
#pragma hull Hull
#pragma domain Domain

2
com.unity.render-pipelines.high-definition/HDRP/Material/Lit/Lit.shader


HLSLPROGRAM
// Note: Require _ObjectId and _PassValue variables
// We reuse depth prepass for the scene selection, allow to handle alpha correctly as well as tessellation and vertex animation
#define SHADERPASS SHADERPASS_DEPTH_ONLY
#define SCENESELECTIONPASS // This will drive the output of the scene selection shader

2
com.unity.render-pipelines.high-definition/HDRP/Material/Lit/LitTessellation.shader


HLSLPROGRAM
// Note: Require _ObjectId and _PassValue variables
#pragma hull Hull
#pragma domain Domain

23
com.unity.render-pipelines.high-definition/HDRP/Material/StackLit/StackLit.shader


// This tags allow to use the shader replacement features
Tags{ "RenderPipeline" = "HDRenderPipeline" "RenderType" = "HDStackLitShader" }
// Caution: The outline selection in the editor use the vertex shader/hull/domain shader of the first pass declare. So it should not be the meta pass.
Pass
{
Name "SceneSelectionPass" // Name is not used
Tags { "LightMode" = "SceneSelectionPass" }
Cull Off
HLSLPROGRAM
// Note: Require _ObjectId and _PassValue variables
// We reuse depth prepass for the scene selection, allow to handle alpha correctly as well as tessellation and vertex animation
#define SHADERPASS SHADERPASS_DEPTH_ONLY
#define SCENESELECTIONPASS // This will drive the output of the scene selection shader
#include "../../ShaderVariables.hlsl"
#include "../../Material/Material.hlsl"
#include "ShaderPass/StackLitDepthPass.hlsl"
#include "StackLitData.hlsl"
#include "../../ShaderPass/ShaderPassDepthOnly.hlsl"
ENDHLSL
}
Pass
{

4
com.unity.render-pipelines.high-definition/HDRP/Material/StackLit/StackLitProperties.hlsl


// TODO: Fix the code in legacy unity so we can customize the behavior for GI
float3 _EmissionColor;
// Following two variables are feeded by the C++ Editor for Scene selection
int _ObjectId;
int _PassValue;
CBUFFER_END

2
com.unity.render-pipelines.high-definition/HDRP/Material/Unlit/Unlit.shader


HLSLPROGRAM
// Note: Require _ObjectId and _PassValue variables
#define SHADERPASS SHADERPASS_DEPTH_ONLY
#define SCENESELECTIONPASS // This will drive the output of the scene selection shader
#include "../../Material/Material.hlsl"

1
com.unity.render-pipelines.high-definition/HDRP/RenderPipeline/Settings/RenderPipelineSettings.cs


public bool supportOnlyForward = false;
public bool enableUltraQualitySSS = false;
public bool supportVolumetric = true;
public bool supportRuntimeDebugDisplay = true;
// Engine
public bool supportDBuffer = false;

12
com.unity.render-pipelines.high-definition/HDRP/ShaderPass/ShaderPassVelocity.hlsl


else
{
bool hasDeformation = unity_MotionVectorsParams.x > 0.0; // Skin or morph target
//Need to apply any vertex animation to the previous worldspace position, if we want it to show up in the velocity buffer
// Need to apply any vertex animation to the previous worldspace position, if we want it to show up in the velocity buffer
#if defined(HAVE_MESH_MODIFICATION)
AttributesMesh previousMesh = inputMesh;
if (hasDeformation)
previousMesh.positionOS = inputPass.previousPositionOS;
previousMesh = ApplyMeshModification(previousMesh);
float3 previousPositionWS = mul(unity_MatrixPreviousM, float4(previousMesh.positionOS, 1.0)).xyz;
#else
#endif
#ifdef ATTRIBUTES_NEED_NORMAL
float3 normalWS = TransformPreviousObjectToWorldNormal(inputMesh.normalOS);
#else

4
com.unity.render-pipelines.high-definition/HDRP/ShaderPass/VertMesh.hlsl


// TODO: Here we will also have all the vertex deformation (GPU skinning, vertex animation, morph target...) or we will need to generate a compute shaders instead (better! but require work to deal with unpacking like fp16)
VaryingsMeshType VertMesh(AttributesMesh input)
{
#if defined(HAVE_MESH_MODIFICATION)
input = ApplyMeshModification(input);
#endif
VaryingsMeshType output;
UNITY_SETUP_INSTANCE_ID(input);

58
com.unity.render-pipelines.lightweight/LWRP/Editor/LightweightLightEditor.cs


[CustomEditorForRenderPipeline(typeof(Light), typeof(LightweightPipelineAsset))]
class LightweightLightEditor : LightEditor
{
AnimBool m_AnimShowSpotOptions = new AnimBool();
AnimBool m_AnimShowPointOptions = new AnimBool();
AnimBool m_AnimShowDirOptions = new AnimBool();
AnimBool m_AnimShowAreaOptions = new AnimBool();
AnimBool m_AnimShowRuntimeOptions = new AnimBool();
AnimBool m_AnimShowShadowOptions = new AnimBool();
AnimBool m_AnimBakedShadowAngleOptions = new AnimBool();
AnimBool m_AnimBakedShadowRadiusOptions = new AnimBool();
AnimBool m_AnimShowLightBounceIntensity = new AnimBool();
AnimBool m_AnimSpotOptions = new AnimBool();
AnimBool m_AnimPointOptions = new AnimBool();
AnimBool m_AnimDirOptions = new AnimBool();
AnimBool m_AnimAreaOptions = new AnimBool();
AnimBool m_AnimRuntimeOptions = new AnimBool();
AnimBool m_AnimShadowOptions = new AnimBool();
AnimBool m_AnimShadowAngleOptions = new AnimBool();
AnimBool m_AnimShadowRadiusOptions = new AnimBool();
AnimBool m_AnimLightBounceIntensity = new AnimBool();
class Styles
{

// When we are switching between two light types that don't show the range (directional and area lights)
// we want the fade group to stay hidden.
using (var group = new EditorGUILayout.FadeGroupScope(1.0f - m_AnimShowDirOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(1.0f - m_AnimDirOptions.faded))
settings.DrawRange(m_AnimShowAreaOptions.target);
settings.DrawRange(m_AnimAreaOptions.target);
using (var group = new EditorGUILayout.FadeGroupScope(m_AnimShowSpotOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(m_AnimSpotOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(m_AnimShowAreaOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(m_AnimAreaOptions.faded))
if (group.visible)
settings.DrawArea();

using (var group = new EditorGUILayout.FadeGroupScope(1.0f - m_AnimShowAreaOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(1.0f - m_AnimAreaOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(m_AnimShowLightBounceIntensity.faded))
using (var group = new EditorGUILayout.FadeGroupScope(m_AnimLightBounceIntensity.faded))
if (group.visible)
settings.DrawBounceIntensity();

void UpdateShowOptions(bool initialize)
{
SetOptions(m_AnimShowSpotOptions, initialize, spotOptionsValue);
SetOptions(m_AnimShowPointOptions, initialize, pointOptionsValue);
SetOptions(m_AnimShowDirOptions, initialize, dirOptionsValue);
SetOptions(m_AnimShowAreaOptions, initialize, areaOptionsValue);
SetOptions(m_AnimShowShadowOptions, initialize, shadowOptionsValue);
SetOptions(m_AnimShowRuntimeOptions, initialize, runtimeOptionsValue);
SetOptions(m_AnimBakedShadowAngleOptions, initialize, bakedShadowAngle);
SetOptions(m_AnimBakedShadowRadiusOptions, initialize, bakedShadowRadius);
SetOptions(m_AnimShowLightBounceIntensity, initialize, showLightBounceIntensity);
SetOptions(m_AnimSpotOptions, initialize, spotOptionsValue);
SetOptions(m_AnimPointOptions, initialize, pointOptionsValue);
SetOptions(m_AnimDirOptions, initialize, dirOptionsValue);
SetOptions(m_AnimAreaOptions, initialize, areaOptionsValue);
SetOptions(m_AnimShadowOptions, initialize, shadowOptionsValue);
SetOptions(m_AnimRuntimeOptions, initialize, runtimeOptionsValue);
SetOptions(m_AnimShadowAngleOptions, initialize, bakedShadowAngle);
SetOptions(m_AnimShadowRadiusOptions, initialize, bakedShadowRadius);
SetOptions(m_AnimLightBounceIntensity, initialize, showLightBounceIntensity);
}
void DrawSpotAngle()

void ShadowsGUI()
{
// Shadows drop-down. Area lights can only be baked and always have shadows.
float show = 1.0f - m_AnimShowAreaOptions.faded;
float show = 1.0f - m_AnimAreaOptions.faded;
show *= m_AnimShowShadowOptions.faded;
show *= m_AnimShadowOptions.faded;
using (var group = new EditorGUILayout.FadeGroupScope(show * m_AnimBakedShadowRadiusOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(show * m_AnimShadowRadiusOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(show * m_AnimBakedShadowAngleOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(show * m_AnimShadowAngleOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(show * m_AnimShowRuntimeOptions.faded))
using (var group = new EditorGUILayout.FadeGroupScope(show * m_AnimRuntimeOptions.faded))
if (group.visible)
settings.DrawRuntimeShadow();
EditorGUI.indentLevel -= 1;

16
com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/LightWeightPBRSubShader.cs


// Get Slot and Node lists per stage
var vertexSlots = pass.VertexShaderSlots.Select(masterNode.FindSlot<MaterialSlot>).ToList();
var vertexNodes = ListPool<AbstractMaterialNode>.Get();
var vertexNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(vertexNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.VertexShaderSlots);
var pixelSlots = pass.PixelShaderSlots.Select(masterNode.FindSlot<MaterialSlot>).ToList();

if (surfaceRequirements.requiresScreenPosition)
surfaceDescriptionInputStruct.AppendLine("float4 {0};", ShaderGeneratorNames.ScreenPosition);
if (surfaceRequirements.requiresFaceSign)
surfaceDescriptionInputStruct.AppendLine("float {0};", ShaderGeneratorNames.FaceSign);
foreach (var channel in surfaceRequirements.requiresMeshUVs.Distinct())
surfaceDescriptionInputStruct.AppendLine("half4 {0};", channel.GetUVName());
}

pixelShaderSurfaceRemap.AppendLine("{0} = surf.{0};", slot.shaderOutputName);
}
// -------------------------------------
// Extra pixel shader work
var faceSign = new ShaderStringBuilder();
if (pixelRequirements.requiresFaceSign)
faceSign.AppendLine(", half FaceSign : VFACE");
// ----------------------------------------------------- //
// FINALIZE //
// ----------------------------------------------------- //

resultPass = resultPass.Replace("${VertexShaderDescriptionInputs}", vertexShaderDescriptionInputs.ToString());
resultPass = resultPass.Replace("${VertexShaderOutputs}", vertexShaderOutputs.ToString());
resultPass = resultPass.Replace("${FaceSign}", faceSign.ToString());
resultPass = resultPass.Replace("${PixelShader}", pixelShader.ToString());
resultPass = resultPass.Replace("${PixelShaderSurfaceInputs}", pixelShaderSurfaceInputs.ToString());
resultPass = resultPass.Replace("${PixelShaderSurfaceRemap}", pixelShaderSurfaceRemap.ToString());

// Get Slot and Node lists per stage
var vertexSlots = pass.VertexShaderSlots.Select(masterNode.FindSlot<MaterialSlot>).ToList();
var vertexNodes = ListPool<AbstractMaterialNode>.Get();
var vertexNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(vertexNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.VertexShaderSlots);
// -------------------------------------

16
com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/LightWeightUnlitSubShader.cs


// Get Slot and Node lists per stage
var vertexSlots = pass.VertexShaderSlots.Select(masterNode.FindSlot<MaterialSlot>).ToList();
var vertexNodes = ListPool<AbstractMaterialNode>.Get();
var vertexNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(vertexNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.VertexShaderSlots);
var pixelSlots = pass.PixelShaderSlots.Select(masterNode.FindSlot<MaterialSlot>).ToList();

if (surfaceRequirements.requiresScreenPosition)
surfaceDescriptionInputStruct.AppendLine("float4 {0};", ShaderGeneratorNames.ScreenPosition);
if (surfaceRequirements.requiresFaceSign)
surfaceDescriptionInputStruct.AppendLine("float {0};", ShaderGeneratorNames.FaceSign);
foreach (var channel in surfaceRequirements.requiresMeshUVs.Distinct())
surfaceDescriptionInputStruct.AppendLine("half4 {0};", channel.GetUVName());
}

pixelShaderSurfaceRemap.AppendLine("{0} = surf.{0};", slot.shaderOutputName);
}
// -------------------------------------
// Extra pixel shader work
var faceSign = new ShaderStringBuilder();
if (pixelRequirements.requiresFaceSign)
faceSign.AppendLine(", half FaceSign : VFACE");
// ----------------------------------------------------- //
// FINALIZE //
// ----------------------------------------------------- //

resultPass = resultPass.Replace("${VertexShaderDescriptionInputs}", vertexShaderDescriptionInputs.ToString());
resultPass = resultPass.Replace("${VertexShaderOutputs}", vertexShaderOutputs.ToString());
resultPass = resultPass.Replace("${FaceSign}", faceSign.ToString());
resultPass = resultPass.Replace("${PixelShader}", pixelShader.ToString());
resultPass = resultPass.Replace("${PixelShaderSurfaceInputs}", pixelShaderSurfaceInputs.ToString());
resultPass = resultPass.Replace("${PixelShaderSurfaceRemap}", pixelShaderSurfaceRemap.ToString());

// Get Slot and Node lists per stage
var vertexSlots = pass.VertexShaderSlots.Select(masterNode.FindSlot<MaterialSlot>).ToList();
var vertexNodes = ListPool<AbstractMaterialNode>.Get();
var vertexNodes = ListPool<INode>.Get();
NodeUtils.DepthFirstCollectNodesFromNode(vertexNodes, masterNode, NodeUtils.IncludeSelf.Include, pass.VertexShaderSlots);
// -------------------------------------

2
com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/lightweightPBRForwardPass.template


return o;
}
half4 frag (GraphVertexOutput IN) : SV_Target
half4 frag (GraphVertexOutput IN ${FaceSign}) : SV_Target
{
UNITY_SETUP_INSTANCE_ID(IN);

2
com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderGraph/lightweightUnlitPass.template


return o;
}
half4 frag (GraphVertexOutput IN) : SV_Target
half4 frag (GraphVertexOutput IN ${FaceSign}) : SV_Target
{
UNITY_SETUP_INSTANCE_ID(IN);

38
com.unity.render-pipelines.lightweight/LWRP/Editor/ShaderPreprocessor.cs


namespace UnityEditor.Experimental.Rendering.LightweightPipeline
{
public static class LightweightKeyword
{
public static readonly ShaderKeyword AdditionalLights = new ShaderKeyword(LightweightKeywordStrings.AdditionalLights);
public static readonly ShaderKeyword VertexLights = new ShaderKeyword(LightweightKeywordStrings.VertexLights);
public static readonly ShaderKeyword MixedLightingSubtractive = new ShaderKeyword(LightweightKeywordStrings.MixedLightingSubtractive);
public static readonly ShaderKeyword MainLightCookie = new ShaderKeyword(LightweightKeywordStrings.MainLightCookie);
public static readonly ShaderKeyword DirectionalShadows = new ShaderKeyword(LightweightKeywordStrings.DirectionalShadows);
public static readonly ShaderKeyword LocalShadows = new ShaderKeyword(LightweightKeywordStrings.LocalShadows);
public static readonly ShaderKeyword SoftShadows = new ShaderKeyword(LightweightKeywordStrings.SoftShadows);
public static readonly ShaderKeyword Lightmap = new ShaderKeyword("LIGHTMAP_ON");
public static readonly ShaderKeyword DirectionalLightmap = new ShaderKeyword("DIRLIGHTMAP_COMBINED");
}
public class ShaderPreprocessor : IPreprocessShaders
{
#if LOG_VARIANTS

bool StripUnusedVariant(PipelineCapabilities capabilities, ShaderCompilerData compilerData)
{
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.AdditionalLights) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.AdditionalLights) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.VertexLights) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.VertexLights) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.DirectionalShadows) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.DirectionalShadows) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.LocalShadows) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.LocalShadows) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.SoftShadows) &&
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.SoftShadows) &&
!CoreUtils.HasFlag(capabilities, PipelineCapabilities.SoftShadows))
return true;

bool StripInvalidVariants(ShaderCompilerData compilerData)
{
bool isShadowVariant = compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.DirectionalShadows) ||
compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.LocalShadows);
bool isShadowVariant = compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.DirectionalShadows) ||
compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.LocalShadows);
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.SoftShadows) && !isShadowVariant)
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.SoftShadows) && !isShadowVariant)
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.VertexLights) &&
!compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.AdditionalLights))
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.VertexLights) &&
!compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.AdditionalLights))
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.DirectionalLightmap) &&
!compilerData.shaderKeywordSet.IsEnabled(LightweightKeywords.Lightmap))
if (compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.DirectionalLightmap) &&
!compilerData.shaderKeywordSet.IsEnabled(LightweightKeyword.Lightmap))
return true;
return false;

22
com.unity.render-pipelines.lightweight/LWRP/LightweightForwardRenderer.cs


EnqueuePass(cmd, RenderPassHandles.LocalShadows, baseDescriptor);
bool requiresDepthAttachment = requiresCameraDepth && !requiresDepthPrepass;
bool requiresColorAttachment = RequiresColorAttachment(ref renderingData.cameraData, baseDescriptor) || requiresDepthAttachment;
bool requiresColorAttachment = RequiresIntermediateColorTexture(ref renderingData.cameraData, baseDescriptor, requiresDepthAttachment);
int[] colorHandles = (requiresColorAttachment) ? new[] {RenderTargetHandles.Color} : null;
int depthHandle = (requiresColorAttachment) ? RenderTargetHandles.DepthAttachment : -1;
EnqueuePass(cmd, RenderPassHandles.ForwardLit, baseDescriptor, colorHandles, depthHandle, renderingData.cameraData.msaaSamples);

// Note: Scene view camera always perform depth prepass
CommandBuffer cmd = CommandBufferPool.Get("Copy Depth to Camera");
CoreUtils.SetRenderTarget(cmd, BuiltinRenderTextureType.CameraTarget);
cmd.EnableShaderKeyword(LightweightKeywords.DepthNoMsaa);
cmd.DisableShaderKeyword(LightweightKeywords.DepthMsaa2);
cmd.DisableShaderKeyword(LightweightKeywords.DepthMsaa4);
cmd.EnableShaderKeyword(LightweightKeywordStrings.DepthNoMsaa);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthMsaa2);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthMsaa4);
cmd.Blit(GetSurface(RenderTargetHandles.DepthTexture), BuiltinRenderTextureType.CameraTarget, GetMaterial(MaterialHandles.DepthCopy));
context.ExecuteCommandBuffer(cmd);
CommandBufferPool.Release(cmd);

public RenderTargetIdentifier GetSurface(int handle)
{
if (handle == -1)
return BuiltinRenderTextureType.CameraTarget;
if (handle < 0 || !m_ResourceMap.TryGetValue(handle, out renderTargetID))
if (!m_ResourceMap.TryGetValue(handle, out renderTargetID))
{
Debug.LogError(string.Format("Handle {0} has not any surface registered to it.", handle));
return new RenderTargetIdentifier();

m_ActiveRenderPassQueue.Add(pass);
}
bool RequiresColorAttachment(ref CameraData cameraData, RenderTextureDescriptor baseDescriptor)
bool RequiresIntermediateColorTexture(ref CameraData cameraData, RenderTextureDescriptor baseDescriptor, bool requiresCameraDepth)
if (cameraData.isOffscreenRender)
return false;
return cameraData.isSceneViewCamera || isScaledRender || cameraData.isHdrEnabled ||
cameraData.postProcessEnabled || cameraData.requiresOpaqueTexture || isTargetTexture2DArray;
return requiresCameraDepth || cameraData.isSceneViewCamera || isScaledRender || cameraData.isHdrEnabled ||
cameraData.postProcessEnabled || cameraData.requiresOpaqueTexture || isTargetTexture2DArray || !cameraData.isDefaultViewport;
}
bool CanCopyDepth(ref CameraData cameraData)

4
com.unity.render-pipelines.lightweight/LWRP/LightweightPipeline.cs


context.ExecuteCommandBuffer(cmd);
cmd.Clear();
#if UNITY_EDITOR
#endif
{
m_IsCameraRendering = true;
#if UNITY_EDITOR

m_Renderer.Setup(ref context, ref m_CullResults, ref renderingData);
m_Renderer.Execute(ref context, ref m_CullResults, ref renderingData);
}
#if UNITY_EDITOR
catch (Exception)
{
CommandBufferPool.Release(cmd);

#endif
{
m_IsCameraRendering = false;
}

30
com.unity.render-pipelines.lightweight/LWRP/LightweightPipelineCore.cs


using System.Collections.Generic;
using UnityEngine.Rendering;
using UnityEngine.Rendering.PostProcessing;
using UnityEngine.XR;
namespace UnityEngine.Experimental.Rendering.LightweightPipeline
{

}
}
public static class LightweightKeywords
public static class LightweightKeywordStrings
public static readonly string AdditionalLightsText = "_ADDITIONAL_LIGHTS";
public static readonly string VertexLightsText = "_VERTEX_LIGHTS";
public static readonly string MixedLightingSubtractiveText = "_MIXED_LIGHTING_SUBTRACTIVE";
public static readonly string MainLightCookieText = "_MAIN_LIGHT_COOKIE";
public static readonly string DirectionalShadowsText = "_SHADOWS_ENABLED";
public static readonly string LocalShadowsText = "_LOCAL_SHADOWS_ENABLED";
public static readonly string SoftShadowsText = "_SHADOWS_SOFT";
public static readonly string CascadeShadowsText = "_SHADOWS_CASCADE";
public static readonly string AdditionalLights = "_ADDITIONAL_LIGHTS";
public static readonly string VertexLights = "_VERTEX_LIGHTS";
public static readonly string MixedLightingSubtractive = "_MIXED_LIGHTING_SUBTRACTIVE";
public static readonly string MainLightCookie = "_MAIN_LIGHT_COOKIE";
public static readonly string DirectionalShadows = "_SHADOWS_ENABLED";
public static readonly string LocalShadows = "_LOCAL_SHADOWS_ENABLED";
public static readonly string SoftShadows = "_SHADOWS_SOFT";
public static readonly string CascadeShadows = "_SHADOWS_CASCADE";
public static readonly ShaderKeyword AdditionalLights = new ShaderKeyword(AdditionalLightsText);
public static readonly ShaderKeyword VertexLights = new ShaderKeyword(VertexLightsText);
public static readonly ShaderKeyword MixedLightingSubtractive = new ShaderKeyword(MixedLightingSubtractiveText);
public static readonly ShaderKeyword MainLightCookie = new ShaderKeyword(MainLightCookieText);
public static readonly ShaderKeyword DirectionalShadows = new ShaderKeyword(DirectionalShadowsText);
public static readonly ShaderKeyword LocalShadows = new ShaderKeyword(LocalShadowsText);
public static readonly ShaderKeyword SoftShadows = new ShaderKeyword(SoftShadowsText);
public static readonly ShaderKeyword Lightmap = new ShaderKeyword("LIGHTMAP_ON");
public static readonly ShaderKeyword DirectionalLightmap = new ShaderKeyword("DIRLIGHTMAP_COMBINED");
}
public partial class LightweightPipeline

3
com.unity.render-pipelines.lightweight/LWRP/Passes/DepthOnlyPass.cs


{
public class DepthOnlyPass : ScriptableRenderPass
{
const string k_SetupRenderTargetTag = "Setup Render Target";
const string k_DepthPrepassTag = "Depth Prepass";
int kDepthBufferBits = 32;

public override void Execute(ref ScriptableRenderContext context, ref CullResults cullResults, ref RenderingData renderingData)
{
CommandBuffer cmd = CommandBufferPool.Get(k_DepthPrepassTag);
using (new ProfilingSample(cmd, k_SetupRenderTargetTag))
using (new ProfilingSample(cmd, k_DepthPrepassTag))
{
SetRenderTarget(cmd, GetSurface(depthAttachmentHandle), RenderBufferLoadAction.DontCare, RenderBufferStoreAction.Store,
ClearFlag.Depth, Color.black);

3
com.unity.render-pipelines.lightweight/LWRP/Passes/DirectionalShadowsPass.cs


ShadowSliceData[] m_CascadeSlices;
Vector4[] m_CascadeSplitDistances;
const string k_SetupRenderTargetTag = "Setup Render Target";
const string k_RenderDirectionalShadowmapTag = "Render Directional Shadowmap";
public DirectionalShadowsPass(LightweightForwardRenderer renderer) : base(renderer)

return;
CommandBuffer cmd = CommandBufferPool.Get(k_RenderDirectionalShadowmapTag);
using (new ProfilingSample(cmd, k_SetupRenderTargetTag))
using (new ProfilingSample(cmd, k_RenderDirectionalShadowmapTag))
{
m_ShadowCasterCascadesCount = shadowData.directionalLightCascadeCount;

49
com.unity.render-pipelines.lightweight/LWRP/Passes/ForwardLitPass.cs


using System.Diagnostics;
using UnityEngine.Experimental.GlobalIllumination;
using UnityEngine.Rendering;
using UnityEngine.Rendering.PostProcessing;
using UnityEngine.XR;
namespace UnityEngine.Experimental.Rendering.LightweightPipeline
{

float[] m_OpaqueScalerValues = {1.0f, 0.5f, 0.25f, 0.25f};
int m_SampleOffsetShaderHandle;
const string k_SetupRenderTargetTag = "Setup Render Target";
const string k_RenderOpaquesTag = "Render Opaques";
const string k_RenderTransparentsTag = "Render Transparents";

{
int vertexLightsCount = lightData.totalAdditionalLightsCount - lightData.pixelAdditionalLightsCount;
CoreUtils.SetKeyword(cmd, LightweightKeywords.AdditionalLightsText, lightData.totalAdditionalLightsCount > 0);
CoreUtils.SetKeyword(cmd, LightweightKeywords.MixedLightingSubtractiveText, m_MixedLightingSetup == MixedLightingSetup.Subtractive);
CoreUtils.SetKeyword(cmd, LightweightKeywords.VertexLightsText, vertexLightsCount > 0);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.AdditionalLights, lightData.totalAdditionalLightsCount > 0);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.MixedLightingSubtractive, m_MixedLightingSetup == MixedLightingSetup.Subtractive);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.VertexLights, vertexLightsCount > 0);
// CoreUtils.SetKeyword(cmd, LightweightKeywords.MainLightCookieText, mainLightIndex != -1 && LightweightUtils.IsSupportedCookieType(visibleLights[mainLightIndex].lightType) && visibleLights[mainLightIndex].light.cookie != null);
// CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.MainLightCookieText, mainLightIndex != -1 && LightweightUtils.IsSupportedCookieType(visibleLights[mainLightIndex].lightType) && visibleLights[mainLightIndex].light.cookie != null);
LightShadows directionalShadowQuality = shadowData.renderedDirectionalShadowQuality;
LightShadows localShadowQuality = shadowData.renderedLocalShadowQuality;

shadowData.supportsSoftShadows;
CoreUtils.SetKeyword(cmd, LightweightKeywords.DirectionalShadowsText, directionalShadowQuality != LightShadows.None);
CoreUtils.SetKeyword(cmd, LightweightKeywords.LocalShadowsText, localShadowQuality != LightShadows.None);
CoreUtils.SetKeyword(cmd, LightweightKeywords.SoftShadowsText, hasSoftShadows);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.DirectionalShadows, directionalShadowQuality != LightShadows.None);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.LocalShadows, localShadowQuality != LightShadows.None);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.SoftShadows, hasSoftShadows);
// TODO: Remove this. legacy particles support will be removed from Unity in 2018.3. This should be a shader_feature instead with prop exposed in the Standard particles shader.
CoreUtils.SetKeyword(cmd, "SOFTPARTICLES_ON", cameraData.requiresSoftParticles);

void RenderOpaques(ref ScriptableRenderContext context, ref CullResults cullResults, ref CameraData cameraData, RendererConfiguration rendererConfiguration, bool dynamicBatching)
{
CommandBuffer cmd = CommandBufferPool.Get(k_RenderOpaquesTag);
using (new ProfilingSample(cmd, k_SetupRenderTargetTag))
using (new ProfilingSample(cmd, k_RenderOpaquesTag))
// If rendering to an intermediate RT we resolve viewport on blit due to offset not being supported
// while rendering to a RT.
if (colorAttachmentHandle == -1 && cameraData.isDefaultViewport)
cmd.SetViewport(camera.pixelRect);
// TODO: We need a proper way to handle multiple camera/ camera stack. Issue is: multiple cameras can share a same RT
// (e.g, split screen games). However devs have to be dilligent with it and know when to clear/preserve color.
// For now we make it consistent by resolving viewport with a RT until we can have a proper camera management system
//if (colorAttachmentHandle == -1 && !cameraData.isDefaultViewport)
// cmd.SetViewport(camera.pixelRect);
context.ExecuteCommandBuffer(cmd);
cmd.Clear();

void RenderTransparents(ref ScriptableRenderContext context, ref CullResults cullResults, ref CameraData cameraData, RendererConfiguration rendererConfiguration, bool dynamicBatching)
{
CommandBuffer cmd = CommandBufferPool.Get(k_RenderTransparentsTag);
using (new ProfilingSample(cmd, k_SetupRenderTargetTag))
using (new ProfilingSample(cmd, k_RenderTransparentsTag))
{
Camera camera = cameraData.camera;
SetRenderTarget(cmd, RenderBufferLoadAction.Load, RenderBufferStoreAction.Store, ClearFlag.None, Color.black);

CommandBuffer cmd = CommandBufferPool.Get("Final Blit Pass");
cmd.SetGlobalTexture("_BlitTex", sourceRT);
// We need to handle viewport on a RT. We do it by rendering a fullscreen quad + viewport
SetRenderTarget(cmd, BuiltinRenderTextureType.CameraTarget, RenderBufferLoadAction.DontCare, RenderBufferStoreAction.Store, ClearFlag.All, Color.black);
SetRenderTarget(cmd, BuiltinRenderTextureType.CameraTarget, RenderBufferLoadAction.DontCare, RenderBufferStoreAction.Store, ClearFlag.None, Color.black);
cmd.SetViewProjectionMatrices(Matrix4x4.identity, Matrix4x4.identity);
cmd.SetViewport(cameraData.camera.pixelRect);
LightweightPipeline.DrawFullScreen(cmd, material);

if (cameraData.msaaSamples > 1)
{
cmd.DisableShaderKeyword(LightweightKeywords.DepthNoMsaa);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthNoMsaa);
cmd.DisableShaderKeyword(LightweightKeywords.DepthMsaa2);
cmd.EnableShaderKeyword(LightweightKeywords.DepthMsaa4);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthMsaa2);
cmd.EnableShaderKeyword(LightweightKeywordStrings.DepthMsaa4);
cmd.EnableShaderKeyword(LightweightKeywords.DepthMsaa2);
cmd.DisableShaderKeyword(LightweightKeywords.DepthMsaa4);
cmd.EnableShaderKeyword(LightweightKeywordStrings.DepthMsaa2);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthMsaa4);
cmd.EnableShaderKeyword(LightweightKeywords.DepthNoMsaa);
cmd.DisableShaderKeyword(LightweightKeywords.DepthMsaa2);
cmd.DisableShaderKeyword(LightweightKeywords.DepthMsaa4);
cmd.EnableShaderKeyword(LightweightKeywordStrings.DepthNoMsaa);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthMsaa2);
cmd.DisableShaderKeyword(LightweightKeywordStrings.DepthMsaa4);
LightweightPipeline.CopyTexture(cmd, depthSurface, copyDepthSurface, m_DepthCopyMaterial);
}
context.ExecuteCommandBuffer(cmd);

3
com.unity.render-pipelines.lightweight/LWRP/Passes/LocalShadowsPass.cs


ShadowSliceData[] m_LocalLightSlices;
float[] m_LocalShadowStrength;
const string k_SetupRenderTargetTag = "Setup Render Target";
const string k_RenderLocalShadows = "Render Local Shadows";
public LocalShadowsPass(LightweightForwardRenderer renderer) : base(renderer)

int shadowSampling = 0;
CommandBuffer cmd = CommandBufferPool.Get(k_RenderLocalShadows);
using (new ProfilingSample(cmd, k_SetupRenderTargetTag))
using (new ProfilingSample(cmd, k_RenderLocalShadows))
{
// TODO: Add support to point light shadows. We make a simplification here that only works
// for spot lights and with max spot shadows per pass.

11
com.unity.render-pipelines.lightweight/LWRP/Passes/ScreenSpaceShadowResolvePass.cs


{
public class ScreenSpaceShadowResolvePass : ScriptableRenderPass
{
public bool softShadows { get; set; }
RenderTextureFormat m_ColorFormat;
Material m_ScreenSpaceShadowsMaterial;

: RenderTextureFormat.ARGB32;
m_ScreenSpaceShadowsMaterial = renderer.GetMaterial(MaterialHandles.ScrenSpaceShadow);
softShadows = false;
}
public override void Setup(CommandBuffer cmd, RenderTextureDescriptor baseDescriptor, int[] colorAttachmentHandles, int depthAttachmentHandle = -1, int samples = 1)

return;
CommandBuffer cmd = CommandBufferPool.Get("Collect Shadows");
SetShadowCollectPassKeywords(cmd, renderingData.shadowData.directionalLightCascadeCount);
SetShadowCollectPassKeywords(cmd, ref renderingData.shadowData);
// Note: The source isn't actually 'used', but there's an engine peculiarity (bug) that
// doesn't like null sources when trying to determine a stereo-ized blit. So for proper

CommandBufferPool.Release(cmd);
}
void SetShadowCollectPassKeywords(CommandBuffer cmd, int cascadeCount)
void SetShadowCollectPassKeywords(CommandBuffer cmd, ref ShadowData shadowData)
CoreUtils.SetKeyword(cmd, LightweightKeywords.SoftShadowsText, softShadows);
CoreUtils.SetKeyword(cmd, LightweightKeywords.CascadeShadowsText, cascadeCount > 1);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.SoftShadows, shadowData.renderedDirectionalShadowQuality == LightShadows.Soft);
CoreUtils.SetKeyword(cmd, LightweightKeywordStrings.CascadeShadows, shadowData.directionalLightCascadeCount > 1);
}
}
}

4
com.unity.render-pipelines.lightweight/LWRP/Passes/ScriptableRenderPass.cs


public TextureDimension textureDimension { get; private set; }
protected List<ShaderPassName> m_ShaderPassNames = new List<ShaderPassName>();
public int samples { get; private set; }
int samples;
protected List<ShaderPassName> m_ShaderPassNames = new List<ShaderPassName>();
public ScriptableRenderPass(LightweightForwardRenderer renderer)
{

30
com.unity.shadergraph/CHANGELOG.md


# Next version
### HD Render Pipeline support
![](.data/hd_render_pipeline.png)
Shader Graph now supports the High Definition Render Pipeline with both PBR and Unlit Master nodes. Shaders built with Shader Graph work with both the Lightweight and HD render pipelines.
### Vertex position
![](.data/vertex_position.png)
You can now modify vertex position via the Position slot on the PBR and Unlit Master nodes. By default, the input to this node is object space position. Custom inputs to this slot should specify the absolute local position of a given vertex. Certain nodes (such as Procedural Shapes) are not viable in the vertex shader. Such nodes are incompatible with this slot.
### Master node settings
![](.data/menu_settings.png)

You can now change the path of Shader Graphs and Sub Graphs. When you change the path of a Shader Graph, this modifies the location it has in the shader selection list. When you change the path of Sub Graph, it will have a different location in the node creation menu.
### Is Front Face node
![](.data/face_sign.png)
With this node, you can change graph output depending on the face sign of a given fragment. If the current fragment is part of a front face, the node returns True. For a back face, the node returns False.
Note: This functionality requires that you have enabled **two sided** on the Master node.
### Gradient nodes

### Texture3D and Texture2D Array
![](.data/texture_nodes.png)
This change expands Unity's support for Texture types via two new property types and four new nodes. These allow you to define and sample Texture 3D and Texture 2D Array type assets in Shader Graph.
### Texture 2D LOD node
![](.data/texture_2d_lod_node.png)
This adds a new node for LOD functionality on a Texture 2D Sample. Sample Texture 2D LOD uses the exact same input and output slots as Sample Texture 2D, but also includes an input for level of detail adjustments via a Vector1 slot.
### Show generated code

- Your system locale can no longer cause incorrect commands due to full stops being converted to commas.
- Deserialization of subgraphs now works correctly.
- Sub graphs are now suffixed with (sub), so you can tell them apart from other nodes.
- The preview of a node does not obstruct the selection outliner anymore.

55
com.unity.shadergraph/Editor/Data/Graphs/PreviewProperty.cs


}
[StructLayout(LayoutKind.Explicit)]
struct Data
struct ClassData
[FieldOffset(0)]
public Color colorValue;
[FieldOffset(0)]
public Texture textureValue;
[FieldOffset(0)]

}
[StructLayout(LayoutKind.Explicit)]
struct StructData
{
[FieldOffset(0)]
public Color colorValue;
[FieldOffset(0)]
public Vector4 vector4Value;
[FieldOffset(0)]

}
Data m_Data;
ClassData m_ClassData;
StructData m_StructData;
public Color colorValue
{

throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Color, propType));
return m_Data.colorValue;
return m_StructData.colorValue;
m_Data.colorValue = value;
m_StructData.colorValue = value;
}
}

{
if (propType != PropertyType.Texture2D && propType != PropertyType.Texture2DArray && propType != PropertyType.Texture3D)
throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Texture2D, propType));
return m_Data.textureValue;
return m_ClassData.textureValue;
m_Data.textureValue = value;
m_ClassData.textureValue = value;
}
}

{
if (propType != PropertyType.Cubemap)
throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Cubemap, propType));
return m_Data.cubemapValue;
return m_ClassData.cubemapValue;
m_Data.cubemapValue = value;
m_ClassData.cubemapValue = value;
}
}

{
if (propType != PropertyType.Gradient)
throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Gradient, propType));
return m_Data.gradientValue;
return m_ClassData.gradientValue;
m_Data.gradientValue = value;
m_ClassData.gradientValue = value;
}
}

{
if (propType != PropertyType.Vector2 && propType != PropertyType.Vector3 && propType != PropertyType.Vector4)
throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Vector4, propType));
return m_Data.vector4Value;
return m_StructData.vector4Value;
}
set
{

m_Data.vector4Value = value;
m_StructData.vector4Value = value;
}
}

{
if (propType != PropertyType.Vector1)
throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Vector1, propType));
return m_Data.floatValue;
return m_StructData.floatValue;
m_Data.floatValue = value;
m_StructData.floatValue = value;
}
}

{
if (propType != PropertyType.Boolean)
throw new ArgumentException(string.Format(k_GetErrorMessage, PropertyType.Boolean, propType));
return m_Data.booleanValue;
return m_StructData.booleanValue;
m_Data.booleanValue = value;
m_StructData.booleanValue = value;
}
}

public void SetMaterialPropertyBlockValue(MaterialPropertyBlock block)
{
if ((propType == PropertyType.Texture2D || propType == PropertyType.Texture2DArray || propType == PropertyType.Texture3D) && textureValue != null)
block.SetTexture(name, m_Data.textureValue);
block.SetTexture(name, m_ClassData.textureValue);
block.SetTexture(name, m_Data.cubemapValue);
block.SetTexture(name, m_ClassData.cubemapValue);
block.SetColor(name, m_Data.colorValue);
block.SetColor(name, m_StructData.colorValue);
block.SetVector(name, m_Data.vector4Value);
block.SetVector(name, m_StructData.vector4Value);
block.SetFloat(name, m_Data.floatValue);
block.SetFloat(name, m_StructData.floatValue);
block.SetFloat(name, m_Data.booleanValue ? 1 : 0);
block.SetFloat(name, m_StructData.booleanValue ? 1 : 0);
}
}

8
com.unity.shadergraph/Editor/Data/Graphs/ShaderGraphRequirements.cs


public NeededCoordinateSpace requiresPosition;
public bool requiresScreenPosition;
public bool requiresVertexColor;
public bool requiresFaceSign;
public List<UVChannel> requiresMeshUVs;
public static ShaderGraphRequirements none

newReqs.requiresPosition = other.requiresPosition | requiresPosition;
newReqs.requiresScreenPosition = other.requiresScreenPosition | requiresScreenPosition;
newReqs.requiresVertexColor = other.requiresVertexColor | requiresVertexColor;
newReqs.requiresFaceSign = other.requiresFaceSign | requiresFaceSign;
newReqs.requiresMeshUVs = new List<UVChannel>();
if (requiresMeshUVs != null)

return newReqs;
}
public static ShaderGraphRequirements FromNodes<T>(List<T> nodes, ShaderStageCapability stageCapability = ShaderStageCapability.All, bool includeIntermediateSpaces = true, bool HDRPBehavior = false)
public static ShaderGraphRequirements FromNodes<T>(List<T> nodes, ShaderStageCapability stageCapability = ShaderStageCapability.All, bool includeIntermediateSpaces = true)
where T : class, INode
{
NeededCoordinateSpace requiresNormal = nodes.OfType<IMayRequireNormal>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresNormal(stageCapability));

NeededCoordinateSpace requiresPosition = nodes.OfType<IMayRequirePosition>().Aggregate(NeededCoordinateSpace.None, (mask, node) => mask | node.RequiresPosition(stageCapability));
bool requiresScreenPosition = nodes.OfType<IMayRequireScreenPosition>().Any(x => x.RequiresScreenPosition());
bool requiresVertexColor = nodes.OfType<IMayRequireVertexColor>().Any(x => x.RequiresVertexColor());
bool requiresFaceSign = nodes.OfType<IMayRequireFaceSign>().Any(x => x.RequiresFaceSign());
var meshUV = new List<UVChannel>();
for (int uvIndex = 0; uvIndex < ShaderGeneratorNames.UVCount; ++uvIndex)

| requiresNormal;
var needsTangentSpace = (compoundSpaces & NeededCoordinateSpace.Tangent) > 0;
if (needsTangentSpace && !HDRPBehavior)
if (needsTangentSpace)
{
requiresBitangent |= NeededCoordinateSpace.World;
requiresNormal |= NeededCoordinateSpace.World;

requiresPosition = requiresPosition,
requiresScreenPosition = requiresScreenPosition,
requiresVertexColor = requiresVertexColor,
requiresFaceSign = requiresFaceSign,
requiresMeshUVs = meshUV
};

14
com.unity.shadergraph/Editor/Data/Nodes/Procedural/CheckerboardNode.cs


return
@"
{
UV = UV + 0.25 / Frequency;
UV = (UV.xy + 0.5) * Frequency;
{precision} width = 0.5;
{precision}2 distance3 = 2.0 * abs(frac((UV.xy + 0.5) * Frequency) - 0.5) - width;
{precision}2 scale = 0.5 / duv_length.xy;
{precision}2 blend_out = saturate(scale / 3);
{precision}2 vector_alpha = clamp(distance3 * scale.xy * blend_out.xy, -1.0, 1.0);
{precision} alpha = saturate(vector_alpha.x * vector_alpha.y);
{precision} width = 1.0;
{precision}2 distance3 = 4.0 * abs(frac(UV + 0.25) - 0.5) - width;
{precision}2 scale = 0.35 / duv_length.xy;
{precision} freqLimiter = sqrt(clamp(1.1f - max(duv_length.x, duv_length.y), 0.0, 1.0));
{precision}2 vector_alpha = clamp(distance3 * scale.xy, -1.0, 1.0);
{precision} alpha = saturate(0.5f + 0.5f * vector_alpha.x * vector_alpha.y * freqLimiter);
Out = lerp(ColorA, ColorB, alpha.xxx);
}";
}

69
com.unity.shadergraph/Editor/Data/Util/GraphUtil.cs


{
return 2;
}
else if (typeName.Equals("float"))
else if (typeName.Equals("Single"))
{
return 1;
}

if (requirements.requiresScreenPosition)
surfaceDescriptionInputStruct.AppendLine("float4 {0};", ShaderGeneratorNames.ScreenPosition);
if (requirements.requiresFaceSign)
surfaceDescriptionInputStruct.AppendLine("float {0};", ShaderGeneratorNames.FaceSign);
results.previewMode = PreviewMode.Preview3D;
if (!isUber)
{

return results;
}
public static void GenerateSurfaceDescriptionStruct(ShaderStringBuilder surfaceDescriptionStruct, List<MaterialSlot> slots, bool isMaster)
public static void GenerateSurfaceDescriptionStruct(ShaderStringBuilder surfaceDescriptionStruct, List<MaterialSlot> slots, bool isMaster, string structName = "SurfaceDescription", HashSet<string> activeFields = null)
surfaceDescriptionStruct.AppendLine("struct SurfaceDescription");
surfaceDescriptionStruct.AppendLine("struct {0}", structName);
{
string hlslName = NodeUtils.GetHLSLSafeName(slot.shaderOutputName);
NodeUtils.GetHLSLSafeName(slot.shaderOutputName));
//surfaceDescriptionStruct.Deindent();
hlslName);
if (activeFields != null)
{
activeFields.Add(structName + "." + hlslName);
}
}
if (activeFields != null)
{
activeFields.Add(structName + ".PreviewOutput");
}
}
}
}

var usedSlots = slots ?? masterNode.GetInputSlots<MaterialSlot>();
foreach (var input in usedSlots)
{
var foundEdges = graph.GetEdges(input.slotReference).ToArray();
if (foundEdges.Any())
if (input != null)
surfaceDescriptionFunction.AppendLine("surface.{0} = {1};", NodeUtils.GetHLSLSafeName(input.shaderOutputName), masterNode.GetSlotValue(input.id, mode));
}
else
{
surfaceDescriptionFunction.AppendLine("surface.{0} = {1};", NodeUtils.GetHLSLSafeName(input.shaderOutputName), input.GetDefaultValue(mode));
var foundEdges = graph.GetEdges(input.slotReference).ToArray();
if (foundEdges.Any())
{
surfaceDescriptionFunction.AppendLine("surface.{0} = {1};", NodeUtils.GetHLSLSafeName(input.shaderOutputName), masterNode.GetSlotValue(input.id, mode));
}
else
{
surfaceDescriptionFunction.AppendLine("surface.{0} = {1};", NodeUtils.GetHLSLSafeName(input.shaderOutputName), input.GetDefaultValue(mode));
}
}
}
}

}
const string k_VertexDescriptionStructName = "VertexDescription";
public static void GenerateVertexDescriptionStruct(ShaderStringBuilder builder, List<MaterialSlot> slots)
public static void GenerateVertexDescriptionStruct(ShaderStringBuilder builder, List<MaterialSlot> slots, string structName = k_VertexDescriptionStructName, HashSet<string> activeFields = null)
builder.AppendLine("struct {0}", k_VertexDescriptionStructName);
builder.AppendLine("struct {0}", structName);
builder.AppendLine("{0} {1};", NodeUtils.ConvertConcreteSlotValueTypeToString(AbstractMaterialNode.OutputPrecision.@float, slot.concreteValueType), NodeUtils.GetHLSLSafeName(slot.shaderOutputName));
{
string hlslName = NodeUtils.GetHLSLSafeName(slot.shaderOutputName);
builder.AppendLine("{0} {1};",
NodeUtils.ConvertConcreteSlotValueTypeToString(AbstractMaterialNode.OutputPrecision.@float, slot.concreteValueType),
hlslName);
if (activeFields != null)
{
activeFields.Add(structName + "." + hlslName);
}
}
}
}

FunctionRegistry functionRegistry,
PropertyCollector shaderProperties,
GenerationMode mode,
List<AbstractMaterialNode> nodes,
List<INode> nodes,
string graphInputStructName = "VertexDescriptionInputs")
string graphInputStructName = "VertexDescriptionInputs",
string functionName = "PopulateVertexData",
string graphOutputStructName = k_VertexDescriptionStructName)
{
if (graph == null)
return;

graph.CollectShaderProperties(shaderProperties, mode);
builder.AppendLine("{0} PopulateVertexData(VertexDescriptionInputs IN)", k_VertexDescriptionStructName);
builder.AppendLine("{0} {1}({2} IN)", graphOutputStructName, functionName, graphInputStructName);
builder.AppendLine("{0} description = ({0})0;", k_VertexDescriptionStructName);
foreach (var node in nodes)
builder.AppendLine("{0} description = ({0})0;", graphOutputStructName);
foreach (var node in nodes.OfType<AbstractMaterialNode>())
{
var generatesFunction = node as IGeneratesFunction;
if (generatesFunction != null)

16
com.unity.shadergraph/Editor/Data/Util/ShaderGenerator.cs


if (combinedRequirements.requiresScreenPosition)
{
var screenPosition = "ComputeScreenPos(mul(GetWorldToHClipMatrix(), mul(GetObjectToWorldMatrix(), v.vertex.xyz)), _ProjectionParams.x)";
var screenPosition = "ComputeScreenPos(mul(GetWorldToHClipMatrix(), mul(GetObjectToWorldMatrix(), v.vertex)), _ProjectionParams.x)";
vertexShader.AppendLine("float4 {0} = {1};", ShaderGeneratorNames.ScreenPosition, screenPosition);
if (graphModelRequirements.requiresScreenPosition)
{

if (pixelRequirements.requiresScreenPosition)
pixelShaderSurfaceInputs.AppendLine("surfaceInput.{0} = {0};", ShaderGeneratorNames.ScreenPosition);
if (pixelRequirements.requiresFaceSign)
pixelShaderSurfaceInputs.AppendLine("surfaceInput.{0} = {0};", ShaderGeneratorNames.FaceSign);
foreach (var channel in pixelRequirements.requiresMeshUVs.Distinct())
pixelShaderSurfaceInputs.AppendLine("surfaceInput.{0} = {0};", ShaderGeneratorNames.GetUVName(channel));

pixelShaderSurfaceRemap.AppendLine("return surf.PreviewOutput;");
}
// -------------------------------------
// Extra pixel shader work
var faceSign = new ShaderStringBuilder();
if (shaderGraphRequirements.requiresFaceSign)
faceSign.AppendLine(", half FaceSign : VFACE");
res = res.Replace("${FaceSign}", faceSign.ToString());
res = res.Replace("${LocalPixelShader}", pixelShader.ToString());
res = res.Replace("${SurfaceInputs}", pixelShaderSurfaceInputs.ToString());
res = res.Replace("${SurfaceOutputRemap}", pixelShaderSurfaceRemap.ToString());

return o;
}
float4 frag (GraphVertexOutput IN) : SV_Target
float4 frag (GraphVertexOutput IN ${FaceSign}) : SV_Target
{
${LocalPixelShader}
SurfaceDescriptionInputs surfaceInput = (SurfaceDescriptionInputs)0;;

1
com.unity.shadergraph/Editor/Data/Util/ShaderGeneratorNames.cs


public const string ScreenPosition = "ScreenPosition";
public const string VertexColor = "VertexColor";
public const string FaceSign = "FaceSign";
public static string GetUVName(this UVChannel channel)

1
com.unity.shadergraph/Editor/Drawing/Views/MaterialNodeView.cs


if (m_PreviewContainer.parent != this)
{
Add(m_PreviewContainer);
m_PreviewContainer.PlaceBehind(this.Q("selection-border"));
}
m_PreviewFiller.AddToClassList("expanded");
m_PreviewFiller.RemoveFromClassList("collapsed");

52
com.unity.shadergraph/Editor/Importers/ShaderGraphImporter.cs


List<PropertyCollector.TextureInfo> configuredTextures;
string path = ctx.assetPath;
string shaderString = null;
var text = GetShaderText(path, out configuredTextures, sourceAssetDependencyPaths);
var shader = ShaderUtil.CreateShaderAsset(text);
EditorMaterialUtility.SetShaderDefaults(
shader,
configuredTextures.Where(x => x.modifiable).Select(x => x.name).ToArray(),
configuredTextures.Where(x => x.modifiable).Select(x => EditorUtility.InstanceIDToObject(x.textureId) as Texture).ToArray());
EditorMaterialUtility.SetShaderNonModifiableDefaults(
shader,
configuredTextures.Where(x => !x.modifiable).Select(x => x.name).ToArray(),
configuredTextures.Where(x => !x.modifiable).Select(x => EditorUtility.InstanceIDToObject(x.textureId) as Texture).ToArray());
ctx.AddObjectToAsset("MainAsset", shader);
ctx.SetMainObject(shader);
foreach (var sourceAssetDependencyPath in sourceAssetDependencyPaths.Distinct())
ctx.DependsOnSourceAsset(sourceAssetDependencyPath);
}
internal static string GetShaderText(string path, out List<PropertyCollector.TextureInfo> configuredTextures, List<string> sourceAssetDependencyPaths)
{
string shaderString = null;
var shaderName = Path.GetFileNameWithoutExtension(path);
try
{

shaderName = graph.path + "/" + shaderName;
shaderString = graph.GetShader(shaderName, GenerationMode.ForReals, out configuredTextures, sourceAssetDependencyPaths);
foreach (var node in graph.GetNodes<AbstractMaterialNode>())
node.GetSourceAssetDependencies(sourceAssetDependencyPaths);
if (sourceAssetDependencyPaths != null)
{
foreach (var node in graph.GetNodes<AbstractMaterialNode>())
node.GetSourceAssetDependencies(sourceAssetDependencyPaths);
}
}
catch (Exception)
{

var text = shaderString ?? k_ErrorShader.Replace("Hidden/GraphErrorShader2", shaderName);
var shader = ShaderUtil.CreateShaderAsset(text);
EditorMaterialUtility.SetShaderDefaults(
shader,
configuredTextures.Where(x => x.modifiable).Select(x => x.name).ToArray(),
configuredTextures.Where(x => x.modifiable).Select(x => EditorUtility.InstanceIDToObject(x.textureId) as Texture).ToArray());
EditorMaterialUtility.SetShaderNonModifiableDefaults(
shader,
configuredTextures.Where(x => !x.modifiable).Select(x => x.name).ToArray(),
configuredTextures.Where(x => !x.modifiable).Select(x => EditorUtility.InstanceIDToObject(x.textureId) as Texture).ToArray());
return shaderString ?? k_ErrorShader.Replace("Hidden/GraphErrorShader2", shaderName);
}
ctx.AddObjectToAsset("MainAsset", shader);
ctx.SetMainObject(shader);
foreach (var sourceAssetDependencyPath in sourceAssetDependencyPaths.Distinct())
ctx.DependsOnSourceAsset(sourceAssetDependencyPath);
internal static string GetShaderText(string path, out List<PropertyCollector.TextureInfo> configuredTextures)
{
return GetShaderText(path, out configuredTextures, null);
}
}

8
com.unity.render-pipelines.core/CoreRP/Editor/Shadow.meta


fileFormatVersion: 2
guid: 61ef33a54404cb747aad57d04e535154
folderAsset: yes
DefaultImporter:
externalObjects: {}
userData:
assetBundleName:
assetBundleVariant:

77
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/BaseShaderPreprocessor.cs


using System;
using System.Collections.Generic;
using UnityEditor.Build;
using UnityEditor.Rendering;
using UnityEngine;
using UnityEngine.Rendering;
using UnityEngine.Experimental.Rendering.HDPipeline;
namespace UnityEditor.Experimental.Rendering.HDPipeline
{
// returns true if the variant should be stripped.
public delegate bool VariantStrippingFunc(HDRenderPipelineAsset hdrpAsset, Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData);
public class BaseShaderPreprocessor
{
protected ShaderKeyword m_ShadowMask;
protected ShaderKeyword m_Transparent;
protected ShaderKeyword m_DebugDisplay;
protected ShaderKeyword m_TileLighting;
protected ShaderKeyword m_ClusterLighting;
public BaseShaderPreprocessor()
{
m_Transparent = new ShaderKeyword("_SURFACE_TYPE_TRANSPARENT");
m_DebugDisplay = new ShaderKeyword("DEBUG_DISPLAY");
m_TileLighting = new ShaderKeyword("USE_FPTL_LIGHTLIST");
m_ClusterLighting = new ShaderKeyword("USE_CLUSTERED_LIGHTLIST");
}
public virtual void AddStripperFuncs(Dictionary<string, VariantStrippingFunc> stripperFuncs) {}
// NOTE: All these keyword should be automatically stripped so there's no need to handle them ourselves.
// LIGHTMAP_ON, DIRLIGHTMAP_COMBINED, DYNAMICLIGHTMAP_ON, LIGHTMAP_SHADOW_MIXING, SHADOWS_SHADOWMASK
// FOG_LINEAR, FOG_EXP, FOG_EXP2
// STEREO_INSTANCING_ON, STEREO_MULTIVIEW_ON, STEREO_CUBEMAP_RENDER_ON, UNITY_SINGLE_PASS_STEREO
// INSTANCING_ON
// Several pass are common to all shader, let's share code here
// This remove variant (return true) for:
// - Scene Selection
// - Motion vectors
// - Tile pass for Transparent (not compatible)
// -
protected bool CommonShaderStripper(HDRenderPipelineAsset hdrpAsset, Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData)
{
bool isSceneSelectionPass = snippet.passName == "SceneSelectionPass";
if (isSceneSelectionPass)
return true;
bool isMotionPass = snippet.passName == "Motion Vectors";
if (!hdrpAsset.renderPipelineSettings.supportMotionVectors && isMotionPass)
return true;
//bool isForwardPass = (snippet.passName == "Forward") || (snippet.passName == "ForwardOnly");
if (inputData.shaderKeywordSet.IsEnabled(m_Transparent))
{
// If we are transparent we use cluster lighting and not tile lighting
if (inputData.shaderKeywordSet.IsEnabled(m_TileLighting))
return true;
}
else // Opaque
{
// Note: we can't assume anything regarding tile/cluster for opaque as multiple view could used different settings and it depends on MSAA
}
// TODO: If static lighting we can remove meta pass, but how to know that?
// If we are in a release build, don't compile debug display variant
// Also don't compile it if not requested by the render pipeline settings
if ((/*!Debug.isDebugBuild || */ !hdrpAsset.renderPipelineSettings.supportRuntimeDebugDisplay) && inputData.shaderKeywordSet.IsEnabled(m_DebugDisplay))
return true;
return false;
}
}
}

11
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/BaseShaderPreprocessor.cs.meta


fileFormatVersion: 2
guid: c23f3fe1f63fff240a5cf70cf0a62c93
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

69
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Lit/LitShaderPreprocessor.cs


using System;
using System.Collections.Generic;
using UnityEditor.Build;
using UnityEditor.Rendering;
using UnityEngine;
using UnityEngine.Experimental.Rendering.HDPipeline;
namespace UnityEditor.Experimental.Rendering.HDPipeline
{
public class LitShaderPreprocessor : BaseShaderPreprocessor
{
bool LitShaderStripper(HDRenderPipelineAsset hdrpAsset, Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData)
{
if (CommonShaderStripper(hdrpAsset, shader, snippet, inputData))
return true;
bool isGBufferPass = snippet.passName == "GBuffer";
bool isForwardPass = snippet.passName == "Forward";
bool isTransparentForwardPass = snippet.passName == "TransparentDepthPostpass" || snippet.passName == "TransparentBackface" || snippet.passName == "TransparentDepthPrepass";
// When using forward only, we never need GBuffer pass (only Forward)
if (hdrpAsset.renderPipelineSettings.supportOnlyForward && isGBufferPass)
return true;
if (inputData.shaderKeywordSet.IsEnabled(m_Transparent))
{
// If transparent, we never need GBuffer pass.
if (isGBufferPass)
return true;
}
else // Opaque
{
// If opaque, we never need transparent specific passes (even in forward only mode)
if (isTransparentForwardPass)
return true;
// When we are in deferred (i.e !hdrpAsset.renderPipelineSettings.supportOnlyForward), we only support tile lighting
if (!hdrpAsset.renderPipelineSettings.supportOnlyForward && inputData.shaderKeywordSet.IsEnabled(m_ClusterLighting))
return true;
if (!hdrpAsset.renderPipelineSettings.supportOnlyForward)
{
// If opaque and not forward only, then we only need the forward debug pass.
if (isForwardPass && !inputData.shaderKeywordSet.IsEnabled(m_DebugDisplay))
return true;
}
}
// TODO: Tests for later
// We need to find a way to strip useless shader features for passes/shader stages that don't need them (example, vertex shaders won't ever need SSS Feature flag)
// This causes several problems:
// - Runtime code that "finds" shader variants based on feature flags might not find them anymore... thus fall backing to the "let's give a score to variant" code path that may find the wrong variant.
// - Another issue is that if a feature is declared without a "_" fall-back, if we strip the other variants, none may be left to use! This needs to be changed on our side.
//if (snippet.shaderType == ShaderType.Vertex && inputData.shaderKeywordSet.IsEnabled(m_FeatureSSS))
// return true;
return false;
}
public override void AddStripperFuncs(Dictionary<string, VariantStrippingFunc> stripperFuncs)
{
// Add name of the shader and corresponding delegate to call to strip variant
stripperFuncs.Add("HDRenderPipeline/Lit", LitShaderStripper);
stripperFuncs.Add("HDRenderPipeline/LitTessellation", LitShaderStripper);
stripperFuncs.Add("HDRenderPipeline/LayeredLit", LitShaderStripper);
stripperFuncs.Add("HDRenderPipeline/LayeredLitTessellation", LitShaderStripper);
}
}
}

11
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Lit/LitShaderPreprocessor.cs.meta


fileFormatVersion: 2
guid: 203e4ecfbd605d54d89374ef35e914c0
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

23
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/StackLit/StackLitShaderPreprocessor.cs


using System;
using System.Collections.Generic;
using UnityEditor.Build;
using UnityEditor.Rendering;
using UnityEngine;
using UnityEngine.Experimental.Rendering.HDPipeline;
namespace UnityEditor.Experimental.Rendering.HDPipeline
{
public class StackLitShaderPreprocessor : BaseShaderPreprocessor
{
bool StackLitShaderStripper(HDRenderPipelineAsset hdrpAsset, Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData)
{
return CommonShaderStripper(hdrpAsset, shader, snippet, inputData);
}
public override void AddStripperFuncs(Dictionary<string, VariantStrippingFunc> stripperFuncs)
{
// Add name of the shader and corresponding delegate to call to strip variant
stripperFuncs.Add("HDRenderPipeline/StackLit", StackLitShaderStripper);
}
}
}

11
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/StackLit/StackLitShaderPreprocessor.cs.meta


fileFormatVersion: 2
guid: 238a7258cd3744f4c9d619f4355c3019
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

23
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Unlit/UnlitShaderPreprocessor.cs


using System;
using System.Collections.Generic;
using UnityEditor.Build;
using UnityEditor.Rendering;
using UnityEngine;
using UnityEngine.Experimental.Rendering.HDPipeline;
namespace UnityEditor.Experimental.Rendering.HDPipeline
{
public class UnlitShaderPreprocessor : BaseShaderPreprocessor
{
bool UnlitShaderStripper(HDRenderPipelineAsset hdrpAsset, Shader shader, ShaderSnippetData snippet, ShaderCompilerData inputData)
{
return CommonShaderStripper(hdrpAsset, shader, snippet, inputData);
}
public override void AddStripperFuncs(Dictionary<string, VariantStrippingFunc> stripperFuncs)
{
// Add name of the shader and corresponding delegate to call to strip variant
stripperFuncs.Add("HDRenderPipeline/Unlit", UnlitShaderStripper);
}
}
}

11
com.unity.render-pipelines.high-definition/HDRP/Editor/Material/Unlit/UnlitShaderPreprocessor.cs.meta


fileFormatVersion: 2
guid: b9d6d9aeb9ea7a5449eb51aa059a75b8
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

3
com.unity.shadergraph/.data/face_sign.png


version https://git-lfs.github.com/spec/v1
oid sha256:056f160ee81fcdeb3f3a26a0116846de50b68bafa0c65db8731f5aca37ee74e7
size 43759

3
com.unity.shadergraph/.data/hd_render_pipeline.png


version https://git-lfs.github.com/spec/v1
oid sha256:aff2679b3a603812e63290cea0829d6d354a94e02765513bb214faa4331adfdd
size 1516111

3
com.unity.shadergraph/.data/texture_2d_lod_node.PNG


version https://git-lfs.github.com/spec/v1
oid sha256:b262d71d68d478f6b6c3dc3086451a764e065b8608a65104e17cb8aefefa5f76
size 238646

3
com.unity.shadergraph/.data/texture_nodes.png


version https://git-lfs.github.com/spec/v1
oid sha256:6e4d23f6b0f35ae888614f05c00c28ca5e064b03bf010159950acaf9e12366d5
size 131836

3
com.unity.shadergraph/.data/vertex_position.png


version https://git-lfs.github.com/spec/v1
oid sha256:3ae6d830f7cff2331af0145171c3287021e8d31e64c97633b06c5155332ddbfe
size 395709

18
com.unity.shadergraph/Editor/Data/Interfaces/IMayRequireFaceSign.cs


using UnityEditor.Graphing;
namespace UnityEditor.ShaderGraph
{
public interface IMayRequireFaceSign
{
bool RequiresFaceSign(ShaderStageCapability stageCapability = ShaderStageCapability.Fragment);
}
public static class IMayRequireFaceSignExtensions
{
public static bool RequiresFaceSign(this ISlot slot)
{
var mayRequireFaceSign = slot as IMayRequireFaceSign;
return mayRequireFaceSign != null && mayRequireFaceSign.RequiresFaceSign();
}
}
}

3
com.unity.shadergraph/Editor/Data/Interfaces/IMayRequireFaceSign.cs.meta


fileFormatVersion: 2
guid: 23f5d9c2f1ec442a7b8c59e893a6724d
timeCreated: 1512469767

120
com.unity.shadergraph/Editor/Data/Nodes/Input/Texture/SampleTexture2DLODNode.cs


using System.Linq;
using UnityEngine;
using UnityEditor.Graphing;
using UnityEditor.ShaderGraph.Drawing.Controls;
namespace UnityEditor.ShaderGraph
{
[Title("Input", "Texture", "Sample Texture 2D LOD")]
public class SampleTexture2DLODNode : AbstractMaterialNode, IGeneratesBodyCode, IMayRequireMeshUV
{
public const int OutputSlotRGBAId = 0;
public const int OutputSlotRId = 5;
public const int OutputSlotGId = 6;
public const int OutputSlotBId = 7;
public const int OutputSlotAId = 8;
public const int TextureInputId = 1;
public const int UVInput = 2;
public const int SamplerInput = 3;
public const int LODInput = 4;
const string kOutputSlotRGBAName = "RGBA";
const string kOutputSlotRName = "R";
const string kOutputSlotGName = "G";
const string kOutputSlotBName = "B";
const string kOutputSlotAName = "A";
const string kTextureInputName = "Texture";
const string kUVInputName = "UV";
const string kSamplerInputName = "Sampler";
const string kLODInputName = "LOD";
public override bool hasPreview { get { return true; } }
public SampleTexture2DLODNode()
{
name = "Sample Texture 2D LOD";
UpdateNodeAfterDeserialization();
}
public override string documentationURL
{
get { return "https://github.com/Unity-Technologies/ShaderGraph/wiki/Sample-Texture-2D-LOD-Node"; }
}
[SerializeField]
private TextureType m_TextureType = TextureType.Default;
[EnumControl("Type")]
public TextureType textureType
{
get { return m_TextureType; }
set
{
if (m_TextureType == value)
return;
m_TextureType = value;
Dirty(ModificationScope.Graph);
}
}
public sealed override void UpdateNodeAfterDeserialization()
{
AddSlot(new Vector4MaterialSlot(OutputSlotRGBAId, kOutputSlotRGBAName, kOutputSlotRGBAName, SlotType.Output, Vector4.zero, ShaderStageCapability.All));
AddSlot(new Vector1MaterialSlot(OutputSlotRId, kOutputSlotRName, kOutputSlotRName, SlotType.Output, 0, ShaderStageCapability.All));
AddSlot(new Vector1MaterialSlot(OutputSlotGId, kOutputSlotGName, kOutputSlotGName, SlotType.Output, 0, ShaderStageCapability.All));
AddSlot(new Vector1MaterialSlot(OutputSlotBId, kOutputSlotBName, kOutputSlotBName, SlotType.Output, 0, ShaderStageCapability.All));
AddSlot(new Vector1MaterialSlot(OutputSlotAId, kOutputSlotAName, kOutputSlotAName, SlotType.Output, 0, ShaderStageCapability.All));
AddSlot(new Texture2DInputMaterialSlot(TextureInputId, kTextureInputName, kTextureInputName));
AddSlot(new UVMaterialSlot(UVInput, kUVInputName, kUVInputName, UVChannel.UV0));
AddSlot(new SamplerStateMaterialSlot(SamplerInput, kSamplerInputName, kSamplerInputName, SlotType.Input));
AddSlot(new Vector1MaterialSlot(LODInput, kLODInputName, kLODInputName, SlotType.Input, 0));
RemoveSlotsNameNotMatching(new[] { OutputSlotRGBAId, OutputSlotRId, OutputSlotGId, OutputSlotBId, OutputSlotAId, TextureInputId, UVInput, SamplerInput, LODInput });
}
// Node generations
public virtual void GenerateNodeCode(ShaderGenerator visitor, GenerationMode generationMode)
{
var uvName = GetSlotValue(UVInput, generationMode);
//Sampler input slot
var samplerSlot = FindInputSlot<MaterialSlot>(SamplerInput);
var edgesSampler = owner.GetEdges(samplerSlot.slotReference);
var lodSlot = GetSlotValue(LODInput, generationMode);
var id = GetSlotValue(TextureInputId, generationMode);
var result = string.Format("{0}4 {1} = SAMPLE_TEXTURE2D_LOD({2}, {3}, {4}, {5});"
, precision
, GetVariableNameForSlot(OutputSlotRGBAId)
, id
, edgesSampler.Any() ? GetSlotValue(SamplerInput, generationMode) : "sampler" + id
, uvName
, lodSlot);
visitor.AddShaderChunk(result, true);
if (textureType == TextureType.Normal)
visitor.AddShaderChunk(string.Format("{0}.rgb = UnpackNormalmapRGorAG({0});", GetVariableNameForSlot(OutputSlotRGBAId)), true);
visitor.AddShaderChunk(string.Format("{0} {1} = {2}.r;", precision, GetVariableNameForSlot(OutputSlotRId), GetVariableNameForSlot(OutputSlotRGBAId)), true);
visitor.AddShaderChunk(string.Format("{0} {1} = {2}.g;", precision, GetVariableNameForSlot(OutputSlotGId), GetVariableNameForSlot(OutputSlotRGBAId)), true);
visitor.AddShaderChunk(string.Format("{0} {1} = {2}.b;", precision, GetVariableNameForSlot(OutputSlotBId), GetVariableNameForSlot(OutputSlotRGBAId)), true);
visitor.AddShaderChunk(string.Format("{0} {1} = {2}.a;", precision, GetVariableNameForSlot(OutputSlotAId), GetVariableNameForSlot(OutputSlotRGBAId)), true);
}
public bool RequiresMeshUV(UVChannel channel, ShaderStageCapability stageCapability)
{
s_TempSlots.Clear();
GetInputSlots(s_TempSlots);
foreach (var slot in s_TempSlots)
{
if (slot.RequiresMeshUV(channel))
return true;
}
return false;
}
}
}

11
com.unity.shadergraph/Editor/Data/Nodes/Input/Texture/SampleTexture2DLODNode.cs.meta


fileFormatVersion: 2
guid: 64b637768540cce4f83b9b10cdcacd23
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

41
com.unity.shadergraph/Editor/Data/Nodes/Utility/Logic/IsFrontFaceNode.cs


using UnityEngine;
using UnityEditor.Graphing;
namespace UnityEditor.ShaderGraph
{
[Title("Utility", "Logic", "Is Front Face")]
public class IsFrontFaceNode : AbstractMaterialNode, IGeneratesBodyCode, IMayRequireFaceSign
{
public IsFrontFaceNode()
{
name = "Is Front Face";
UpdateNodeAfterDeserialization();
}
public override string documentationURL
{
get { return "https://github.com/Unity-Technologies/ShaderGraph/wiki/Is-Front-Face-Node"; }
}
public override bool hasPreview { get { return false; } }
public const int OutputSlotId = 0;
private const string kOutputSlotName = "Out";
public override void UpdateNodeAfterDeserialization()
{
AddSlot(new BooleanMaterialSlot(OutputSlotId, kOutputSlotName, kOutputSlotName, SlotType.Output, true, ShaderStageCapability.Fragment));
RemoveSlotsNameNotMatching(new[] { OutputSlotId });
}
public void GenerateNodeCode(ShaderGenerator visitor, GenerationMode generationMode)
{
visitor.AddShaderChunk(string.Format("{0} {1} = max(0, IN.{2});", precision, GetVariableNameForSlot(OutputSlotId), ShaderGeneratorNames.FaceSign), true);
}
public bool RequiresFaceSign(ShaderStageCapability stageCapability = ShaderStageCapability.Fragment)
{
return true;
}
}
}

11
com.unity.shadergraph/Editor/Data/Nodes/Utility/Logic/IsFrontFaceNode.cs.meta


fileFormatVersion: 2
guid: c7e3dd61523f54e52ade29765e299d3f
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

214
com.unity.render-pipelines.core/CoreRP/Editor/Shadow/ShadowCascadeSplitGUI.cs


using System;
using System.IO;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Reflection;
using System.Text;
using UnityEngine;
namespace UnityEditor.Experimental.Rendering
{
static class ShadowCascadeSplitGUI
{
private const int kSliderbarTopMargin = 2;
private const int kSliderbarHeight = 24;
private const int kSliderbarBottomMargin = 2;
private const int kPartitionHandleWidth = 2;
private const int kPartitionHandleExtraHitAreaWidth = 2;
private static readonly Color[] kCascadeColors =
{
new Color(0.5f, 0.5f, 0.6f, 1.0f),
new Color(0.5f, 0.6f, 0.5f, 1.0f),
new Color(0.6f, 0.6f, 0.5f, 1.0f),
new Color(0.6f, 0.5f, 0.5f, 1.0f),
};
// using a LODGroup skin
private static readonly GUIStyle s_CascadeSliderBG = "LODSliderRange";
private static readonly GUIStyle s_TextCenteredStyle = new GUIStyle(EditorStyles.whiteMiniLabel)
{
alignment = TextAnchor.MiddleCenter
};
// Internal struct to bundle drag information
private class DragCache
{
public int m_ActivePartition; // the cascade partition that we are currently dragging/resizing
public float m_NormalizedPartitionSize; // the normalized size of the partition (0.0f < size < 1.0f)
public Vector2 m_LastCachedMousePosition; // mouse position the last time we registered a drag or mouse down.
public DragCache(int activePartition, float normalizedPartitionSize, Vector2 currentMousePos)
{
m_ActivePartition = activePartition;
m_NormalizedPartitionSize = normalizedPartitionSize;
m_LastCachedMousePosition = currentMousePos;
}
};
private static DragCache s_DragCache;
private static readonly int s_CascadeSliderId = "s_CascadeSliderId".GetHashCode();
private static SceneView s_RestoreSceneView;
private static SceneView.CameraMode s_OldSceneDrawMode;
private static bool s_OldSceneLightingMode;
/**
* Static function to handle the GUI and User input related to the cascade slider.
*
* @param normalizedCascadePartition The array of partition sizes in the range 0.0f - 1.0f; expects ONE entry if cascades = 2, and THREE if cascades=4
* The last entry will be automatically determined by summing up the array, and doing 1.0f - sum
*/
public static void HandleCascadeSliderGUI(ref float[] normalizedCascadePartitions)
{
EditorGUILayout.LabelField("Cascade splits");
// get the inspector width since we need it while drawing the partition rects.
// Only way currently is to reserve the block in the layout using GetRect(), and then immediately drawing the empty box
// to match the call to GetRect.
// From this point on, we move to non-layout based code.
var sliderRect = GUILayoutUtility.GetRect(GUIContent.none
, s_CascadeSliderBG
, GUILayout.Height(kSliderbarTopMargin + kSliderbarHeight + kSliderbarBottomMargin)
, GUILayout.ExpandWidth(true));
GUI.Box(sliderRect, GUIContent.none);
float currentX = sliderRect.x;
float cascadeBoxStartY = sliderRect.y + kSliderbarTopMargin;
float cascadeSliderWidth = sliderRect.width - (normalizedCascadePartitions.Length * kPartitionHandleWidth);
Color origTextColor = GUI.color;
Color origBackgroundColor = GUI.backgroundColor;
int colorIndex = -1;
// setup the array locally with the last partition
float[] adjustedCascadePartitions = new float[normalizedCascadePartitions.Length + 1];
System.Array.Copy(normalizedCascadePartitions, adjustedCascadePartitions, normalizedCascadePartitions.Length);
adjustedCascadePartitions[adjustedCascadePartitions.Length - 1] = 1.0f - normalizedCascadePartitions.Sum();
// check for user input on any of the partition handles
// this mechanism gets the current event in the queue... make sure that the mouse is over our control before consuming the event
int sliderControlId = GUIUtility.GetControlID(s_CascadeSliderId, FocusType.Passive);
Event currentEvent = Event.current;
int hotPartitionHandleIndex = -1; // the index of any partition handle that we are hovering over or dragging
// draw each cascade partition
for (int i = 0; i < adjustedCascadePartitions.Length; ++i)
{
float currentPartition = adjustedCascadePartitions[i];
colorIndex = (colorIndex + 1) % kCascadeColors.Length;
GUI.backgroundColor = kCascadeColors[colorIndex];
float boxLength = (cascadeSliderWidth * currentPartition);
// main cascade box
Rect partitionRect = new Rect(currentX, cascadeBoxStartY, boxLength, kSliderbarHeight);
GUI.Box(partitionRect, GUIContent.none, s_CascadeSliderBG);
currentX += boxLength;
// cascade box percentage text
GUI.color = Color.white;
Rect textRect = partitionRect;
var cascadeText = string.Format("{0}\n{1:F1}%", i, currentPartition * 100.0f);
GUI.Label(textRect, cascadeText, s_TextCenteredStyle);
// no need to draw the partition handle for last box
if (i == adjustedCascadePartitions.Length - 1)
break;
// partition handle
GUI.backgroundColor = Color.black;
Rect handleRect = partitionRect;
handleRect.x = currentX;
handleRect.width = kPartitionHandleWidth;
GUI.Box(handleRect, GUIContent.none, s_CascadeSliderBG);
// we want a thin handle visually (since wide black bar looks bad), but a slightly larger
// hit area for easier manipulation
Rect handleHitRect = handleRect;
handleHitRect.xMin -= kPartitionHandleExtraHitAreaWidth;
handleHitRect.xMax += kPartitionHandleExtraHitAreaWidth;
if (handleHitRect.Contains(currentEvent.mousePosition))
hotPartitionHandleIndex = i;
// add regions to slider where the cursor changes to Resize-Horizontal
if (s_DragCache == null)
{
EditorGUIUtility.AddCursorRect(handleHitRect, MouseCursor.ResizeHorizontal, sliderControlId);
}
currentX += kPartitionHandleWidth;
}
GUI.color = origTextColor;
GUI.backgroundColor = origBackgroundColor;
EventType eventType = currentEvent.GetTypeForControl(sliderControlId);
switch (eventType)
{
case EventType.MouseDown:
if (hotPartitionHandleIndex >= 0)
{
s_DragCache = new DragCache(hotPartitionHandleIndex, normalizedCascadePartitions[hotPartitionHandleIndex], currentEvent.mousePosition);
if (GUIUtility.hotControl == 0)
GUIUtility.hotControl = sliderControlId;
currentEvent.Use();
// Switch active scene view into shadow cascades visualization mode, once we start
// tweaking cascade splits.
if (s_RestoreSceneView == null)
{
s_RestoreSceneView = SceneView.lastActiveSceneView;
if (s_RestoreSceneView != null)
{
s_OldSceneDrawMode = s_RestoreSceneView.cameraMode;
s_OldSceneLightingMode = s_RestoreSceneView.m_SceneLighting;
s_RestoreSceneView.cameraMode = SceneView.GetBuiltinCameraMode(DrawCameraMode.ShadowCascades);
}
}
}
break;
case EventType.MouseUp:
// mouseUp event anywhere should release the hotcontrol (if it belongs to us), drags (if any)
if (GUIUtility.hotControl == sliderControlId)
{
GUIUtility.hotControl = 0;
currentEvent.Use();
}
s_DragCache = null;
// Restore previous scene view drawing mode once we stop tweaking cascade splits.
if (s_RestoreSceneView != null)
{
s_RestoreSceneView.cameraMode = s_OldSceneDrawMode;
s_RestoreSceneView.m_SceneLighting = s_OldSceneLightingMode;
s_RestoreSceneView = null;
}
break;
case EventType.MouseDrag:
if (GUIUtility.hotControl != sliderControlId)
break;
// convert the mouse movement to normalized cascade width. Make sure that we are safe to apply the delta before using it.
float delta = (currentEvent.mousePosition - s_DragCache.m_LastCachedMousePosition).x / cascadeSliderWidth;
bool isLeftPartitionHappy = ((adjustedCascadePartitions[s_DragCache.m_ActivePartition] + delta) > 0.0f);
bool isRightPartitionHappy = ((adjustedCascadePartitions[s_DragCache.m_ActivePartition + 1] - delta) > 0.0f);
if (isLeftPartitionHappy && isRightPartitionHappy)
{
s_DragCache.m_NormalizedPartitionSize += delta;
normalizedCascadePartitions[s_DragCache.m_ActivePartition] = s_DragCache.m_NormalizedPartitionSize;
if (s_DragCache.m_ActivePartition < normalizedCascadePartitions.Length - 1)
normalizedCascadePartitions[s_DragCache.m_ActivePartition + 1] -= delta;
GUI.changed = true;
}
s_DragCache.m_LastCachedMousePosition = currentEvent.mousePosition;
currentEvent.Use();
break;
}
}
}
}

11
com.unity.render-pipelines.core/CoreRP/Editor/Shadow/ShadowCascadeSplitGUI.cs.meta


fileFormatVersion: 2
guid: 1a130d84c83d6d24a9c62c149265bfbc
MonoImporter:
externalObjects: {}
serializedVersion: 2
defaultReferences: []
executionOrder: 0
icon: {instanceID: 0}
userData:
assetBundleName:
assetBundleVariant:

1
TestProjects/GraphicsTests/ProjectSettings/ProjectVersion.txt


m_EditorVersion: 2018.2.0b4

1
TestProjects/LWGraphicsTest/ProjectSettings/ProjectVersion.txt


m_EditorVersion: 2018.2.0b1

1
TestProjects/ShaderGraph/ProjectSettings/ProjectVersion.txt


m_EditorVersion: 2018.3.0a1
正在加载...
取消
保存