在我们的WPF应用程序中,有几个文本框,用户应该只输入货币。强制文本框在输入时格式化输入:
<TextBox Text="{Binding CostOut, StringFormat='{}{0:C}' />
然而,这种格式如此之快以至于它会导致用户意外的效果,因为文本是类型,因为小数点前后的数字似乎几乎被视为单独的字段。
为了解决这个问题,我们添加了延迟:
<TextBox Text="{Binding CostOut, StringFormat='{}{0:C}', Delay=1000 />
由于大多数人在数字格式化之前完成了打字,因此效果更好。但是,应用程序很复杂并且处理重要的财务数据,并且一些用户在输入数字时仔细考虑这些数字。对于这些慢速打字机,这种延迟仍然导致他们的输入被重新格式化为中型。
我不愿意在“延迟”路线上走得更远,因为我们最终会在某人保存之前达到没有格式化的程度。我发现并尝试了一个WPF CurrencyTextBox作为解决方案被拒绝,因为“收银机”式打字太不熟悉了。
目前建议的解决方案是从应用程序中删除所有格式,并仅在保存时格式化。这对我来说很激动,我不禁想知道是否有更好的解决方案?
答案 0 :(得分:3)
当textBox失去对文本框的LostFocus
事件的关注时,您可以尝试设置所需的格式。它允许用户输入他/她必须的时间,并且不会像在保存按钮上格式化那样激烈。
答案 1 :(得分:3)
正如评论中所提到的,我创建了一个关于如何将LostFocus-Event绑定到ViewModel中的ICommand
- 属性的小例子。
附属物看起来像:
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
namespace TextBoxLostFocusBehaviorExample
{
internal static class TextBoxExtensions
{
public static readonly DependencyProperty LostFocusCommandProperty = DependencyProperty.RegisterAttached(
"LostFocusCommand",
typeof(ICommand),
typeof(TextBoxExtensions),
new PropertyMetadata(default(ICommand), OnLostFocusCommandChanged));
private static void OnLostFocusCommandChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
TextBox textBox = d as TextBox;
if (textBox == null)
{
return;
}
if (e.NewValue != null)
{
textBox.LostFocus += TextBoxOnLostFocus;
}
}
private static void TextBoxOnLostFocus(object sender, RoutedEventArgs e)
{
TextBox textBox = sender as TextBox;
if (textBox == null)
{
return;
}
ICommand command = GetLostFocusCommand(textBox);
command.Execute(null);
}
public static void SetLostFocusCommand(DependencyObject element, ICommand value)
{
element.SetValue(LostFocusCommandProperty, value);
}
public static ICommand GetLostFocusCommand(DependencyObject element)
{
return (ICommand)element.GetValue(LostFocusCommandProperty);
}
}
}
在ViewModel中,您有一个ICommand
类型的属性,它看起来像:
private ICommand lostFocusCommand;
public ICommand LostFocusCommand
{
get { return lostFocusCommand ?? (lostFocusCommand = new RelayCommand(p => CostOutLostFocus())); }
}
当CostOutLostFocus
- 事件被触发时,LostFocus
- 方法将被调用。
视图中附加属性的用法如下所示:
<TextBox Text="{Binding CostOut, Mode=TwoWay}" TextBoxLostFocusBehaviorExample:TextBoxExtensions.LostFocusCommand="{Binding LostFocusCommand}"/>
TextBoxLostFocusBehaviorExample是定义附加属性的class
的命名空间。
答案 2 :(得分:1)
目前建议的解决方案是从应用程序中删除所有格式,并仅在保存时格式化。这对我来说很激动,我不知道是否有更好的解决方案?
您可以更新源属性并在用户走出TextBox时应用格式,只需在XAML标记中将绑定的UpdateSourceTrigger属性设置为其默认值LostFocus:
<TextBox Text="{Binding CostOut, StringFormat={}{0:C}, UpdateSourceTrigger=LostFocus}" />
这至少应该比保存时应用格式更好一些。
另一个选择是使用某种蒙版TextBox。没有内置的,但您可以尝试开源的Extended WPF Toolkit中提供的那个:https://wpftoolkit.codeplex.com/wikipage?title=MaskedTextBox&referringTitle=Home
还有商业选项:http://docs.telerik.com/devtools/wpf/controls/radmaskedinput/features/maskedinput-controls/currency