WPF中的强大验证
时间:2020-03-05 18:47:46 来源:igfitidea点击:
我的应用程序中有一个数据绑定文本框,如下所示:(" Height"的类型是" decimal?")
<TextBox Text="{Binding Height, UpdateSourceTrigger=PropertyChanged, ValidatesOnExceptions=True, Converter={StaticResource NullConverter}}" /> public class NullableConverter : IValueConverter { public object Convert(object o, Type type, object parameter, CultureInfo culture) { return o; } public object ConvertBack(object o, Type type, object parameter, CultureInfo culture) { if (o as string == null || (o as string).Trim() == string.Empty) return null; return o; } }
通过这种方式配置,任何不能转换为十进制的非空字符串都将导致验证错误,该错误将立即突出显示文本框。但是,TextBox仍会失去焦点并保持无效状态。我想做的是:
- 在文本框包含有效值之前,不要让它失去焦点。
- 将文本框中的值还原为最后一个有效值。
做这个的最好方式是什么?
更新:
我找到了一种方法来做#2. 我不喜欢它,但是它可以工作:
private void TextBox_LostKeyboardFocus(object sender, RoutedEventArgs e) { var box = sender as TextBox; var binding = box.GetBindingExpression(TextBox.TextProperty); if (binding.HasError) binding.UpdateTarget(); }
有谁知道如何做得更好? (或者执行#1. )
解决方案
回答
在我看来,我们将要处理两个事件:
GotFocus:当文本框获得焦点时将触发。我们可以存储框的初始值。
LostFocus:当文本框失去焦点时将触发。此时,我们可以进行验证并决定是否要回滚。
回答
我们可以通过如下处理PreviewLostKeyBoardFocus事件来强制键盘焦点停留在TextBox上:
<TextBox PreviewLostKeyboardFocus="TextBox_PreviewLostKeyboardFocus" /> private void TextBox_PreviewLostKeyboardFocus(object sender, KeyboardFocusChangedEventArgs e) { e.Handled = true; }