DataBindings有问题,请解释一下
public partial class Form1 : Form
{
MyClass myClass = new MyClass("one", "two");
public Form1()
{
InitializeComponent();
textBox1.DataBindings.Add("Text", myClass, "Text1", false, DataSourceUpdateMode.Never);
textBox2.DataBindings.Add("Text", myClass, "Text2", false, DataSourceUpdateMode.Never);
}
private void saveButton_Click(object sender, EventArgs e)
{
myClass.Text1 = textBox1.Text;
myClass.Text2 = textBox2.Text;
//textBox1.DataBindings["Text"].WriteValue();
//textBox2.DataBindings["Text"].WriteValue();
}
}
public class MyClass : INotifyPropertyChanged
{
private string _Text1;
private string _Text2;
public event PropertyChangedEventHandler PropertyChanged;
public string Text1
{
get { return _Text1; }
set { _Text1 = value; OnPropertyChanged(new PropertyChangedEventArgs("Text1")); }
}
public string Text2
{
get { return _Text2; }
set { _Text2 = value; OnPropertyChanged(new PropertyChangedEventArgs("Text2")); }
}
public MyClass(string text1, string text2)
{
Text1 = text1;
Text2 = text2;
}
protected void OnPropertyChanged(PropertyChangedEventArgs e)
{
if (PropertyChanged != null) PropertyChanged(this, e);
}
}
我想我很清楚自己想要达到什么目的。我希望我的表单将我在两个TextBox
ES中所做的更改保存到myClass
。但是,无论何时在编辑两个文本框后按下保存按钮,并且调用saveButton_Click
,第二个textBox2
的Text
都会返回原始文本(“2”)。我尝试使用Binding
的WriteValue
函数,但同样的事情发生。使用.net 4.0。DataBindings有问题,请解释一下
编辑感谢您的回答,但我不需要解决方法。我可以自己找到它们。我只需要更好地理解绑定是如何工作的。我想了解为什么会发生这种情况?
显然,更新数据源上的任何值都会导致更新所有绑定。这解释了行为(设置myClass.Text1
导致textBox2
用当前值myClass.Text2
更新)。不幸的是,我几乎可以找到的几篇文章只是说,“这就是它的工作原理”。
处理此问题的一种方法是创建一个BindingSource,BindingSource.DataSource = myClass
,然后将您的TextBoxes绑定到BindingSource
。
BindingSource
引发ListChanged事件,如果基础数据源是一个列表和项目被添加,删除等,或如果DataSource
性质发生变化。您可以通过将BindingSource.RaiseListChangedEvents设置为false
来禁止这些事件,这会允许您在没有数据绑定更新绑定控件的情况下在myClass
上设置多个属性。
public partial class Form1 : Form
{
MyClass myClass = new MyClass("one", "two");
BindingSource bindingSource = new BindingSource();
public Form1()
{
InitializeComponent();
bindingSource.DataSource = myClass;
textBox1.DataBindings.Add("Text", bindingSource, "Text1", true, DataSourceUpdateMode.Never);
textBox2.DataBindings.Add("Text", bindingSource, "Text2", true, DataSourceUpdateMode.Never);
}
private void button1_Click(object sender, EventArgs e)
{
bindingSource.RaiseListChangedEvents = false;
myClass.Text1 = textBox1.Text;
myClass.Text2 = textBox2.Text;
bindingSource.RaiseListChangedEvents = true;
}
}
HTH
你需要改变你的数据绑定方式。尝试这个。
MyClass myClass = new MyClass("one", "two");
public Form1()
{
InitializeComponent();
textBox1.DataBindings.Add("Text", myClass, "Text1", false, DataSourceUpdateMode.OnPropertyChanged);
textBox2.DataBindings.Add("Text", myClass, "Text2", false, DataSourceUpdateMode.OnPropertyChanged);
}
private void saveButton_Click(object sender, EventArgs e)
{
// your object should already have new text values entered.
// Save your object!
//myClass.Text1 = textBox1.Text;
//myClass.Text2 = textBox2.Text;
//textBox1.DataBindings["Text"].WriteValue();
//textBox2.DataBindings["Text"].WriteValue();
}
的关键是DataSourceUpdateMode,这将使文本框的文本属性级联到您的自定义对象属性发生变化时。我希望这有帮助。
[编辑]
我相信你需要做的,达到你问的这是什么: TextBox1.DataBindings[0].ControlUpdateMode = ControlUpdateMode.Never
这link应该提供一些额外的信息。
但我不想当'TextBox'的'Text'的变化,我想在按下保存按钮,当它改变要保存的数据。我怎样才能做到这一点?不是'DataSourceUpdateMode.Never'和'WriteValue()'一起实现这种功能吗? – Juan 2010-10-28 18:27:33
请勿使用数据绑定。只需在表单构造函数中手动分配文本值到文本框中,如下所示:'textBox1.Text = myClass.Text1;' – James 2010-10-28 18:28:55
@jsoldi - 然后不对这些值使用数据绑定 - 设置saveButton_Click事件中的值。这就是数据绑定的目的 - 它将控件实例的属性绑定到数据对象的属性。 – JeremyDWill 2010-10-28 18:31:47
工作。但我不明白为什么如果我的属性不是列表的一部分。 – Juan 2010-10-29 02:08:00
@jsoldi,我编辑了我的答案,以包含“DataCource”属性更改时也引发'ListChanged'的事实。 – 2010-10-29 03:20:07