You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

215 lines
7.1 KiB

  1. using UnityEngine;
  2. using UnityEditor;
  3. using System;
  4. namespace AmplifyShaderEditor
  5. {
  6. [Serializable]
  7. [NodeAttributes( "Matrix From Vectors", "Matrix Operators", "Matrix From Vectors" )]
  8. public sealed class MatrixFromVectors : ParentNode
  9. {
  10. private const string RowFromVector = "Input to Row";
  11. [SerializeField]
  12. private WirePortDataType m_selectedOutputType = WirePortDataType.FLOAT3x3;
  13. [SerializeField]
  14. private int m_selectedOutputTypeInt = 0;
  15. [SerializeField]
  16. private Vector3[] m_defaultValuesV3 = { Vector3.zero, Vector3.zero, Vector3.zero };
  17. [SerializeField]
  18. private Vector4[] m_defaultValuesV4 = { Vector4.zero, Vector4.zero, Vector4.zero, Vector4.zero };
  19. [SerializeField]
  20. private bool m_rowsFromVector = true;
  21. private string[] m_defaultValuesStr = { "[0]", "[1]", "[2]", "[3]" };
  22. private readonly string[] _outputValueTypes ={ "Matrix3X3",
  23. "Matrix4X4"};
  24. private UpperLeftWidgetHelper m_upperLeftWidget = new UpperLeftWidgetHelper();
  25. protected override void CommonInit( int uniqueId )
  26. {
  27. base.CommonInit( uniqueId );
  28. AddInputPort( WirePortDataType.FLOAT4, false, "[0]" );
  29. AddInputPort( WirePortDataType.FLOAT4, false, "[1]" );
  30. AddInputPort( WirePortDataType.FLOAT4, false, "[2]" );
  31. AddInputPort( WirePortDataType.FLOAT4, false, "[3]" );
  32. AddOutputPort( m_selectedOutputType, Constants.EmptyPortValue );
  33. m_textLabelWidth = 90;
  34. m_autoWrapProperties = true;
  35. m_hasLeftDropdown = true;
  36. UpdatePorts();
  37. }
  38. public override void AfterCommonInit()
  39. {
  40. base.AfterCommonInit();
  41. if( PaddingTitleLeft == 0 )
  42. {
  43. PaddingTitleLeft = Constants.PropertyPickerWidth + Constants.IconsLeftRightMargin;
  44. if( PaddingTitleRight == 0 )
  45. PaddingTitleRight = Constants.PropertyPickerWidth + Constants.IconsLeftRightMargin;
  46. }
  47. }
  48. public override void Destroy()
  49. {
  50. base.Destroy();
  51. m_upperLeftWidget = null;
  52. }
  53. public override void Draw( DrawInfo drawInfo )
  54. {
  55. base.Draw( drawInfo );
  56. EditorGUI.BeginChangeCheck();
  57. m_selectedOutputTypeInt = m_upperLeftWidget.DrawWidget( this, m_selectedOutputTypeInt, _outputValueTypes );
  58. if( EditorGUI.EndChangeCheck() )
  59. {
  60. switch( m_selectedOutputTypeInt )
  61. {
  62. case 0: m_selectedOutputType = WirePortDataType.FLOAT3x3; break;
  63. case 1: m_selectedOutputType = WirePortDataType.FLOAT4x4; break;
  64. }
  65. UpdatePorts();
  66. }
  67. }
  68. public override void DrawProperties()
  69. {
  70. base.DrawProperties();
  71. EditorGUI.BeginChangeCheck();
  72. m_selectedOutputTypeInt = EditorGUILayoutPopup( "Output type", m_selectedOutputTypeInt, _outputValueTypes );
  73. if( EditorGUI.EndChangeCheck() )
  74. {
  75. switch( m_selectedOutputTypeInt )
  76. {
  77. case 0: m_selectedOutputType = WirePortDataType.FLOAT3x3; break;
  78. case 1: m_selectedOutputType = WirePortDataType.FLOAT4x4; break;
  79. }
  80. UpdatePorts();
  81. }
  82. int count = 0;
  83. switch( m_selectedOutputType )
  84. {
  85. case WirePortDataType.FLOAT3x3:
  86. count = 3;
  87. for( int i = 0; i < count; i++ )
  88. {
  89. if( !m_inputPorts[ i ].IsConnected )
  90. m_defaultValuesV3[ i ] = EditorGUILayoutVector3Field( m_defaultValuesStr[ i ], m_defaultValuesV3[ i ] );
  91. }
  92. break;
  93. case WirePortDataType.FLOAT4x4:
  94. count = 4;
  95. for( int i = 0; i < count; i++ )
  96. {
  97. if( !m_inputPorts[ i ].IsConnected )
  98. m_defaultValuesV4[ i ] = EditorGUILayoutVector4Field( m_defaultValuesStr[ i ], m_defaultValuesV4[ i ] );
  99. }
  100. break;
  101. }
  102. m_rowsFromVector = EditorGUILayoutToggle( RowFromVector, m_rowsFromVector );
  103. }
  104. void UpdatePorts()
  105. {
  106. m_sizeIsDirty = true;
  107. ChangeOutputType( m_selectedOutputType, false );
  108. switch( m_selectedOutputType )
  109. {
  110. case WirePortDataType.FLOAT3x3:
  111. m_inputPorts[ 0 ].ChangeType( WirePortDataType.FLOAT3, false );
  112. m_inputPorts[ 1 ].ChangeType( WirePortDataType.FLOAT3, false );
  113. m_inputPorts[ 2 ].ChangeType( WirePortDataType.FLOAT3, false );
  114. m_inputPorts[ 3 ].ChangeType( WirePortDataType.FLOAT3, false );
  115. m_inputPorts[ 3 ].Visible = false;
  116. break;
  117. case WirePortDataType.FLOAT4x4:
  118. m_inputPorts[ 0 ].ChangeType( WirePortDataType.FLOAT4, false );
  119. m_inputPorts[ 1 ].ChangeType( WirePortDataType.FLOAT4, false );
  120. m_inputPorts[ 2 ].ChangeType( WirePortDataType.FLOAT4, false );
  121. m_inputPorts[ 3 ].ChangeType( WirePortDataType.FLOAT4, false );
  122. m_inputPorts[ 3 ].Visible = true;
  123. break;
  124. }
  125. }
  126. public override string GenerateShaderForOutput( int outputId, ref MasterNodeDataCollector dataCollector, bool ignoreLocalvar )
  127. {
  128. base.GenerateShaderForOutput( outputId, ref dataCollector, ignoreLocalvar );
  129. string result = "";
  130. switch( m_selectedOutputType )
  131. {
  132. case WirePortDataType.FLOAT3x3:
  133. if( m_rowsFromVector )
  134. {
  135. result = "float3x3(" + m_inputPorts[ 0 ].GeneratePortInstructions( ref dataCollector ) + ", "
  136. + m_inputPorts[ 1 ].GeneratePortInstructions( ref dataCollector ) + ", "
  137. + m_inputPorts[ 2 ].GeneratePortInstructions( ref dataCollector ) + ")";
  138. }
  139. else
  140. {
  141. string vec0 = m_inputPorts[ 0 ].GeneratePortInstructions( ref dataCollector );
  142. string vec1 = m_inputPorts[ 1 ].GeneratePortInstructions( ref dataCollector );
  143. string vec2 = m_inputPorts[ 2 ].GeneratePortInstructions( ref dataCollector );
  144. result = string.Format( "float3x3({0}.x,{1}.x,{2}.x,{0}.y,{1}.y,{2}.y,{0}.z,{1}.z,{2}.z )", vec0, vec1, vec2 );
  145. }
  146. break;
  147. case WirePortDataType.FLOAT4x4:
  148. if( m_rowsFromVector )
  149. {
  150. result = "float4x4(" + m_inputPorts[ 0 ].GeneratePortInstructions( ref dataCollector ) + ", "
  151. + m_inputPorts[ 1 ].GeneratePortInstructions( ref dataCollector ) + ", "
  152. + m_inputPorts[ 2 ].GeneratePortInstructions( ref dataCollector ) + ", "
  153. + m_inputPorts[ 3 ].GeneratePortInstructions( ref dataCollector ) + ")";
  154. }
  155. else
  156. {
  157. string vec0 = m_inputPorts[ 0 ].GeneratePortInstructions( ref dataCollector );
  158. string vec1 = m_inputPorts[ 1 ].GeneratePortInstructions( ref dataCollector );
  159. string vec2 = m_inputPorts[ 2 ].GeneratePortInstructions( ref dataCollector );
  160. string vec3 = m_inputPorts[ 3 ].GeneratePortInstructions( ref dataCollector );
  161. result = string.Format( "float4x4( {0}.x,{1}.x,{2}.x,{3}.x,{0}.y,{1}.y,{2}.y,{3}.y,{0}.z,{1}.z,{2}.z,{3}.z,{0}.w,{1}.w,{2}.w,{3}.w )", vec0, vec1, vec2, vec3 );
  162. }
  163. break;
  164. }
  165. return result;
  166. }
  167. public override void ReadFromString( ref string[] nodeParams )
  168. {
  169. base.ReadFromString( ref nodeParams );
  170. m_selectedOutputType = (WirePortDataType)Enum.Parse( typeof( WirePortDataType ), GetCurrentParam( ref nodeParams ) );
  171. if( UIUtils.CurrentShaderVersion() > 15310 )
  172. {
  173. m_rowsFromVector = Convert.ToBoolean( GetCurrentParam( ref nodeParams ) );
  174. }
  175. switch( m_selectedOutputType )
  176. {
  177. case WirePortDataType.FLOAT3x3:
  178. m_selectedOutputTypeInt = 0;
  179. break;
  180. case WirePortDataType.FLOAT4x4:
  181. m_selectedOutputTypeInt = 1;
  182. break;
  183. }
  184. UpdatePorts();
  185. }
  186. public override void WriteToString( ref string nodeInfo, ref string connectionsInfo )
  187. {
  188. base.WriteToString( ref nodeInfo, ref connectionsInfo );
  189. IOUtils.AddFieldValueToString( ref nodeInfo, m_selectedOutputType );
  190. IOUtils.AddFieldValueToString( ref nodeInfo, m_rowsFromVector );
  191. }
  192. }
  193. }