我正在尝试写一个像这样的markupextension:
[MarkupExtensionReturnType(typeof(Length))]
public class LengthExtension : MarkupExtension
{
// adding the attribute like this compiles but does nothing.
public LengthExtension([TypeConverter(typeof(LengthTypeConverter))]Length value)
{
this.Value = value;
}
[ConstructorArgument("value")]
public Length Value { get; set; }
public override object ProvideValue(IServiceProvider serviceProvider)
{
return this.Value;
}
}
要像这样使用:
<Label Content="{units:Length 1 mm}" />
Errs with:
“长度”类型的TypeConverter不支持从字符串转换。
如果I:
,TypeConverter可以正常工作Value
属性上并拥有默认的ctor。Length
类型。虽然这可能是x / y,但我不想要任何这些解决方案。
以下是转换器的代码:
public class LengthTypeConverter : TypeConverter
{
public override bool CanConvertFrom(ITypeDescriptorContext context, Type sourceType)
{
if (sourceType == typeof(string))
{
return true;
}
return base.CanConvertFrom(context, sourceType);
}
public override bool CanConvertTo(ITypeDescriptorContext context, Type destinationType)
{
if (destinationType == typeof(InstanceDescriptor) || destinationType == typeof(string))
{
return true;
}
return base.CanConvertTo(context, destinationType);
}
public override object ConvertFrom(ITypeDescriptorContext context, CultureInfo culture, object value)
{
var text = value as string;
if (text != null)
{
return Length.Parse(text, culture);
}
return base.ConvertFrom(context, culture, value);
}
public override object ConvertTo(ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
{
if (value is Length && destinationType != null)
{
var length = (Length)value;
if (destinationType == typeof(string))
{
return length.ToString(culture);
}
else if (destinationType == typeof(InstanceDescriptor))
{
var factoryMethod = typeof(Length).GetMethod(nameof(Length.FromMetres), BindingFlags.Public | BindingFlags.Static, null, new Type[] { typeof(double) }, null);
if (factoryMethod != null)
{
var args = new object[] { length.metres };
return new InstanceDescriptor(factoryMethod, args);
}
}
}
return base.ConvertTo(context, culture, value, destinationType);
}
}
答案 0 :(得分:3)
来自MSDN, Applying the TypeConverterAttribute(强调我的):
为了将自定义类型转换器用作代理类型 由XAML处理器转换为自定义类,您必须应用 .NET Framework属性TypeConverterAttribute指向类 定义强> ...
和
您还可以基于每个属性提供类型转换器。代替 将.NET Framework属性TypeConverterAttribute应用于 类定义,将其应用于属性定义 ...
没有提及任何其他地方来应用该属性。所以你问题的答案很可能是
不,TypeConverter不能用于构造函数参数。
答案 1 :(得分:2)
发表此批评:
[MarkupExtensionReturnType(typeof(Length))]
public class LengthExtension : MarkupExtension
{
public LengthExtension(string value)
{
this.Value = Length.Parse(value, CultureInfo.InvariantCulture);
}
public Length Value { get; private set; }
public override object ProvideValue(IServiceProvider serviceProvider)
{
return this.Value;
}
}
这有效,但我不确定是否有任何缺点。