在ObservableCollection上实现AddRange,并对DataBinding提供适当的支持

我想我自己的ObservableCollection后代支持AddRange方法。 这是我目前拥有的:

 public class ObservableCollectionPlus : ObservableCollection { public void InsertRange(IEnumerable items) { this.CheckReentrancy(); foreach (var item in items) Items.Add(item); var type = NotifyCollectionChangedAction.Reset; var colChanged = new NotifyCollectionChangedEventArgs(type); var countChanged = new PropertyChangedEventArgs("Count"); OnPropertyChanged(countChanged); OnCollectionChanged(colChanged); } } 

我不太了解这里到底发生了什么,为什么会引发这些事件。 这是我在对google和stackoverflow进行一些研究后组装的一个解决方案。

现在,如果我将我的类的实例绑定到LongListSelector然后,在通过InsertRange动态地将项添加到ObservableCollectionPlus ,绑定的LongListSelector的滚动位置将被发送到它的顶部。

如果我以这种标准方式添加项目: foreach (var item in items) collection.Add(item); 那么LongListSelector的位置不会被移位。 但是当然这样我得到的DataBinding通知开销是不受欢迎的。

显然,在我目前的解决方案中出现了问题。 如何实现与foreach (var item in items) collection.Add(item);完全相同的InsertRange foreach (var item in items) collection.Add(item); 但是只会触发一次DataBinding通知,并且不会对绑定对象的滚动位置做些奇怪的事情吗?

可能是因为你发送NotifyCollectionChangedAction.Reset通知,也许只是NotifyCollectionChangedAction.Add会起作用,也许:)

 public class ObservableRangeCollection : ObservableCollection { public void AddRange(IEnumerable collection) { foreach (var i in collection) { Items.Add(i); } OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Add, collection.ToList())); } } 

我最近在一个项目中使用过这个……

 public class RangeObservableCollection : ObservableCollection { private bool _suppressNotification = false; protected override void OnCollectionChanged(NotifyCollectionChangedEventArgs e) { if (!_suppressNotification) base.OnCollectionChanged(e); } public void AddRange(IEnumerable list) { if (list == null) throw new ArgumentNullException("list"); _suppressNotification = true; foreach (T item in list) { Add(item); } _suppressNotification = false; OnCollectionChanged(new NotifyCollectionChangedEventArgs(NotifyCollectionChangedAction.Reset)); } } 

您遇到的DataBinding问题可能与您没有为索引器(属性名称“Item []”)引发PropertyChanged的事实有关,因为它根据源代码在ObservableCollection中发生。

您还可以在GitHub上查看 James Montemagno对ObservableRangeCollection的一个很好的实现,它inheritance自ObservableColection,并包含AddRangeReplaceRange方法以及DataBinding所需的所有PropertyChaged和CollectionChanged通知。

我花了很长时间,麻烦始终是传递给NotifyCollectionChangedEventArgs ctor的参数。 根据行动,有许多不同的ctors采取不同的论点。 以下似乎最终对我有用 : https : //github.com/lolluslollus/Utilz/blob/master/Utilz/SwitchableObservableCollection.cs

    Interesting Posts