Introduction
Most of us would have needed to use Generic types in Xaml, be it in Style or DataTemplate or some similar places. Since .Net does not allow Generic type to be declared in Xaml, we need this work around. While solution provided here far from perfect, it still solves problems for most usecases.
Using the code
Using the new Extension provided here, you would be able to use Generic types in Xaml as shown below
<DataTemplate x:Key="genericTemplate" DataType="{ge:Generic GenericTypeName=System.Collections.Generic.KeyValuePair, GenericTypeAssemblyName=mscorlib, ArgumentType1={x:Type sys:String},ArgumentType2={x:Type sys:String}}">
<StackPanel Orientation="Horizontal">
<Label Background="Green" Content="{Binding Path=Key}" />
<Label Background="Yellow" Content="{Binding Path=Value}" />
</StackPanel>
</DataTemplate>
In your markup extension class (GenericExtension) add following properties:
public string GenericTypeName { get; set; }
public string GenericTypeAssemblyName { get; set; }
public Type ArgumentType1 { get; set; }
public Type ArgumentType2 { get; set; }
public Type ArgumentType3 { get; set; }
And add implementation of ProvideValue method:
public override object ProvideValue(IServiceProvider serviceProvider)
{
var genericArguments = new List<Type>();
if(ArgumentType1 != null)
{
genericArguments.Add(ArgumentType1);
}
if(ArgumentType2 != null)
{
genericArguments.Add(ArgumentType2);
}
if(ArgumentType3 != null)
{
genericArguments.Add(ArgumentType3);
}
if(!string.IsNullOrWhiteSpace(GenericTypeName) && !string.IsNullOrWhiteSpace(GenericTypeAssemblyName) && genericArguments.Count > 1)
{
var genericType = Type.GetType(string.Format(_genericTypeFormat, GenericTypeName, genericArguments.Count, GenericTypeAssemblyName));
if(genericType != null)
{
var returnType = genericType.MakeGenericType(genericArguments.ToArray());
return returnType;
}
}
return null;
}
Notice that there a constant _genericTypeFormat, which is declared as follows:
private const string _genericTypeFormat="{0}`{1},{2}";
Attachment contains basic usage and GenericExtension itself.