C# 将转换器指定为MarkupExtension时,设计时出现InvalidCastException
我想实现值转换器来指定RenderTransform的点。在我实现IValueConverter接口之前,这一切都很好。我知道我可以实现MarkupExtension类,以避免每次为转换器声明分离的XAML资源。当我试图实现这一点时,我 InvalidCastException:无法将“System.object”类型的对象强制转换为“System.Windows.Data.IValueConverter”类型。 转换器实现:C# 将转换器指定为MarkupExtension时,设计时出现InvalidCastException,c#,wpf,xaml,C#,Wpf,Xaml,我想实现值转换器来指定RenderTransform的点。在我实现IValueConverter接口之前,这一切都很好。我知道我可以实现MarkupExtension类,以避免每次为转换器声明分离的XAML资源。当我试图实现这一点时,我 InvalidCastException:无法将“System.object”类型的对象强制转换为“System.Windows.Data.IValueConverter”类型。 转换器实现: [ValueConversion(typeof(Point), ty
[ValueConversion(typeof(Point), typeof(Transform))]
public class PointToTransformConverter : MarkupExtension, IValueConverter
{
private PointToTransformConverter _instance = null;
public object Convert(
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
var point = (Point)value;
return new TransformGroup
{
Children = new TransformCollection
{
new TranslateTransform(point.X, point.Y)
}
};
}
public object ConvertBack(
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
var transform = value as TransformGroup;
if (transform?.Children.Count > 0)
{
var translateTransform = transform.Children[0] as TranslateTransform;
if (translateTransform != null)
{
return new Point(
translateTransform.X,
translateTransform.Y);
}
}
return null;
}
public override object ProvideValue(IServiceProvider serviceProvider)
{
return _instance ?? (_instance = new PointToTransformConverter());
}
}
XAML用法:
<local:PathControl x:Class="PathToWiringTube.PathView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:PathToWiringTube"
xmlns:view="clr-namespace:PathToWiringTube.View"
xmlns:vm="clr-namespace:PathToWiringTube.VM"
xmlns:crocodile="clr-namespace:Crocodile;assembly=Crocodile"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance vm:PathVm}">
<local:PathControl.Resources>
<crocodile:PointToTransformConverter x:Key="pointToTransformConverter"/>
</local:PathControl.Resources>
<Canvas>
<ItemsControl x:Name="itemsMarkers" ItemsSource="{Binding Markers}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<view:SplineDensityMarker Width="5" RenderTransform="{Binding Position, Converter={StaticResource pointToTransformConverter}}"/>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</Canvas>
</local:PathControl>
我做错了什么?请尝试下面的代码并检查是否出现异常? 我已经改正了。实例应该是静态的,而xaml则可以直接引用转换器,而不是将其作为静态资源调用。这是使用标记扩展名的主要用途。下面的代码应该可以正常工作。如果有任何问题,请回复 转换器:
[ValueConversion(typeof(Point), typeof(Transform))]
public class PointToTransformConverter : MarkupExtension, IValueConverter
{
private static PointToTransformConverter _instance = null;
public object Convert(
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
var point = (Point)value;
return new TransformGroup
{
Children = new TransformCollection
{
new TranslateTransform(point.X, point.Y)
}
};
}
public object ConvertBack(
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
var transform = value as TransformGroup;
if (transform?.Children.Count > 0)
{
var translateTransform = transform.Children[0] as TranslateTransform;
if (translateTransform != null)
{
return new Point(
translateTransform.X,
translateTransform.Y);
}
}
return null;
}
public override object ProvideValue(IServiceProvider serviceProvider)
{
return _instance ?? (_instance = new PointToTransformConverter());
}
}
<local:PathControl x:Class="PathToWiringTube.PathView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:PathToWiringTube"
xmlns:view="clr-namespace:PathToWiringTube.View"
xmlns:vm="clr-namespace:PathToWiringTube.VM"
xmlns:crocodile="clr-namespace:Crocodile;assembly=Crocodile"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance vm:PathVm}">
</local:PathControl.Resources>
<Canvas>
<ItemsControl x:Name="itemsMarkers" ItemsSource="{Binding Markers}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<view:SplineDensityMarker Width="5" RenderTransform="{Binding Position, Converter={crocodile:PointToTransformConverter}}"/>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</Canvas>
</local:PathControl>
Xaml:
[ValueConversion(typeof(Point), typeof(Transform))]
public class PointToTransformConverter : MarkupExtension, IValueConverter
{
private static PointToTransformConverter _instance = null;
public object Convert(
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
var point = (Point)value;
return new TransformGroup
{
Children = new TransformCollection
{
new TranslateTransform(point.X, point.Y)
}
};
}
public object ConvertBack(
object value,
Type targetType,
object parameter,
CultureInfo culture)
{
var transform = value as TransformGroup;
if (transform?.Children.Count > 0)
{
var translateTransform = transform.Children[0] as TranslateTransform;
if (translateTransform != null)
{
return new Point(
translateTransform.X,
translateTransform.Y);
}
}
return null;
}
public override object ProvideValue(IServiceProvider serviceProvider)
{
return _instance ?? (_instance = new PointToTransformConverter());
}
}
<local:PathControl x:Class="PathToWiringTube.PathView"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="clr-namespace:PathToWiringTube"
xmlns:view="clr-namespace:PathToWiringTube.View"
xmlns:vm="clr-namespace:PathToWiringTube.VM"
xmlns:crocodile="clr-namespace:Crocodile;assembly=Crocodile"
mc:Ignorable="d"
d:DataContext="{d:DesignInstance vm:PathVm}">
</local:PathControl.Resources>
<Canvas>
<ItemsControl x:Name="itemsMarkers" ItemsSource="{Binding Markers}">
<ItemsControl.ItemTemplate>
<DataTemplate>
<view:SplineDensityMarker Width="5" RenderTransform="{Binding Position, Converter={crocodile:PointToTransformConverter}}"/>
</DataTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</Canvas>
</local:PathControl>
我在另一个环境中检查了我的代码,并检测到它可以工作。我对Visual Studio版本不匹配进行了研究,并发现了它(14.0.23107.0 D14REL和14.0.24720.00 Update1)。在我的旧环境上安装最新的Visual Studio Update 2后,一切正常 是的,我已经说过它工作得很好。但是,在这种情况下,我如何能够同时实现MarkupExtension类和IValueConverter接口?不,我想检查转换器是否在没有标记扩展的情况下工作,即作为静态资源添加?谢谢Vishakh,我已经复制粘贴了您的代码。但这会在重建后的设计时再次导致异常。我对此进行了调查,并将在这里报告我的进度。您能替换代码中的返回null并用一些值初始化它吗??