BlackWaspTM

This web site uses cookies. By using the site you accept the cookie policy.This message is for compliance with the UK ICO law.

Windows Presentation Foundation
.NET 4.0+

WPF Control Templates - Displaying Content

The one hundred and sixty-second part of the Windows Presentation Foundation Fundamentals tutorial continues to look at the creation of control templates. This article explains how the content of a ContentControl can be incorporated into a template.

ContentPresenter

Earlier in the tutorial we saw how you can create a custom control template and apply it to a control. We then looked at template bindings, which let you link items in a control template to the properties of its target controls. In the first article, we created a control template for a button. This changed the button's user interface but had the limitation that the content applied to the button was not included in the final output.

In this article we will see how to add a ContentPresenter to a control template. ContentPresenters are used with classes that inherit from ContentControl to render the content, which could be as simple as plain text or much more complex, including user interface elements such as layout controls, images or video. When added to a control template, ContentPresenters provide placeholders for the parent control's content.

To demonstrate we'll use a sample WPF application in Visual Studio. Create a new solution named, "ContentPresenterDemo" and replace the XAML of the main window with the following code:

<Window x:Class="ContentPresenterDemo.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="ContentPresenter Demo" Height="250" Width="350">
    <Window.Resources>
        <ControlTemplate x:Key="MyButtonTemplate" TargetType="Button">
            <Grid>
                <Border Background="Black" Margin="5 5 0 0" />
                <Border BorderBrush="Black" BorderThickness="1"
                        Background="Yellow" Margin="0 0 5 5">
                    <TextBlock HorizontalAlignment="Center" VerticalAlignment="Center">
                        OK
                    </TextBlock>
                </Border>
            </Grid>
        </ControlTemplate>
    </Window.Resources>

    <Grid>
        <Button Width="100" Height="50"
                Template="{StaticResource MyButtonTemplate}">
            <StackPanel Orientation="Horizontal" HorizontalAlignment="Center"
                        VerticalAlignment="Center">
                <TextBlock FontFamily="Wingdings" FontSize="16" Text="ü"/>
                <TextBlock Text="Yes"/>
            </StackPanel>
        </Button>
    </Grid>
</Window>

The window contains a button with a custom template that is similar to that from the first control template article. Note that the button's content is set to a StackPanel containing two text blocks. However, because the contents are not used in the control template, the resultant window shows the "OK" text from the template.

WPF ContentPresenter demo window

Adding a ContentPresenter

You can add a ContentPresenter anywhere in a control template where it would make sense for the content to be included. All you need to do is include a ContentPresenter element. No additional properties are required, although the class does include all of the FrameworkElement members, should you wish to use them.

For our button template, the obvious place to put the ContentPresenter is within the second Border, in place of the text block containing the text, "OK". Update the control template, as follows:

<ControlTemplate x:Key="MyButtonTemplate" TargetType="Button">
    <Grid>
        <Border Background="Black" Margin="5 5 0 0" />
        <Border BorderBrush="Black" BorderThickness="1"
                Background="Yellow" Margin="0 0 5 5">
            <ContentPresenter/>
        </Border>
    </Grid>
</ControlTemplate>

The templated button now shows the StackPanel and TextBlocks from its Content property, as shown below:

WPF ContentPresenter

31 May 2015