繁体   English   中英

如何将ObservableCollection与datagrid WPF绑定

[英]How to bind ObservableCollection with datagrid WPF

我已经检查了这些链接,但没有解决我的问题。

我有两个模型类( Order.csOrderItems.cs )和一个视图( Invoice.xaml

Order类中有ObservableCollection(OrderItem) ,Invoice.xaml中有一个数据网格。 我需要将ObservableCollection绑定到datagrid。 问题是,当将项目添加到ObservableCollection时,通过编写xaml代码进行绑定不会自动更新datagrid。

代码如下所示

订单类别

public class Order
{
    public Order()
    {
        OrderItems =new ObservableCollection<OrderItem>();
    }

    public ObservableCollection<OrderItem> OrderItems { get; set; }

    public void GetOrderDetails(string customerId)
    {
        // method for getting set of OrderItmes objects and add to the 
        // ObservableCollection<OrderItem>
    }
}

OrderItem类

public class OrderItem
{
    public OrderItem(string supplierId, string itemId, string    itemName,decimal weight)
    {
        // some codes here
    }
    public string SupplierId { get; set; } // Supplier's ID
    public string ItemId { get; set; } // Item ID
    public string ItemName { get; set; }// Item Name
    public decimal Weight { get; set; } // weight of the item
}

所述Invoice.xaml的XAML代码(为简单起见,仅在必要的代码被示出。 模型是订单和OrderItem的类的包。

    xmlns:model="clr-namespace:Onion.Model"
<Window.Resources>
    <model:Order x:Key="Order"/>
</Window.Resources>

<DataGrid x:Name="dataGrid" AutoGenerateColumns="False" CanUserResizeRows="False" Grid.ColumnSpan="8"
            Margin="0,0,30.5,0" CanUserResizeColumns="False" CanUserReorderColumns="False"
            CanUserSortColumns="False" CanUserAddRows="False" IsReadOnly="True"
            DataContext="{Binding Source={StaticResource Order}}" ItemsSource="{Binding OrderItems}">
            <DataGrid.Columns>
                <DataGridTextColumn Binding="{Binding SupplierId}" CanUserResize="False" FontSize="16"
                    Header="Supplier" Width="0.18*" />
                <DataGridTextColumn Binding="{Binding ItemId}" CanUserResize="False" FontSize="16"
                    Header="ItemID" Width="0.13*" />
                <DataGridTextColumn Binding="{Binding ItemName}" CanUserResize="False" FontSize="16"
                    Header="Item name" Width="0.2*" />
                <DataGridTextColumn Binding="{Binding Weight}" CanUserResize="False" FontSize="16" 
                    Header="Weight" Width="0.1*" />

 </DataGrid>

但是我可以通过在需要的地方在Invoice.xaml.cs类中编写代码而无需编写xaml代码来实现此目的。

    private void txtBox_PreviewKeyDown(object sender, KeyEventArgs e){
    Order _order = new Order();
    _order.GetOrderDetails(customerId);// add OrderItems to the ObservableCollection

    // If this code is written some xaml codes are not needed (they are shown  below in the question
    dataGrid.ItemsSource = _order.OrderItems; // OrderItems is the ObservableCollection<OrderItem>  
}

(包括将各列绑定到OrderItem中的属性)如果dataGrid.ItemsSource = _order.OrderItems行,则不需要以下代码; 用来。

xmlns:model="clr-namespace:Onion.Model"
<Window.Resources>
    <model:Order x:Key="Order"/>
 </Window.Resources>
 DataContext="{Binding Source={StaticResource Order}}" ItemsSource="{Binding OrderItems}"

谁能指出我如何克服这个问题。

您的网格绑定到Order静态资源:

<Window.Resources>
    <model:Order x:Key="Order"/>
</Window.Resources>

<DataGrid DataContext="{Binding Source={StaticResource Order}}" ...

在事件处理程序中,您正在创建一个新的Order实例:

Order _order = new Order();

然后,您要调用一个方法,例如,将一个OrderItem添加到_orderOrderItems集合中。 不是您的DataGrid.ItemsSource绑定到的OrderItems集合。

一个简单的解决方法是在后面的代码中声明您的Order并将其分配给构造函数中的DataContext

private readonly Order _order = new Order();

public WindowName()
{
    DataContext = _order;
}

然后从您的DataGrid删除DataContext绑定(它将继承Window.DataContext )。 然后,您可以从事件处理程序中删除Order _order = new Order() ,而改用实例字段_order

理想情况下,不需要您的事件处理程序,并且您的Order中将有一个ICommand ,该ICommand将绑定到应该添加新订单的任何按钮上。

填充数据时,您需要告诉框架数据已更新。

因此,从集合的Setter中的Viewmodel代码中,添加一行写有RaisePropertyChanged(“ OrderItems”)的行,这是您告诉网格的绑定源名称。

其工作流程为:

  1. 在您的Xaml中,添加ItemsSource =“ {Binding Orders}”。 这将是属性更改的名称,用于向框架发出信号某些更改。
  2. 在视图模型代码中,当您对集合进行更改时,将出现RaisePropertyChanged(“ Orders”),该信号指示框架将数据封送至UI组件。
  3. 您的下一步将确定数据是从代码到UI还是从UI到代码,还是双向。 因此,在您的xaml ItemSource =“ {Binding Orders,Mode = OneWay}中,当您在Visual Studio中时,它将弹出整个列表。在双向模式下,该框架会将您的数据从UI封送至observablecollection。

抱歉,我没有时间修改您的代码。 希望这足以解释它。 干杯。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM