C# WPF中如何跨窗口传递类属性值并绑定至主窗口DataGrid
问题修复方案
你现有代码存在3个核心错误,按以下步骤修改即可实现需求:
- 新增窗口创建的商品对象是局部变量,没有暴露给主窗口,主窗口中自行new的是空对象,自然拿不到录入值
- DataGrid列的绑定路径和实体类属性名不匹配,绑定不生效
- 没有给DataGrid设置支持自动刷新的数据源集合,新增数据无法推送到UI展示
第一步:补全必要命名空间引用
主窗口和新增窗口的后台代码顶部,添加可观察集合的命名空间引用:
using System.Collections.ObjectModel;
第二步:修改新增商品窗口(PnlAddItem)后台代码
将录入完成的商品对象通过公共属性暴露,使用DialogResult标记操作状态,不要仅隐藏窗口:
public partial class PnlAddItem : Window { public PnlAddItem() { InitializeComponent(); } // 公共属性,用于向外传递录入完成的商品信息 public AddItemToPRGrid NewItem { get; private set; } private void btnAddItem_Click(object sender, RoutedEventArgs e) { // 可自行补充输入校验:比如数量是否为合法数字、日期是否已选择,避免转换报错 NewItem = new AddItemToPRGrid { ItemNo = txtItemNo.Text.Trim(), ItemName = txtItemName.Text.Trim(), Qty = int.Parse(txtItemQty.Text.Trim()), expDate = dpItemExpDate.SelectedDate.Value }; // 标记新增操作完成,自动关闭弹窗 DialogResult = true; Close(); } // 如果你有取消按钮,加对应事件即可 private void btnCancel_Click(object sender, RoutedEventArgs e) { DialogResult = false; Close(); } }
第三步:修改主窗口(MainWindow)后台代码
初始化可观察集合作为DataGrid数据源,打开新增窗口后判断操作结果,将新商品追加到集合:
public partial class MainWindow : Window { // 存储所有商品条目的可观察集合,增删条目时UI会自动刷新 private readonly ObservableCollection<AddItemToPRGrid> _itemList = new ObservableCollection<AddItemToPRGrid>(); public MainWindow() { InitializeComponent(); // 给DataGrid绑定数据源 dataGridAddItem.ItemsSource = _itemList; } private void btnCreatePR_Click(object sender, RoutedEventArgs e) { // 直接从_itemList中取已录入的商品数据即可 if (_itemList.Count > 0) { MessageBox.Show($"第一条商品编号:{_itemList[0].ItemNo}"); } } private void btnAddItem_Click(object sender, RoutedEventArgs e) { var addWindow = new PnlAddItem(); // 只有用户点了新增按钮确认提交时,才把数据加到列表 if (addWindow.ShowDialog() == true && addWindow.NewItem != null) { _itemList.Add(addWindow.NewItem); } } }
第四步:修正DataGrid的XAML绑定配置
把列的绑定路径改成和实体类属性名完全一致,关闭多余的自带新增行功能:
<Grid Height="250"> <DataGrid x:Name="dataGridAddItem" CanUserAddRows="False" AutoGenerateColumns="False" ColumnWidth="*"> <DataGrid.Columns> <!-- 绑定路径严格匹配实体类属性名,WPF绑定大小写敏感 --> <DataGridTextColumn Header="Item No" Binding="{Binding ItemNo}"/> <DataGridTextColumn Header="Item Name" Binding="{Binding ItemName}"/> <DataGridTextColumn Header="Quantity" Binding="{Binding Qty}"/> <DataGridTextColumn Header="Expiry Date" Binding="{Binding expDate, StringFormat='yyyy-MM-dd'}"/> </DataGrid.Columns> </DataGrid> </Grid>
注意事项
- 不要用静态变量传值,静态变量全局共享,多次打开新增窗口容易出现数据覆盖问题,公共属性+DialogResult是WPF弹窗传值的标准实现
- 正式使用前务必补充输入校验:比如数量输入非数字、日期未选择时要给出提示,不要直接强转,避免运行时报错
- 如果你需要后续对条目做增删改操作,直接操作
_itemList集合即可,DataGrid会自动同步UI变化
内容的提问来源于stack exchange,提问作者Tharindu
相关产品推荐
相关产品推荐

