Binding to property on root element in DataTemplate through a ContentControl
In my user interface I sometimes want to put titles above usercontrols.
I want to declare these titles in XAML for future localizability, so I want to keep them out of the datacontexts.
Can databinding fetch them from a propert开发者_运维百科y set on the root node of the usercontrol?
I have boiled the problem down to the following code example:
using System.Windows;
namespace WpfApplication12
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
this.Person = new Author { Name = "Guge" };
this.DataContext = this;
}
public object Person { get; set; }
}
public class Author
{
public string Name { get; set; }
}
}
And:
<Window x:Class="WpfApplication12.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:WpfApplication12"
Title="MainWindow" Height="350" Width="525">
<Window.Resources>
<DataTemplate DataType="{x:Type local:Author}">
<Border AutomationProperties.Name="Author" BorderThickness="1" BorderBrush="Black">
<Label Content="{Binding Name}"/>
</Border>
</DataTemplate>
</Window.Resources>
<StackPanel>
<Label x:Name="Position" Content="Author"/>
<ContentControl x:Name="presentation" Content="{Binding Person}"/>
</StackPanel>
And the practical problem is: how can I use databinding in the content property of the "Position" Label to fetch the word "Author" from the AutomationProperties.Name property of the Border in the DataTemplate?
How about going the route over your data object:
public class Author
{
public string Name { get; set; }
public string TypeName { get; set; } // might be better in base class Person
}
And:
<Window.Resources>
<DataTemplate DataType="{x:Type local:Author}">
<Border AutomationProperties.Name="{Binding TypeName}"
BorderThickness="1" BorderBrush="Black">
<Label Content="{Binding Name}"/>
</Border>
</DataTemplate>
</Window.Resources>
<StackPanel>
<Label x:Name="Position" Content="{Binding ElementName=presentation, Path=DataContext.TypeName}"/>
<ContentControl x:Name="presentation" Content="{Binding Person}"/>
</StackPanel>
The solution so far is to add a string property for TypeName to the viewmodel and fill this with the contents of the AutomationProperties.Name in code-behind. And use the following binding:
<StackPanel>
<Label x:Name="Position" Content="{Binding Person.TypeName}"/>
<ContentControl x:Name="presentation" Content="{Binding Person}"/>
</StackPanel>
However, I still think it should be possible to do this without using the ViewModel, I hope to be able to revisit this issue when my databinding skills have improved.
精彩评论