views:

27

answers:

1

Here's the top of my usercontrol:

<UserControl x:Class="MyApp.Common.Controls.Views.SimpleView"
             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:Framework="http://www.memoryexpress.com/UIFramework"
             mc:Ignorable="d" 
             Height="130" Width="450"
             x:Name="Master"
             >
    <!-- Behaviour under the context of the generic dialog -->
    <Framework:DialogMetadata.Instance>
        <Framework:DialogMetadata SizeToContent="WidthAndHeight" 
                                  ResizeMode="NoResize" 
                                  ConfirmCommand="{Binding ConfirmCommand, RelativeSource={RelativeSource FindAncestor,AncestorType={x:Type UserControl}}}"
                                  ConfirmButtonText="Run"/>
    </Framework:DialogMetadata.Instance>

Long story short, I've got a UserControl, and I've defined an attached property: DialogMetadata.Instance that takes an object of type DialogMetadata. This construct is just a list of attached properties for me to use if I ever launch this control as a stand-alone dialog.

This all works for the most part, I've got it picking up the SizeToContent, ResizeMode, and ConfirmButtonText.

However, In the spirit of MVVM I want to pass this command along to the dialog to be executed when we click the Confirm Button. So as you can see I've attempted to bind the Command off the ViewModel into the DialogMetadata's ConfirmCommand DependencyProperty.

The DP Is Defined like this:

    #region DP - ConfirmCommand

    public static DependencyProperty ConfirmCommandProperty =
        DependencyProperty.Register("ConfirmCommand", typeof (IBaseCommand), typeof (DialogMetadata),
                                    new PropertyMetadata(null));

    /// <summary>
    /// The Confirmation Command for a dialog. This allows us to sync up to the user-control for 
    /// determining if we can can hit the Ok Button, and to perform additional logic
    /// </summary>
    public virtual IBaseCommand ConfirmCommand
    {
        get { return GetValue(ConfirmCommandProperty) as IBaseCommand; }
        set { SetValue(ConfirmCommandProperty, value); }
    }

    #endregion

However when I bind up like in the first code block: (Note: The Property 'ConfirmCommand' Exists on the data-context of the UserControl, and has a non-null value.)

Binding

{Binding ConfirmCommand, RelativeSource={RelativeSource FindAncestor,AncestorType={x:Type UserControl}}}

Error

System.Windows.Data Error: 4 : Cannot find source for binding with reference 'RelativeSource FindAncestor, AncestorType='System.Windows.Controls.UserControl', AncestorLevel='1''. BindingExpression:Path=ConfirmCommand; DataItem=null; target element is 'DialogMetadata' (Name=''); target property is 'ConfirmCommand' (type 'IBaseCommand')

Binding

{Binding ConfirmCommand, ElementName=Master}

Error

System.Windows.Data Error: 4 : Cannot find source for binding with reference 'ElementName=Master'. BindingExpression:Path=ConfirmCommand; DataItem=null; target element is 'DialogMetadata' (Name=''); target property is 'ConfirmCommand' (type 'IBaseCommand')


Anyone have any insight into what's going on with my bindings?

+1  A: 

"Cannot find source for binding"

I suspect that Framework:DialogMetadata's datacontext is not your ViewModel. You should check that and if its not you need to pass the datacontext of your UserControl to to DialogMetaData.

I must admit I don't correctly understand <Framework:DialogMetadata.Instance> stuff so I am just trying to point out the symptoms rather than the disease. :D

NVM
Hrm, maybe your right, even so, the first binding points to a relative source which should locate the UserControl. It can't find the usercontrol to bind to it's DataContext.The Framework:DialogMetadata.Instance is just an attached property, it's similar to ` Framework:DialogMetadata.Instance="{something here}"` but since I need to specify an object, it's pulled out into a Tag
Aren
Aaah... so its not exactly a view in a view. In that case are you sure that a DialogMetaData's parent is indeed UserControl?? Its just defined in an attached property, its not a child of the UserControl.
NVM
DataContext={Binding ElementName=Master, Path=DataContext}
NVM
`ElementName` didn't work. I managed to get it working through a sort of "hack". I made a new DP on the DialogMetadata called `ParentElement` and assigned it when the AttachedProperty was set. Then I used binding: `{Binding RelativeSource={RelativeSource Self}, Path=ParentElement.DataContext.ConfirmCommand}` It's a bit of a hack, but it works for now. If you can think of a way to simplify it, I'd be grateful.
Aren
DataContext={Binding ElementName=Master, Path=DataContext} does adding this to <Framework:DialogMetadata ...> not work? I suspect it should. It will also be a lot cleaner.
NVM
The Binding Engine cannot locate `ElementName=Master` no matter what I do (In fact, the only reason `x:Name="Master"` was on that control was for this exact purpose. It was the first thing I tried)
Aren
Hmm. I guess the binding engine can only work with elements in the visual tree. Anyway if its any consolation I did a similar hack to pass a 'conceptual' parent to an element just the way you did. Cheers!
NVM