What is ItemContainerTemplate used for? It is derived from DataTemplate, but I don't see any difference between them except the ItemContainerTemplateKey property. When should I use one and when the other?
The ItemContainerTemplate describes the world around your Item. For example in a ListBox the selection rectangle around your ListBoxItem. The DataTemplate describes how you ListBoxItem apears and of which elements it consists.
Dr. WPF did a good example: http://drwpf.com/blog/category/item-containers/
The only difference between DataTemplate
and ItemContainerTemplate
is the way the resource dictionary key is automatically provided (assuming it is not set explicitly). Namely, DataTemplate
is decorated with [DictionaryKeyProperty("DataTemplateKey")]
attribute, and the DataTemplateKey
is basically defined as:
public object DataTemplateKey
{
get { return (DataType != null) ? new DataTemplateKey(DataType) : null;
}
See DataTemplate source for reference.
ItemContainerTemplate
derives from DataTemplate
, but is decorated with [DictionaryKeyProperty("ItemContainerTemplateKey")]
attribute (which in practice replaces the inherited one), and ItemContainerTemplateKey
property is defined as follows:
public object ItemContainerTemplateKey
{
get { return (DataType != null) ? new ItemContainerTemplateKey(DataType) : null; }
}
See ItemContainerTemplate source for reference.
The difference seems small - DataTemplate
returns an instance of DataTemplateKey
and ItemContainerTemplate
returns an instance of ItemContainerTemplateKey
(both derive from TemplateKey
). So basically these two are equivalent1:
<ItemContainerTemplate DataType="{x:Type sys:String}" />
<DataTemplate x:Key="{ItemContainerTemplateKey {x:Type sys:String}}" />
and so are these:
<ItemContainerTemplate x:Key="{DataTemplateKey {x:Type sys:String}}" />
<DataTemplate DataType="{x:Type sys:String}" />
The main practical difference between these two is that DataTemplate
with default key is treated as an implicit template2, whereas ItemContainerTemplate
is not. In fact, you need to manually reference it, e.g.:
<ListBox ItemTemplate="{StaticResource {ItemContainerTemplate {x:Type sys:String}}}" />
I'm not sure about the intentions behind creating ItemContainerTemplate
class. I guess it gives you a clearer overview of the code, where you know that such a template is specifically intended to be used in an ItemsControl
(or a derived control). Also, I guess it would prove to be pretty simple to write a strongly reusable DataTemplateSelector
that would take advantage of this class.
1They're not equivalent in the sense that created objects are of different types, but functionally they're equivalent.
2Implicit templates are applied to all objects of corresponding type within the scope, unless a template is set explicitly.
You can put an ItemContainerTemplate
in a ResourceDictionary
, and it will automatically use the DataType
as its key.
That's the only difference.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With