tags:

views:

122

answers:

1

I have a custom control in WPF. In this I have a DependencyProperty of the type integer. In the template for the custom control I have a TextBlock, I and would like to show the value of the integer in the TextBlock. But I can't get it to work.

I'm using TemplateBinding. If I use the same code but change the type of the DependencyProperty to string it works fine. But I really want it to be an integer for the rest of my application to work.

How can I do this?

I've written simplified code that shows the problem. First the custom control:

public class MyCustomControl : Control
{
    static MyCustomControl()
    {
        DefaultStyleKeyProperty.OverrideMetadata(typeof(MyCustomControl), new FrameworkPropertyMetadata(typeof(MyCustomControl)));

        MyIntegerProperty = DependencyProperty.Register("MyInteger", typeof(int), typeof(MyCustomControl), new FrameworkPropertyMetadata(0));
    }


    public int MyInteger
    {
        get
        {
            return (int)GetValue(MyCustomControl.MyIntegerProperty);
        }
        set
        {
            SetValue(MyCustomControl.MyIntegerProperty, value);
        }
    }
    public static readonly DependencyProperty MyIntegerProperty;
}

And this is my default template:

<Style TargetType="{x:Type local:MyCustomControl}">
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type local:MyCustomControl}">
                <Border BorderThickness="1" CornerRadius="4" BorderBrush="Black" Background="Azure">
                    <StackPanel Orientation="Vertical">
                        <TextBlock Text="{TemplateBinding MyInteger}" HorizontalAlignment="Center" />
                    </StackPanel>
                </Border>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

And usage:

<Window x:Class="CustomControlBinding.MainWindow"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:local="clr-namespace:CustomControlBinding"
    Title="MainWindow" Height="350" Width="525">
<Grid>
    <local:MyCustomControl Width="100" Height="100" MyInteger="456" />
</Grid>

What am I doing wrong?

Thanks // David

+3  A: 

Try using a regular Binding with a RelativeSource of TemplatedParent:

<TextBlock Text="{Binding MyInteger, RelativeSource={RelativeSource TemplatedParent}}" HorizontalAlignment="Center" />

According to this thread, this is a limitation of TemplateBinding:

TemplateBinding is a lightweight "binding", it doesn't support some features of traditional Binding, such as automatically type conversion using the known type converters associated with the target property

Quartermeister
Using regular Binding like this you can also specify your own value converter (see IValueConverter) which you can code your own type conversion behavior.
Aardvark
Works great! Thank you Quartermeister! :)
haagel
@Aardvark: Good point. You can actually specify a Converter even if you use a TemplateBinding.
Quartermeister
I *think* Silverlight's version of TemplateBinding doesn't support a Converter parameter - but I guess WPF does. My mistake!
Aardvark