如果在代码中更改了ObservableCollection的项目,我应该怎么做才能使WPF DataGrid显示更改?
<DataGrid HorizontalAlignment="Left" Height="100" Margin="54,25,0,0" VerticalAlignment="Top" Width="264"
IsSynchronizedWithCurrentItem="True" AutoGenerateColumns="False"
ItemsSource="{Binding DataSource}" SelectedItem="{Binding SelectedPerson}">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding FirstName}" />
<DataGridTextColumn Binding="{Binding LastName}" />
</DataGrid.Columns>
</DataGrid>
我在代码中更新SelectedPerson.FirstName
并执行DataSource
的setter。当前DataSource.FirstName
已更新,但DataGrid不显示更改。如果单击列标题,DataGrid将刷新并显示已更改的数据。当我使用MVVM并且没有对DataGrid的引用时,如何使其快速刷新?
public class Person
{
public string FirstName { get; set; }
public string LastName { get; set; }
}
public class VM : Notifier
{
private ObservableCollection<Person> dataSource;
public ObservableCollection<Person> DataSource
{
get { return dataSource; }
set
{
dataSource = value;
OnPropertyChanged("DataSource");
}
}
private Person selectedPerson;
public Person SelectedPerson
{
get { return selectedPerson; }
set
{
selectedPerson = value;
OnPropertyChanged("SelectedPerson");
}
}
private string string1;
public string String1
{
get { return string1; }
set
{
string1 = value;
OnPropertyChanged(String1);
}
}
public VM()
{
String1 = "abc";
DataSource = new ObservableCollection<Person>();
DataSource.Add(new Person { FirstName = "Alpha", LastName = "Apple" });
DataSource.Add(new Person { FirstName = "Beta", LastName = "Banana" });
DataSource.Add(new Person { FirstName = "Charlie", LastName = "Cucumber" });
}
public ICommand SetSelectedCommand => new RelayCommandBase(SetSelected);
private void SetSelected(object parameter = null)
{
SelectedPerson.FirstName = String1;
SelectedPerson = SelectedPerson; // force setter to run
DataSource = DataSource; // force ObservableCollection setter to run
}
}
答案 0 :(得分:1)
Person
类应该实现INotifyPropertyChanged接口:
public class Person : INotifyPropertyChanged
{
private string _firstName;
public string FirstName
{
get { return _firstName; }
set
{
_firstName = value;
NotifyPropertyChanged();
}
}
private string _lastName;
public string LastName
{
get { return _lastName; }
set
{
_lastName = value;
NotifyPropertyChanged();
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
{
if (PropertyChanged != null)
PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
}
}
答案 1 :(得分:0)
您的更改未反映为正在更新的项目(人员)不会提出更改通知以更新UI。为此,您需要更新Person类以在Person类中实现接口INotifyPropertyChanged,这与您在viewmodel中实现的方式相同,这应该可行。
public class Person:Notifier
{
private string _firstName;
public string FirstName
{
get { return _firstName; }
set
{
_firstName = value;
OnPropertyChanged(nameof(this.FirstName));
}
}
private string _lastName;
public string LastName
{
get { return _lastName; }
set
{
_lastName = value;
OnPropertyChanged(nameof(this.LastName));
}
}
}
还有一件事。在您的.NET Framework版本中如果支持,您可以使用C# nameof 以字符串形式获取属性名称,而不是对名称进行硬编码。当您重构/重命名属性时,这会有所帮助。