C# WPF:将ListBox ContextMenu的命令参数绑定到ListBox的选定项
是否可以将列表框上下文菜单的命令参数绑定到列表框的选定项?我应该说ContCommand在主窗口中,在单击上下文菜单项时调用它-但是,我需要让参数正常工作 我尝试了此操作,但绑定失败:C# WPF:将ListBox ContextMenu的命令参数绑定到ListBox的选定项,c#,wpf,data-binding,listbox,C#,Wpf,Data Binding,Listbox,是否可以将列表框上下文菜单的命令参数绑定到列表框的选定项?我应该说ContCommand在主窗口中,在单击上下文菜单项时调用它-但是,我需要让参数正常工作 我尝试了此操作,但绑定失败: <Window x:Class="ListBoxContextMenu.MainWindow" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.
<Window x:Class="ListBoxContextMenu.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:ListBoxContextMenu"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<StackPanel>
<TextBlock Text="ListBox here:"/>
<ListBox ItemsSource="{Binding Items}" MinHeight="100" TabIndex="0" x:Name="LB">
<ListBox.ContextMenu>
<ContextMenu>
<MenuItem Header="Foo" Command="{Binding ContCommand}" CommandParameter="{Binding RelativeSource={RelativeSource AncestorType={x:Type ListBox}},Path=SelectedItem}"/>
</ContextMenu>
</ListBox.ContextMenu>
</ListBox>
</StackPanel>
</Grid>
</Window>
主窗口的C#代码:
using System.Collections.ObjectModel;
using System.Windows;
using System.Windows.Input;
using MvvmFoundation.Wpf;
namespace ListBoxContextMenu
{
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
DataContext = this;
Loaded += (sender, e) => MoveFocus(new TraversalRequest(FocusNavigationDirection.Next));
ContCommand = new RelayCommand<object>((object o) =>
{
System.Diagnostics.Debug.WriteLine("Context Menu pressed");
});
}
public ObservableCollection<string> Items { get; set; } = new ObservableCollection<string>{"Fred", "Jim", "Sheila"};
public RelayCommand<object> ContCommand { get; set; }
}
}
使用System.Collections.ObjectModel;
使用System.Windows;
使用System.Windows.Input;
使用MvvmFoundation.Wpf;
名称空间ListBoxContextMenu
{
公共部分类主窗口:窗口
{
公共主窗口()
{
初始化组件();
DataContext=this;
Loaded+=(发送方,e)=>MoveFocus(新的遍历请求(FocusNavigationDirection.Next));
CONTCOMAND=新的RelayCommand((对象o)=>
{
System.Diagnostics.Debug.WriteLine(“按下上下文菜单”);
});
}
公共ObservableCollection项{get;set;}=新的ObservableCollection{“Fred”、“Jim”、“Sheila”};
public RelayCommand ContCommand{get;set;}
}
}
上下文菜单位于另一棵树上,因此根据具体情况,绑定很棘手。这里有两个选项:
1
通过列表框的名称绑定到列表框,例如
Binding SelectedItem, ElementName=LB
2使用引用名称
有时元素名称绑定失败,必须使用x:ref名称(您已经使用了)
至于原因,请引用 在WPF和XAML2006中,元素引用由ElementName绑定的框架级特性处理。对于大多数WPF应用程序和场景,仍应使用ElementName绑定。本一般指南的例外情况可能包括数据上下文或其他范围考虑因素导致数据绑定不切实际以及不涉及标记编译的情况
将
Mode=FindAncestor
添加到RelativeSource
绑定中
CommandParameter="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ListBox}}, Path=SelectedItem}"
ListBox
不是ContextMenu
的可视祖先,因为后者位于自己的可视树中
但是您可以绑定到上下文菜单
的位置目标
,即列表框
这项工作:
<ListBox ItemsSource="{Binding Items}" MinHeight="100" TabIndex="0" x:Name="LB">
<ListBox.ContextMenu>
<ContextMenu>
<MenuItem Header="Foo" Command="{Binding ContCommand}"
CommandParameter="{Binding RelativeSource={RelativeSource AncestorType={x:Type ContextMenu}},
Path=PlacementTarget.SelectedItem}"/>
</ContextMenu>
</ListBox.ContextMenu>
</ListBox>
将其绑定到已单击的listboxitem,而不是绑定到listbox 他是最关心的人!!不是列表框,他持有你正在寻找的对象
<ListBox x:Name="lstAllTags" FocusVisualStyle="{x:Null}" ItemsSource="{Binding ResearchedTagsResult}" Margin="0" Background="{x:Null}" BorderBrush="{x:Null}" ItemTemplate="{DynamicResource SearchTagDataTemplate}" FontFamily="Consolas" Foreground="{DynamicResource {x:Static SystemColors.InfoBrushKey}}" MouseMove="LstAllTags_MouseMove" MouseLeave="LstAllTags_MouseLeave" HorizontalContentAlignment="Stretch" Focusable="False" FontSize="13" SelectionChanged="LstTags_SelectionChanged" BorderThickness="0">
<ListBox.Resources>
<!--Defines a context menu-->
<ContextMenu x:Key="ContextMenu">
<MenuItem Command="{Binding DeleteTagCmd }" CommandParameter="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ListBoxItem}}, Path=DataContext}" Foreground="{DynamicResource AppTextForeground}" DataContext="{DynamicResource TagManagement_instance}" Header="Edit" BorderBrush="#FF919191" BorderThickness="0" Padding="0">
<MenuItem.Icon>
<Image Source="/Resx/pencil.png"/>
</MenuItem.Icon>
</MenuItem>
</ContextMenu>
</ListBox.Resources>
</ListBox>
删除代码示例中的非相关项。例如使用/命名空间
和窗口属性的。只需关注阅读它的人的完整部分。
会产生绑定错误:System.Windows.Data错误:4:找不到引用“ElementName=LB”的绑定源。BindingExpression:Path=SelectedItem;DataItem=null;目标元素是“MenuItem”(名称=“”);目标属性为“CommandParameter”(类型为“Object”)@AdrianS您是否尝试过x:reference绑定?x:reference绑定导致引发异常:System.Windows.Markup.XamlParseException:'由于循环依赖关系,无法调用MarkupExtension.ProvideValue。MarkupExtension内的属性不能引用引用MarkupExtension结果的对象。受影响的标记扩展名是:“System.Windows.Data.Binding”行号“18”和行位置“80”System.Windows.Data错误:4:找不到引用为“RelativeSource FindAncestor,AncestorType='System.Windows.Controls.ListBox',AncestorLevel='1'的绑定源。BindingExpression:Path=SelectedItem;DataItem=null;目标元素是“MenuItem”(名称=“”);目标属性为“CommandParameter”(类型为“Object”)
<ListBox x:Name="lstAllTags" FocusVisualStyle="{x:Null}" ItemsSource="{Binding ResearchedTagsResult}" Margin="0" Background="{x:Null}" BorderBrush="{x:Null}" ItemTemplate="{DynamicResource SearchTagDataTemplate}" FontFamily="Consolas" Foreground="{DynamicResource {x:Static SystemColors.InfoBrushKey}}" MouseMove="LstAllTags_MouseMove" MouseLeave="LstAllTags_MouseLeave" HorizontalContentAlignment="Stretch" Focusable="False" FontSize="13" SelectionChanged="LstTags_SelectionChanged" BorderThickness="0">
<ListBox.Resources>
<!--Defines a context menu-->
<ContextMenu x:Key="ContextMenu">
<MenuItem Command="{Binding DeleteTagCmd }" CommandParameter="{Binding RelativeSource={RelativeSource Mode=FindAncestor, AncestorType={x:Type ListBoxItem}}, Path=DataContext}" Foreground="{DynamicResource AppTextForeground}" DataContext="{DynamicResource TagManagement_instance}" Header="Edit" BorderBrush="#FF919191" BorderThickness="0" Padding="0">
<MenuItem.Icon>
<Image Source="/Resx/pencil.png"/>
</MenuItem.Icon>
</MenuItem>
</ContextMenu>
</ListBox.Resources>
</ListBox>