WPF MenuItem.Command 绑定到 ElementName 结果到 System.Windows.Data 错误:4:无法找到带有引用的绑定源 [英] WPF MenuItem.Command binding to ElementName results to System.Windows.Data Error: 4 : Cannot find source for binding with reference

查看:22
本文介绍了WPF MenuItem.Command 绑定到 ElementName 结果到 System.Windows.Data 错误:4:无法找到带有引用的绑定源的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有以下 XAML:

<树视图x:Name="TOCTreeView"背景=白色"填充="3,5"ContextMenuOpening="TOCTreeView_ContextMenuOpening"ItemsSource="{Binding Children}" BorderBrush="{x:Null}" ><TreeView.ItemTemplate><HierarchicalDataTemplate ItemsSource="{Binding Path=Children, Mode=OneTime}"><网格><Grid.ColumnDefinitions><ColumnDefinition Width="自动"/><!--<ColumnDefinition Width="Auto"/>--><ColumnDefinition Width="*"/></Grid.ColumnDefinitions><!--<CheckBox VerticalAlignment="Center" IsChecked="{Binding IsVisible}"/>--><ContentPresenter Grid.Column="0" Height="16" Width="20"Content="{Binding LayerRepresentation}"/><!--<ContentPresenter Grid.Column="1" ><ContentPresenter.Content>测试</ContentPresenter.Content></ContentPresenter>--><TextBlock Grid.Column="2" FontWeight="Normal" Text="{Binding Path=Alias, Mode=OneWay}" ><工具提示服务.工具提示><TextBlock Text="{绑定描述}" TextWrapping="Wrap"/></ToolTipService.ToolTip></TextBlock></网格><HierarchicalDataTemplate.ItemTemplate><HierarchicalDataTemplate ItemsSource="{Binding Path=Children, Mode=OneTime}"><!--<数据模板>--><网格><Grid.ColumnDefinitions><ColumnDefinition Width="自动"/><ColumnDefinition Width="自动"/><ColumnDefinition Width="*"/></Grid.ColumnDefinitions><CheckBox VerticalAlignment="Center" IsChecked="{Binding IsVisible}"/><ContentPresenter Grid.Column="1"Content="{Binding LayerRepresentation, Mode=OneWay}"/><TextBlock Margin="0,1,0,1" Text="{Binding Path=Alias, Mode=OneWay}" Grid.Column="2"><工具提示服务.工具提示><TextBlock Text="{绑定描述}" TextWrapping="Wrap"/></ToolTipService.ToolTip></TextBlock></网格><!--</DataTemplate>--></HierarchicalDataTemplate></HierarchicalDataTemplate.ItemTemplate></HierarchicalDataTemplate></TreeView.ItemTemplate><TreeView.ContextMenu><上下文菜单><MenuItem Name="miRemove" Header="Remove"命令="{绑定元素名称=根,路径=RemoveItemCmd,诊断:PresentationTraceSources.TraceLevel=High}"><菜单项.图标><Image Source=".​​./images/16x16/Delete.png"/></MenuItem.Icon></菜单项><MenuItem Header="属性"Command="{Binding ElementName=root, Path=GetItemPropertiesCmd}"/></ContextMenu></TreeView.ContextMenu></树视图></用户控件>

此 UserControl 背后的代码具有两个 ICommand 属性,名称为:RemoveItemCmd 和 GetItemPropertiesCmd.但是,我得到

<块引用><前>System.Windows.Data 错误:4:无法找到引用ElementName=root"的绑定源.BindingExpression:Path=RemoveItemCmd;数据项=空;目标元素是 'MenuItem' (Name='miRemove');目标属性是命令"(类型ICommand")System.Windows.Data 错误:4:无法找到引用ElementName=root"的绑定源.BindingExpression:Path=GetItemPropertiesCmd;数据项=空;目标元素是 'MenuItem' (Name='');目标属性是命令"(类型ICommand")

构造 UserControl 时.这是为什么,我该如何解决?

解决方案

您不能使用上下文菜单中的元素名称进行绑定.上下文菜单与其放置目标之间的链接已断开.不过,您可以使用一些技巧来解决它...

  1. 将 RoutedUICommands 与 UserControl 上的命令绑定一起使用,则不需要绑定.
  2. 在上下文菜单的 DataContext 上使用放置目标绑定.这允许您至少获得上下文菜单出现在上下文菜单上的元素的数据上下文.

    DataContext="{Binding RelativeSource={RelativeSource Mode=Self}, Path=PlacementTarget.DataContext}"

  3. (我认为这就是您想要的)您可以访问静态资源,ElementSpy 允许您使用静态资源链接到窗口,以便您可以使用事实上的 ElementName 绑定.

I have the following XAML:

