DocumentStructureModule.cs 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118
  1. using System.Collections.Generic;
  2. using PixiEditor.AvaloniaUI.Models.Handlers;
  3. namespace PixiEditor.AvaloniaUI.Models.DocumentModels.Public;
  4. #nullable enable
  5. internal class DocumentStructureModule
  6. {
  7. private readonly IDocument doc;
  8. public DocumentStructureModule(IDocument owner)
  9. {
  10. this.doc = owner;
  11. }
  12. public IStructureMemberHandler FindOrThrow(Guid guid) => Find(guid) ?? throw new ArgumentException("Could not find member with guid " + guid.ToString());
  13. public IStructureMemberHandler? Find(Guid guid)
  14. {
  15. return FindNode<IStructureMemberHandler>(guid);
  16. }
  17. public T? FindNode<T>(Guid guid) where T : class, INodeHandler
  18. {
  19. return doc.NodeGraphHandler.AllNodes.FirstOrDefault(x => x.Id == guid && x is T) as T;
  20. }
  21. public IStructureMemberHandler? FindFirstWhere(Predicate<IStructureMemberHandler> predicate)
  22. {
  23. return FindFirstWhere(predicate, doc.NodeGraphHandler);
  24. }
  25. private IStructureMemberHandler? FindFirstWhere(Predicate<IStructureMemberHandler> predicate, INodeGraphHandler graphVM)
  26. {
  27. IStructureMemberHandler? result = null;
  28. graphVM.TryTraverse(node =>
  29. {
  30. if (node is IStructureMemberHandler structureMemberNode && predicate(structureMemberNode))
  31. {
  32. result = structureMemberNode;
  33. return false;
  34. }
  35. return true;
  36. });
  37. return result;
  38. }
  39. public (IStructureMemberHandler?, IFolderHandler?) FindChildAndParent(Guid childGuid)
  40. {
  41. List<IStructureMemberHandler>? path = FindPath(childGuid);
  42. return path.Count switch
  43. {
  44. 0 => (null, null),
  45. 1 => (path[0], null),
  46. >= 2 => (path[0], (IFolderHandler)path[1]),
  47. _ => (null, null),
  48. };
  49. }
  50. public (IStructureMemberHandler, IFolderHandler) FindChildAndParentOrThrow(Guid childGuid)
  51. {
  52. List<IStructureMemberHandler>? path = FindPath(childGuid);
  53. if (path.Count < 2)
  54. throw new ArgumentException("Couldn't find child and parent");
  55. return (path[0], (IFolderHandler)path[1]);
  56. }
  57. public List<IStructureMemberHandler> FindPath(Guid guid)
  58. {
  59. List<INodeHandler>? list = new List<INodeHandler>();
  60. FillPath(doc.NodeGraphHandler.OutputNode, guid, list);
  61. return list.Cast<IStructureMemberHandler>().ToList();
  62. }
  63. /// <summary>
  64. /// Returns all layers in the document.
  65. /// </summary>
  66. /// <returns>List of ILayerHandlers. Empty if no layers found.</returns>
  67. public List<ILayerHandler> GetAllLayers()
  68. {
  69. List<ILayerHandler> layers = new List<ILayerHandler>();
  70. doc.NodeGraphHandler.TryTraverse(node =>
  71. {
  72. if (node is ILayerHandler layer)
  73. layers.Add(layer);
  74. return true;
  75. });
  76. return layers;
  77. }
  78. private bool FillPath(INodeHandler node, Guid guid, List<INodeHandler> toFill)
  79. {
  80. if (node.Id == guid)
  81. {
  82. return true;
  83. }
  84. if (node is IStructureMemberHandler structureNode)
  85. {
  86. toFill.Add(structureNode);
  87. }
  88. bool found = false;
  89. node.TraverseBackwards(newNode =>
  90. {
  91. if (newNode is IStructureMemberHandler strNode && newNode.Id == guid)
  92. {
  93. toFill.Add(strNode);
  94. found = true;
  95. return false;
  96. }
  97. return true;
  98. });
  99. return found;
  100. }
  101. }