How to access parent DataContext from UserControl

I need to access the DataContext container from UserControl (a grid containing text fields and a list: I need to insert elements into this list) that I created in WPF: what's the best way to do this?

I was thinking of passing the DataContext as a parameter to the user control, but I think there is a cleaner way to do this.

+11
wpf user-controls datacontext
Jul 04 '11 at 19:00
source share
4 answers

Normally the DataContext will be inherited , just don’t set it explicitly on the UserControl , and it will get it from its parent. If you need to set it, you can still use the Parent property to get the parent, which can then be safely assigned to FrameworkElement and if it doesn’t is null, you can capture its DataContext .

+11
Jul 04 2018-11-11T00:
source share

I sometimes have nested User controls, and for the grandchild usercontrol sometimes I need a grandparent view data context. The easiest way I've found so far (and I'm a little newbie) is this:

 <Shared:GranchildControl DataContext="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type GrandparentView}}, Path=DataContext.GrandparentViewModel}" /> 

I wrote a more detailed example on my blog if you want more detail.

+7
Oct 27 '11 at 19:13
source share

Add this BindingProxy class to your project:

 using System.Windows; namespace YourNameSpace { /// <summary> /// Add Proxy <ut:BindingProxy x:Key="Proxy" Data="{Binding}" /> to Resources /// Bind like <Element Property="{Binding Data.MyValue, Source={StaticResource Proxy}}" /> /// </summary> public class BindingProxy : Freezable { protected override Freezable CreateInstanceCore() { return new BindingProxy(); } public object Data { get { return (object)GetValue(DataProperty); } set { SetValue(DataProperty, value); } } public static readonly DependencyProperty DataProperty = DependencyProperty.Register("Data", typeof(object), typeof(BindingProxy)); } } 
  • Add BindingProxy to UserControl resources.
  • Set the Data property for BindingProxy to everything you need, for example. search parent window. Data="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}},Path=DataContext}" If you need something more complex, you can use your own converter.

You now have access to this parent DataContext: {Binding Data.MyCommand, Source={StaticResource BindingProxy}}

 <UserControl 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" xmlns:common="clr-namespace:YourNameSpace;assembly=YourAssembly" mc:Ignorable="d" d:DesignHeight="300" d:DesignWidth="300"> <UserControl.Resources> <common:BindingProxy x:Key="BindingProxy" Data="{Binding RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}},Path=DataContext}" /> </UserControl.Resources> <Border> <Button Command="{Binding Data.MyCommand, Source={StaticResource BindingProxy}}">Execute My Command</Button> <!-- some visual stuff --> </Border> </UserControl> 
+2
Aug 27 '16 at 4:01
source share

HB answers the question in your title.

However, the text is another design issue. I would ask you to reconsider your design.

The control inherits the DataContext property of its ancestor if none of them explicitly overrides.
If the user control needs data, it should get it from its data source (viewmodel for the user control). Therefore, in this case, the user control can get the data it needs from the ListItemsForDisplay property opened in the SomeViewModel instance. No need to pick up the parent and throw .. much cleaner.

 <ContainerType DataSource={Binding SomeViewModel}> <YourUserControl> <ListBox ItemsSource={Binding ListItemsForDisplay}"/> ... 
+1
Jul 05 2018-11-11T00:
source share



All Articles