<UserControl x:Class="EMS.Controls.Dictionary.TOCControl"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:vm="clr-namespace:EMS.Controls.Dictionary.Models"
    xmlns:diagnostics="clr-namespace:System.Diagnostics;assembly=WindowsBase"
    x:Name="root"  >

    <TreeView                    
        x:Name="TOCTreeView"                    
        Background="White"
         Padding="3,5"      
        ContextMenuOpening="TOCTreeView_ContextMenuOpening"
        ItemsSource="{Binding Children}" BorderBrush="{x:Null}"  >

        <TreeView.ItemTemplate>
            <HierarchicalDataTemplate ItemsSource="{Binding Path=Children, Mode=OneTime}">
                <Grid >
                    <Grid.ColumnDefinitions>
                        <ColumnDefinition Width="Auto"/>
                        <!--<ColumnDefinition Width="Auto"/>-->                       
                        <ColumnDefinition Width="*"/>
                    </Grid.ColumnDefinitions>
                    <!--<CheckBox VerticalAlignment="Center" IsChecked="{Binding IsVisible}"/>-->   
                    <ContentPresenter Grid.Column="0" Height="16" Width="20"
                                    Content="{Binding LayerRepresentation}"  />
                    <!--<ContentPresenter Grid.Column="1"      >
                        <ContentPresenter.Content>
                            Test
                        </ContentPresenter.Content>
                    </ContentPresenter>-->
                    <TextBlock Grid.Column="2" FontWeight="Normal" Text="{Binding Path=Alias, Mode=OneWay}" >
                        <ToolTipService.ToolTip>
                            <TextBlock Text="{Binding Description}" TextWrapping="Wrap"/>
                        </ToolTipService.ToolTip>
                    </TextBlock>
                </Grid>
                <HierarchicalDataTemplate.ItemTemplate>
                    <HierarchicalDataTemplate ItemsSource="{Binding Path=Children, Mode=OneTime}">
                        <!--<DataTemplate>-->
                        <Grid >
                            <Grid.ColumnDefinitions>
                                <ColumnDefinition Width="Auto"/>
                                <ColumnDefinition Width="Auto"/>                               
                                <ColumnDefinition Width="*"/>
                            </Grid.ColumnDefinitions>
                            <CheckBox VerticalAlignment="Center" IsChecked="{Binding IsVisible}"/>
                            <ContentPresenter Grid.Column="1"
                                    Content="{Binding LayerRepresentation, Mode=OneWay}"  />
                            <TextBlock Margin="0,1,0,1" Text="{Binding Path=Alias, Mode=OneWay}" Grid.Column="2">
                                <ToolTipService.ToolTip>
                                    <TextBlock Text="{Binding Description}" TextWrapping="Wrap"/>
                                </ToolTipService.ToolTip>                   
                            </TextBlock>
                        </Grid>
                        <!--</DataTemplate>-->
                    </HierarchicalDataTemplate>                  
                </HierarchicalDataTemplate.ItemTemplate>
            </HierarchicalDataTemplate>
        </TreeView.ItemTemplate> 

        <TreeView.ContextMenu>
            <ContextMenu>
                <MenuItem Name="miRemove" Header="Remove"
                          Command="{Binding ElementName=root, Path=RemoveItemCmd, 
                    diagnostics:PresentationTraceSources.TraceLevel=High}">
                    <MenuItem.Icon>
                        <Image Source="../images/16x16/Delete.png"/>
                    </MenuItem.Icon>
                </MenuItem>
                <MenuItem Header="Properties"
                          Command="{Binding ElementName=root, Path=GetItemPropertiesCmd}"/>               
            </ContextMenu>       
        </TreeView.ContextMenu>


    </TreeView>

</UserControl>

Code behind for this UserControl has two ICommand properties with names: RemoveItemCmd and GetItemPropertiesCmd. However, I get

System.Windows.Data Error: 4 : Cannot find source for binding with reference 'ElementName=root'. BindingExpression:Path=RemoveItemCmd; DataItem=null; target element is 'MenuItem' (Name='miRemove'); target property is 'Command' (type 'ICommand')
System.Windows.Data Error: 4 : Cannot find source for binding with reference 'ElementName=root'. BindingExpression:Path=GetItemPropertiesCmd; DataItem=null; target element is 'MenuItem' (Name=''); target property is 'Command' (type 'ICommand')

when UserControl is constructed. Why is this and how do I resolve?

解决方案

You can't bind using element name from a context menu. The link is broken between the context menu and its placement target. You can get around it using a couple of tricks though...

  1. Use RoutedUICommands with a command binding on the UserControl, then no binding is needed.
  2. Use the placement target binding on the context menu's DataContext. This allows you to at least get the data context of the element the context menu appears on to the context menu.

    DataContext="{Binding RelativeSource={RelativeSource Mode=Self}, Path=PlacementTarget.DataContext}"

  3. (and i think this is what you want) You can access a static resource, ElementSpy lets you link to the window using a static resource so you can then use a defacto ElementName bindings.

这篇关于WPF MenuItem.Command 绑定到 ElementName 结果到 System.Windows.Data 错误:4:无法找到带有引用的绑定源的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