簡體   English   中英

將可觀察的集合綁定到數據網格?

[英]Binding an observable collection to a datagrid?

最近,我一直在嘗試學習WPF,為了學習WPF,我一直在創建一個小的項目來熟悉WPF。 當前,此刻我在WPF中遇到綁定問題。 更具體地說,將可觀察的集合綁定到數據網格。 你可以在下面看到我的代碼

<Window x:Class="Progress_bar_example.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">
    <Grid>
        <DataGrid AutoGenerateColumns="False" Height="287" HorizontalAlignment="Left"
            Margin="20,12,0,0" Name="dataGrid1" VerticalAlignment="Top" Width="471"
            ItemsSource="{Binding personsInformation}">
            <DataGrid.Columns>
                <DataGridTextColumn Header="First Name" Binding="{Binding .firstName}"/>
            </DataGrid.Columns>
        </DataGrid>
    </Grid>
</Window>

后端代碼是

namespace Progress_bar_example
{
    /// <summary>
    /// Interaction logic for MainWindow.xaml
    /// </summary>
    public partial class MainWindow : Window
    {
        public class myDataContext
        {
            private ObservableCollection<PersonData> personsInformation;
        }

        public class PersonData
        {
            public String firstName;
            //public String sureName;
            //public int dayOfBirth;
            //public int monthOfBirth;
            //public int yearOfBirth;
        }

        public ObservableCollection<PersonData> personsInformation;

        public MainWindow()
        {
            InitializeComponent();
            this.DataContext = this;
            personsInformation = new ObservableCollection<PersonData>();
            PersonData person = new PersonData() 
            { 
                firstName = "Thomas"
            };
            personsInformation.Add(person);

            ContentRendered += Window_ContentRendered;
        }

        private void Window_ContentRendered(object sender, EventArgs e)
        {            
            //this.DataContext = _dt;
        }
    }
}

更改datagrid代碼,因為datagridtextcolumn列名稱不應與Dot(。)綁定

<DataGrid AutoGenerateColumns="False" Height="287" HorizontalAlignment="Left" Margin="20,12,0,0" Name="dataGrid1" VerticalAlignment="Top" Width="471" ItemsSource="{Binding personsInformation}">
    <DataGrid.Columns>
        <DataGridTextColumn Header="First Name" Binding="{Binding firstName}"/>
    </DataGrid.Columns>
</DataGrid>

值得慶幸的是,有一些事情使您的示例無法正常工作,大部分都是小小的調整。

首先要注意的是,通常,您應該始終綁定到public Properties ,而不是當前正在綁定的字段。

因此,您所需的綁定屬性應變為:

// More Code
public ObservableCollection<PersonData> PersonsInformation { get; set; }

public class PersonData
{
    public String FirstName { get; set; }
    // More Code
}

(請注意,我已使屬性以大寫字母開頭,這通常是公共屬性的良好做法。此站點上已經存在許多出色的解釋,而其他人則提供有關此主題的更多信息。

另外,當您分配DataContext ,然后初始化屬性personsInformation ,您實際上是在不通知UI的情況下更改personsInformation字段-此更改將不會被使用,並且對新集合的任何其他更改(或屬性的分配)本身),則不會反映在用戶界面中。

在此階段,最簡單的解決方法是在this.DataContext = this;行之前的某個點簡單地初始化personsInformation this.DataContext = this; 例如:

public MainWindow()
{
    InitializeComponent();
    this.DataContext = this;
    personsInformation = new ObservableCollection<PersonData>();

    this.DataContext = this;
    // Code that modifies personsInformation.
}

注意:與綁定到集合(尤其是ObservableCollection )有關的錯誤的一個相當普遍的原因是,分配分配持有集合的Property和修改該集合之間的區別被絆倒了。 ObservableCollection本身實現INotifyPropertyChanged ,當添加/刪除/清除項目時,該通知提供通知。 如果您將新集合分配給您的personsInformation ,則不會引發任何通知(除非您已實現INotifyPropertyChanged並提出了適當的通知(關於該主題有大量出色的指南)。

您還可以考慮其他事項,例如在其他地方分配DataContext,包括ViewModels ,實現iNotifyPropertyChanged。

此外,綁定到.firstName應該可以按.firstName工作,但。可以。 不需要。 我傾向於寫諸如{Binding Path=firstName}類的{Binding Path=firstName} ,這純粹是一種樣式首選項(它對我來說很清楚),您可以像完成{Binding firstName}一樣省略路徑。 但這應該可以啟動並運行您的示例,並允許您進行一些有趣的探索/測試。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM