Question

I am trying to create different themes for a custom PropertyGrid control that inherits from TreeView, and uses TreeViewItems as the item containers. Additionally, I want to set the control template for the TreeViewItems based on the type of object the TreeViewItem is bound to. I would prefer to populate the PropertyGrid as I am now by setting ItemsSource.

Currently I am applying different control templates based on the type of bound object by setting the TreeViewItems.ItemContainerStyleSelector via a HierarchialDataTemplate. In this style selector I am returning a static resource via a resource key. I would like to not use this selector and resource key method, but rather create different derived TreeViewItem objects based on the type of the object it is to be bound to. This would allow me to apply a different style per theme based on type, in the same way that other controls are themed. But I don’t see a way to do this. The override ItemsControl.GetContainerForItemOverride would do what I want if it was passed the object to be bound to, or at least its type, but I don’t see a way to make this work. Any ideas on how to do this? Or, am I going about his all wrong?

Was it helpful?

Solution

Your best bet would be to add a read-only custom dependency property to your custom TreeViewItem. For lack of a better name, let's call this "Look". This property can then be an enumeration with the various looks or Styles you want applied.

Then you can create a single Style for your custom TreeViewItem, which uses Style Triggers based on your Look property to change the Template or various other properties.

You can then set your Look property in a PrepareContainerForItemOverride, based on the item that is given.

The ItemsControl in general expect their "container" to be of a single type, but this isn't strictly enforced. But as you said, you can't create different containers based on the item it is wrapping.

In addition, virtualization adds a bit of complexity to the mix. As in that case, containers may be reused so you would not have a chance to "create" a new one of the property type. But, even with virtualization enabled, the PrepareContainerForItemOverride will be called.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top