1

I have a user control with this code behind:

/// <summary>
/// The text to use for the header.
/// </summary>
public UIElement HeaderText
{
    get { return (UIElement) GetValue(HeaderTextProperty); }
    set { SetValue(HeaderTextProperty, value); }
}

public static DependencyProperty HeaderTextProperty =
    DependencyProperty.Register("HeaderText",
                                typeof(UIElement),
                                typeof(Panel),
                                new PropertyMetadata(null, new PropertyChangedCallback(HeaderTextPropertyChanged)));

private static void HeaderTextPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
    var control = d as Panel;
    if (control != null)
    {
        control.HeaderText = (UIElement) e.NewValue;
    }
}

And this XAML:

<TextBlock Text="{TemplateBinding local:CustomPanel.HeaderText}" />

And I'm trying to use the user control like this:

<controls:CustomPanel>
    <controls:CustomPanel.HeaderText>
        <TextBlock Text="Foo " />
        <TextBlock Text="{Binding Bar}" />
        <TextBlock Text=" baz." />
    </controls:CustomPanel.HeaderText>
</controls:CustomPanel>

However, what I get is blank/empty text.

I can get it to work if I change UIElement into string in code-behind, but I want to accept both string, TextBlock and practically any UIElement that makes sense for text.

How can I achieve this?

Dave Clemmer
  • 3,741
  • 12
  • 49
  • 72
Tower
  • 98,741
  • 129
  • 357
  • 507

1 Answers1

2

Don't use a TextBlock in your control but a ContentPresenter (and bind the Content), it can host anything. Make the property type object and change the name to Header for consistency.

(As a side-note: Usually you have additional properties that go along with the Header, namely a HeaderTemplate and a HeaderTemplateSelector. If the ContentPresenter is in a template you can make it bind to all three properties by setting the ContentSource to "Header")

H.B.
  • 166,899
  • 29
  • 327
  • 400
  • "TextBlock does not match the element ContentPresenter". Is there something special I need to do? – Tower Jun 02 '12 at 23:06
  • @rFactor: Not really, just change the declaration XAML to this: `` and change the property type to `object`. How did you get that error? Sounds odd... – H.B. Jun 02 '12 at 23:08
  • Okay I solved it, there was some extra style that caused the issue. :) – Tower Jun 02 '12 at 23:12
  • But what made you say "property changed callback" is useless? – Tower Jun 02 '12 at 23:21
  • @rFactor: It does nothing, you don't need to manually change the property, that has happend at the point of the callback already. – H.B. Jun 02 '12 at 23:23