首页 > 代码库 > 0001 WindowsForms的数据绑定(基础)
0001 WindowsForms的数据绑定(基础)
<!DOCTYPE html>
<html><head>
<meta http-equiv="Content-Type" content="text/html; charset=unicode">
<title>0001 WindowsForms的数据绑定(基础).md</title>
<!--mark |wiz_custom_css| for wizeditor replace it-->
<style id="wiz_custom_css">html, body { font-size: 15px; } body { font-family: Helvetica, ‘Hiragino Sans GB‘, ‘微软雅黑‘, ‘Microsoft YaHei UI‘, SimSun, SimHei, arial, sans-serif; line-height: 1.6; margin: 0; padding: 20px 15px; padding: 1.33rem 1rem; } h1, h2, h3, h4, h5, h6 { margin: 20px 0 10px; margin: 1.33rem 0 0.667rem; padding: 0; font-weight: bold; } h1 { font-size: 21px; font-size: 1.4rem; } h2 { font-size: 20px; font-size: 1.33rem; } h3 { font-size: 18px; font-size: 1.2rem; } h4 { font-size: 17px; font-size: 1.13rem; } h5 { font-size: 15px; font-size: 1rem; } h6 { font-size: 15px; font-size: 1rem; color: #777777; margin: 1rem 0; } div, p, ul, ol, dl, li { margin: 0; } blockquote, table, pre, code { margin: 8px 0; } ul, ol { padding-left: 32px; padding-left: 2.13rem; } blockquote { padding: 0 12px; padding: 0 0.8rem; } blockquote > :first-child { margin-top: 0; } blockquote > :last-child { margin-bottom: 0; } img { border: 0; max-width: 100%; height: auto !important; margin: 2px 0; } table { border-collapse: collapse; border: 1px solid #bbbbbb; } td, th { padding: 4px 8px; border-collapse: collapse; border: 1px solid #bbbbbb; } @media only screen and (-webkit-max-device-width: 1024px), only screen and (-o-max-device-width: 1024px), only screen and (max-device-width: 1024px), only screen and (-webkit-min-device-pixel-ratio: 3), only screen and (-o-min-device-pixel-ratio: 3), only screen and (min-device-pixel-ratio: 3) { html, body { font-size: 17px; } body { line-height: 1.7; padding: 0.75rem 0.9375rem; color: #353c47; } h1 { font-size: 2.125rem; } h2 { font-size: 1.875rem; } h3 { font-size: 1.625rem; } h4 { font-size: 1.375rem; } h5 { font-size: 1.125rem; } h6 { color: inherit; } ul, ol { padding-left: 2.5rem; } blockquote { padding: 0 0.9375rem; } }</style><style name="wiz_unsave_style">html, body { font-size: 15px;}body { font-family: Helvetica, ‘Hiragino Sans GB‘, 微软雅黑, ‘Microsoft YaHei UI‘, SimSun, SimHei, arial, sans-serif; line-height: 1.6; color: ; background-color: ; margin: 0; padding: 20px 15px; padding: 1.33rem 1rem;}img{ max-width: 100%;}</style><style id="wiz_style_for_load" name="wiz_unsave_style"></style><link rel="stylesheet" charset="utf-8" name="wiz_tmp_editor_style" href="D:/Program Files (x86)/WizNote/WizTools/htmleditor/dependency/fonts.css"><style name="wiz_tmp_editor_style">html {height:100%;} body {min-height:100%;box-sizing:border-box;word-wrap: break-word !important;}a {word-wrap: break-word;}.wiz-img-resize-handle {position: absolute;z-index: 1000;border: 1px solid black;background-color: white;}.wiz-img-resize-handle {width:5px;height:5px;}.wiz-img-resize-handle.lt {cursor: nw-resize;}.wiz-img-resize-handle.tm {cursor: n-resize;}.wiz-img-resize-handle.rt {cursor: ne-resize;}.wiz-img-resize-handle.lm {cursor: w-resize;}.wiz-img-resize-handle.rm {cursor: e-resize;}.wiz-img-resize-handle.lb {cursor: sw-resize;}.wiz-img-resize-handle.bm {cursor: s-resize;}.wiz-img-resize-handle.rb {cursor: se-resize;}.wiz-table-body.wiz-table-moving *, .wiz-table-body.wiz-table-moving *:before, .wiz-table-body.wiz-table-moving *:after {cursor:default !important;}td,th {position:relative;}#wiz-table-range-border {display: none;width: 0;height: 0;position: absolute;top: 0;left: 0; z-index:105}#wiz-table-col-line, #wiz-table-row-line {display: none;background-color: #448aff;position: absolute;z-index:120;}#wiz-table-col-line {width: 1px;cursor:col-resize;}#wiz-table-row-line {height: 1px;cursor:row-resize;}#wiz-table-range-border_start, #wiz-table-range-border_range {display: none;width: 0;height: 0;position: absolute;}#wiz-table-range-border_start_top, #wiz-table-range-border_range_top {height: 2px;background-color: #448aff;position: absolute;top: 0;left: 0;}#wiz-table-range-border_range_top {height: 1px;}#wiz-table-range-border_start_right, #wiz-table-range-border_range_right {width: 2px;background-color: #448aff;position: absolute;top: 0;}#wiz-table-range-border_range_right {width: 1px;}#wiz-table-range-border_start_bottom, #wiz-table-range-border_range_bottom {height: 2px;background-color: #448aff;position: absolute;top: 0;}#wiz-table-range-border_range_bottom {height: 1px;}#wiz-table-range-border_start_left, #wiz-table-range-border_range_left {width: 2px;background-color: #448aff;position: absolute;top: 0;left: 0;}#wiz-table-range-border_range_left {width: 1px;}#wiz-table-range-border_start_dot, #wiz-table-range-border_range_dot {width: 5px;height: 5px;border: 2px solid rgb(255, 255, 255);background-color: #448aff;cursor: crosshair;position: absolute;z-index:110;}.wiz-table-tools {display: block;background-color:#fff;position: absolute;left: 0px;border: 1px solid #ddd;-webkit-border-radius: 5px;-moz-border-radius: 5px;border-radius: 5px;z-index:130;}.wiz-table-tools ul {list-style: none;padding: 0;}.wiz-table-tools .wiz-table-menu-item {position: relative;float: left;margin:5px 2px 5px 8px;}.wiz-table-tools .wiz-table-menu-item .wiz-table-menu-button {font-size:15px;width:20px;height:20px;line-height:20px;cursor: pointer;position:relative;}.wiz-table-tools i.editor-icon{font-size: 15px;color: #455a64;}.wiz-table-tools .wiz-table-menu-item .wiz-table-menu-button i#wiz-menu-bg-demo{position: absolute;top:1px;left:0;}.wiz-table-tools .wiz-table-menu-sub {position: absolute;display: none;width: 125px;padding: 5px 0;background: #fff;border-radius: 3px;border: 1px solid #E0E0E0;top:28px;left:-9px;box-shadow: 1px 1px 5px #d0d0d0;}.wiz-table-tools .wiz-table-menu-sub > div{font-size:15px;}.wiz-table-tools .wiz-table-menu-item.active .wiz-table-menu-sub {display: block}.wiz-table-tools .wiz-table-menu-sub:before, .wiz-table-tools .wiz-table-menu-sub:after {position: absolute;content: " ";border-style: solid;border-color: transparent;border-bottom-color: #cccccc;left: 22px;margin-left: -14px;top: -8px;border-width: 0 8px 8px 8px;z-index:10;}.wiz-table-tools .wiz-table-menu-sub:after {border-bottom-color: #ffffff;top: -7px;}.wiz-table-tools .wiz-table-menu-sub-item {padding: 4px 12px;font-size: 14px;}.wiz-table-tools .wiz-table-menu-sub-item.split {border-top: 1px solid #E0E0E0;}.wiz-table-tools .wiz-table-menu-sub-item:hover {background-color: #ececec;}.wiz-table-tools .wiz-table-menu-sub-item.disabled {color: #bbbbbb;cursor: default;}.wiz-table-tools .wiz-table-menu-sub-item.disabled:hover {background-color: transparent;}.wiz-table-tools .wiz-table-menu-item.wiz-table-cell-bg:hover .wiz-table-color-pad {display: block;}.wiz-table-tools .wiz-table-color-pad {display: none;padding: 10px;box-sizing: border-box;width: 85px;height: 88px;background-color: #fff;cursor: default;}.wiz-table-tools .wiz-table-color-pad > div{font-size:15px;}.wiz-table-tools .wiz-table-color-pad .wiz-table-color-pad-item {display: inline-block;width: 15px;height: 15px;margin-right: 9px;position: relative;}.wiz-table-tools .wiz-table-color-pad .wiz-table-color-pad-item i.pad-demo {position: absolute;top:3px;left:0;}.wiz-table-tools .wiz-table-color-pad .wiz-table-color-pad-item .icon-oblique_line{color: #cc0000;}.wiz-table-tools .wiz-table-color-pad .wiz-table-color-pad-item:last-child {margin-right: 0;}.wiz-table-tools .wiz-table-color-pad .wiz-table-color-pad-item.active i.editor-icon.icon-box {color: #448aff;}.wiz-table-tools .wiz-table-cell-align {display: none;padding: 10px;box-sizing: border-box;width: 85px;height: 65px;background-color: #fff;cursor: default;}.wiz-table-tools .wiz-table-cell-align .wiz-table-cell-align-item {display: inline-block;width: 15px;height: 15px;margin-right: 9px;position: relative;}.wiz-table-tools .wiz-table-cell-align .wiz-table-cell-align-item:last-child {margin-right:0}.wiz-table-tools .wiz-table-cell-align .wiz-table-cell-align-item i.valign{position: absolute;top:3px;left:0;color: #d2d2d2;}.wiz-table-tools .wiz-table-cell-align-item.active i.editor-icon.valign {color: #a1c4ff;}.wiz-table-tools .wiz-table-cell-align-item.active i.editor-icon.icon-box,.wiz-table-tools .wiz-table-cell-align-item.active i.editor-icon.align {color: #448aff;}.wiz-table-tools .wiz-table-color-pad .wiz-table-color-pad-item:last-child,.wiz-table-tools .wiz-table-cell-align .wiz-table-cell-align-item:last-child {margin-right: 0;}th.wiz-selected-cell-multi, td.wiz-selected-cell-multi {background: rgba(0,102,255,.05);}th:before,td:before,#wiz-table-col-line:before,#wiz-table-range-border_start_right:before,#wiz-table-range-border_range_right:before{content: " ";position: absolute;top: 0;bottom: 0;right: -5px;width: 9px;cursor: col-resize;background: transparent;z-index:100;}th:after,td:after,#wiz-table-row-line:before,#wiz-table-range-border_start_bottom:before,#wiz-table-range-border_range_bottom:before{content: " ";position: absolute;left: 0;right: 0;bottom: -5px;height: 9px;cursor: row-resize;background: transparent;z-index:100;}.wiz-table-container {}.wiz-table-body {position:relative;padding:0 0 10px;overflow-x:auto;overflow-y:hidden;-webkit-overflow-scrolling:touch;}.wiz-table-body table {margin:0;outline:none;}td,th {height:28px;word-break:break-all;box-sizing:border-box;outline:none;}body pre.prettyprint {padding:0;}body pre.prettyprint code {white-space: pre;}body pre.prettyprint.linenums {box-shadow:none; overflow: auto;-webkit-overflow-scrolling: touch;}body pre.prettyprint.linenums ol.linenums {box-shadow: 40px 0 0 #FBFBFC inset, 41px 0 0 #ECECF0 inset; padding: 10px 10px 10px 40px !important;}</style></head>
<body spellcheck="false" style="" contenteditable="true"><div>[TOC]</div><div># 一、数据绑定原理</div><div>> 逻辑上,**数据绑定**是*“对象属性”*和*“控件属性”*之间的关联,这种关联是由数据绑定引擎完成的。</div><div>当对象属性和控件属性其中之一发生变化时,就会自动更新另一方的数据。</div><div><br></div><div>### 创建一个简单的数据绑定引擎:</div><div>定义一个数据源RaceCarDriver.cs,实现接口<span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">System.ComponentModel.INotifyPropertyChanged。</span></div><div>``` C#</div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">using</span> System.ComponentModel;
<span style="color:blue;">namespace</span> BasicBindingEngine
{
<span style="color:blue;">class</span> <span style="color:#2b91af;">RaceCarDriver</span> : <span style="color:#2b91af;">INotifyPropertyChanged</span>
{
<span style="color:green;">//实现接口INotifyPropertyChanged</span>
<span style="color:blue;">public</span> <span style="color:blue;">event</span> <span style="color:#2b91af;">PropertyChangedEventHandler</span> PropertyChanged;
<span style="color:blue;">void</span> OnPropertyChanged(<span style="color:blue;">string</span> propertyName)
{
<span style="color:blue;">if</span> (<span style="color:blue;">this</span>.PropertyChanged != <span style="color:blue;">null</span>)
{
<span style="color:blue;">this</span>.PropertyChanged(<span style="color:blue;">this</span>, <span style="color:blue;">new</span> <span style="color:#2b91af;">PropertyChangedEventArgs</span>(propertyName));
}
}
<span style="color:blue;">string</span> name;
<span style="color:blue;">int</span> wins;
<span style="color:blue;">public</span> RaceCarDriver(<span style="color:blue;">string</span> name, <span style="color:blue;">int</span> wins)
{
<span style="color:blue;">this</span>.name = name;
<span style="color:blue;">this</span>.wins = wins;
}
<span style="color:blue;">public</span> <span style="color:blue;">string</span> Name
{
<span style="color:blue;">get</span> { <span style="color:blue;">return</span> name; }
<span style="color:blue;">set</span>
{
name = <span style="color:blue;">value</span>;
<span style="color:green;">//提供被修改的属性名称</span>
OnPropertyChanged(<span style="color:#a31515;">"Name"</span>);
}
}
<span style="color:blue;">public</span> <span style="color:blue;">int</span> Wins
{
<span style="color:blue;">get</span> { <span style="color:blue;">return</span> wins; }
<span style="color:blue;">set</span>
{
wins = <span style="color:blue;">value</span>;
OnPropertyChanged(<span style="color:#a31515;">"Wins"</span>);
}
}
}
}</pre></div><div>```</div><div><img src="http://www.mamicode.com/index_files/560483265.png" border="0" class="" width="232" height="177"></div><div>窗体代码,实现数据绑定。</div><div>```c#</div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">using</span> System;
<span style="color:blue;">using</span> System.ComponentModel;
<span style="color:blue;">using</span> System.Windows.Forms;
<span style="color:blue;">namespace</span> BasicBindingEngine
{
<span style="color:blue;">public</span> <span style="color:blue;">partial</span> <span style="color:blue;">class</span> <span style="color:#2b91af;">Form1</span> : <span style="color:#2b91af;">Form</span>
{
<span style="color:#2b91af;">RaceCarDriver</span> raceCarDriver = <span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"M Schumacher"</span>, 500);
<span style="color:blue;">public</span> Form1()
{
InitializeComponent();
<span style="color:green;">//将初始的RaceCarDriver状态复制到文本框控件</span>
<span style="color:blue;">this</span>.nameText.Text = <span style="color:blue;">this</span>.raceCarDriver.Name;
<span style="color:blue;">this</span>.winsText.Text = <span style="color:blue;">this</span>.raceCarDriver.Wins.ToString();
</pre><pre style="font-family: 微软雅黑; background: white;"> //数据绑定,双向检测
<span style="color:green;">//检测文本框控件的修改,更新数据源数据</span>
<span style="color:blue;">this</span>.nameText.TextChanged += NameText_TextChanged;
<span style="color:blue;">this</span>.winsText.TextChanged += WinsText_TextChanged;
<span style="color:green;">//检测RaceCarDriver对象的修改,更新文本框数据显示</span>
<span style="color:blue;">this</span>.raceCarDriver.PropertyChanged += RaceCarDriver_PropertyChanged;
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> WinsText_TextChanged(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
<span style="color:blue;">this</span>.raceCarDriver.Wins = <span style="color:blue;">int</span>.Parse(<span style="color:blue;">this</span>.winsText.Text);
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> NameText_TextChanged(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
<span style="color:blue;">this</span>.raceCarDriver.Name = <span style="color:blue;">this</span>.nameText.Text;
}
<span style="color:green;">//直接修改RaceCarDriver的wins数据</span>
<span style="color:blue;">private</span> <span style="color:blue;">void</span> AddWinBtn_Click(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
++<span style="color:blue;">this</span>.raceCarDriver.Wins;
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> RaceCarDriver_PropertyChanged(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">PropertyChangedEventArgs</span> e)
{
<span style="color:blue;">switch</span> (e.PropertyName)
{
<span style="color:blue;">case</span> <span style="color:#a31515;">"Name"</span>:
<span style="color:blue;">this</span>.nameText.Text = <span style="color:blue;">this</span>.raceCarDriver.Name;
<span style="color:blue;">break</span>;
<span style="color:blue;">case</span> <span style="color:#a31515;">"Wins"</span>:
<span style="color:blue;">this</span>.winsText.Text = <span style="color:blue;">this</span>.raceCarDriver.Wins.ToString();
<span style="color:blue;">break</span>;
}
}
}
}</pre></div><div>```</div><div><br></div><div># 二、简单数据绑定和项数据源</div><div>> Windows Forms 数据绑定引擎的基本生成块就是Binding对象,它将控件数据绑定到对象属性上。 </div><div><br></div><div>> **简单绑定**:将控件属性绑定到对象属性的操作叫做**简单绑定**。 <br></div><div><br></div><div>> **项数据源**:数据源的数据是存在于单个项中。例如RaceCarDriver这样的绑定对象。</div><div><br></div><div>绑定关系类`System.Windows.Forms.Binding`,通过此可以省却写属性检测代码。</div><div>```</div><div><span style="line-height: 1.6; font-family: 微软雅黑; color: blue;">public</span><span style="line-height: 1.6; font-family: 微软雅黑; background-color: white;"> Binding(</span><span style="line-height: 1.6; font-family: 微软雅黑; color: blue;">string</span><span style="line-height: 1.6; font-family: 微软雅黑; background-color: white;"> propertyName, </span><span style="line-height: 1.6; font-family: 微软雅黑; color: blue;">object</span><span style="line-height: 1.6; font-family: 微软雅黑; background-color: white;"> dataSource, </span><span style="line-height: 1.6; font-family: 微软雅黑; color: blue;">string</span><span style="line-height: 1.6; font-family: 微软雅黑; background-color: white;"> dataMember);</span></div><div><span style="line-height: 1.6;"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: green;">propertyName:</span><span style="font-family: 微软雅黑; line-height: 1.6;"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: green;">要绑定的控件属性的名称。</span></div><div><span style="line-height: 1.6;"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: green;">dataSource:</span><span style="font-family: 微软雅黑; line-height: 1.6; color: green;"> 一个 System.Object,它代表数据源。</span></div><div><span style="line-height: 1.6;"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: green;">dataMember:</span><span style="font-family: 微软雅黑; line-height: 1.6; color: green;"> 要绑定到的属性或列表。</span></div><div><span style="line-height: 1.6;">```</span><br style="font-family: 微软雅黑; line-height: 1.6;"></div><div><span style="line-height: 1.6;"><br></span></div><div>窗体代码,通过Binding实现数据绑定。控件的<span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">DataBindings添加绑定关系。</span></div><div>```C#</div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">using</span> System;
</pre></div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">using</span> System.Windows.Forms;</pre><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">namespace</span> BasicBindingEngine
{
<span style="color:blue;">public</span> <span style="color:blue;">partial</span> <span style="color:blue;">class</span> <span style="color:#2b91af;">Form1</span> : <span style="color:#2b91af;">Form</span>
{
<span style="color:#2b91af;">RaceCarDriver</span> raceCarDriver = <span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"M Schumacher"</span>, 500);
<span style="color:blue;">public</span> Form1()
{
InitializeComponent();
<span style="color:green;">//将Name和Wins属性绑定到Name和Wins文本框上</span>
<span style="color:#2b91af;">Binding</span> nameBinding = <span style="color:blue;">new</span> <span style="color:#2b91af;">Binding</span>(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDriver, <span style="color:#a31515;">"Name"</span>, <span style="color:blue;">true</span>);
<span style="color:blue;">this</span>.nameText.DataBindings.Add(nameBinding);
<span style="color:#2b91af;">Binding</span> winsBinding = <span style="color:blue;">new</span> <span style="color:#2b91af;">Binding</span>(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDriver, <span style="color:#a31515;">"Wins"</span>, <span style="color:blue;">true</span>);
<span style="color:blue;">this</span>.winsText.DataBindings.Add(winsBinding);
}
<span style="color:green;">//直接修改RaceCarDriver的wins数据</span>
<span style="color:blue;">private</span> <span style="color:blue;">void</span> AddWinBtn_Click(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
++<span style="color:blue;">this</span>.raceCarDriver.Wins;
}
}
}</pre></div><div>```</div><div>添加绑定时会发生两件事情:1.数据绑定引擎自动使用对象属性的值来填充控件的属性。2.任何必需的数据转换都自动完成。</div><div><br></div><div>初始化之后,数据绑定引擎负责控件属性和数据源对象属性之间的同步。为了确保数据的变化可以从对象复制到控件上,绑定引擎会查找INotifyPropertyChanged.PropertyChanged事件。</div><div><br></div><div>只有在对象触发INotifyPropertyChanged.PropertyChanged事件并且公共属性是可读写(实现了get,set访问器)的情况下,简单绑定才是双向的。</div><div><br></div><div><br></div><div># 三、简单绑定和列表数据源</div><div>> **<span style="line-height: 1.6;">列表数据源**:是在绑定操作中作为数据来使用的同构对象的集合。对象是必须实现‘ IList ‘接口的类。</span></div><div><span style="line-height: 1.6;"><br></span></div><div><span style="line-height: 1.6;">> **绑定管理器**:负责管理特定数据源的绑定集合,有两个方面的作用:**属性管理器**和**当前项管理器**。两个管理器都是由抽象基类BindingManagerBase的具体实现。</span></div><div><span style="line-height: 1.6;"><br></span></div><div>> **属性管理器**:是PropertyManager类的一个实例,并且是为项数据源创建的。</div><div><br></div><div>> **当前项管理器**:是CurrencyManager类的一个实例,并且是为列表数据源来创建的。可用于跟踪当前对象的位置。</div><div><br></div><div><img src="http://www.mamicode.com/index_files/5602156.png" border="0" class="" width="312" height="152"></div><div>```C#</div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">using</span> System;
<span style="color:blue;">using</span> System.Collections.Generic;
<span style="color:blue;">using</span> System.Windows.Forms;
<span style="color:blue;">namespace</span> SimpleBindingAndListDataSource
{
<span style="color:blue;">public</span> <span style="color:blue;">partial</span> <span style="color:blue;">class</span> <span style="color:#2b91af;">SBALDS</span> : <span style="color:#2b91af;">Form</span>
{
<span style="color:green;">//创建强类型数据列表数据源</span>
<span style="color:#2b91af;">List</span><<span style="color:#2b91af;">RaceCarDriver</span>> raceCarDrivers = <span style="color:blue;">new</span> <span style="color:#2b91af;">List</span><<span style="color:#2b91af;">RaceCarDriver</span>>();
<span style="color:blue;">public</span> SBALDS()
{
InitializeComponent();
<span style="color:green;">//用数据项填充列表数据源</span>
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"M.Schumacher"</span>, 500));
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"A.Senna"</span>, 1000));
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"A.Prost"</span>, 400));
<span style="color:green;">//将Name和Wins属性绑定到Name和Wins文本框上</span>
<span style="color:blue;">this</span>.nameTextBox.DataBindings.Add(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDrivers, <span style="color:#a31515;">"Name"</span>);
<span style="color:blue;">this</span>.winsTextBox.DataBindings.Add(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDrivers, <span style="color:#a31515;">"Wins"</span>);
RefreshShowMangerPositon();
}
<span style="color:#2b91af;">BindingManagerBase</span> BindingManager
{
<span style="color:green;">//访问RaceCarDriver列表数据源的绑定管理器</span>
<span style="color:blue;">get</span> { <span style="color:blue;">return</span> <span style="color:blue;">this</span>.BindingContext[<span style="color:blue;">this</span>.raceCarDrivers]; }
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> MoveFirstBtn_Click(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
<span style="color:blue;">this</span>.BindingManager.Position = 0;
RefreshShowMangerPositon();
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> MovePreviousBtn_Click(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
--<span style="color:blue;">this</span>.BindingManager.Position;
RefreshShowMangerPositon();
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> MoveNextBtn_Click(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
++<span style="color:blue;">this</span>.BindingManager.Position;
RefreshShowMangerPositon();
}
<span style="color:blue;">private</span> <span style="color:blue;">void</span> MoveLastBtn_Click(<span style="color:blue;">object</span> sender, <span style="color:#2b91af;">EventArgs</span> e)
{
<span style="color:blue;">this</span>.BindingManager.Position = <span style="color:blue;">this</span>.BindingManager.Count - 1;
RefreshShowMangerPositon();
}
<span style="color:blue;">void</span> RefreshShowMangerPositon()
{
<span style="color:blue;">int</span> count = <span style="color:blue;">this</span>.BindingManager.Count;
<span style="color:blue;">int</span> position = <span style="color:blue;">this</span>.BindingManager.Position + 1;
<span style="color:blue;">this</span>.bindingNavigatorPositionItem.Text = position.ToString();
<span style="color:blue;">this</span>.bindingNavigatorCountItem.Text = <span style="color:blue;">string</span>.Format(<span style="color:#a31515;">"/{0}"</span>, count);
<span style="color:blue;">this</span>.bindingNavigatorMoveFirstItem.Enabled = (position > 1);
<span style="color:blue;">this</span>.bindingNavigatorMovePreviousItem.Enabled = (position > 1);
<span style="color:blue;">this</span>.bindingNavigatorMoveNextItem.Enabled = (position < count);
<span style="color:blue;">this</span>.bindingNavigatorMoveLastItem.Enabled = (position < count);
}
}
}
</pre></div><div>```</div><div>使用这种方式时,简单绑定和列表数据源中在添加绑定时没有实现事件`<span style="font-family: 微软雅黑; line-height: 1.6; color: blue;"></span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"></span><span style="font-family: 微软雅黑; line-height: 1.6; color: blue;">event</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">PropertyChangedEventHandler</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"> PropertyChanged`,导致在修改数据源属性时不能更新控件属性。使用`</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">IBindingList</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">`接口解决这种问题。</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"><br></span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"># 四、复杂绑定和列表数据源</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">> **复杂绑定**:将控件的一个属性绑定到整个列表数据源中。复杂绑定中的**复杂**是指控件自身内置的对操作和输出列表数据的附加支持。</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"><br></span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">复杂控件使用`DataSource`属性访问列表数据源,使用`DisplayMember`设置需要显示的列表数据源属性</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"><div>```C#</div><div>...引用</div><div><pre style="font-family: 微软雅黑; background-image: initial; background-attachment: initial; background-size: initial; background-origin: initial; background-clip: initial; background-position: initial; background-repeat: initial;"><span style="color:blue;">namespace</span> ComplexBindingListDataSources
{
<span style="color:blue;">public</span> <span style="color:blue;">partial</span> <span style="color:blue;">class</span> <span style="color:#2b91af;">Form1</span> : <span style="color:#2b91af;">Form</span>
{
<span style="color:green;">//创建强类型列表数据源</span>
<span style="color:#2b91af;">List</span><<span style="color:#2b91af;">RaceCarDriver</span>> raceCarDrivers = <span style="color:blue;">new</span> <span style="color:#2b91af;">List</span><<span style="color:#2b91af;">RaceCarDriver</span>>();
<span style="color:blue;">public</span> Form1()
{
InitializeComponent();
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"M.Schuamacher"</span>, 500));
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"A.Senna"</span>, 1000));
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"A.Prost"</span>, 400));
<span style="color:green;">//将Name和Wins属性简单绑定到Name和Wins文本框</span>
<span style="color:green;">//当用户输入数据时保持对象属性的同步</span>
<span style="color:blue;">this</span>.nameTextBox.DataBindings.Add(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDrivers, <span style="color:#a31515;">"Name"</span>);
<span style="color:blue;">this</span>.winTextBox.DataBindings.Add(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDrivers, <span style="color:#a31515;">"Wins"</span>);
<span style="color:green;">//复杂绑定列表框到RaceCarDriver列表数据源</span>
<span style="color:blue;">this</span>.raceCarDriverListBox.DataSource = <span style="color:blue;">this</span>.raceCarDrivers;
<span style="color:green;">//指定列表数据源中的项出现在列表框中的属性</span>
<span style="color:blue;">this</span>.raceCarDriverListBox.DisplayMember = <span style="color:#a31515;">"Name"</span>;
<span style="color:blue;">this</span>.raceCarDriversDataGridView.DataSource = <span style="color:blue;">this</span>.raceCarDrivers;
RefreshShowMangerPositon();
}</pre></div><div> ....<br></div><div> 导航相关代码<br></div><div> .... <br></div><div> }</div><div>}</div><div>``` </div></span></div><div><font face="微软雅黑"><img src="http://www.mamicode.com/index_files/f98e25ba-db6e-45f0-bb62-5699b0d1b6dc.png" border="0" class=""><div> </div></font></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"># 五、IBindingList接口 和 BindingList<T>类</span></div><div><font face="微软雅黑"><span style="background-color: rgb(255, 255, 255);">在绑定中,对**</span></font><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">列表</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">数据源**的修改不会立即显示在界面上。这就需要实现一个通信协议让控件能够知道列表数据源的变化。通过实现接口`IBindingList`来实现通知。</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">> **IBindingList**:是关于数据绑定架构的约定,扩展了**IList**接口,增加了为列表数据源提供的数据绑定特定的功能。实现添加、更新、删除列表数据源项。支持列表修改通知功能,通过订阅**ListChanged**事件。</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);"><br></span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">> **System.ComponentModel.BindingList<T>**:是**IBindingList**接口的泛型实现。实现了列表管理功能(AllowEdit、AllowNew、AllowRemove、AddNew)和 实现IBindingList的变更通知功能的子集(SupportsChangeNotification、ListChanged)。</span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);"><br></span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">将</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">`</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">List</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);"><</span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">RaceCarDriver</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">> raceCarDrivers = </span><span style="font-family: 微软雅黑; line-height: 1.6; color: blue;">new</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">List</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);"><</span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">RaceCarDriver</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">>();</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">`改写为`</span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">BindingList</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"><</span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">RaceCarDriver</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">> raceCarDrivers = </span><span style="font-family: 微软雅黑; line-height: 1.6; color: blue;">new</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"> </span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">BindingList</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"><</span><span style="font-family: 微软雅黑; line-height: 1.6; color: rgb(43, 145, 175);">RaceCarDriver</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">>();</span><span style="font-family: 微软雅黑; line-height: 1.6; background-color: rgb(255, 255, 255);">`就实现了列表数据源变更时通知功能。</span><br style="font-family: 微软雅黑; line-height: 1.6;"></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;"><br></span></div><div><span style="font-family: 微软雅黑; line-height: 1.6; background-color: white;">```</span></div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:blue;">class</span> <span style="color:#2b91af;">RaceCarDriver</span> : <span style="color:#2b91af;">INotifyPropertyChanged</span>
{
<span style="color:green;">//要让DataGridView可以添加新行,就需要这个构造函数</span>
<span style="color:blue;">public</span> RaceCarDriver()
{
}</pre><pre style="font-family: 微软雅黑; background: white;"> ....</pre><pre style="font-family: 微软雅黑; background: white;">}</pre><pre style="font-family: 微软雅黑; background: white;">```</pre><pre style="font-family: 微软雅黑; background: white;"><img src="http://www.mamicode.com/index_files/26271156.png" border="0" class=""><div> </div></pre></div><div># 六、BindingSource (System.Window.Forms.BindingSource)</div><div>> 通过**BindingSource类**可将现存的IList升级到IBindingList。</div><div><br></div><div>### 将项类型转变为列表数据源</div><div>```</div><div><span style="color: green; font-family: 微软雅黑; line-height: 1.6; background-color: white;">//创建强类型数据列表数据源</span></div><div><pre style="font-family: 微软雅黑; background: white;"><span style="color:#2b91af;">List</span><<span style="color:#2b91af;">RaceCarDriver</span>> raceCarDrivers = <span style="color:blue;">new</span> <span style="color:#2b91af;">List</span><<span style="color:#2b91af;">RaceCarDriver</span>>();
<span style="color:#2b91af;">BindingSource</span> raceCarDriversBS = <span style="color:blue;">new</span> <span style="color:#2b91af;">BindingSource</span>();
<span style="color:blue;">public</span> SBALDS()
{
InitializeComponent();
<span style="color:green;">//用数据项填充列表数据源</span>
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"M.Schumacher"</span>, 500));
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"A.Senna"</span>, 1000));
<span style="color:blue;">this</span>.raceCarDrivers.Add(<span style="color:blue;">new</span> <span style="color:#2b91af;">RaceCarDriver</span>(<span style="color:#a31515;">"A.Prost"</span>, 400));</pre><pre style="font-family: 微软雅黑; background: white;"> //给List<RaceCarDriver>加上列表管理和变更通知功能
raceCarDriversBS.DataSource = <span style="color:blue;">this</span>.raceCarDrivers;</pre><pre style="font-family: 微软雅黑; background: white;"> <span style="color:green;">//将数据源变为</span><span style="line-height: 1.6; color: blue;">this</span><span style="line-height: 1.6;">.raceCarDriversBS</span>
<span style="color:blue;">this</span>.nameTextBox.DataBindings.Add(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDriversBS, <span style="color:#a31515;">"Name"</span>);
<span style="color:blue;">this</span>.winsTextBox.DataBindings.Add(<span style="color:#a31515;">"Text"</span>, <span style="color:blue;">this</span>.raceCarDriversBS, <span style="color:#a31515;">"Wins"</span>);</pre><pre style="font-family: 微软雅黑; background: white;"> ...<br></pre><pre style="font-family: 微软雅黑; background: white;">}</pre><pre style="font-family: 微软雅黑; background: white;">```</pre></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><div><br></div><wiz_tmp_tag id="wiz-table-range-border" contenteditable="false" style="display: none;"><div id="wiz-table-col-line" style="display: none;"></div><div id="wiz-table-row-line" style="display: none;"></div><div id="wiz-table-range-border_start" style="display: none;"><div id="wiz-table-range-border_start_top"></div><div id="wiz-table-range-border_start_right"></div><div id="wiz-table-range-border_start_bottom"></div><div id="wiz-table-range-border_start_left"></div><div id="wiz-table-range-border_start_dot"></div></div><div id="wiz-table-range-border_range" style="display: none;"><div id="wiz-table-range-border_range_top"></div><div id="wiz-table-range-border_range_right"></div><div id="wiz-table-range-border_range_bottom"></div><div id="wiz-table-range-border_range_left"></div><div id="wiz-table-range-border_range_dot"></div></div></wiz_tmp_tag></body></html>
0001 WindowsForms的数据绑定(基础)