我有一个ViewModel,它有两个ICollectionView
s,它们被绑定为ItemsSource
s到两个不同的ListBox
es。两者都 Package 了相同的ObservableCollection
,但使用了不同的过滤器。最初一切正常,两个ListBox都显示正确填充。
然而,当我在ObservableCollection中更改一个项目并修改一个与过滤相关的属性时,ListBox不会更新。在调试器中,我发现两个ICollectionVIEws的SourceCollection都是null,尽管我的ObservableCollection仍然在那里。
这是我如何修改一个项目,确保通过删除和添加相同的项目来更新ICollectionViews:
private void UnassignTag(TagViewModel tag)
{
TrackChangedTagOnCollectionViews(tag, t => t.IsAssigned = false);
}
private void TrackChangedTagOnCollectionViews(TagViewModel tag, Action<TagViewModel> changeTagAction)
{
_tags.Remove(tag);
changeTagAction.Invoke(tag);
_tags.Add(tag);
}
该机制在我使用相同类的另一个上下文中工作。
我还意识到,如果我在ICollectionViews的CollectionChanged事件上注册侦听器,问题就消失了。我确保我从GUI线程创建和修改了它们,并怀疑垃圾回收是问题所在,但目前我被卡住了...
更新日期:
调试时我意识到,就在我对托管UserControl的WinForms窗体调用ShowDialog()
之前,SourceCollections还在那里。当对话框显示时,它们消失了。
我这样创建ICollectionViews:
AvailableTags = new CollectionViewSource { Source = _tags }.View;
AssignedTags = new CollectionViewSource { Source = _tags }.View;
下面是我如何绑定其中一个(另一个非常相似):
<ListBox Grid.Column="0" ItemsSource="{Binding AvailableTags}" Style="{StaticResource ListBoxStyle}">
<ListBox.ItemTemplate>
<DataTemplate>
<Border Style="{StaticResource ListBoxItemBorderStyle}">
<DockPanel>
<Button DockPanel.Dock="Right" ToolTip="Assign" Style="{StaticResource IconButtonStyle}"
Command="{Binding Path=DataContext.AssignSelectedTagCommand, RelativeSource={RelativeSource AncestorType={x:Type tags:TagsListView}}}"
CommandParameter="{Binding}">
<Image Source="..."/>
</Button>
<TextBlock Text="{Binding Name}" Style="{StaticResource TagNameTextBlockStyle}"/>
</DockPanel>
</Border>
</DataTemplate>
</ListBox.ItemTemplate>
</ListBox>
我在我的ViewModel中使用MvvmLight的RelayCommand<T>
作为ICommand
实现:
AssignSelectedTagCommand = new RelayCommand<TagViewModel>(AssignTag);
2条答案
按热度按时间rqdpfwrv1#
我也有这个问题,有一个类似的用例。当我更新底层集合时,我会在所有过滤的视图上调用
Refresh()
。有时,这会导致从ListCollectionView.PrepareLocalArray()
中抛出NullReferenceException
,因为SourceCollection
为null。问题是你不应该绑定到
CollectionView
,而是绑定到CollectionViewSource.View
属性。我是这么做的:
68de4m5k2#
问题的原因是
CollectionViewSource
正在进行垃圾收集。如果只保留对
ICollectionView
的引用,并且在我从CollectionViewSource
获取视图后让CollectionViewSource
退出作用域,就会出现这个问题。请保留对CollectionViewSource
的引用。