Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

WPF Binding inner control with parent data context

I made a user control

<UserControl x:Class="MyApp.MyControl"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
         xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
         mc:Ignorable="d"  x:Name="uc">
<Grid Width="Auto" Height="Auto">
    <TextBlock Text="{Binding Path=DataContext.TextContent, ElementName=uc}"/>
    <TextBlock Text="{Binding Path=DataContext.TextContent2, ElementName=uc}"/>
</Grid>

I want the sub-controls in the defined control(uc) will bind to the properties of uc.DataContext. I used the defined control as follows:

<Window x:Class="Tms.TMSClient.Views.MainWindow" Name="window"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:control="clr-namespace:MyApp"
    xmlns:ribbon="clr-namespace:Microsoft.Windows.Controls.Ribbon;assembly=RibbonControlsLibrary">      

    <control:MyControl DataContext="{Binding Path=MyControlVM}"/>

The DataContext which is assigned to the window has this structure: WindowVM.MyControlVM.TextContent.

The given code does not work because the textbox's DataContext is bound to WindowVM instead. I think the problem may be because the inner textbox is bound before the defined control (uc) is, thus the bounded DataContext for uc does not take effect yet.

What I want is: the custom control (MyControl) will be bound to its corresponding viewmodel (MyControlVM), and the inner elements of MyControl will be bound to the properties of MyControlVM.

Do you have any solutions for this problem?

like image 226
Nghia Le Avatar asked Dec 09 '22 06:12

Nghia Le


1 Answers

If I understand you correctly, you want to data bind a property from your MyControl view model to a TextBox.Text property inside the MyControl UserControl. If that is correct, then you can use a RelativeSource Binding, or the ElementName syntax that you are already using.

First, make sure that your view model is set as the DataContext for the UserControl:

public MyControl()
{
    DataContext = new YourControlViewModel();
}

As child controls automatically inherit their parent's DataContext objects, you can now reference this view model from the TextBox through the MyControl.DataContext property from the UserControl's XAML:

<TextBlock Text="{Binding DataContext.TextContent, 
    RelativeSource={RelativeSource AncestorType={x:Type Window}}}" />

That's all you need.

like image 54
Sheridan Avatar answered Dec 11 '22 08:12

Sheridan