Control templates in WPF

DZone 's Guide to

Control templates in WPF

· ·
Free Resource

One of the paradigms switches that is mostly unusual for those developers who start using WPF with a WinForms background is that everything in WPF revolves around templates. Templates basically define the structure of the UI.

Often being confused with styles, templates are completely different elements. Unlike styles, that define the appearance of the UI, templates define the visual tree – the structure and hierarchy of elements. The control that a developer sees on a window/page in WPF has a complex visual tree – it is basically a control composed of multiple other individual controls. A template can also define the style of included elements. A style customizes the default look (set by the default template), but the template is defining the element “from scratch”, taking it as only having default properties and behaviors.

A control template is defined by using the ControlTemplate element that is placed inside the Resources element (either for the window/page or application). Same as styles, control templates are type-specific, therefore can only be applied to elements that have the same type as the one defined.

Here is an example:

<Window x:Class="WPF_Test.MainWindow"
Title="MainWindow" Height="380" Width="568" Loaded="Window_Loaded">

<ControlTemplate x:Key="Custom2" TargetType="{x:Type Button}">
<Grid x:Name="ButtonGrid">
<Border Margin="2" Padding="10" BorderThickness="2" BorderBrush="Blue" />
<TextBox Height="30" Width="100"></TextBox>
<Button Template="{StaticResource Custom2}" Margin="227,12,111,216" Click="Button_Click">

As you see, I created a control template that can be applied to buttons (hence, I used {x:Type Button} as TargetType). Some of the developers who used WinForms might be wondering, why there is a TextBox declared inside the content template. The answer is simple – in WPF almost anything can be a container for other controls. Therefore, if I place a Grid or a StackPanel inside the ControlTemplate, I can also insert other elements inside the root one.

Notice the fact, that when I am using a custom template, I have to define the control appearance from ground zero – the default look is not preserved for the base element. I am then referncing the template in the Button control, as a StaticResource. It is referenced the same way the referencing for styles is done, the only difference is the targeted property, which is Template in this case.

In a control template, the developer can also specify the control behavior. By customizing the ControlTemplate.Triggers element, various property changes can be automated without any code-behind parts. Basically, there are two ways to modify control properties – by using Triggers (regular property changes) or EventTriggers (triggered by events).

The interesting moment here, is that the way properties are modified. If you are going to use Setters (elements used to set other element’s properties) inside regular Triggers (caused by modified properties), it will all work fine. Here is an example:

<Trigger Property="Background" Value="White">
<Setter Property="Foreground" Value="Black" />

As you see, here I have a sample trigger caused by the background color change and it changes the foreground accordingly.

However, when you will want to trigger a property change via an EventTrigger, Setters will be a no-no – now you need to think of performing an animation of the property being changed. A bit unusual, but if you set the animation times to 0, then no actual animation will be seen by the user.

Although a rather simple concept, control templates carry with them a great potential when it comes to custom controls. Especially if those controls radically differ from those provided in the toolbox. A complete understanding of the templates concept is fundamental for WPF development in general.


Opinions expressed by DZone contributors are their own.

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}