A game about forced loneliness, made by TACStudios
1using System;
2
3namespace Unity.VisualScripting
4{
5 public sealed class GraphElementCollection<TElement> : GuidCollection<TElement>, IGraphElementCollection<TElement>, IProxyableNotifyCollectionChanged<TElement>
6 where TElement : IGraphElement
7 {
8 public GraphElementCollection(IGraph graph) : base()
9 {
10 Ensure.That(nameof(graph)).IsNotNull(graph);
11
12 this.graph = graph;
13 }
14
15 public IGraph graph { get; }
16
17 public event Action<TElement> ItemAdded;
18
19 public event Action<TElement> ItemRemoved;
20
21 public event Action CollectionChanged;
22
23 public bool ProxyCollectionChange { get; set; }
24
25 public void BeforeAdd(TElement element)
26 {
27 if (element.graph != null)
28 {
29 if (element.graph == graph)
30 {
31 throw new InvalidOperationException("Graph elements cannot be added multiple time into the same graph.");
32 }
33 else
34 {
35 throw new InvalidOperationException("Graph elements cannot be shared across graphs.");
36 }
37 }
38
39 element.graph = graph;
40 element.BeforeAdd();
41 }
42
43 public void AfterAdd(TElement element)
44 {
45 element.AfterAdd();
46 ItemAdded?.Invoke(element);
47 CollectionChanged?.Invoke();
48 }
49
50 public void BeforeRemove(TElement element)
51 {
52 element.BeforeRemove();
53 }
54
55 public void AfterRemove(TElement element)
56 {
57 element.graph = null;
58 element.AfterRemove();
59 ItemRemoved?.Invoke(element);
60 CollectionChanged?.Invoke();
61 }
62
63 protected override void InsertItem(int index, TElement element)
64 {
65 Ensure.That(nameof(element)).IsNotNull(element);
66
67 if (!ProxyCollectionChange)
68 {
69 BeforeAdd(element);
70 }
71
72 base.InsertItem(index, element);
73
74 if (!ProxyCollectionChange)
75 {
76 AfterAdd(element);
77 }
78 }
79
80 protected override void RemoveItem(int index)
81 {
82 var element = this[index];
83
84 if (!Contains(element))
85 {
86 throw new ArgumentOutOfRangeException(nameof(element));
87 }
88
89 if (!ProxyCollectionChange)
90 {
91 BeforeRemove(element);
92 }
93
94 base.RemoveItem(index);
95
96 if (!ProxyCollectionChange)
97 {
98 AfterRemove(element);
99 }
100 }
101
102 protected override void ClearItems()
103 {
104 // this.OrderByDescending(e => e.dependencyOrder).ToList()
105 var toRemove = ListPool<TElement>.New();
106 foreach (var element in this)
107 {
108 toRemove.Add(element);
109 }
110 toRemove.Sort((a, b) => b.dependencyOrder.CompareTo(a.dependencyOrder));
111
112 foreach (var element in toRemove)
113 {
114 Remove(element);
115 }
116
117 ListPool<TElement>.Free(toRemove);
118 }
119
120 protected override void SetItem(int index, TElement item)
121 {
122 throw new NotSupportedException();
123 }
124
125 public new NoAllocEnumerator<TElement> GetEnumerator()
126 {
127 return new NoAllocEnumerator<TElement>(this);
128 }
129 }
130}