gpt4 book ai didi

c# - 有没有一种方法可以使用ObservableCollection和MVVM刷新WPF DataGrid,而无需通知ItemsSource集合?

转载 作者:行者123 更新时间:2023-12-03 10:35:17 25 4
gpt4 key购买 nike

这是我的第一个问题,所以我会努力的。

我正在尝试使用ObservableCollection和MVVM“刷新”一个简单的WPF DataGrid控件,正如网络上的许多教程所述。

在上下文中,这些是我的模型分类:

(PersonViewModel.cs)

public class PersonViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;

private int _id;
private int _idAddress;
private string _name;
private int _age;
private string _address;

public int Id
{
get { return this._id; }
set
{
if (value != this._id)
{
this._id = value;
OnPropertyChanged();
}
}
}
public int IdAddress
{
get { return this._idAddress; }
set
{
if (value != this._idAddress)
{
this._idAddress = value;
OnPropertyChanged();
}
}
}
public string Name
{
get { return this._name; }
set
{
if (value != this._name)
{
this._name = value;
OnPropertyChanged();
}
}
}
public int Age
{
get { return this._age; }
set
{
if (value != this._age)
{
this._age = value;
OnPropertyChanged();
}
}
}
public string Address
{
get { return this._address; }
set
{
if (value != this._address)
{
this._address = value;
OnPropertyChanged();
}
}
}

private void OnPropertyChanged([CallerMemberName]String caller = null)
{
var handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(caller));
}
}
}

(AddressViewModel.cs)
public class AddressViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;

private int _id;
private string _street;
private int _number;

public int Id
{
get { return this._id; }
set
{
if (value != this._id)
{
this._id = value;
OnPropertyChanged();
}
}
}
public string Street
{
get { return this._street; }
set
{
if (value != this._street)
{
this._street = value;
OnPropertyChanged();
}
}
}
public int Number
{
get { return this._number; }
set
{
if (value != this._number)
{
this._number = value;
OnPropertyChanged();
}
}
}

private void OnPropertyChanged([CallerMemberName]String caller = null)
{
var handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(caller));
}
}
}

这是数据库模型的表示形式(无法上传图片<10个帖子)

地址

ID
街道
数字



ID
ID地址
姓名
年龄
地址--->此属性连接“街道”和“地址数”实体。

因此,如您所见,这是一个非常简单的示例。只是概念证明。问题是,每当我尝试通过Entity Framework 6和LINQ向数据库中添加新实体时,都不可避免地必须将该ViewModel实体添加到DataGrid的数据上下文中。

这是直到今天的代码:
public static Person CreatePerson(PersonViewModel personVM)
{
var person = new Person
{
IdAddress = personVM.IdAddress,
Name = personVM.Name,
Age = personVM.Age
};

try
{
using (var context = new OCDemoContext())
{
context.Database.Connection.Open();
context.Person.Add(person);
context.SaveChanges();
context.Database.Connection.Close();
}
}
catch
{
throw;
}

return person;
}

如您所见,这里需要在DataGrid中显示一列,该列连接Address数据库实体的两个属性:Street和Number,并将该值提供给PersonViewModel类的Address属性以在DataGrid中显示为一列。

将实体插入数据库后,将实体添加到DataGrid itemssource集合的代码:
        // Add to the database
PersonsGateway.CreatePerson(personVM);

// Update view on DataGrid's itemssource collection
ViewModel model = this.xGrid.DataContext as ViewModel;

model.Persons.Insert(0, personVM);

XAML为:
<Window x:Class="OCDemo.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525" xmlns:local="clr-namespace:OCDemo">
<Window.Resources>
<local:ViewModel x:Key="xViewModel" />
</Window.Resources>
<Grid x:Name="xGrid" DataContext="{StaticResource xViewModel}">
<DataGrid x:Name="xDataGrid" Grid.Row="0" ItemsSource="{Binding Persons}" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTextColumn Binding="{Binding Path=Name}" Header="Name"/>
<DataGridTextColumn Binding="{Binding Path=Age}" Header="Age"/>
<DataGridTextColumn Binding="{Binding Path=Address}" Header="Address"/>
</DataGrid.Columns>
</DataGrid>
</Grid>

和ViewModel.cs
public class ViewModel
{
public ObservableCollection<PersonViewModel> Persons { get; set; }

public ViewModel()
{
this.Persons = PersonsGateway.RetrievePersons();
}
}

T4 .tt文件已更新为 MSDN - Updating code generation for data binding说明。

因此,在ObservableCollection场景中,可能仅依赖于将实体添加到数据库中,而不必始终将实体添加到itemssource集合中?

最佳答案

将您的 View 模型更改为以下内容

public class ViewModel
{
public ObservableCollection<PersonViewModel> Persons { get; private set; }

public ViewModel()
{
Persons = new ObservableCollection<PersonViewModel>();
Persons.AddRange(PersonsGateway.RetrievePersons().ToList());
}
}

重要的是,一次创建可观察的集合而不是重新创建它,而是依赖于更改通知,因此先创建它,然后使用标准方法来对其进行管理。

关于c# - 有没有一种方法可以使用ObservableCollection和MVVM刷新WPF DataGrid,而无需通知ItemsSource集合?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32784941/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com