我想创建一个字符串DependencyProperty
,它可以处理分配给可以为空的数字值(就像文本框TextProperty
那样)。
我基本上复制了来自TextBox
的反编译代码,并将其更改为我正在创建的DependencyProperty
。
[DefaultValue(null)]
//[DefaultValue(string.Empty)]
[Localizability(LocalizationCategory.Text)]
public string Number
{
get { return (string)GetValue(NumberProperty); }
set { SetValue(NumberProperty, value); }
}
public static readonly DependencyProperty NumberProperty =
DependencyProperty.Register(
"Number", // Property name
typeof(string), // Property type
typeof(NumberControl), // Property owner
new FrameworkPropertyMetadata( // Property metadata
null, // default value
//string.Empty, // default value
FrameworkPropertyMetadataOptions.BindsTwoWayByDefault | // Flags
FrameworkPropertyMetadataOptions.Journal,
OnNumberPropertyChanged, // property changed callback
CoerceText,
true, // IsAnimationProhibited
UpdateSourceTrigger.PropertyChanged // DefaultUpdateSourceTrigger
));
private static object CoerceText(DependencyObject d, object value)
{
var sv = value as string;
if (sv == String.Empty) return null;
return value;
//if( value == null) return string.Empty;
}
private static void OnNumberPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var tb = (NumberControl) d;
if (tb.Number != tb.Text)
{
tb.Text = tb.Number;
}
}
但是,将此属性绑定到小数时?这是发生的例外
System.Windows.Data错误:7:ConvertBack无法转换值''(类型'String')。 BindingExpression:路径= DecimalProperty; DataItem ='MainWindowViewModel'(HashCode = 58431997); target元素是'NumberControl'(Name =''); target属性为'Number'(类型'String')FormatException:'System.FormatException:输入字符串的格式不正确。
at System.Number.StringToNumber(String str,NumberStyles options,NumberBuffer& number,NumberFormatInfo info,Boolean parseDecimal)
at System.Number.ParseDecimal(String value,NumberStyles options,NumberFormatInfo numfmt)
在System.Convert.ToDecimal(字符串值,IFormatProvider提供者)
在System.Convert.ChangeType(对象值,类型conversionType,IFormatProvider提供者)
at System.Windows.Data.BindingExpression.ConvertBackHelper(IValueConverter converter,Object value,Type sourceType,Object parameter,CultureInfo culture)'
注意:我尝试保留默认的string.empty行为,但这些行为无效,而我提供的代码尝试为null,但也无效
TextBox.Text
是否有某种方式指定了其他默认转换器?
答案 0 :(得分:2)
快速回答
您需要使用为DependancyProperty
指定的null
方法将PropertyChangedCallback
直接设置为DependancyProperty
,以便它不会使用默认转换器。
所以在我的情况下,OnNumberPropertyChanged
方法被用作PropertyChangedCallback
中需要调用的DependancyProperty
tb.SetValue(NumberProperty, null);
长答案
该死的我在发布问题后发现了question和answer,这个问题并没有真正用我的搜索方式表达,直到我发布了#&# 34;默认转换器"在我的问题的最后。
我使用它的方法是在适当的时候使用代码手动将DependancyProperty
值设置为null
:
if (tb.Number == null)
{
tb.SetValue(NumberProperty, null);
}
因此完整的OnNumberPropertyChanged方法是:
/// <summary>
/// Callback for changes to the Number property
/// </summary>
private static void OnNumberPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var tb = (NumberControl) d;
if (tb.Number != tb.Text)
{
tb.Text = tb.Number;
}
if (tb.Number == null)
{
tb.SetValue(NumberProperty, null);
}
}