4

I discovered when using a ContentTemplate/DataTemplate in a WPF TabControl my Bindings will not work anymore.

I have set up a small example to illustrate:

<Window x:Class="HAND.BindingExample" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" Title="BindingExample" Height="506" Width="656" DataContext="{Binding RelativeSource={RelativeSource Self}}" > <Grid> <TabControl HorizontalAlignment="Left" Height="381" VerticalAlignment="Top" Width="608"> <TabItem Header="TabItem"> <Label Content="{Binding Path=myString}"/> </TabItem> <TabItem Header="TabItem"> <TabItem.ContentTemplate> <DataTemplate> <Label Content="{Binding Path=myString}"/> </DataTemplate> </TabItem.ContentTemplate> </TabItem> </TabControl> </Grid> </Window> 

Tab1 works as expected, Tab2 is empty.

the code behind:

using System.Windows; namespace HAND { public partial class BindingExample : Window { public string myString { get; set; } public BindingExample() { myString = "Hello Stackoverflow"; InitializeComponent(); } } } 

2 Answers 2

6

You are using the ContentTemplate property incorrectly. From the ContentControl.ContentTemplate Property page on MSDN:

Gets or sets the data template used to display the content of the ContentControl.

Therefore, when setting this property, you also need to set the Content property to some sort of data source:

<TabControl> <TabItem Header="TabItem"> <Label Content="{Binding Path=myString}"/> </TabItem> <TabItem Header="TabItem" Content="{Binding Path=myString}"> <TabItem.ContentTemplate> <DataTemplate> <Label Content="{Binding}" /> </DataTemplate> </TabItem.ContentTemplate> </TabItem> </TabControl> 
Sign up to request clarification or add additional context in comments.

4 Comments

Same conclusion as Miiite. Thank you very much also for the good explanation!
why do you need to set the Content="{Binding Path=mystring}" in the <TabItem> AND then also set Content="{Binding}" in the <Label>? In this example it doesn't seem necessary for the TabItem.ContentTemplate at all? Wouldn't it work just as well without the Template? I'm trying to understand templates and how I can bind other properties of the Label to parent's DataContext... thanks!
We data bind the myString property to the Content property to give it some value. Here, that value is just a single string, but it could have been an object with other properties. In the ContentTemplate, we tell it which part of the data bound object we want to display in the Label. In this case, we want to bind to the whole string object, so we use {Binding} to do that.
Noto though: the sample would work only for read-only bindings - if you changed Label to TextBox, myString would never get written back.
4
<TabItem Content="{Binding myString}" Header="TabItem"> <TabItem.ContentTemplate> <DataTemplate> <Label Content="{Binding}" /> </DataTemplate> </TabItem.ContentTemplate> </TabItem> 

But just so you know, to bind a window on itself, is just not the way to go. I don't know if you did that just for the example, but if not try and create a proper viewModel to bind your window on ;)

4 Comments

I have it running on my machine. Maybe it does not run when you bind a window on itself, which I did not do.
Thank you! This works for my example. I am using a different binding class in my real world program using the MVVM pattern. I still do not understand why your code works and mine doesn't. I will now try to apply the solution of the example to my application.
Sheridan posted an answer with the same XAML code as mine, but with a better explanation of how the ContentTemplate works. It should help you understanding it
hi miiite, your answer worked for me, wrongly tested. make an edit to ur answer i will revert the downvote

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.