Silverlight xaml bind to extension method
So I'm working on a small project using the bing maps silverlight sdk. I'm getting a bunch of objects off a server (through wcf services) and each of these devices has a lat/long properties. To map something on bing maps, you supply it with a Location type (essentially just a wrapper for lat/long)
The types I'm working with are stored on the server and only have lat long. I wrote an extension method called Location that wraps them into a location and returns them.
<DataTemplate x:Key="MapVisualDataTemplate">
<m:Pushpin m:MapLayer.Position="{Binding Location}" />
</DataTemplate>
Even though the extension method is visible and usable from within C#, it is not properly used by the xaml. If I add the property directly into the type on the server it works fine. Only by having it defin开发者_StackOverflow中文版ed as an extension method it doesn't work. I'd rather have it be an extension method because it's eventually going to be used on a wide variety of types.
Is it possible to bind using the above syntax when Location is an extension method for whatever type is currently bound to?
I believe the reason is that in xaml you must bind to either a property or a dependency property. An extension method is just that, a method. Even if the method mimics a property it still isn't quite the same thing.
The XAML equivalent of Extension Methods are Value Converters. Here is an example:
public class Converter:IValueConverter
{
object IValueConverter.Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
return "foo";
}
object IValueConverter.ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
throw new NotImplementedException();
}
}
I think this is possible. If I will have some time I'll try to create MarkupExtension that will help to do that.
For now, my idea is to create MarkupExtension class with Source and Method properties. In XAML we would use it like here:
<TextBlock Text="{BindExt Source={Binding DataContext}, Method=MyExtMethod}" />
Source is a property where we set a source object on which we invoke MyExtMethod (Extension Method). Because of performance of finding such a method I probably add another property called ExType, where will be stored a type of static class where MyExtMethod was declared. This can help improve performance of searching for extension method, but XAML syntax will be longer :/
So we have now some prototype expression:
<TextBlock Text="{BindExt Source={Binding DataContext}, Method=MyExtMethod, ExType=ex:ExtMethods}" />
where "ex" prefix can be e.g. BrightShadow.Data.Extensions namespace:
xmlns:ex="clr-namespace:BrightShadow.Data.Extensions;assembly=BrightShadowAssembly"
Maybe in near future something about it I will post on my polish blog here.
精彩评论