INotifyPropertyChanged 接口
用于向客户端(通常是执行绑定的客户端)发出某一属性值已更改的通知。
例如,考虑一个带有名为 FirstName 属性的 Person 对象。若要提供一般性属性更改通知,则 Person 类型实现 INotifyPropertyChanged 接口并在 FirstName 更改时引发 PropertyChanged 事件。
若要在将客户端与数据源进行绑定时发出更改通知,则绑定类型应具有下列任一功能:
-
实现 INotifyPropertyChanged 接口(首选)。
-
为绑定类型的每个属性提供更改事件。
上述这两个功能不要同时实现。
下面的代码示例演示如何实现 INotifyPropertyChanged 接口。在运行此示例时,您将注意到绑定的 DataGridView 控件无需重置绑定即能反映数据源中的更改。如果使用 CallerMemberName 属性,对 NotifyPropertyChanged 方法不必指定属性名称作为字符串参数。有关详细信息,请参阅Caller Information (C# and Visual Basic)。
1 using System; 2 using System.Collections.Generic; 3 using System.ComponentModel; 4 using System.Drawing; 5 using System.Runtime.CompilerServices; 6 using System.Windows.Forms; 7 8 // Change the namespace to the project name. 9 namespace TestNotifyPropertyChangedCS 10 { 11 // This form demonstrates using a BindingSource to bind 12 // a list to a DataGridView control. The list does not 13 // raise change notifications. However the DemoCustomer type 14 // in the list does. 15 public partial class Form1 : Form 16 { 17 // This button causes the value of a list element to be changed. 18 private Button changeItemBtn = new Button(); 19 20 // This DataGridView control displays the contents of the list. 21 private DataGridView customersDataGridView = new DataGridView(); 22 23 // This BindingSource binds the list to the DataGridView control. 24 private BindingSource customersBindingSource = new BindingSource(); 25 26 public Form1() 27 { 28 InitializeComponent(); 29 30 // Set up the "Change Item" button. 31 this.changeItemBtn.Text = "Change Item"; 32 this.changeItemBtn.Dock = DockStyle.Bottom; 33 this.changeItemBtn.Click += 34 new EventHandler(changeItemBtn_Click); 35 this.Controls.Add(this.changeItemBtn); 36 37 // Set up the DataGridView. 38 customersDataGridView.Dock = DockStyle.Top; 39 this.Controls.Add(customersDataGridView); 40 41 this.Size = new Size(400, 200); 42 } 43 44 private void Form1_Load(object sender, EventArgs e) 45 { 46 // Create and populate the list of DemoCustomer objects 47 // which will supply data to the DataGridView. 48 BindingList<DemoCustomer> customerList = new BindingList<DemoCustomer>(); 49 customerList.Add(DemoCustomer.CreateNewCustomer()); 50 customerList.Add(DemoCustomer.CreateNewCustomer()); 51 customerList.Add(DemoCustomer.CreateNewCustomer()); 52 53 // Bind the list to the BindingSource. 54 this.customersBindingSource.DataSource = customerList; 55 56 // Attach the BindingSource to the DataGridView. 57 this.customersDataGridView.DataSource = 58 this.customersBindingSource; 59 60 } 61 62 // Change the value of the CompanyName property for the first 63 // item in the list when the "Change Item" button is clicked. 64 void changeItemBtn_Click(object sender, EventArgs e) 65 { 66 // Get a reference to the list from the BindingSource. 67 BindingList<DemoCustomer> customerList = 68 this.customersBindingSource.DataSource as BindingList<DemoCustomer>; 69 70 // Change the value of the CompanyName property for the 71 // first item in the list. 72 customerList[0].CustomerName = "Tailspin Toys"; 73 customerList[0].PhoneNumber = "(708)555-0150"; 74 } 75 76 } 77 78 // This is a simple customer class that 79 // implements the IPropertyChange interface. 80 public class DemoCustomer : INotifyPropertyChanged 81 { 82 // These fields hold the values for the public properties. 83 private Guid idValue = Guid.NewGuid(); 84 private string customerNameValue = String.Empty; 85 private string phoneNumberValue = String.Empty; 86 87 public event PropertyChangedEventHandler PropertyChanged; 88 89 // This method is called by the Set accessor of each property. 90 // The CallerMemberName attribute that is applied to the optional propertyName 91 // parameter causes the property name of the caller to be substituted as an argument. 92 private void NotifyPropertyChanged([CallerMemberName] String propertyName = "") 93 { 94 if (PropertyChanged != null) 95 { 96 PropertyChanged(this, new PropertyChangedEventArgs(propertyName)); 97 } 98 } 99 100 // The constructor is private to enforce the factory pattern. 101 private DemoCustomer() 102 { 103 customerNameValue = "Customer"; 104 phoneNumberValue = "(312)555-0100"; 105 } 106 107 // This is the public factory method. 108 public static DemoCustomer CreateNewCustomer() 109 { 110 return new DemoCustomer(); 111 } 112 113 // This property represents an ID, suitable 114 // for use as a primary key in a database. 115 public Guid ID 116 { 117 get 118 { 119 return this.idValue; 120 } 121 } 122 123 public string CustomerName 124 { 125 get 126 { 127 return this.customerNameValue; 128 } 129 130 set 131 { 132 if (value != this.customerNameValue) 133 { 134 this.customerNameValue = value; 135 NotifyPropertyChanged(); 136 } 137 } 138 } 139 140 public string PhoneNumber 141 { 142 get 143 { 144 return this.phoneNumberValue; 145 } 146 147 set 148 { 149 if (value != this.phoneNumberValue) 150 { 151 this.phoneNumberValue = value; 152 NotifyPropertyChanged(); 153 } 154 } 155 } 156 } 157 }
转自微软官网技术文章: