A game about forced loneliness, made by TACStudios
at master 116 lines 5.8 kB view raw
1using System; 2using UnityEngine; 3using UnityEditor.Graphing; 4using UnityEditor.ShaderGraph.Drawing.Controls; 5 6namespace UnityEditor.ShaderGraph 7{ 8 [Title("Math", "Matrix", "Matrix Construction")] 9 class MatrixConstructionNode : AbstractMaterialNode, IGeneratesBodyCode, IGeneratesFunction 10 { 11 const string kInputSlotM0Name = "M0"; 12 const string kInputSlotM1Name = "M1"; 13 const string kInputSlotM2Name = "M2"; 14 const string kInputSlotM3Name = "M3"; 15 const string kOutput4x4SlotName = "4x4"; 16 const string kOutput3x3SlotName = "3x3"; 17 const string kOutput2x2SlotName = "2x2"; 18 19 public const int InputSlotM0Id = 0; 20 public const int InputSlotM1Id = 1; 21 public const int InputSlotM2Id = 2; 22 public const int InputSlotM3Id = 3; 23 public const int Output4x4SlotId = 4; 24 public const int Output3x3SlotId = 5; 25 public const int Output2x2SlotId = 6; 26 27 public MatrixConstructionNode() 28 { 29 name = "Matrix Construction"; 30 UpdateNodeAfterDeserialization(); 31 } 32 33 [SerializeField] 34 MatrixAxis m_Axis; 35 36 [EnumControl("")] 37 MatrixAxis axis 38 { 39 get { return m_Axis; } 40 set 41 { 42 if (m_Axis.Equals(value)) 43 return; 44 m_Axis = value; 45 Dirty(ModificationScope.Graph); 46 } 47 } 48 49 string GetFunctionName() 50 { 51 return $"Unity_MatrixConstruction_{axis}_$precision"; 52 } 53 54 public sealed override void UpdateNodeAfterDeserialization() 55 { 56 AddSlot(new Vector4MaterialSlot(InputSlotM0Id, kInputSlotM0Name, kInputSlotM0Name, SlotType.Input, Vector4.zero)); 57 AddSlot(new Vector4MaterialSlot(InputSlotM1Id, kInputSlotM1Name, kInputSlotM1Name, SlotType.Input, Vector4.zero)); 58 AddSlot(new Vector4MaterialSlot(InputSlotM2Id, kInputSlotM2Name, kInputSlotM2Name, SlotType.Input, Vector4.zero)); 59 AddSlot(new Vector4MaterialSlot(InputSlotM3Id, kInputSlotM3Name, kInputSlotM3Name, SlotType.Input, Vector4.zero)); 60 AddSlot(new Matrix4MaterialSlot(Output4x4SlotId, kOutput4x4SlotName, kOutput4x4SlotName, SlotType.Output)); 61 AddSlot(new Matrix3MaterialSlot(Output3x3SlotId, kOutput3x3SlotName, kOutput3x3SlotName, SlotType.Output)); 62 AddSlot(new Matrix2MaterialSlot(Output2x2SlotId, kOutput2x2SlotName, kOutput2x2SlotName, SlotType.Output)); 63 RemoveSlotsNameNotMatching(new int[] { InputSlotM0Id, InputSlotM1Id, InputSlotM2Id, InputSlotM3Id, Output4x4SlotId, Output3x3SlotId, Output2x2SlotId }); 64 } 65 66 public void GenerateNodeCode(ShaderStringBuilder sb, GenerationMode generationMode) 67 { 68 var inputM0Value = GetSlotValue(InputSlotM0Id, generationMode); 69 var inputM1Value = GetSlotValue(InputSlotM1Id, generationMode); 70 var inputM2Value = GetSlotValue(InputSlotM2Id, generationMode); 71 var inputM3Value = GetSlotValue(InputSlotM3Id, generationMode); 72 73 sb.AppendLine("{0} {1};", FindOutputSlot<MaterialSlot>(Output4x4SlotId).concreteValueType.ToShaderString(), GetVariableNameForSlot(Output4x4SlotId)); 74 sb.AppendLine("{0} {1};", FindOutputSlot<MaterialSlot>(Output3x3SlotId).concreteValueType.ToShaderString(), GetVariableNameForSlot(Output3x3SlotId)); 75 sb.AppendLine("{0} {1};", FindOutputSlot<MaterialSlot>(Output2x2SlotId).concreteValueType.ToShaderString(), GetVariableNameForSlot(Output2x2SlotId)); 76 sb.AppendLine("{0}({1}, {2}, {3}, {4}, {5}, {6}, {7});", 77 GetFunctionName(), 78 inputM0Value, 79 inputM1Value, 80 inputM2Value, 81 inputM3Value, 82 GetVariableNameForSlot(Output4x4SlotId), 83 GetVariableNameForSlot(Output3x3SlotId), 84 GetVariableNameForSlot(Output2x2SlotId)); 85 } 86 87 public void GenerateNodeFunction(FunctionRegistry registry, GenerationMode generationMode) 88 { 89 registry.ProvideFunction(GetFunctionName(), s => 90 { 91 s.AppendLine("void {0} ({1} M0, {1} M1, {1} M2, {1} M3, out {2} Out4x4, out {3} Out3x3, out {4} Out2x2)", 92 GetFunctionName(), 93 FindInputSlot<MaterialSlot>(InputSlotM0Id).concreteValueType.ToShaderString(), 94 FindOutputSlot<MaterialSlot>(Output4x4SlotId).concreteValueType.ToShaderString(), 95 FindOutputSlot<MaterialSlot>(Output3x3SlotId).concreteValueType.ToShaderString(), 96 FindOutputSlot<MaterialSlot>(Output2x2SlotId).concreteValueType.ToShaderString()); 97 using (s.BlockScope()) 98 { 99 switch (m_Axis) 100 { 101 case MatrixAxis.Column: 102 s.AppendLine("Out4x4 = $precision4x4(M0.x, M1.x, M2.x, M3.x, M0.y, M1.y, M2.y, M3.y, M0.z, M1.z, M2.z, M3.z, M0.w, M1.w, M2.w, M3.w);"); 103 s.AppendLine("Out3x3 = $precision3x3(M0.x, M1.x, M2.x, M0.y, M1.y, M2.y, M0.z, M1.z, M2.z);"); 104 s.AppendLine("Out2x2 = $precision2x2(M0.x, M1.x, M0.y, M1.y);"); 105 break; 106 default: 107 s.AppendLine("Out4x4 = $precision4x4(M0.x, M0.y, M0.z, M0.w, M1.x, M1.y, M1.z, M1.w, M2.x, M2.y, M2.z, M2.w, M3.x, M3.y, M3.z, M3.w);"); 108 s.AppendLine("Out3x3 = $precision3x3(M0.x, M0.y, M0.z, M1.x, M1.y, M1.z, M2.x, M2.y, M2.z);"); 109 s.AppendLine("Out2x2 = $precision2x2(M0.x, M0.y, M1.x, M1.y);"); 110 break; 111 } 112 } 113 }); 114 } 115 } 116}