WPF custom control binding issue
That's what I essentially want. A UserControl
c TextBlock
, property is Text
bound to property Prop
UserControl
. (This is just a representation of my actual problem)
Below is part of my UserControl
( ClientDetailsControl.xaml
)
<TextBlock Text="{Binding Prop}" />
Next is ClientDetailsControl.xaml.cs
public partial class ClientDetailsControl : UserControl
{
public static DependencyProperty PropProperty = DependencyProperty.Register("Prop", typeof(String), typeof(ClientDetailsControl));
public String Prop { get; set; }
public ClientDetailsControl()
{
InitializeComponent();
DataContext = this;
}
}
Now, in my main WPF window ( NewOrder.xaml
), I am using this UserControl
as
<userControl:ClientDetailsControl Prop="{Binding MyProp}" />
The property is MyProp
declared like this inNewOrder.xaml.cs
public String MyProp { get { return "HELLO"; } }
When I run this code, I get the following error:
BindingExpression path error: Property MyProp was not found in 'object' 'ClientDetailsControl' (Name = '') '. BindingExpression: Path = MyProp; DataItem = 'ClientDetailsControl' (Name = ''); target element 'ClientDetailsControl' (Name = ''); target property - "Prop" (type 'String')
When I just write
<userControl:ClientDetailsControl Prop="ABCD" />
It works. However, when I try to bind a property Prop
from UserControl
to MyProp
, it doesn't work.
How to do it?
source to share
Use the property RelativeSource
like this:
<userControl:ClientDetailsControl
Prop="{Binding MyProp,RelativeSource={RelativeSource Mode=FindAncestor,AncestorType=Window}}"/>
source to share
The reason it doesn't work is because the binding paths are relative to the DataContext and not to the (parent) control.
This is why you can fix this by setting RelativeSource; in this case, the binding path uses the RelativeSource as the starting point for finding the property.
Another way to solve it is to assign a parent element and set the ElementName of the binding.
The MVVM way is to add a property to the ViewModel class, set the parent DataContext control to an instance of the ViewModel, and bind both the parent control and the client control to that property.
source to share