WPF often provides you with an option to set an ItemTemplate or an ItemTemplateSelector when styling say lists or even content controls (ContentTemplate). This is useful although most would probably just define an implicit style by not giving it a key:

<DataTemplate DataType="TextBlock">
...
</DataTemplate>

This is all fine and even works if you’ve got multiple different items in a list. The problem arises when you want to style an interface of a view model. In lack of a better way around it I usually end up creating an interface for my view models using an implementation for production and one for design time. But, WPF can’t handle implicit data templates for interfaces. So doing this wouldn’t work:

<DataTemplate DataType="IViewModelOne">...</DataTemplate>
<DataTemplate DataType="IViewModelTwo">...</DataTemplate>

Why not? We’ll it’s a design choice made by Microsoft since a type might implement multiple interfaces, what if an item had both IViewModelOne and IViewModelTwo? Instead of throwing an exception or something MS has decided to just not support this behaviour. So the way to get around this is to use a TemplateSelector. I don’t really like to rely on code behind code too much though, not for the sake of it being code but because it makes the styling less declarative.

<ListBox>
   <ListBox.ItemTemplateSelector><MySelectorThatIDontReallyKnowWhatItsDoing /></ListBox.ItemTemplateSelector>
</ListBox>

To get around this I’ve written a small template class that allows you to define the templates and bind them to types in XAML instead. So this is how it looks:

<local:TemplateByTypeSelector>
 <local:TemplateByTypeSelector.Templates>
 <local:TemplateForType Type="{x:Type IViewModelOne}" Template="{StaticResource MyTemplate}"/>
 <local:TemplateForType Type="{x:Type IViewModelTwo}">
 <local:TemplateForType.Template>
 <DataTemplate DataType="{x:Type IViewModelTwo}">
 ...
 </DataTemplate>
 </local:TemplateForType.Template>
 </local:TemplateForType>
 </local:TemplateByTypeSelector.Templates>
</local:TemplateByTypeSelector>

And this is the class(es):

public class TemplateByTypeSelector : DataTemplateSelector
{
    public TemplateByTypeSelector()
    {
        Templates = new ObservableCollection<TemplateForType>();
    }

    public ObservableCollection<TemplateForType> Templates { get; set; }

    public DataTemplate TemplateForNullItem { get; set; }

    internal DataTemplate SelectValue(object item, DependencyObject obj)
    {
        if (item == null)
            return NullIfSpecified;

        return FindSingleTValueFor(item);
    }

    private DataTemplate FindSingleTValueFor(object item)
    {
        var type = item.GetType();
        var possibleTypes = Templates.Where(mapping => mapping.Type.IsAssignableFrom(type)).ToList();
        if (possibleTypes.Count > 1)
        {
            var typeNames = string.Join(", ", possibleTypes.Select(t => t.Type.Name));
            var errorMessage = string.Format("Item '{0}' can be mapped to multiple types, please specify type TValue mapping more distinctly: " + typeNames, type.Name);
            throw new InvalidOperationException(errorMessage);
        }

        if (possibleTypes.Count == 0)
            throw new InvalidOperationException("No type mapping found for: " + type.Name);

        return possibleTypes[0].DataTemplate;
    }

    protected DataTemplate NullIfSpecified
    {
        get
        {
            if (TemplateForNullItem == null)
                throw new Exception("TemplateForNullItem is not specified");

            return TemplateForNullItem;
        }
    }
}

public class TemplateForType
{
    public Type Type { get; set; }
    public DataTemplate DataTemplate { get; set; }
}

This should be simple to convert to a similar style selector as well if that’s needed. Just a snippet to help you along the way.

Cheers