C# 如何在数据刷新后保持当前类型的ICollection?
我的应用程序客户端/服务器有问题。我使用MVVM模式。在我看来,我有一个C# 如何在数据刷新后保持当前类型的ICollection?,c#,wpf,data-binding,mvvm,icollectionview,C#,Wpf,Data Binding,Mvvm,Icollectionview,我的应用程序客户端/服务器有问题。我使用MVVM模式。在我看来,我有一个DataGrid,它与我的ViewModel中的ICollection绑定,代码行如下: public ICollectionView Customers { get { return _customers; } set { _customers= value; Ra
DataGrid
,它与我的ViewModel中的ICollection
绑定,代码行如下:
public ICollectionView Customers
{
get
{
return _customers;
}
set
{
_customers= value;
RaisePropertyChanged("Customers");
}
}
_customers = CollectionViewSource.GetDefaultView(Manager.Instance.Customers());
_customers .SortDescriptions.Add(new SortDescription("CreationDate", ListSortDirection.Descending));
在开始时,这两行工作正常:myDataGrid
有我的客户列表,排序正常
但是,当服务器更新我的客户列表时,我想更新我的收藏,以及我的DataGrid
。
因此,我收到了一份新客户名单的通知。收到此通知后,我使用以下行更新我的收藏:
Customers = CollectionViewSource.GetDefaultView(e.CustomersInfo);
_customers.SortDescriptions.Clear();
_customers .SortDescriptions.Add(new SortDescription("CreationDate", ListSortDirection.Descending));
Customers.Refresh();
在这里,我的DataGrid
可以很好地使用良好的数据进行刷新,但排序不是刷新,因为在开始时,我的客户列表是按CreationDate排序的,但在刷新之后,我的列表是按CustomerName排序的
这里是我的XAML代码:
<DataGrid AutoGenerateColumns="false" ItemsSource="{Binding Customers, Mode=TwoWay}" IsSynchronizedWithCurrentItem="True" Name="dtgEventInfo" SelectedItem="{Binding SelectedCustomers, Mode=TwoWay, UpdateSourceTrigger=PropertyChanged}" ItemContainerStyle="{StaticResource ItemContStyle}" IsEnabled="True" IsReadOnly="True" Margin="0,0,330,0" GridLinesVisibility="None" SelectionMode="Single">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Name, Mode=TwoWay}" Header="Name" MinWidth="40" Width="Auto"/>
<DataGridTextColumn Binding="{Binding CreationDate, Mode=TwoWay}" Header="Date" MinWidth="50" Width="Auto"/>
</DataGrid.Columns>
</DataGrid>
你有什么办法帮我吗?经过一些研究,我没有找到任何解决方案…我认为您应该替换
RaisePropertyChanged(“事件”)代码>由raiseProperty更改(“客户”)代码>当需要您想要的行为时,我会执行以下操作:
- 我创建了一个我类型的可观察集合,例如_mysource
- 我创建了一个ICollectionView,例如
- 我使用Clear/Add/Remove更新_mysource
- 在_myview.Refresh()上应用排序/分组/筛选
这对你有用吗
this._mysource.Clear();
this._mysource.AddRange(e.CustomersInfo);
_myview.Refresh();
你可以尝试两件事
在ViewModel类中实现INotifyPropertyChanged接口,该接口可在需要时更新UI。请看
使用ObservableCollection而不是CollectionView,CollectionView已在TifyPropertyChanged接口中实现,并在需要时更新UI。通过实现IComparer接口,也可以进行排序操作。请查看链接
如果有用,请标记答案我猜您的更新方法是在与主线程不同的线程中运行的。您可以尝试以下方法:
if (Application.Current.Dispatcher.CheckAccess())
{
UpdateCollectionView(e.CustomersInfo);
}
else
{
Application.Current.Dispatcher.Invoke(new Action(() => UpdateCollectionView(e.CustomersInfo)));
}
private void UpdateCollectionView(IEnumerable<Customer> customers)
{
Customers = CollectionViewSource.GetDefaultView(customers);
Customers.SortDescriptions.Clear();
Customers.SortDescriptions.Add(new SortDescription("CreationDate", ListSortDirection.Descending));
Customers.Refresh();
}
if(Application.Current.Dispatcher.CheckAccess())
{
UpdateCollectionView(如CustomerInfo);
}
其他的
{
Application.Current.Dispatcher.Invoke(新操作(()=>UpdateCollectionView(e.CustomerInfo));
}
私有void UpdateCollectionView(IEnumerable客户)
{
Customers=CollectionViewSource.GetDefaultView(客户);
Customers.SortDescriptions.Clear();
Customers.SortDescriptions.Add(新的SortDescription(“CreationDate”,ListSortDirection.Descending));
Customers.Refresh();
}
在Visual Studio中进行了一些搜索和大量调试后,我想我已经找到了问题所在。在我的managermanager.cs
中,当我收到通知时,我这样做了:
ObservableCollection<CustomerInfo> collection = new ObservableCollection<CustomerInfo>(e.CustomersInfoList);
CustomerListViewModel.Instance.Customers = collection;
observedcollection collection=新的observedcollection(如CustomerInfo列表);
CustomerListViewModel.Instance.Customers=集合;
因此,这个新的实例化可能会导致我的问题,因为在同一个集合上,我实现了一些过滤器,并且,在过滤器方法之后排序是正确的
那你现在有什么想法吗?对不起,这是一个错误的复制/粘贴,我的RaiseProperty已更改,我将发布我的第一篇帖子!我的ViewModel已经实现了一个ViewModelBase,它还实现了在_Customers.Refresh()之后调用“RaisePropertyChanged(“Customers”);”的inotifyPropertyChanged;此解决方案无法解决问题。我的datagrid使用良好的客户列表进行刷新,但排序又不是很好。在我的代码中,刷新方法是aslready调用。更新我的数据是可行的,但我的列表中定义的排序并不是keepi,而是发布工作更新和排序的代码。我不知道为什么排序与你的解决方案不起作用,我会做一个小测试项目嗯,如果我像你一样尝试它-它的工作。你检查过你的e.CustomerInfo类型了吗?它与您的初始集合类型相同吗?我将在我的ViewModel中尝试此方法。如果它能解决我的问题,我会告诉你的。谢谢,刷新后,我将更新我的ICollection。现在使用您的解决方案,我更新了一个observableCollection。但是现在,当我尝试在viewModel中刷新我的ICollection时,我有一个错误,它告诉我线程不是所有者,因此,我现在无法更新我的排序使用ObservableCollection而不是ICollection。