【问题标题】:Databinding to object - How to cancel datasource changes数据绑定到对象 - 如何取消数据源更改
【发布时间】:2018-07-16 07:08:19
【问题描述】:

这是场景: 我有一个编辑对话框表单,上面有 BindingSource 和一些数据绑定文本框:

我将一个实体传递给表单构造函数,并将其加载到BindingSource.DataSource,这会导致数据绑定控件显示属性值。

问题是当用户编辑TextBox 控件中的值并且Validating 事件被传递时,数据源发生了变化,尽管它没有应用于数据库,但是当用户看到编辑后的值时,它仍然会使用户感到困惑在列表表单上,直到下一个应用程序重新启动。

所以问题是:如何防止绑定源立即反映更改或如何回滚?

我继承了绑定源并创建了一个新的绑定源,如下所示:

public class SuperBindingSource:BindingSource
{
    #region Properties

    public object DataSourceBeforeChange { get; private set; }

    #endregion

    #region Methods

    public void ResetChanges()
    {
        this.DataSource = this.DataSourceBeforeChange;
    }

    #endregion

    protected override void OnDataSourceChanged(EventArgs e)
    {
        base.OnDataSourceChanged(e);

        DataSourceBeforeChange=this.DataSource.DeepClone();
    }
}

虽然我不确定这是否是一个好方法。

【问题讨论】:

  • DeepClone() 来自创建克隆的 DeepCloner Nuget 包。

标签: c# .net winforms data-binding bindingsource


【解决方案1】:

作为一个选项,在设置数据绑定时,您可以将它们设置为从不更新数据源。

然后在您要应用更改的点上,例如按下OK 按钮时,您可以设置数据绑定以在属性更改时更新数据源,然后调用绑定源的结束编辑方法。

对于Cancel按钮,你不需要做任何事情,因为数据源没有更新。

示例

在表单加载事件中:

this.BindingContext[bindingSource].Bindings.Cast<Binding>().ToList()
    .ForEach(b=>b.DataSourceUpdateMode= DataSourceUpdateMode.Never);

按下确定时:

this.BindingContext[productBindingSource].Bindings.Cast<Binding>().ToList()
    .ForEach(b => b.DataSourceUpdateMode = DataSourceUpdateMode.OnPropertyChanged);
productBindingSource.EndEdit();

您可以下载/克隆完整的源代码:

【讨论】:

  • 非常感谢您的回答。那么没有更清洁的方法吗?问题是,如果我想这样做,最好手动设置并逐个设置控件。比如 :txtname.text=myObject.name 等。其实我正在寻找一种更清洁的方法。
  • 您无需手动执行任何操作。您将使用数据绑定在控件中显示数据,但在您按下 OK 按钮之前,更新不会被写回数据源。
  • 实际上,通过我添加到答案中的新更新,您只需添加这些代码以形成加载事件和确定按钮的单击事件,而无需对现有代码进行任何更改。只需使用标准的BindingSource
  • 非常感谢。我将您的答案标记为正确。我有最后一个问题。在您的想法中,哪种方法更清洁?我的还是你的?
  • 关于您的解决方案的一点,this.DataSource = this.DataSourceBeforeChange,它似乎有一个陷阱。您正在编辑的实体是 Class 并且类是引用类型,因此将 this.DataSource 重置为对象的新实例并不意味着您重置更改。实例已编辑。您刚刚决定在数据源中放置另一个实例。看看this question
【解决方案2】:

您可以在加载值后使用SuspendBinding 方法。
之后,在您调用 ResumeBinding 之前,这些值不应更新源:

SuspendBinding 和 ResumeBinding 是允许在简单绑定方案中临时挂起和恢复数据绑定的两种方法。如果必须允许用户在验证发生之前对数据字段进行多次编辑,您通常会暂停数据绑定。例如,如果必须根据第二个字段更改一个字段,但验证第一个字段会导致第二个字段出错。

根据文档,您应该可以将它与您的文本框一起使用。如果用户单击Ok 保存值,则您将恢复绑定,如果他取消您则不会。

【讨论】:

  • 感谢您的帮助。我使用了 SuspendBinding,但它从文本框中清除了加载的值。我是否以错误的方式使用它?
  • @SaboueiAlireza 您确定它“清除了值”并且您不只是提前调用暂停吗?因为根据文档,该方法不应清除任何值...
  • 我在表单上放了一个按钮来调用 Suspend 方法。表单完美地加载了数据,但只要我按下按钮,它就会清除所有文本框。
猜你喜欢
  • 1970-01-01
  • 2010-10-24
  • 1970-01-01
  • 2014-06-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-12-08
  • 2016-03-22
相关资源
最近更新 更多