WPF中DataGrid控件无法显示ObservableCollection数据求助
首先,你的DataGrid无法加载数据的核心原因是Dog类没有暴露公共的可绑定属性——DataGrid需要通过公共属性来读取和显示数据,而你的Dog类里只有私有字段name和number,没有对应的公共getter,绑定系统根本找不到要显示的数据。
一、修复核心问题:完善Dog类
修改Dog类,添加公共属性,并确保INotifyPropertyChanged接口正确生效(初始化时触发不是必须,但养成好习惯能为后续属性变更通知打下基础):
using System.ComponentModel; using System.Runtime.CompilerServices; namespace PetProject { public class Dog : INotifyPropertyChanged { private string _name; private string _number; public event PropertyChangedEventHandler PropertyChanged; // 供DataGrid绑定的公共属性 public string Name { get => _name; set { _name = value; OnPropertyChanged(); } } public string Number { get => _number; set { _number = value; OnPropertyChanged(); } } public Dog(string name, int number) { Name = name; Number = number.ToString("D4"); } // 简化PropertyChanged触发逻辑,用CallerMemberName自动获取属性名,避免拼写错误 private void OnPropertyChanged([CallerMemberName] string propertyName = null) { PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); } } }
二、验证绑定逻辑(现有绑定可行,也可优化)
你的CollectionViewSource绑定到Application.Current.Dogs的写法是正确的,但如果暂时不需要排序/过滤功能,可以直接简化DataGrid的绑定,省去CollectionViewSource:
<!-- 移除Window.Resources中的CollectionViewSource,修改DataGrid绑定 --> <DataGrid ItemsSource="{Binding Source={x:Static Application.Current}, Path=Dogs}" />
如果后续需要排序、过滤等功能,保留CollectionViewSource的写法即可,只要Dog类有公共属性就能正常显示数据。
三、代码改进建议
不要在App类中存放业务数据:App类是应用程序入口,适合存放全局配置,业务数据应该放在专门的ViewModel类中,遵循MVVM模式(这是WPF开发的最佳实践,能让代码结构更清晰、易维护)。
ObservableCollection属性设为只读:你的
App.Dogs属性的setter是多余的,因为ObservableCollection本身是可变集合(支持Add/Remove操作),不需要替换整个集合。修改为:
public ObservableCollection<Dog> Dogs { get; } = new ObservableCollection<Dog>();
之后在LoadData里直接用Dogs.Add(...)即可,无需初始化私有字段。
删除无用代码:MainWindow里的
DogsDataView变量没有实际用途,可以直接删除。显式定义DataGrid列:自动生成列偶尔会出现意外,显式定义列更可控,比如:
<DataGrid ItemsSource="{Binding Source={x:Static Application.Current}, Path=Dogs}" AutoGenerateColumns="False"> <DataGrid.Columns> <DataGridTextColumn Header="Name" Binding="{Binding Name}" /> <DataGridTextColumn Header="Number" Binding="{Binding Number}" /> </DataGrid.Columns> </DataGrid>
做完这些修改后,你的DataGrid应该就能正常显示Johnny和Diamond的数据了。
内容的提问来源于stack exchange,提问作者Ne_Plus_Ultra

