S/L 4 & IDataErrorInfo - 如何强制重新验证控件(当触摸相关控件时)
我有两个绑定到属性 MinCartValue 和 MaxCartValue 的控件。 MinCartValue 必须小于 MaxCartValue。为了实现此验证,我实现了 IDataErrorInfo 接口,并在触摸了 MinCartValue 或 MaxCartValue 时在 this[columnName] 方法中运行上述检查。 ValidatesOnDataErrors=True 在两个控件的绑定中设置。 验证工作正常,当属性值的更改违反规则时突出显示每个控件。问题是,一旦一个控件被标记为无效,如果用户通过更改另一个控件的值来纠正问题,第一个控件仍会被标记为无效。这是可以理解的,因为 IDataErrorInfo 方法没有对第一个控件的属性进行验证。
因此,我需要一种在验证属性 #2 时强制重新验证属性 #1 的方法(或清除无效状态的方法),反之亦然。我尝试在 this[columnName] 方法中调用 RaisePropertyChanged 但它什么也没做。还尝试将属性设置为其自己的值以尝试欺骗它来验证自身,但同样没有任何反应。
谢谢
I have two controls bound to properties MinCartValue and MaxCartValue. MinCartValue must be less than MaxCartValue. To achieve this validation I have implemented the the IDataErrorInfo interface, and run the above check in the this[columnName] method if either MinCartValue or MaxCartValue are touched. ValidatesOnDataErrors=True is set in the binding of both controls.
The validation works correctly, highlighting each control when a change to its property value violates the rule. The problem is that once a control is flagged as invalid, if the user corrects the problem by altering the other control's value, the first control remains flagged as invalid. This is understandable because the IDataErrorInfo method was not doing validation on the first control's property.
So what I need is a way to force property #1 to be re-validated (or a way to clear the invalid state) when property #2 is validated, and vice versa. I have tried calling RaisePropertyChanged within my this[columnName] method but it does nothing. Also tried setting the property to its own value to try to trick it to validate itself, but again nothing happens.
Thanks
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(4)
我建议查看
INotifyDataErrorInfo
接口(在 Silverlight 4 中引入)。如果属性变得无效,它能够异步通知,因此我认为该框架更好地在许多属性中尊重这一点,而不是期望当前正在更改的属性是唯一可能更改其有效性的属性。I would recommend looking at the
INotifyDataErrorInfo
interface (introduced in Silverlight 4). It's able to async-notify if properties become invalid, so I think the framework is better about respecting this across many properties instead of expecting that the property currently being changed is the only one whose validity may be changing.我有两个 DateTime 属性(DateFrom 和 DateTo),需要相互验证。在这些属性的设置器中,我刚刚为 DateTo 和 DateFrom 引发了一个 PropertyChanged 事件。工作起来就像一个魅力。
I had two DateTime properties (DateFrom and DateTo) that needed to be validated against each other. In the setters for these properties I just raised a PropertyChanged event for both DateTo and DateFrom. Worked like a charm.
我不确定我是否完全理解你的问题,但这也许会有所帮助。提供一些示例 XAML 和绑定属性代码会有所帮助。
这听起来像是代码的问题,具体取决于默认的 UpdateSourceTrigger,在 TextBox 控件的情况下是它们的焦点/非焦点。您可以在 XAML 中设置 UpdateSourceTrigger 属性,方法是将 UpdateSourceTrigger=Explicit 添加到发生验证的绑定中。然后在每个 TextBox (MinCartValue、MaxCartValue) 中,将事件处理程序添加到 TextChanged 事件。
在事件处理程序的代码隐藏中,您可以执行以下操作:
在本例中,TheTextBox 将是您的购物车控件之一。 UpdateSource() 方法是一种手动更新绑定值的方法,这应该会触发您的验证。此方法提供了绑定到触发器以更新值的方法,并引发属性已更改到默认范围之外(在此实例中使用文本更改而不是 TextBox 上的焦点和取消焦点)。
I'm not sure if I'm understanding your problem exactly, but perhaps this may help. Providing some example XAML and the binding property code would help.
It sounds like an issue of your code depending on the default UpdateSourceTrigger, which in the case of TextBox controls is their focus/unfocus. You can set in the XAML the UpdateSourceTrigger attribute by adding UpdateSourceTrigger=Explicit to your binding where your validation occurs. Then in each TextBox (MinCartValue, MaxCartValue), add an event handler to the TextChanged event.
In the code-behind in the event handler, you can do something like this:
TheTextBox in this case would be one of your cart controls. The UpdateSource() method is a way to manually update the binding value, which should trigger your validation. This method provides away to tie into a trigger to update values and raising properties have changed outside of the default scope (using text changed intead of focus and unfocus on TextBox in this instance).
我是这样解决的。假设 Property1 和 Property2 是相互依赖的。我还不熟悉 MVVM,但您可能正在扩展实体类来实现 IDataErrorInfo。在这种情况下,您还可以扩展 On[Property]Changed 方法并报告相互依赖的属性中的更改:
在这种情况下,此属性之一的更新会使两个绑定控件重新评估自身。
EDIT2:看来您应该使用 OnPropertyChang* 而不是 ReportPropertyChang*。 ReportPropertyChanged 将通知实体框架模型中存在挂起的更改,但实际上您要做的就是通知视图。您不想使用未真正更改的属性来更新数据库。 ReportPropertyChang* 在数据库中没有映射的计算字段上也会失败。
EDIT1:发现在 ReportPropertyChanged 之前调用 ReportPropertyChanging 至关重要。
Here's how I solved it. Let's say Property1 and Property2 are codependent. I'm not familiar with MVVM (yet), but you're probably extending your entity class to implement IDataErrorInfo. In this case you can also extend On[Property]Changed method and report change in codependent property:
In this case the update in either one of this properties makes both bound controls re-evaluate themselves.
EDIT2: It appears that you should use OnPropertyChang* instead of ReportPropertyChang*. ReportPropertyChanged will notify the entity framework that there are pending changes in the model, but in fact all you're trying to do is inform the view. You don't want to update the database with the property that didn't really change. ReportPropertyChang* will also fail on computed fields that have no mappings in the database.
EDIT1: Found out that it's essential to call ReportPropertyChanging before ReportPropertyChanged.