com.fofx.observething 1.0.0 → 1.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/Runtime/CollectionIdProvider.cs +71 -71
- package/Runtime/CollectionIdProvider.cs.meta +1 -1
- package/Runtime/IObservable.cs +66 -66
- package/Runtime/IObservable.cs.meta +1 -1
- package/Runtime/Implementations/Observable.cs +29 -29
- package/Runtime/Implementations/Observable.cs.meta +1 -1
- package/Runtime/Implementations/ObservableBase.cs +172 -172
- package/Runtime/Implementations/ObservableBase.cs.meta +1 -1
- package/Runtime/Implementations/ObservableCollection.cs +140 -140
- package/Runtime/Implementations/ObservableCollection.cs.meta +1 -1
- package/Runtime/Implementations/ObservableDictionary.cs +165 -165
- package/Runtime/Implementations/ObservableDictionary.cs.meta +1 -1
- package/Runtime/Implementations/ObservableList.cs +162 -162
- package/Runtime/Implementations/ObservableList.cs.meta +1 -1
- package/Runtime/Implementations/ObservableSet.cs +136 -136
- package/Runtime/Implementations/ObservableSet.cs.meta +1 -1
- package/Runtime/Implementations/ObservableValue.cs +58 -58
- package/Runtime/Implementations/ObservableValue.cs.meta +1 -1
- package/Runtime/Observables/BatchObservable.cs +71 -71
- package/Runtime/Observables/BatchObservable.cs.meta +1 -1
- package/Runtime/Observables/CastObservable.cs +127 -127
- package/Runtime/Observables/CastObservable.cs.meta +1 -1
- package/Runtime/Observables/CombineObservable.cs +95 -95
- package/Runtime/Observables/CombineObservable.cs.meta +1 -1
- package/Runtime/Observables/CombineValueObservable.cs +318 -318
- package/Runtime/Observables/CombineValueObservable.cs.meta +1 -1
- package/Runtime/Observables/ConcatObservable.cs +74 -74
- package/Runtime/Observables/ConcatObservable.cs.meta +1 -1
- package/Runtime/Observables/ContainsObservable.cs +70 -70
- package/Runtime/Observables/ContainsObservable.cs.meta +1 -1
- package/Runtime/Observables/CountObservable.cs +29 -29
- package/Runtime/Observables/CountObservable.cs.meta +1 -1
- package/Runtime/Observables/DistinctObservable.cs +54 -54
- package/Runtime/Observables/DistinctObservable.cs.meta +1 -1
- package/Runtime/Observables/FirstObservable.cs +52 -52
- package/Runtime/Observables/FirstObservable.cs.meta +1 -1
- package/Runtime/Observables/IndexOfObservable.cs +82 -82
- package/Runtime/Observables/IndexOfObservable.cs.meta +1 -1
- package/Runtime/Observables/OperationStreamObservable.cs +193 -193
- package/Runtime/Observables/OperationStreamObservable.cs.meta +1 -1
- package/Runtime/Observables/OrderByObservable.cs +115 -116
- package/Runtime/Observables/OrderByObservable.cs.meta +1 -1
- package/Runtime/Observables/SelectCollectionObservable.cs +28 -28
- package/Runtime/Observables/SelectCollectionObservable.cs.meta +1 -1
- package/Runtime/Observables/SelectListObservable.cs +28 -28
- package/Runtime/Observables/SelectListObservable.cs.meta +1 -1
- package/Runtime/Observables/SelectManyObservable.cs +77 -77
- package/Runtime/Observables/SelectManyObservable.cs.meta +1 -1
- package/Runtime/Observables/SelectValueObservable.cs +27 -27
- package/Runtime/Observables/SelectValueObservable.cs.meta +1 -1
- package/Runtime/Observables/SkipWhileObservable.cs +31 -31
- package/Runtime/Observables/SkipWhileObservable.cs.meta +1 -1
- package/Runtime/Observables/ThenObservable.cs +208 -208
- package/Runtime/Observables/ThenObservable.cs.meta +1 -1
- package/Runtime/Observables/ToDictionaryObservable.cs +35 -35
- package/Runtime/Observables/ToDictionaryObservable.cs.meta +1 -1
- package/Runtime/Observables/TrackObservable.cs +74 -74
- package/Runtime/Observables/TrackObservable.cs.meta +1 -1
- package/Runtime/Observables/UnwrapCollectionObservable.cs +63 -63
- package/Runtime/Observables/UnwrapCollectionObservable.cs.meta +1 -1
- package/Runtime/Observables/UnwrapListObservable.cs +69 -69
- package/Runtime/Observables/UnwrapListObservable.cs.meta +1 -1
- package/Runtime/Observables/UnwrapValueObservable.cs +55 -55
- package/Runtime/Observables/UnwrapValueObservable.cs.meta +1 -1
- package/Runtime/Observables/WhereObservable.cs +84 -84
- package/Runtime/Observables/WhereObservable.cs.meta +1 -1
- package/Runtime/Observables/WithPreviousObservable.cs +36 -36
- package/Runtime/Observables/WithPreviousObservable.cs.meta +1 -1
- package/Runtime/Observables.cs +466 -466
- package/Runtime/Observables.meta +8 -8
- package/Runtime/ObservationContext.cs +125 -125
- package/Runtime/ObservationContext.cs.meta +1 -1
- package/Runtime/Observers.cs +402 -402
- package/Runtime/Observers.cs.meta +1 -1
- package/Runtime/Operators/BatchOperator.cs +70 -70
- package/Runtime/Operators/BatchOperator.cs.meta +1 -1
- package/Runtime/Operators/CollectionOperator.cs +30 -30
- package/Runtime/Operators/CollectionOperator.cs.meta +1 -1
- package/Runtime/Operators/DictionaryOperator.cs +45 -45
- package/Runtime/Operators/DictionaryOperator.cs.meta +1 -1
- package/Runtime/Operators/IInitializationOperationsProvider.cs +10 -10
- package/Runtime/Operators/IInitializationOperationsProvider.cs.meta +1 -1
- package/Runtime/Operators/ListOperator.cs +44 -44
- package/Runtime/Operators/ListOperator.cs.meta +1 -1
- package/Runtime/Operators/ObservableOperator.cs +74 -74
- package/Runtime/Operators/ObservableOperator.cs.meta +1 -1
- package/Runtime/Operators/Operator.cs +65 -65
- package/Runtime/Operators/Operator.cs.meta +1 -1
- package/Runtime/Operators/SetOperator.cs +44 -44
- package/Runtime/Operators/SetOperator.cs.meta +1 -1
- package/Runtime/Operators/ValueOperator.cs +29 -29
- package/Runtime/Operators/ValueOperator.cs.meta +1 -1
- package/Runtime/Operators.meta +8 -8
- package/Runtime/PriorityQueue.cs +1095 -1095
- package/Runtime/PriorityQueue.cs.meta +1 -1
- package/Tests/CollectionObservableTests.cs +738 -738
- package/Tests/DictionaryObservableTests.cs +84 -84
- package/Tests/ListObservableTests.cs +147 -147
- package/Tests/ObservationContextTests.cs +359 -359
- package/Tests/ObservationContextTests.cs.meta +1 -1
- package/Tests/ValueObservableTests.cs +321 -321
- package/package.json +24 -24
|
@@ -1,166 +1,166 @@
|
|
|
1
|
-
using System;
|
|
2
|
-
using System.Collections;
|
|
3
|
-
using System.Collections.Generic;
|
|
4
|
-
using System.Linq;
|
|
5
|
-
|
|
6
|
-
namespace ObserveThing
|
|
7
|
-
{
|
|
8
|
-
public interface IDictionaryOp : IOperation
|
|
9
|
-
{
|
|
10
|
-
uint elementId { get; }
|
|
11
|
-
object key { get; }
|
|
12
|
-
object value { get; }
|
|
13
|
-
bool isRemove { get; }
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
public struct DictionaryOp<TKey, TValue> : IDictionaryOp
|
|
17
|
-
{
|
|
18
|
-
public IObservable<IOperation> source { get; set; }
|
|
19
|
-
public uint elementId { get; set; }
|
|
20
|
-
public TKey key { get; set; }
|
|
21
|
-
public TValue value { get; set; }
|
|
22
|
-
public bool isRemove { get; set; }
|
|
23
|
-
|
|
24
|
-
object IDictionaryOp.key => key;
|
|
25
|
-
object IDictionaryOp.value => value;
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
public class ObservableDictionary<TKey, TValue> : ObservableBase<IDictionaryObserver<TKey, TValue>, DictionaryOp<TKey, TValue>>, IDictionaryObservable<TKey, TValue>, IEnumerable<KeyValuePair<TKey, TValue>>
|
|
29
|
-
{
|
|
30
|
-
public TValue this[TKey key]
|
|
31
|
-
{
|
|
32
|
-
get => _dictionary[key];
|
|
33
|
-
set
|
|
34
|
-
{
|
|
35
|
-
Remove(key);
|
|
36
|
-
Add(key, value);
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
|
|
40
|
-
public int Count => _dictionary.Count;
|
|
41
|
-
|
|
42
|
-
public IEnumerable<TKey> Keys => _dictionary.Keys;
|
|
43
|
-
public IEnumerable<TValue> Values => _dictionary.Values;
|
|
44
|
-
|
|
45
|
-
IEnumerator<KeyValuePair<TKey, TValue>> IEnumerable<KeyValuePair<TKey, TValue>>.GetEnumerator()
|
|
46
|
-
=> _dictionary.GetEnumerator();
|
|
47
|
-
|
|
48
|
-
IEnumerator IEnumerable.GetEnumerator()
|
|
49
|
-
=> _dictionary.GetEnumerator();
|
|
50
|
-
|
|
51
|
-
private Dictionary<TKey, TValue> _dictionary = new Dictionary<TKey, TValue>();
|
|
52
|
-
private Dictionary<TKey, uint> _ids = new Dictionary<TKey, uint>();
|
|
53
|
-
private CollectionIdProvider _idProvider;
|
|
54
|
-
|
|
55
|
-
public ObservableDictionary() : this(default, default) { }
|
|
56
|
-
public ObservableDictionary(IEnumerable<KeyValuePair<TKey, TValue>> value) : this(default, value) { }
|
|
57
|
-
|
|
58
|
-
public ObservableDictionary(ObservationContext context) : this(context, default) { }
|
|
59
|
-
public ObservableDictionary(ObservationContext context, IEnumerable<KeyValuePair<TKey, TValue>> value) : base(context)
|
|
60
|
-
{
|
|
61
|
-
_idProvider = new CollectionIdProvider(_ids.Values.Contains);
|
|
62
|
-
|
|
63
|
-
if (value == null)
|
|
64
|
-
return;
|
|
65
|
-
|
|
66
|
-
foreach (var kvp in value)
|
|
67
|
-
{
|
|
68
|
-
_dictionary.Add(kvp.Key, kvp.Value);
|
|
69
|
-
_ids.Add(kvp.Key, _idProvider.GetUnusedId());
|
|
70
|
-
}
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
public void Add(TKey key, TValue value)
|
|
74
|
-
{
|
|
75
|
-
var id = _idProvider.GetUnusedId();
|
|
76
|
-
_dictionary.Add(key, value);
|
|
77
|
-
_ids.Add(key, id);
|
|
78
|
-
EnqueuePendingOperation(new DictionaryOp<TKey, TValue>() { source = this, elementId = id, key = key, value = value, isRemove = false });
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
public bool Remove(TKey key)
|
|
82
|
-
{
|
|
83
|
-
if (!_dictionary.TryGetValue(key, out var value))
|
|
84
|
-
return false;
|
|
85
|
-
|
|
86
|
-
var id = _ids[key];
|
|
87
|
-
|
|
88
|
-
_dictionary.Remove(key);
|
|
89
|
-
_ids.Remove(key);
|
|
90
|
-
EnqueuePendingOperation(new DictionaryOp<TKey, TValue>() { source = this, elementId = id, key = key, value = value, isRemove = true });
|
|
91
|
-
|
|
92
|
-
return true;
|
|
93
|
-
}
|
|
94
|
-
|
|
95
|
-
public void Clear()
|
|
96
|
-
{
|
|
97
|
-
foreach (var kvp in _dictionary.ToArray())
|
|
98
|
-
{
|
|
99
|
-
var id = _ids[kvp.Key];
|
|
100
|
-
_dictionary.Remove(kvp.Key);
|
|
101
|
-
_ids.Remove(kvp.Key);
|
|
102
|
-
EnqueuePendingOperation(new DictionaryOp<TKey, TValue>() { source = this, elementId = id, key = kvp.Key, value = kvp.Value, isRemove = true });
|
|
103
|
-
}
|
|
104
|
-
}
|
|
105
|
-
|
|
106
|
-
public bool TryGetValueInternal(TKey key, out TValue value)
|
|
107
|
-
=> _dictionary.TryGetValue(key, out value);
|
|
108
|
-
|
|
109
|
-
public bool ContainsKey(TKey key)
|
|
110
|
-
=> _dictionary.ContainsKey(key);
|
|
111
|
-
|
|
112
|
-
public bool ContainsValue(TValue value)
|
|
113
|
-
=> _dictionary.ContainsValue(value);
|
|
114
|
-
|
|
115
|
-
protected override IEnumerable<DictionaryOp<TKey, TValue>> GetInitializationOperations()
|
|
116
|
-
{
|
|
117
|
-
foreach (var kvp in _dictionary)
|
|
118
|
-
{
|
|
119
|
-
yield return new DictionaryOp<TKey, TValue>()
|
|
120
|
-
{
|
|
121
|
-
source = this,
|
|
122
|
-
elementId = _ids[kvp.Key],
|
|
123
|
-
key = kvp.Key,
|
|
124
|
-
value = kvp.Value,
|
|
125
|
-
isRemove = false
|
|
126
|
-
};
|
|
127
|
-
}
|
|
128
|
-
}
|
|
129
|
-
|
|
130
|
-
protected override void SendOperation(IDictionaryObserver<TKey, TValue> observer, DictionaryOp<TKey, TValue> operation)
|
|
131
|
-
{
|
|
132
|
-
if (operation.isRemove)
|
|
133
|
-
{
|
|
134
|
-
observer.OnRemove(operation.elementId, KeyValuePair.Create(operation.key, operation.value));
|
|
135
|
-
}
|
|
136
|
-
else
|
|
137
|
-
{
|
|
138
|
-
observer.OnAdd(operation.elementId, KeyValuePair.Create(operation.key, operation.value));
|
|
139
|
-
}
|
|
140
|
-
}
|
|
141
|
-
|
|
142
|
-
IDisposable IDictionaryObservable.Subscribe(IDictionaryObserver observer, bool immediate, uint? priority)
|
|
143
|
-
=> Subscribe(new DictionaryObserver<TKey, TValue>(
|
|
144
|
-
onAdd: (id, kvp) => observer.OnAdd(id, new KeyValuePair<object, object>(kvp.Key, kvp.Value)),
|
|
145
|
-
onRemove: (id, kvp) => observer.OnRemove(id, new KeyValuePair<object, object>(kvp.Key, kvp.Value)),
|
|
146
|
-
onDispose: observer.OnDispose,
|
|
147
|
-
onError: observer.OnError
|
|
148
|
-
), immediate, priority);
|
|
149
|
-
|
|
150
|
-
IDisposable ICollectionObservable<KeyValuePair<TKey, TValue>>.Subscribe(ICollectionObserver<KeyValuePair<TKey, TValue>> observer, bool immediate, uint? priority)
|
|
151
|
-
=> Subscribe(new DictionaryObserver<TKey, TValue>(
|
|
152
|
-
onAdd: (id, kvp) => observer.OnAdd(id, kvp),
|
|
153
|
-
onRemove: (id, kvp) => observer.OnRemove(id, kvp),
|
|
154
|
-
onDispose: observer.OnDispose,
|
|
155
|
-
onError: observer.OnError
|
|
156
|
-
), immediate, priority);
|
|
157
|
-
|
|
158
|
-
IDisposable ICollectionObservable.Subscribe(ICollectionObserver observer, bool immediate, uint? priority)
|
|
159
|
-
=> Subscribe(new DictionaryObserver<TKey, TValue>(
|
|
160
|
-
onAdd: (id, kvp) => observer.OnAdd(id, kvp),
|
|
161
|
-
onRemove: (id, kvp) => observer.OnRemove(id, kvp),
|
|
162
|
-
onDispose: observer.OnDispose,
|
|
163
|
-
onError: observer.OnError
|
|
164
|
-
), immediate, priority);
|
|
165
|
-
}
|
|
1
|
+
using System;
|
|
2
|
+
using System.Collections;
|
|
3
|
+
using System.Collections.Generic;
|
|
4
|
+
using System.Linq;
|
|
5
|
+
|
|
6
|
+
namespace ObserveThing
|
|
7
|
+
{
|
|
8
|
+
public interface IDictionaryOp : IOperation
|
|
9
|
+
{
|
|
10
|
+
uint elementId { get; }
|
|
11
|
+
object key { get; }
|
|
12
|
+
object value { get; }
|
|
13
|
+
bool isRemove { get; }
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
public struct DictionaryOp<TKey, TValue> : IDictionaryOp
|
|
17
|
+
{
|
|
18
|
+
public IObservable<IOperation> source { get; set; }
|
|
19
|
+
public uint elementId { get; set; }
|
|
20
|
+
public TKey key { get; set; }
|
|
21
|
+
public TValue value { get; set; }
|
|
22
|
+
public bool isRemove { get; set; }
|
|
23
|
+
|
|
24
|
+
object IDictionaryOp.key => key;
|
|
25
|
+
object IDictionaryOp.value => value;
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
public class ObservableDictionary<TKey, TValue> : ObservableBase<IDictionaryObserver<TKey, TValue>, DictionaryOp<TKey, TValue>>, IDictionaryObservable<TKey, TValue>, IEnumerable<KeyValuePair<TKey, TValue>>
|
|
29
|
+
{
|
|
30
|
+
public TValue this[TKey key]
|
|
31
|
+
{
|
|
32
|
+
get => _dictionary[key];
|
|
33
|
+
set
|
|
34
|
+
{
|
|
35
|
+
Remove(key);
|
|
36
|
+
Add(key, value);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
public int Count => _dictionary.Count;
|
|
41
|
+
|
|
42
|
+
public IEnumerable<TKey> Keys => _dictionary.Keys;
|
|
43
|
+
public IEnumerable<TValue> Values => _dictionary.Values;
|
|
44
|
+
|
|
45
|
+
IEnumerator<KeyValuePair<TKey, TValue>> IEnumerable<KeyValuePair<TKey, TValue>>.GetEnumerator()
|
|
46
|
+
=> _dictionary.GetEnumerator();
|
|
47
|
+
|
|
48
|
+
IEnumerator IEnumerable.GetEnumerator()
|
|
49
|
+
=> _dictionary.GetEnumerator();
|
|
50
|
+
|
|
51
|
+
private Dictionary<TKey, TValue> _dictionary = new Dictionary<TKey, TValue>();
|
|
52
|
+
private Dictionary<TKey, uint> _ids = new Dictionary<TKey, uint>();
|
|
53
|
+
private CollectionIdProvider _idProvider;
|
|
54
|
+
|
|
55
|
+
public ObservableDictionary() : this(default, default) { }
|
|
56
|
+
public ObservableDictionary(IEnumerable<KeyValuePair<TKey, TValue>> value) : this(default, value) { }
|
|
57
|
+
|
|
58
|
+
public ObservableDictionary(ObservationContext context) : this(context, default) { }
|
|
59
|
+
public ObservableDictionary(ObservationContext context, IEnumerable<KeyValuePair<TKey, TValue>> value) : base(context)
|
|
60
|
+
{
|
|
61
|
+
_idProvider = new CollectionIdProvider(_ids.Values.Contains);
|
|
62
|
+
|
|
63
|
+
if (value == null)
|
|
64
|
+
return;
|
|
65
|
+
|
|
66
|
+
foreach (var kvp in value)
|
|
67
|
+
{
|
|
68
|
+
_dictionary.Add(kvp.Key, kvp.Value);
|
|
69
|
+
_ids.Add(kvp.Key, _idProvider.GetUnusedId());
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
public void Add(TKey key, TValue value)
|
|
74
|
+
{
|
|
75
|
+
var id = _idProvider.GetUnusedId();
|
|
76
|
+
_dictionary.Add(key, value);
|
|
77
|
+
_ids.Add(key, id);
|
|
78
|
+
EnqueuePendingOperation(new DictionaryOp<TKey, TValue>() { source = this, elementId = id, key = key, value = value, isRemove = false });
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
public bool Remove(TKey key)
|
|
82
|
+
{
|
|
83
|
+
if (!_dictionary.TryGetValue(key, out var value))
|
|
84
|
+
return false;
|
|
85
|
+
|
|
86
|
+
var id = _ids[key];
|
|
87
|
+
|
|
88
|
+
_dictionary.Remove(key);
|
|
89
|
+
_ids.Remove(key);
|
|
90
|
+
EnqueuePendingOperation(new DictionaryOp<TKey, TValue>() { source = this, elementId = id, key = key, value = value, isRemove = true });
|
|
91
|
+
|
|
92
|
+
return true;
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
public void Clear()
|
|
96
|
+
{
|
|
97
|
+
foreach (var kvp in _dictionary.ToArray())
|
|
98
|
+
{
|
|
99
|
+
var id = _ids[kvp.Key];
|
|
100
|
+
_dictionary.Remove(kvp.Key);
|
|
101
|
+
_ids.Remove(kvp.Key);
|
|
102
|
+
EnqueuePendingOperation(new DictionaryOp<TKey, TValue>() { source = this, elementId = id, key = kvp.Key, value = kvp.Value, isRemove = true });
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
public bool TryGetValueInternal(TKey key, out TValue value)
|
|
107
|
+
=> _dictionary.TryGetValue(key, out value);
|
|
108
|
+
|
|
109
|
+
public bool ContainsKey(TKey key)
|
|
110
|
+
=> _dictionary.ContainsKey(key);
|
|
111
|
+
|
|
112
|
+
public bool ContainsValue(TValue value)
|
|
113
|
+
=> _dictionary.ContainsValue(value);
|
|
114
|
+
|
|
115
|
+
protected override IEnumerable<DictionaryOp<TKey, TValue>> GetInitializationOperations()
|
|
116
|
+
{
|
|
117
|
+
foreach (var kvp in _dictionary)
|
|
118
|
+
{
|
|
119
|
+
yield return new DictionaryOp<TKey, TValue>()
|
|
120
|
+
{
|
|
121
|
+
source = this,
|
|
122
|
+
elementId = _ids[kvp.Key],
|
|
123
|
+
key = kvp.Key,
|
|
124
|
+
value = kvp.Value,
|
|
125
|
+
isRemove = false
|
|
126
|
+
};
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
protected override void SendOperation(IDictionaryObserver<TKey, TValue> observer, DictionaryOp<TKey, TValue> operation)
|
|
131
|
+
{
|
|
132
|
+
if (operation.isRemove)
|
|
133
|
+
{
|
|
134
|
+
observer.OnRemove(operation.elementId, KeyValuePair.Create(operation.key, operation.value));
|
|
135
|
+
}
|
|
136
|
+
else
|
|
137
|
+
{
|
|
138
|
+
observer.OnAdd(operation.elementId, KeyValuePair.Create(operation.key, operation.value));
|
|
139
|
+
}
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
IDisposable IDictionaryObservable.Subscribe(IDictionaryObserver observer, bool immediate, uint? priority)
|
|
143
|
+
=> Subscribe(new DictionaryObserver<TKey, TValue>(
|
|
144
|
+
onAdd: (id, kvp) => observer.OnAdd(id, new KeyValuePair<object, object>(kvp.Key, kvp.Value)),
|
|
145
|
+
onRemove: (id, kvp) => observer.OnRemove(id, new KeyValuePair<object, object>(kvp.Key, kvp.Value)),
|
|
146
|
+
onDispose: observer.OnDispose,
|
|
147
|
+
onError: observer.OnError
|
|
148
|
+
), immediate, priority);
|
|
149
|
+
|
|
150
|
+
IDisposable ICollectionObservable<KeyValuePair<TKey, TValue>>.Subscribe(ICollectionObserver<KeyValuePair<TKey, TValue>> observer, bool immediate, uint? priority)
|
|
151
|
+
=> Subscribe(new DictionaryObserver<TKey, TValue>(
|
|
152
|
+
onAdd: (id, kvp) => observer.OnAdd(id, kvp),
|
|
153
|
+
onRemove: (id, kvp) => observer.OnRemove(id, kvp),
|
|
154
|
+
onDispose: observer.OnDispose,
|
|
155
|
+
onError: observer.OnError
|
|
156
|
+
), immediate, priority);
|
|
157
|
+
|
|
158
|
+
IDisposable ICollectionObservable.Subscribe(ICollectionObserver observer, bool immediate, uint? priority)
|
|
159
|
+
=> Subscribe(new DictionaryObserver<TKey, TValue>(
|
|
160
|
+
onAdd: (id, kvp) => observer.OnAdd(id, kvp),
|
|
161
|
+
onRemove: (id, kvp) => observer.OnRemove(id, kvp),
|
|
162
|
+
onDispose: observer.OnDispose,
|
|
163
|
+
onError: observer.OnError
|
|
164
|
+
), immediate, priority);
|
|
165
|
+
}
|
|
166
166
|
}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
fileFormatVersion: 2
|
|
1
|
+
fileFormatVersion: 2
|
|
2
2
|
guid: b12213423807af14cb011dc6d7b4c20a
|
|
@@ -1,163 +1,163 @@
|
|
|
1
|
-
using System;
|
|
2
|
-
using System.Collections;
|
|
3
|
-
using System.Collections.Generic;
|
|
4
|
-
|
|
5
|
-
namespace ObserveThing
|
|
6
|
-
{
|
|
7
|
-
public interface IListOp : IOperation
|
|
8
|
-
{
|
|
9
|
-
uint elementId { get; }
|
|
10
|
-
int index { get; }
|
|
11
|
-
object element { get; }
|
|
12
|
-
bool isRemove { get; }
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
public struct ListOp<T> : IListOp
|
|
16
|
-
{
|
|
17
|
-
public IObservable<IOperation> source { get; set; }
|
|
18
|
-
public int index { get; set; }
|
|
19
|
-
public uint elementId { get; set; }
|
|
20
|
-
public T element { get; set; }
|
|
21
|
-
public bool isRemove { get; set; }
|
|
22
|
-
|
|
23
|
-
object IListOp.element => element;
|
|
24
|
-
}
|
|
25
|
-
|
|
26
|
-
public class ObservableList<T> : ObservableBase<IListObserver<T>, ListOp<T>>, IListObservable<T>, IEnumerable<T>
|
|
27
|
-
{
|
|
28
|
-
public T this[int index]
|
|
29
|
-
{
|
|
30
|
-
get => _list[index];
|
|
31
|
-
set
|
|
32
|
-
{
|
|
33
|
-
RemoveAt(index);
|
|
34
|
-
Insert(index, value);
|
|
35
|
-
}
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
IEnumerator<T> IEnumerable<T>.GetEnumerator()
|
|
39
|
-
=> _list.GetEnumerator();
|
|
40
|
-
|
|
41
|
-
IEnumerator IEnumerable.GetEnumerator()
|
|
42
|
-
=> _list.GetEnumerator();
|
|
43
|
-
|
|
44
|
-
public int count => _list.Count;
|
|
45
|
-
|
|
46
|
-
private List<T> _list = new List<T>();
|
|
47
|
-
private List<uint> _ids = new List<uint>();
|
|
48
|
-
private CollectionIdProvider _idProvider;
|
|
49
|
-
|
|
50
|
-
public ObservableList() : this(default, default(IEnumerable<T>)) { }
|
|
51
|
-
public ObservableList(params T[] value) : this(default, (IEnumerable<T>)value) { }
|
|
52
|
-
public ObservableList(IEnumerable<T> value) : this(default, value) { }
|
|
53
|
-
|
|
54
|
-
public ObservableList(ObservationContext context) : this(context, default(IEnumerable<T>)) { }
|
|
55
|
-
public ObservableList(ObservationContext context, params T[] value) : this(context, (IEnumerable<T>)value) { }
|
|
56
|
-
public ObservableList(ObservationContext context, IEnumerable<T> value) : base(context)
|
|
57
|
-
{
|
|
58
|
-
_idProvider = new CollectionIdProvider(_ids.Contains);
|
|
59
|
-
|
|
60
|
-
if (value == null)
|
|
61
|
-
return;
|
|
62
|
-
|
|
63
|
-
foreach (var element in value)
|
|
64
|
-
{
|
|
65
|
-
_list.Add(element);
|
|
66
|
-
_ids.Add(_idProvider.GetUnusedId());
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
public void Add(T added)
|
|
71
|
-
=> Insert(_list.Count, added);
|
|
72
|
-
|
|
73
|
-
public void AddRange(IEnumerable<T> toAdd)
|
|
74
|
-
{
|
|
75
|
-
foreach (var added in toAdd)
|
|
76
|
-
Add(added);
|
|
77
|
-
}
|
|
78
|
-
|
|
79
|
-
public bool Remove(T removed)
|
|
80
|
-
{
|
|
81
|
-
var index = _list.IndexOf(removed);
|
|
82
|
-
|
|
83
|
-
if (index == -1)
|
|
84
|
-
return false;
|
|
85
|
-
|
|
86
|
-
RemoveAt(index);
|
|
87
|
-
return true;
|
|
88
|
-
}
|
|
89
|
-
|
|
90
|
-
public void RemoveAt(int index)
|
|
91
|
-
{
|
|
92
|
-
var removed = _list[index];
|
|
93
|
-
var id = _ids[index];
|
|
94
|
-
_list.RemoveAt(index);
|
|
95
|
-
_ids.RemoveAt(index);
|
|
96
|
-
EnqueuePendingOperation(new ListOp<T>() { source = this, element = removed, elementId = id, index = index, isRemove = true });
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
public void Insert(int index, T item)
|
|
100
|
-
{
|
|
101
|
-
var id = _idProvider.GetUnusedId();
|
|
102
|
-
_list.Insert(index, item);
|
|
103
|
-
_ids.Insert(index, id);
|
|
104
|
-
EnqueuePendingOperation(new ListOp<T>() { source = this, element = item, elementId = id, index = index, isRemove = false });
|
|
105
|
-
}
|
|
106
|
-
|
|
107
|
-
public void Clear()
|
|
108
|
-
{
|
|
109
|
-
while (_list.Count > 0)
|
|
110
|
-
RemoveAt(_list.Count - 1);
|
|
111
|
-
}
|
|
112
|
-
|
|
113
|
-
public int IndexOf(T item)
|
|
114
|
-
=> _list.IndexOf(item);
|
|
115
|
-
|
|
116
|
-
public bool Contains(T item)
|
|
117
|
-
=> _list.Contains(item);
|
|
118
|
-
|
|
119
|
-
protected override IEnumerable<ListOp<T>> GetInitializationOperations()
|
|
120
|
-
{
|
|
121
|
-
for (int i = 0; i < _list.Count; i++)
|
|
122
|
-
{
|
|
123
|
-
yield return new ListOp<T>() { source = this, element = _list[i], elementId = _ids[i], index = i, isRemove = false };
|
|
124
|
-
}
|
|
125
|
-
}
|
|
126
|
-
|
|
127
|
-
protected override void SendOperation(IListObserver<T> observer, ListOp<T> operation)
|
|
128
|
-
{
|
|
129
|
-
if (operation.isRemove)
|
|
130
|
-
{
|
|
131
|
-
observer.OnRemove(operation.elementId, operation.index, operation.element);
|
|
132
|
-
}
|
|
133
|
-
else
|
|
134
|
-
{
|
|
135
|
-
observer.OnAdd(operation.elementId, operation.index, operation.element);
|
|
136
|
-
}
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
IDisposable IListObservable.Subscribe(IListObserver observer, bool immediate, uint? priority)
|
|
140
|
-
=> Subscribe(new ListObserver<T>(
|
|
141
|
-
onAdd: (id, index, element) => observer.OnAdd(id, index, element),
|
|
142
|
-
onRemove: (id, index, element) => observer.OnRemove(id, index, element),
|
|
143
|
-
onDispose: observer.OnDispose,
|
|
144
|
-
onError: observer.OnError
|
|
145
|
-
), immediate, priority);
|
|
146
|
-
|
|
147
|
-
IDisposable ICollectionObservable<T>.Subscribe(ICollectionObserver<T> observer, bool immediate, uint? priority)
|
|
148
|
-
=> Subscribe(new ListObserver<T>(
|
|
149
|
-
onAdd: (id, index, element) => observer.OnAdd(id, element),
|
|
150
|
-
onRemove: (id, index, element) => observer.OnRemove(id, element),
|
|
151
|
-
onDispose: observer.OnDispose,
|
|
152
|
-
onError: observer.OnError
|
|
153
|
-
), immediate, priority);
|
|
154
|
-
|
|
155
|
-
IDisposable ICollectionObservable.Subscribe(ICollectionObserver observer, bool immediate, uint? priority)
|
|
156
|
-
=> Subscribe(new ListObserver<T>(
|
|
157
|
-
onAdd: (id, index, element) => observer.OnAdd(id, element),
|
|
158
|
-
onRemove: (id, index, element) => observer.OnRemove(id, element),
|
|
159
|
-
onDispose: observer.OnDispose,
|
|
160
|
-
onError: observer.OnError
|
|
161
|
-
), immediate, priority);
|
|
162
|
-
}
|
|
1
|
+
using System;
|
|
2
|
+
using System.Collections;
|
|
3
|
+
using System.Collections.Generic;
|
|
4
|
+
|
|
5
|
+
namespace ObserveThing
|
|
6
|
+
{
|
|
7
|
+
public interface IListOp : IOperation
|
|
8
|
+
{
|
|
9
|
+
uint elementId { get; }
|
|
10
|
+
int index { get; }
|
|
11
|
+
object element { get; }
|
|
12
|
+
bool isRemove { get; }
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
public struct ListOp<T> : IListOp
|
|
16
|
+
{
|
|
17
|
+
public IObservable<IOperation> source { get; set; }
|
|
18
|
+
public int index { get; set; }
|
|
19
|
+
public uint elementId { get; set; }
|
|
20
|
+
public T element { get; set; }
|
|
21
|
+
public bool isRemove { get; set; }
|
|
22
|
+
|
|
23
|
+
object IListOp.element => element;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
public class ObservableList<T> : ObservableBase<IListObserver<T>, ListOp<T>>, IListObservable<T>, IEnumerable<T>
|
|
27
|
+
{
|
|
28
|
+
public T this[int index]
|
|
29
|
+
{
|
|
30
|
+
get => _list[index];
|
|
31
|
+
set
|
|
32
|
+
{
|
|
33
|
+
RemoveAt(index);
|
|
34
|
+
Insert(index, value);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
IEnumerator<T> IEnumerable<T>.GetEnumerator()
|
|
39
|
+
=> _list.GetEnumerator();
|
|
40
|
+
|
|
41
|
+
IEnumerator IEnumerable.GetEnumerator()
|
|
42
|
+
=> _list.GetEnumerator();
|
|
43
|
+
|
|
44
|
+
public int count => _list.Count;
|
|
45
|
+
|
|
46
|
+
private List<T> _list = new List<T>();
|
|
47
|
+
private List<uint> _ids = new List<uint>();
|
|
48
|
+
private CollectionIdProvider _idProvider;
|
|
49
|
+
|
|
50
|
+
public ObservableList() : this(default, default(IEnumerable<T>)) { }
|
|
51
|
+
public ObservableList(params T[] value) : this(default, (IEnumerable<T>)value) { }
|
|
52
|
+
public ObservableList(IEnumerable<T> value) : this(default, value) { }
|
|
53
|
+
|
|
54
|
+
public ObservableList(ObservationContext context) : this(context, default(IEnumerable<T>)) { }
|
|
55
|
+
public ObservableList(ObservationContext context, params T[] value) : this(context, (IEnumerable<T>)value) { }
|
|
56
|
+
public ObservableList(ObservationContext context, IEnumerable<T> value) : base(context)
|
|
57
|
+
{
|
|
58
|
+
_idProvider = new CollectionIdProvider(_ids.Contains);
|
|
59
|
+
|
|
60
|
+
if (value == null)
|
|
61
|
+
return;
|
|
62
|
+
|
|
63
|
+
foreach (var element in value)
|
|
64
|
+
{
|
|
65
|
+
_list.Add(element);
|
|
66
|
+
_ids.Add(_idProvider.GetUnusedId());
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
public void Add(T added)
|
|
71
|
+
=> Insert(_list.Count, added);
|
|
72
|
+
|
|
73
|
+
public void AddRange(IEnumerable<T> toAdd)
|
|
74
|
+
{
|
|
75
|
+
foreach (var added in toAdd)
|
|
76
|
+
Add(added);
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
public bool Remove(T removed)
|
|
80
|
+
{
|
|
81
|
+
var index = _list.IndexOf(removed);
|
|
82
|
+
|
|
83
|
+
if (index == -1)
|
|
84
|
+
return false;
|
|
85
|
+
|
|
86
|
+
RemoveAt(index);
|
|
87
|
+
return true;
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
public void RemoveAt(int index)
|
|
91
|
+
{
|
|
92
|
+
var removed = _list[index];
|
|
93
|
+
var id = _ids[index];
|
|
94
|
+
_list.RemoveAt(index);
|
|
95
|
+
_ids.RemoveAt(index);
|
|
96
|
+
EnqueuePendingOperation(new ListOp<T>() { source = this, element = removed, elementId = id, index = index, isRemove = true });
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
public void Insert(int index, T item)
|
|
100
|
+
{
|
|
101
|
+
var id = _idProvider.GetUnusedId();
|
|
102
|
+
_list.Insert(index, item);
|
|
103
|
+
_ids.Insert(index, id);
|
|
104
|
+
EnqueuePendingOperation(new ListOp<T>() { source = this, element = item, elementId = id, index = index, isRemove = false });
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
public void Clear()
|
|
108
|
+
{
|
|
109
|
+
while (_list.Count > 0)
|
|
110
|
+
RemoveAt(_list.Count - 1);
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
public int IndexOf(T item)
|
|
114
|
+
=> _list.IndexOf(item);
|
|
115
|
+
|
|
116
|
+
public bool Contains(T item)
|
|
117
|
+
=> _list.Contains(item);
|
|
118
|
+
|
|
119
|
+
protected override IEnumerable<ListOp<T>> GetInitializationOperations()
|
|
120
|
+
{
|
|
121
|
+
for (int i = 0; i < _list.Count; i++)
|
|
122
|
+
{
|
|
123
|
+
yield return new ListOp<T>() { source = this, element = _list[i], elementId = _ids[i], index = i, isRemove = false };
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
protected override void SendOperation(IListObserver<T> observer, ListOp<T> operation)
|
|
128
|
+
{
|
|
129
|
+
if (operation.isRemove)
|
|
130
|
+
{
|
|
131
|
+
observer.OnRemove(operation.elementId, operation.index, operation.element);
|
|
132
|
+
}
|
|
133
|
+
else
|
|
134
|
+
{
|
|
135
|
+
observer.OnAdd(operation.elementId, operation.index, operation.element);
|
|
136
|
+
}
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
IDisposable IListObservable.Subscribe(IListObserver observer, bool immediate, uint? priority)
|
|
140
|
+
=> Subscribe(new ListObserver<T>(
|
|
141
|
+
onAdd: (id, index, element) => observer.OnAdd(id, index, element),
|
|
142
|
+
onRemove: (id, index, element) => observer.OnRemove(id, index, element),
|
|
143
|
+
onDispose: observer.OnDispose,
|
|
144
|
+
onError: observer.OnError
|
|
145
|
+
), immediate, priority);
|
|
146
|
+
|
|
147
|
+
IDisposable ICollectionObservable<T>.Subscribe(ICollectionObserver<T> observer, bool immediate, uint? priority)
|
|
148
|
+
=> Subscribe(new ListObserver<T>(
|
|
149
|
+
onAdd: (id, index, element) => observer.OnAdd(id, element),
|
|
150
|
+
onRemove: (id, index, element) => observer.OnRemove(id, element),
|
|
151
|
+
onDispose: observer.OnDispose,
|
|
152
|
+
onError: observer.OnError
|
|
153
|
+
), immediate, priority);
|
|
154
|
+
|
|
155
|
+
IDisposable ICollectionObservable.Subscribe(ICollectionObserver observer, bool immediate, uint? priority)
|
|
156
|
+
=> Subscribe(new ListObserver<T>(
|
|
157
|
+
onAdd: (id, index, element) => observer.OnAdd(id, element),
|
|
158
|
+
onRemove: (id, index, element) => observer.OnRemove(id, element),
|
|
159
|
+
onDispose: observer.OnDispose,
|
|
160
|
+
onError: observer.OnError
|
|
161
|
+
), immediate, priority);
|
|
162
|
+
}
|
|
163
163
|
}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
fileFormatVersion: 2
|
|
1
|
+
fileFormatVersion: 2
|
|
2
2
|
guid: f3cca6c4b227d4249897d38a09947287
|