Assignment for RMIT Mixed Reality in 2020
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.

837 lines
26 KiB

  1. // Amplify Shader Editor - Visual Shader Editing Tool
  2. // Copyright (c) Amplify Creations, Lda <info@amplify.pt>
  3. using System;
  4. using System.IO;
  5. using System.Collections.Generic;
  6. using UnityEditor;
  7. using UnityEngine;
  8. using UnityEditorInternal;
  9. namespace AmplifyShaderEditor
  10. {
  11. public enum AdditionalLineType
  12. {
  13. Include,
  14. Define,
  15. Pragma,
  16. Custom
  17. }
  18. public enum AdditionalContainerOrigin
  19. {
  20. Native,
  21. ShaderFunction,
  22. Custom
  23. }
  24. [Serializable]
  25. public class AdditionalDirectiveContainerSaveItem
  26. {
  27. public AdditionalLineType LineType = AdditionalLineType.Include;
  28. public string LineValue = string.Empty;
  29. public bool GUIDToggle = false;
  30. public string GUIDValue = string.Empty;
  31. public AdditionalContainerOrigin Origin = AdditionalContainerOrigin.Custom;
  32. public AdditionalDirectiveContainerSaveItem( AdditionalLineType lineType, string lineValue, bool guidToggle, string guidValue, AdditionalContainerOrigin origin )
  33. {
  34. LineType = lineType;
  35. LineValue = lineValue;
  36. GUIDToggle = guidToggle;
  37. GUIDValue = guidValue;
  38. Origin = origin;
  39. }
  40. public AdditionalDirectiveContainerSaveItem( AdditionalDirectiveContainer container )
  41. {
  42. LineType = container.LineType;
  43. LineValue = container.LineValue;
  44. GUIDToggle = container.GUIDToggle;
  45. GUIDValue = container.GUIDValue;
  46. Origin = container.Origin;
  47. }
  48. }
  49. [Serializable]
  50. public class AdditionalDirectiveContainer : ScriptableObject
  51. {
  52. public AdditionalLineType LineType = AdditionalLineType.Include;
  53. public string LineValue = string.Empty;
  54. public bool GUIDToggle = false;
  55. public string GUIDValue = string.Empty;
  56. public AdditionalContainerOrigin Origin = AdditionalContainerOrigin.Custom;
  57. public TextAsset LibObject = null;
  58. public string OwnerId = string.Empty;
  59. public void Init( string ownerId, AdditionalDirectiveContainer item )
  60. {
  61. LineType = item.LineType;
  62. LineValue = item.LineValue;
  63. GUIDToggle = item.GUIDToggle;
  64. GUIDValue = item.GUIDValue;
  65. Origin = item.Origin;
  66. LibObject = item.LibObject;
  67. OwnerId = ownerId;
  68. }
  69. public void Init( AdditionalDirectiveContainerSaveItem item )
  70. {
  71. LineType = item.LineType;
  72. LineValue = item.LineValue;
  73. GUIDToggle = item.GUIDToggle;
  74. GUIDValue = item.GUIDValue;
  75. Origin = item.Origin;
  76. if( GUIDToggle )
  77. {
  78. LibObject = AssetDatabase.LoadAssetAtPath<TextAsset>( AssetDatabase.GUIDToAssetPath( GUIDValue ) );
  79. }
  80. }
  81. public void OnDestroy()
  82. {
  83. //Debug.Log( "Destoying directives" );
  84. LibObject = null;
  85. }
  86. public string Value
  87. {
  88. get
  89. {
  90. switch( LineType )
  91. {
  92. case AdditionalLineType.Include:
  93. {
  94. if( GUIDToggle )
  95. {
  96. string shaderPath = AssetDatabase.GUIDToAssetPath( GUIDValue );
  97. if( !string.IsNullOrEmpty( shaderPath ) )
  98. return shaderPath;
  99. }
  100. return LineValue;
  101. }
  102. case AdditionalLineType.Define: return LineValue;
  103. case AdditionalLineType.Pragma: return LineValue;
  104. }
  105. return LineValue;
  106. }
  107. }
  108. public string FormattedValue
  109. {
  110. get
  111. {
  112. switch( LineType )
  113. {
  114. case AdditionalLineType.Include:
  115. {
  116. if( GUIDToggle )
  117. {
  118. string shaderPath = AssetDatabase.GUIDToAssetPath( GUIDValue );
  119. if( !string.IsNullOrEmpty( shaderPath ) )
  120. return string.Format( Constants.IncludeFormat, shaderPath );
  121. }
  122. return string.Format( Constants.IncludeFormat, LineValue );
  123. }
  124. case AdditionalLineType.Define:
  125. return string.Format( Constants.DefineFormat, LineValue );
  126. case AdditionalLineType.Pragma:
  127. return string.Format( Constants.PragmaFormat, LineValue );
  128. }
  129. return LineValue;
  130. }
  131. }
  132. }
  133. public enum ReordableAction
  134. {
  135. None,
  136. Add,
  137. Remove
  138. }
  139. [Serializable]
  140. public sealed class TemplateAdditionalDirectivesHelper : TemplateModuleParent
  141. {
  142. private string NativeFoldoutStr = "Native";
  143. [SerializeField]
  144. private List<AdditionalDirectiveContainer> m_additionalDirectives = new List<AdditionalDirectiveContainer>();
  145. [SerializeField]
  146. private List<AdditionalDirectiveContainer> m_shaderFunctionDirectives = new List<AdditionalDirectiveContainer>();
  147. [SerializeField]
  148. private List<string> m_nativeDirectives = new List<string>();
  149. [SerializeField]
  150. private int m_nativeDirectivesIndex = -1;
  151. [SerializeField]
  152. private bool m_nativeDirectivesFoldout = false;
  153. //ONLY USED BY SHADER FUNCTIONS
  154. // Since AdditionalDirectiveContainer must be a ScriptableObject because of serialization shenanigans it will not serialize the info correctly into the shader function when saving it into a file ( it only saves the id )
  155. // For it to properly work, each AdditionalDirectiveContainer should be added to the SF asset, but that would make it to have children ( which are seen on the project inspector )
  156. // Must revisit this later on and come up with a proper solution
  157. [SerializeField]
  158. private List<AdditionalDirectiveContainerSaveItem> m_directivesSaveItems = new List<AdditionalDirectiveContainerSaveItem>();
  159. private ReordableAction m_actionType = ReordableAction.None;
  160. private int m_actionIndex = 0;
  161. private ReorderableList m_reordableList = null;
  162. private GUIStyle m_propertyAdjustment;
  163. private UndoParentNode m_currOwner;
  164. private Rect m_nativeRect = Rect.zero;
  165. public TemplateAdditionalDirectivesHelper( string moduleName ) : base( moduleName ) { }
  166. //public void AddShaderFunctionItem( AdditionalLineType type, string item )
  167. //{
  168. // UpdateShaderFunctionDictionary();
  169. // string id = type + item;
  170. // if( !m_shaderFunctionDictionary.ContainsKey( id ) )
  171. // {
  172. // AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  173. // newItem.LineType = type;
  174. // newItem.LineValue = item;
  175. // newItem.hideFlags = HideFlags.HideAndDontSave;
  176. // m_shaderFunctionDirectives.Add( newItem );
  177. // m_shaderFunctionDictionary.Add( id, newItem );
  178. // }
  179. //}
  180. public void AddShaderFunctionItems( string ownerOutputId, List<AdditionalDirectiveContainer> functionList )
  181. {
  182. RemoveShaderFunctionItems( ownerOutputId );
  183. if( functionList.Count > 0 )
  184. {
  185. for( int i = 0; i < functionList.Count; i++ )
  186. {
  187. AdditionalDirectiveContainer item = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  188. item.Init( ownerOutputId, functionList[ i ] );
  189. m_shaderFunctionDirectives.Add( item );
  190. }
  191. }
  192. //if( functionList.Count > 0 )
  193. //{
  194. // m_shaderFunctionDirectives.AddRange( functionList );
  195. //}
  196. }
  197. public void RemoveShaderFunctionItems( string ownerOutputId/*, List<AdditionalDirectiveContainer> functionList */)
  198. {
  199. List<AdditionalDirectiveContainer> list = m_shaderFunctionDirectives.FindAll( ( x ) => x.OwnerId.Equals( ownerOutputId ));
  200. for( int i = 0; i < list.Count; i++ )
  201. {
  202. m_shaderFunctionDirectives.Remove( list[ i ] );
  203. ScriptableObject.DestroyImmediate( list[ i ] );
  204. }
  205. list.Clear();
  206. list = null;
  207. //for( int i = 0; i < functionList.Count; i++ )
  208. //{
  209. // m_shaderFunctionDirectives.Remove( functionList[ i ] );
  210. //}
  211. }
  212. //public void RemoveShaderFunctionItem( AdditionalLineType type, string item )
  213. //{
  214. // m_shaderFunctionDirectives.RemoveAll( x => x.LineType == type && x.LineValue.Equals( item ) );
  215. //}
  216. public void AddItems( AdditionalLineType type, List<string> items )
  217. {
  218. int count = items.Count;
  219. for( int i = 0; i < count; i++ )
  220. {
  221. AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  222. newItem.LineType = type;
  223. newItem.LineValue = items[ i ];
  224. newItem.hideFlags = HideFlags.HideAndDontSave;
  225. m_additionalDirectives.Add( newItem );
  226. }
  227. UpdateNativeIndex();
  228. }
  229. public void AddNativeContainer()
  230. {
  231. if( m_nativeDirectives.Count > 0 )
  232. {
  233. if( m_additionalDirectives.FindIndex( x => x.Origin.Equals( AdditionalContainerOrigin.Native ) ) == -1 )
  234. {
  235. AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  236. newItem.Origin = AdditionalContainerOrigin.Native;
  237. newItem.hideFlags = HideFlags.HideAndDontSave;
  238. //m_additionalDirectives.Add( newItem );
  239. //m_nativeDirectivesIndex = m_additionalDirectives.Count - 1;
  240. m_additionalDirectives.Insert( 0, newItem );
  241. m_nativeDirectivesIndex = 0;
  242. }
  243. }
  244. }
  245. public void FillNativeItems( List<string> nativeItems )
  246. {
  247. m_nativeDirectives.Clear();
  248. m_nativeDirectives.AddRange( nativeItems );
  249. AddNativeContainer();
  250. }
  251. void DrawNativeItems()
  252. {
  253. EditorGUILayout.Separator();
  254. EditorGUI.indentLevel++;
  255. int count = m_nativeDirectives.Count;
  256. for( int i = 0; i < count; i++ )
  257. {
  258. EditorGUILayout.LabelField( m_nativeDirectives[ i ] );
  259. }
  260. EditorGUI.indentLevel--;
  261. EditorGUILayout.Separator();
  262. }
  263. void DrawNativeItemsRect()
  264. {
  265. int count = m_nativeDirectives.Count;
  266. m_nativeRect.y += EditorGUIUtility.singleLineHeight;
  267. for( int i = 0; i < count; i++ )
  268. {
  269. EditorGUI.LabelField( m_nativeRect, m_nativeDirectives[ i ] );
  270. m_nativeRect.y += EditorGUIUtility.singleLineHeight;
  271. }
  272. }
  273. void DrawButtons()
  274. {
  275. EditorGUILayout.Separator();
  276. // Add keyword
  277. if( GUILayout.Button( string.Empty, UIUtils.PlusStyle, GUILayout.Width( Constants.PlusMinusButtonLayoutWidth ) ) )
  278. {
  279. AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  280. newItem.hideFlags = HideFlags.HideAndDontSave;
  281. m_additionalDirectives.Add( newItem );
  282. UpdateNativeIndex();
  283. EditorGUI.FocusTextInControl( null );
  284. m_isDirty = true;
  285. }
  286. //Remove keyword
  287. if( GUILayout.Button( string.Empty, UIUtils.MinusStyle, GUILayout.Width( Constants.PlusMinusButtonLayoutWidth ) ) )
  288. {
  289. if( m_additionalDirectives.Count > 0 )
  290. {
  291. AdditionalDirectiveContainer itemToDelete = m_additionalDirectives[ m_additionalDirectives.Count - 1 ];
  292. m_additionalDirectives.RemoveAt( m_additionalDirectives.Count - 1 );
  293. ScriptableObject.DestroyImmediate( itemToDelete );
  294. EditorGUI.FocusTextInControl( null );
  295. }
  296. m_isDirty = true;
  297. }
  298. }
  299. public override void Draw( UndoParentNode currOwner, bool style = true )
  300. {
  301. m_currOwner = currOwner;
  302. if( m_reordableList == null )
  303. {
  304. m_reordableList = new ReorderableList( m_additionalDirectives, typeof( AdditionalDirectiveContainer ), true, false, false, false )
  305. {
  306. headerHeight = 0,
  307. footerHeight = 0,
  308. showDefaultBackground = false,
  309. elementHeightCallback = ( index ) =>
  310. {
  311. if( m_additionalDirectives[ index ].Origin == AdditionalContainerOrigin.Native && m_nativeDirectivesFoldout )
  312. {
  313. return ( m_nativeDirectives.Count + 1 ) * ( EditorGUIUtility.singleLineHeight ) + 5;
  314. }
  315. return EditorGUIUtility.singleLineHeight + 5;
  316. },
  317. drawElementCallback = ( Rect rect, int index, bool isActive, bool isFocused ) =>
  318. {
  319. if( m_additionalDirectives[ index ].Origin == AdditionalContainerOrigin.Native && m_nativeDirectivesFoldout )
  320. {
  321. rect.height = ( m_nativeDirectives.Count + 1 ) * ( EditorGUIUtility.singleLineHeight ) + 5;
  322. }
  323. if( m_additionalDirectives[ index ] != null )
  324. {
  325. float labelWidthStyleAdjust = 0;
  326. if( style )
  327. {
  328. rect.xMin -= 10;
  329. labelWidthStyleAdjust = 15;
  330. }
  331. else
  332. {
  333. rect.xMin -= 1;
  334. }
  335. float popUpWidth = style ? 80 : 65f;
  336. float widthAdjust = m_additionalDirectives[ index ].LineType == AdditionalLineType.Include ? -14 : 0;
  337. Rect popupPos = new Rect( rect.x, rect.y, popUpWidth, EditorGUIUtility.singleLineHeight );
  338. Rect GUIDTogglePos = m_additionalDirectives[ index ].LineType == AdditionalLineType.Include ? new Rect( rect.x + rect.width - 3 * Constants.PlusMinusButtonLayoutWidth, rect.y, Constants.PlusMinusButtonLayoutWidth, Constants.PlusMinusButtonLayoutWidth ) : new Rect();
  339. Rect buttonPlusPos = new Rect( rect.x + rect.width - 2 * Constants.PlusMinusButtonLayoutWidth, rect.y - 2, Constants.PlusMinusButtonLayoutWidth, Constants.PlusMinusButtonLayoutWidth );
  340. Rect buttonMinusPos = new Rect( rect.x + rect.width - Constants.PlusMinusButtonLayoutWidth, rect.y - 2, Constants.PlusMinusButtonLayoutWidth, Constants.PlusMinusButtonLayoutWidth );
  341. float labelWidthBuffer = EditorGUIUtility.labelWidth;
  342. Rect labelPos = new Rect( rect.x + popupPos.width - labelWidthStyleAdjust, rect.y, labelWidthStyleAdjust + rect.width - popupPos.width - buttonPlusPos.width - buttonMinusPos.width + widthAdjust, EditorGUIUtility.singleLineHeight );
  343. if( m_additionalDirectives[ index ].Origin == AdditionalContainerOrigin.Native )
  344. {
  345. m_nativeRect = rect;
  346. #if UNITY_2019_3_OR_NEWER
  347. m_nativeRect.y -= ( m_nativeRect.height - ( EditorGUIUtility.singleLineHeight + 5 ) ) * 0.5f;
  348. #endif
  349. m_nativeRect.xMin += 2;
  350. m_nativeRect.xMax -= 2;
  351. m_nativeRect.yMax -= 2;
  352. NodeUtils.DrawNestedPropertyGroup( ref m_nativeDirectivesFoldout, rect, NativeFoldoutStr, DrawNativeItemsRect, 4 );
  353. return;
  354. }
  355. m_additionalDirectives[ index ].LineType = (AdditionalLineType)m_currOwner.EditorGUIEnumPopup( popupPos, m_additionalDirectives[ index ].LineType );
  356. if( m_additionalDirectives[ index ].LineType == AdditionalLineType.Include )
  357. {
  358. if( m_additionalDirectives[ index ].GUIDToggle )
  359. {
  360. //if( m_additionalDirectives[ index ].LibObject == null && !string.IsNullOrEmpty( m_additionalDirectives[ index ].GUIDValue ) )
  361. //{
  362. // m_additionalDirectives[ index ].LibObject = AssetDatabase.LoadAssetAtPath<TextAsset>( AssetDatabase.GUIDToAssetPath( m_additionalDirectives[ index ].GUIDValue ) );
  363. //}
  364. EditorGUI.BeginChangeCheck();
  365. TextAsset obj = m_currOwner.EditorGUIObjectField( labelPos, m_additionalDirectives[ index ].LibObject, typeof( TextAsset ), false ) as TextAsset;
  366. if( EditorGUI.EndChangeCheck() )
  367. {
  368. string pathName = AssetDatabase.GetAssetPath( obj );
  369. string extension = Path.GetExtension( pathName );
  370. extension = extension.ToLower();
  371. if( extension.Equals( ".cginc" ) || extension.Equals( ".hlsl" ) )
  372. {
  373. m_additionalDirectives[ index ].LibObject = obj;
  374. m_additionalDirectives[ index ].GUIDValue = AssetDatabase.AssetPathToGUID( pathName );
  375. }
  376. }
  377. }
  378. else
  379. {
  380. m_additionalDirectives[ index ].LineValue = m_currOwner.EditorGUITextField( labelPos, string.Empty, m_additionalDirectives[ index ].LineValue );
  381. }
  382. if( GUI.Button( GUIDTogglePos, m_additionalDirectives[ index ].GUIDToggle ? UIUtils.FloatIntIconOFF : UIUtils.FloatIntIconON, UIUtils.FloatIntPickerONOFF ) )
  383. m_additionalDirectives[ index ].GUIDToggle = !m_additionalDirectives[ index ].GUIDToggle;
  384. }
  385. else
  386. {
  387. m_additionalDirectives[ index ].LineValue = m_currOwner.EditorGUITextField( labelPos, string.Empty, m_additionalDirectives[ index ].LineValue );
  388. }
  389. if( GUI.Button( buttonPlusPos, string.Empty, UIUtils.PlusStyle ) )
  390. {
  391. m_actionType = ReordableAction.Add;
  392. m_actionIndex = index;
  393. }
  394. if( GUI.Button( buttonMinusPos, string.Empty, UIUtils.MinusStyle ) )
  395. {
  396. m_actionType = ReordableAction.Remove;
  397. m_actionIndex = index;
  398. }
  399. }
  400. },
  401. onReorderCallback = ( ReorderableList list ) =>
  402. {
  403. UpdateNativeIndex();
  404. }
  405. };
  406. }
  407. if( m_actionType != ReordableAction.None )
  408. {
  409. switch( m_actionType )
  410. {
  411. case ReordableAction.Add:
  412. {
  413. AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  414. newItem.hideFlags = HideFlags.HideAndDontSave;
  415. m_additionalDirectives.Insert( m_actionIndex + 1, newItem );
  416. }
  417. break;
  418. case ReordableAction.Remove:
  419. AdditionalDirectiveContainer itemToDelete = m_additionalDirectives[ m_actionIndex ];
  420. m_additionalDirectives.RemoveAt( m_actionIndex );
  421. ScriptableObject.DestroyImmediate( itemToDelete );
  422. break;
  423. }
  424. m_isDirty = true;
  425. m_actionType = ReordableAction.None;
  426. EditorGUI.FocusTextInControl( null );
  427. }
  428. bool foldoutValue = currOwner.ContainerGraph.ParentWindow.InnerWindowVariables.ExpandedAdditionalDirectives;
  429. if( style )
  430. {
  431. NodeUtils.DrawPropertyGroup( ref foldoutValue, m_moduleName, DrawReordableList, DrawButtons );
  432. }
  433. else
  434. {
  435. NodeUtils.DrawNestedPropertyGroup( ref foldoutValue, m_moduleName, DrawReordableList, DrawButtons );
  436. }
  437. currOwner.ContainerGraph.ParentWindow.InnerWindowVariables.ExpandedAdditionalDirectives = foldoutValue;
  438. }
  439. void DrawReordableList()
  440. {
  441. if( m_reordableList != null )
  442. {
  443. if( m_propertyAdjustment == null )
  444. {
  445. m_propertyAdjustment = new GUIStyle();
  446. m_propertyAdjustment.padding.left = 17;
  447. }
  448. //EditorGUILayout.BeginVertical( m_propertyAdjustment );
  449. EditorGUILayout.Space();
  450. if( m_nativeDirectives.Count > 0 )
  451. {
  452. //NodeUtils.DrawNestedPropertyGroup( ref m_nativeDirectivesFoldout, NativeFoldoutStr, DrawNativeItems, 4 );
  453. }
  454. if( m_additionalDirectives.Count == 0 )
  455. {
  456. EditorGUILayout.HelpBox( "Your list is Empty!\nUse the plus button to add one.", MessageType.Info );
  457. }
  458. else
  459. {
  460. m_reordableList.DoLayoutList();
  461. }
  462. EditorGUILayout.Space();
  463. //EditorGUILayout.EndVertical();
  464. }
  465. }
  466. public void AddAllToDataCollector( ref MasterNodeDataCollector dataCollector, TemplateIncludePragmaContainter nativesContainer )
  467. {
  468. //List<AdditionalDirectiveContainer> list = m_additionalDirectives;
  469. //int count = list.FindIndex( x => x.Origin.Equals( AdditionalContainerOrigin.Native ) );
  470. //for( int i = 0; i < count; i++ )
  471. //{
  472. // switch( list[ i ].LineType )
  473. // {
  474. // case AdditionalLineType.Include:
  475. // {
  476. // string value = list[ i ].Value;
  477. // if( !string.IsNullOrEmpty( value ) &&
  478. // !nativesContainer.HasInclude( value ) )
  479. // {
  480. // dataCollector.AddToMisc( list[ i ].FormattedValue );
  481. // }
  482. // }
  483. // break;
  484. // case AdditionalLineType.Define:
  485. // {
  486. // if( !string.IsNullOrEmpty( list[ i ].LineValue ) &&
  487. // !nativesContainer.HasDefine( list[ i ].LineValue ) )
  488. // {
  489. // dataCollector.AddToMisc( list[ i ].FormattedValue );
  490. // }
  491. // }
  492. // break;
  493. // case AdditionalLineType.Pragma:
  494. // {
  495. // if( !string.IsNullOrEmpty( list[ i ].LineValue ) &&
  496. // !nativesContainer.HasPragma( list[ i ].LineValue ) )
  497. // {
  498. // dataCollector.AddToMisc( list[ i ].FormattedValue );
  499. // }
  500. // }
  501. // break;
  502. // default:
  503. // case AdditionalLineType.Custom:
  504. // dataCollector.AddToMisc( list[ i ].LineValue );
  505. // break;
  506. // }
  507. //}
  508. AddToDataCollector( ref dataCollector, nativesContainer, false );
  509. AddToDataCollector( ref dataCollector, nativesContainer, true );
  510. }
  511. public void AddAllToDataCollector( ref MasterNodeDataCollector dataCollector )
  512. {
  513. AddToDataCollector( ref dataCollector, false );
  514. AddToDataCollector( ref dataCollector, true );
  515. }
  516. void AddToDataCollector( ref MasterNodeDataCollector dataCollector, TemplateIncludePragmaContainter nativesContainer, bool fromSF )
  517. {
  518. List<AdditionalDirectiveContainer> list = fromSF ? m_shaderFunctionDirectives : m_additionalDirectives;
  519. int count = list.Count;
  520. for( int i = 0; i < count; i++ )
  521. {
  522. int orderIdx = fromSF ? 1 : ( i > m_nativeDirectivesIndex ? 1 : -1 );
  523. switch( list[ i ].LineType )
  524. {
  525. case AdditionalLineType.Include:
  526. {
  527. string value = list[ i ].Value;
  528. if( !string.IsNullOrEmpty( value ) &&
  529. !nativesContainer.HasInclude( value ) )
  530. {
  531. dataCollector.AddToDirectives( list[ i ].FormattedValue, orderIdx );
  532. }
  533. }
  534. break;
  535. case AdditionalLineType.Define:
  536. {
  537. if( !string.IsNullOrEmpty( list[ i ].LineValue ) &&
  538. !nativesContainer.HasDefine( list[ i ].LineValue ) )
  539. {
  540. dataCollector.AddToDirectives( list[ i ].FormattedValue, orderIdx );
  541. }
  542. }
  543. break;
  544. case AdditionalLineType.Pragma:
  545. {
  546. if( !string.IsNullOrEmpty( list[ i ].LineValue ) &&
  547. !nativesContainer.HasPragma( list[ i ].LineValue ) )
  548. {
  549. dataCollector.AddToDirectives( list[ i ].FormattedValue, orderIdx );
  550. }
  551. }
  552. break;
  553. default:
  554. case AdditionalLineType.Custom:
  555. dataCollector.AddToDirectives( list[ i ].LineValue, orderIdx );
  556. break;
  557. }
  558. }
  559. }
  560. void AddToDataCollector( ref MasterNodeDataCollector dataCollector, bool fromSF )
  561. {
  562. List<AdditionalDirectiveContainer> list = fromSF ? m_shaderFunctionDirectives : m_additionalDirectives;
  563. int orderIdx = 1;
  564. int count = list.Count;
  565. for( int i = 0; i < count; i++ )
  566. {
  567. switch( list[ i ].LineType )
  568. {
  569. case AdditionalLineType.Include:
  570. {
  571. string value = list[ i ].FormattedValue;
  572. if( !string.IsNullOrEmpty( value ) )
  573. {
  574. dataCollector.AddToDirectives( value, orderIdx );
  575. }
  576. }
  577. break;
  578. case AdditionalLineType.Define:
  579. {
  580. if( !string.IsNullOrEmpty( list[ i ].LineValue ) )
  581. {
  582. dataCollector.AddToDirectives( list[ i ].FormattedValue, orderIdx );
  583. }
  584. }
  585. break;
  586. case AdditionalLineType.Pragma:
  587. {
  588. if( !string.IsNullOrEmpty( list[ i ].LineValue ) )
  589. {
  590. dataCollector.AddToDirectives( list[ i ].FormattedValue, orderIdx );
  591. }
  592. }
  593. break;
  594. default:
  595. case AdditionalLineType.Custom:
  596. dataCollector.AddToDirectives( list[ i ].LineValue, orderIdx );
  597. break;
  598. }
  599. }
  600. }
  601. public override void ReadFromString( ref uint index, ref string[] nodeParams )
  602. {
  603. try
  604. {
  605. m_nativeDirectivesIndex = -1;
  606. int count = Convert.ToInt32( nodeParams[ index++ ] );
  607. m_additionalDirectives.Clear();
  608. for( int i = 0; i < count; i++ )
  609. {
  610. AdditionalLineType lineType = (AdditionalLineType)Enum.Parse( typeof( AdditionalLineType ), nodeParams[ index++ ] );
  611. string lineValue = nodeParams[ index++ ];
  612. AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  613. newItem.hideFlags = HideFlags.HideAndDontSave;
  614. newItem.LineType = lineType;
  615. newItem.LineValue = lineValue.Replace( Constants.SemiColonSeparator, ';' );
  616. if( UIUtils.CurrentShaderVersion() > 15607 )
  617. {
  618. newItem.GUIDToggle = Convert.ToBoolean( nodeParams[ index++ ] );
  619. newItem.GUIDValue = nodeParams[ index++ ];
  620. if( newItem.GUIDToggle )
  621. {
  622. newItem.LibObject = AssetDatabase.LoadAssetAtPath<TextAsset>( AssetDatabase.GUIDToAssetPath( newItem.GUIDValue ) );
  623. if( newItem.LibObject == null )
  624. {
  625. Debug.LogWarning( "Include file not found with GUID " + newItem.GUIDValue );
  626. }
  627. }
  628. }
  629. AdditionalContainerOrigin origin = AdditionalContainerOrigin.Custom;
  630. if( UIUtils.CurrentShaderVersion() > 16902 )
  631. {
  632. origin = (AdditionalContainerOrigin)Enum.Parse( typeof( AdditionalContainerOrigin ), nodeParams[ index++ ] );
  633. newItem.Origin = origin;
  634. }
  635. m_additionalDirectives.Add( newItem );
  636. if( origin == AdditionalContainerOrigin.Native )
  637. {
  638. m_nativeDirectivesIndex = i;
  639. }
  640. }
  641. AddNativeContainer();
  642. }
  643. catch( Exception e )
  644. {
  645. Debug.LogException( e );
  646. }
  647. }
  648. public override void WriteToString( ref string nodeInfo )
  649. {
  650. if( m_additionalDirectives.Count == 1 && m_additionalDirectives[ 0 ].Origin == AdditionalContainerOrigin.Native )
  651. {
  652. IOUtils.AddFieldValueToString( ref nodeInfo, 0 );
  653. return;
  654. }
  655. IOUtils.AddFieldValueToString( ref nodeInfo, m_additionalDirectives.Count );
  656. for( int i = 0; i < m_additionalDirectives.Count; i++ )
  657. {
  658. IOUtils.AddFieldValueToString( ref nodeInfo, m_additionalDirectives[ i ].LineType );
  659. IOUtils.AddFieldValueToString( ref nodeInfo, m_additionalDirectives[ i ].LineValue.Replace( ';', Constants.SemiColonSeparator ) );
  660. IOUtils.AddFieldValueToString( ref nodeInfo, m_additionalDirectives[ i ].GUIDToggle );
  661. IOUtils.AddFieldValueToString( ref nodeInfo, m_additionalDirectives[ i ].GUIDValue );
  662. IOUtils.AddFieldValueToString( ref nodeInfo, m_additionalDirectives[ i ].Origin );
  663. }
  664. }
  665. // read comment on m_directivesSaveItems declaration
  666. public void UpdateSaveItemsFromDirectives()
  667. {
  668. bool foundNull = false;
  669. m_directivesSaveItems.Clear();
  670. for( int i = 0; i < m_additionalDirectives.Count; i++ )
  671. {
  672. if( m_additionalDirectives[ i ] != null )
  673. {
  674. m_directivesSaveItems.Add( new AdditionalDirectiveContainerSaveItem( m_additionalDirectives[ i ] ) );
  675. }
  676. else
  677. {
  678. foundNull = true;
  679. }
  680. }
  681. if( foundNull )
  682. {
  683. m_additionalDirectives.RemoveAll( item => item == null );
  684. }
  685. }
  686. public void CleanNullDirectives()
  687. {
  688. m_additionalDirectives.RemoveAll( item => item == null );
  689. }
  690. public void ResetDirectivesOrigin()
  691. {
  692. for( int i = 0; i < m_directivesSaveItems.Count; i++ )
  693. {
  694. m_directivesSaveItems[ i ].Origin = AdditionalContainerOrigin.Custom;
  695. }
  696. }
  697. // read comment on m_directivesSaveItems declaration
  698. public void UpdateDirectivesFromSaveItems()
  699. {
  700. if( m_directivesSaveItems.Count > 0 )
  701. {
  702. for( int i = 0; i < m_additionalDirectives.Count; i++ )
  703. {
  704. if( m_additionalDirectives[ i ] != null )
  705. ScriptableObject.DestroyImmediate( m_additionalDirectives[ i ] );
  706. }
  707. m_additionalDirectives.Clear();
  708. for( int i = 0; i < m_directivesSaveItems.Count; i++ )
  709. {
  710. AdditionalDirectiveContainer newItem = ScriptableObject.CreateInstance<AdditionalDirectiveContainer>();
  711. newItem.hideFlags = HideFlags.HideAndDontSave;
  712. newItem.Init( m_directivesSaveItems[ i ] );
  713. m_additionalDirectives.Add( newItem );
  714. }
  715. UpdateNativeIndex();
  716. //m_directivesSaveItems.Clear();
  717. }
  718. }
  719. void UpdateNativeIndex()
  720. {
  721. m_nativeDirectivesIndex = -1;
  722. int count = m_additionalDirectives.Count;
  723. for( int i = 0; i < count; i++ )
  724. {
  725. if( m_additionalDirectives[ i ].Origin == AdditionalContainerOrigin.Native )
  726. {
  727. m_nativeDirectivesIndex = i;
  728. break;
  729. }
  730. }
  731. }
  732. public override void Destroy()
  733. {
  734. base.Destroy();
  735. m_nativeDirectives.Clear();
  736. m_nativeDirectives = null;
  737. for( int i = 0; i < m_additionalDirectives.Count; i++ )
  738. {
  739. ScriptableObject.DestroyImmediate( m_additionalDirectives[ i ] );
  740. }
  741. m_additionalDirectives.Clear();
  742. m_additionalDirectives = null;
  743. for( int i = 0; i < m_shaderFunctionDirectives.Count; i++ )
  744. {
  745. ScriptableObject.DestroyImmediate( m_shaderFunctionDirectives[ i ] );
  746. }
  747. m_shaderFunctionDirectives.Clear();
  748. m_shaderFunctionDirectives = null;
  749. m_propertyAdjustment = null;
  750. m_reordableList = null;
  751. }
  752. public List<AdditionalDirectiveContainer> DirectivesList { get { return m_additionalDirectives; } }
  753. public bool IsValid { get { return m_validData; } set { m_validData = value; } }
  754. }
  755. }