diff --git a/src/SharpIDE.Application/ObservableCollectionExtensions/ObservableSortedSet.Views.cs b/src/SharpIDE.Application/ObservableCollectionExtensions/ObservableSortedSet.Views.cs deleted file mode 100644 index ffcff89..0000000 --- a/src/SharpIDE.Application/ObservableCollectionExtensions/ObservableSortedSet.Views.cs +++ /dev/null @@ -1,227 +0,0 @@ -using System.Collections; -using System.Collections.Specialized; - -namespace ObservableCollections -{ - public partial class ObservableSortedSet : IReadOnlyCollection, IObservableCollection - { - public ISynchronizedView CreateView(Func transform) - { - return new View(this, transform); - } - - sealed class View : ISynchronizedView - { - public ISynchronizedViewFilter Filter - { - get { lock (SyncRoot) return filter; } - } - - readonly ObservableSortedSet source; - readonly Func selector; - readonly Dictionary dict; - int filteredCount; - - ISynchronizedViewFilter filter; - - public event NotifyViewChangedEventHandler? ViewChanged; - public event Action? RejectedViewChanged; - public event Action? CollectionStateChanged; - - public object SyncRoot { get; } - - public View(ObservableSortedSet source, Func selector) - { - this.source = source; - this.selector = selector; - this.filter = SynchronizedViewFilter.Null; - this.SyncRoot = new object(); - lock (source.SyncRoot) - { - this.dict = source._set.ToDictionary(x => x, x => (x, selector(x))); - this.filteredCount = dict.Count; - this.source.CollectionChanged += SourceCollectionChanged; - } - } - - public int Count - { - get - { - lock (SyncRoot) - { - return filteredCount; - } - } - } - - public int UnfilteredCount - { - get - { - lock (SyncRoot) - { - return dict.Count; - } - } - } - - public void AttachFilter(ISynchronizedViewFilter filter) - { - if (filter.IsNullFilter()) - { - ResetFilter(); - return; - } - - lock (SyncRoot) - { - this.filter = filter; - this.filteredCount = 0; - foreach (var (_, (value, view)) in dict) - { - if (filter.IsMatch(value, view)) - { - filteredCount++; - } - } - ViewChanged?.Invoke(new SynchronizedViewChangedEventArgs(NotifyCollectionChangedAction.Reset, true)); - } - } - - public void ResetFilter() - { - lock (SyncRoot) - { - this.filter = SynchronizedViewFilter.Null; - this.filteredCount = dict.Count; - ViewChanged?.Invoke(new SynchronizedViewChangedEventArgs(NotifyCollectionChangedAction.Reset, true)); - } - } - - public ISynchronizedViewList ToViewList() - { - return new FiltableSynchronizedViewList(this, isSupportRangeFeature: true); - } - - public NotifyCollectionChangedSynchronizedViewList ToNotifyCollectionChanged() - { - return new FiltableSynchronizedViewList(this, isSupportRangeFeature: false); - } - - public NotifyCollectionChangedSynchronizedViewList ToNotifyCollectionChanged(ICollectionEventDispatcher? collectionEventDispatcher) - { - return new FiltableSynchronizedViewList(this, isSupportRangeFeature: false, collectionEventDispatcher); - } - - public IEnumerator GetEnumerator() - { - lock (SyncRoot) - { - foreach (var item in dict) - { - if (filter.IsMatch(item.Value)) - { - yield return item.Value.Item2; - } - } - } - } - - IEnumerator IEnumerable.GetEnumerator() => GetEnumerator(); - - public IEnumerable<(T Value, TView View)> Filtered - { - get - { - lock (SyncRoot) - { - foreach (var item in dict) - { - if (filter.IsMatch(item.Value)) - { - yield return item.Value; - } - } - } - } - } - - public IEnumerable<(T Value, TView View)> Unfiltered - { - get - { - lock (SyncRoot) - { - foreach (var item in dict) - { - yield return item.Value; - } - } - } - } - - public void Dispose() - { - this.source.CollectionChanged -= SourceCollectionChanged; - } - - private void SourceCollectionChanged(in NotifyCollectionChangedEventArgs e) - { - lock (SyncRoot) - { - switch (e.Action) - { - case NotifyCollectionChangedAction.Add: - if (e.IsSingleItem) - { - var v = (e.NewItem, selector(e.NewItem)); - dict.Add(e.NewItem, v); - this.InvokeOnAdd(ref filteredCount, ViewChanged, RejectedViewChanged, v, -1); - } - else - { - var i = e.NewStartingIndex; - foreach (var item in e.NewItems) - { - var v = (item, selector(item)); - dict.Add(item, v); - this.InvokeOnAdd(ref filteredCount, ViewChanged, RejectedViewChanged, v, i++); - } - } - break; - case NotifyCollectionChangedAction.Remove: - if (e.IsSingleItem) - { - if (dict.Remove(e.OldItem, out var value)) - { - this.InvokeOnRemove(ref filteredCount, ViewChanged, RejectedViewChanged, value, -1); - } - } - else - { - foreach (var item in e.OldItems) - { - if (dict.Remove(item, out var value)) - { - this.InvokeOnRemove(ref filteredCount, ViewChanged, RejectedViewChanged, value, -1); - } - } - } - break; - case NotifyCollectionChangedAction.Reset: - dict.Clear(); - this.InvokeOnReset(ref filteredCount, ViewChanged); - break; - case NotifyCollectionChangedAction.Replace: - case NotifyCollectionChangedAction.Move: - default: - break; - } - - CollectionStateChanged?.Invoke(e.Action); - } - } - } - } -} diff --git a/src/SharpIDE.Application/ObservableCollectionExtensions/ObservableSortedSet.cs b/src/SharpIDE.Application/ObservableCollectionExtensions/ObservableSortedSet.cs deleted file mode 100644 index 6025dec..0000000 --- a/src/SharpIDE.Application/ObservableCollectionExtensions/ObservableSortedSet.cs +++ /dev/null @@ -1,318 +0,0 @@ -using ObservableCollections.Internal; -using System.Collections; -using System.Diagnostics.CodeAnalysis; - -// Courtesy of Copilot Agent -// Replace with https://github.com/Cysharp/ObservableCollections/pull/111 if it gets merged -namespace ObservableCollections -{ - // can not implements ISet because set operation can not get added/removed values. - public partial class ObservableSortedSet : IReadOnlySet, IReadOnlyCollection, IObservableCollection where T : notnull - { - private readonly SortedSet _set; - public object SyncRoot { get; } = new object(); - - public ObservableSortedSet() - { - _set = new SortedSet(); - } - - public ObservableSortedSet(IComparer? comparer) - { - _set = new SortedSet(comparer: comparer); - } - - public ObservableSortedSet(IEnumerable collection) - { - _set = new SortedSet(collection: collection); - } - - public ObservableSortedSet(IEnumerable collection, IComparer? comparer) - { - _set = new SortedSet(collection: collection, comparer: comparer); - } - - public event NotifyCollectionChangedEventHandler? CollectionChanged; - - public int Count - { - get - { - lock (SyncRoot) - { - return _set.Count; - } - } - } - - public bool IsReadOnly => false; - - public bool Add(T item) - { - lock (SyncRoot) - { - if (_set.Add(item)) - { - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Add(item, -1)); - return true; - } - - return false; - } - } - - public void AddRange(IEnumerable items) - { - lock (SyncRoot) - { - if (!items.TryGetNonEnumeratedCount(out var capacity)) - { - capacity = 4; - } - - using (var list = new ResizableArray(capacity)) - { - foreach (var item in items) - { - if (_set.Add(item)) - { - list.Add(item); - } - } - - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Add(list.Span, -1)); - } - } - } - - public void AddRange(T[] items) - { - AddRange(items.AsSpan()); - } - - public void AddRange(ReadOnlySpan items) - { - lock (SyncRoot) - { - using (var list = new ResizableArray(items.Length)) - { - foreach (var item in items) - { - if (_set.Add(item)) - { - list.Add(item); - } - } - - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Add(list.Span, -1)); - } - } - } - - public bool Remove(T item) - { - lock (SyncRoot) - { - if (_set.Remove(item)) - { - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Remove(item, -1)); - return true; - } - - return false; - } - } - - public void RemoveRange(IEnumerable items) - { - lock (SyncRoot) - { - if (!items.TryGetNonEnumeratedCount(out var capacity)) - { - capacity = 4; - } - - using (var list = new ResizableArray(capacity)) - { - foreach (var item in items) - { - if (_set.Remove(item)) - { - list.Add(item); - } - } - - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Remove(list.Span, -1)); - } - } - } - - public void RemoveRange(T[] items) - { - RemoveRange(items.AsSpan()); - } - - public void RemoveRange(ReadOnlySpan items) - { - lock (SyncRoot) - { - using (var list = new ResizableArray(items.Length)) - { - foreach (var item in items) - { - if (_set.Remove(item)) - { - list.Add(item); - } - } - - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Remove(list.Span, -1)); - } - } - } - - public void Clear() - { - lock (SyncRoot) - { - _set.Clear(); - CollectionChanged?.Invoke(NotifyCollectionChangedEventArgs.Reset()); - } - } - -#if !NETSTANDARD2_0 && !NET_STANDARD_2_0 && !NET_4_6 - - public bool TryGetValue(T equalValue, [MaybeNullWhen(false)] out T actualValue) - { - lock (SyncRoot) - { - return _set.TryGetValue(equalValue, out actualValue); - } - } - -#endif - - public bool Contains(T item) - { - lock (SyncRoot) - { - return _set.Contains(item); - } - } - - public bool IsProperSubsetOf(IEnumerable other) - { - lock (SyncRoot) - { - return _set.IsProperSubsetOf(other); - } - } - - public bool IsProperSupersetOf(IEnumerable other) - { - lock (SyncRoot) - { - return _set.IsProperSupersetOf(other); - } - } - - public bool IsSubsetOf(IEnumerable other) - { - lock (SyncRoot) - { - return _set.IsSubsetOf(other); - } - } - - public bool IsSupersetOf(IEnumerable other) - { - lock (SyncRoot) - { - return _set.IsSupersetOf(other); - } - } - - public bool Overlaps(IEnumerable other) - { - lock (SyncRoot) - { - return _set.Overlaps(other); - } - } - - public bool SetEquals(IEnumerable other) - { - lock (SyncRoot) - { - return _set.SetEquals(other); - } - } - - public IEnumerator GetEnumerator() - { - lock (SyncRoot) - { - foreach (var item in _set) - { - yield return item; - } - } - } - - IEnumerator IEnumerable.GetEnumerator() - { - return GetEnumerator(); - } - - public IComparer Comparer - { - get - { - lock (SyncRoot) - { - return _set.Comparer; - } - } - } - - // SortedSet-specific properties - public T? Min - { - get - { - lock (SyncRoot) - { - return _set.Count > 0 ? _set.Min : default; - } - } - } - - public T? Max - { - get - { - lock (SyncRoot) - { - return _set.Count > 0 ? _set.Max : default; - } - } - } - - // SortedSet-specific methods - public IEnumerable Reverse() - { - lock (SyncRoot) - { - return _set.Reverse().ToArray(); - } - } - - public IEnumerable GetViewBetween(T lowerValue, T upperValue) - { - lock (SyncRoot) - { - return _set.GetViewBetween(lowerValue, upperValue).ToArray(); - } - } - } -}