如何将命令绑定到祖先数据上下文? WPF::MVVM
How to bind command to ancestor datacontext? WPF :: MVVM
我有一个 ContextMenu
和一个 button
,在 TabControl
里面,我让按钮 Command
可以正常工作,但不知道如何绑定 Context menu items
命令。你能指出我做错了什么吗?
注意:CloseTabCommand
和CloseAllTabsCommand
这两个命令在将它们绑定到按钮时工作正常。
Xaml代码:
<TabControl ItemsSource="{Binding TabItems}">
<TabControl.ItemTemplate>
<DataTemplate>
<DockPanel Width="120" ToolTip="{Binding HeaderText}">
<DockPanel.ContextMenu>
<ContextMenu>
<MenuItem Header="Close Tab"
Command="{Binding DataContext.CloseTabCommand, RelativeSource={RelativeSource AncestorType=TabControl}}"
CommandParameter="{Binding ItemId}" />
<MenuItem Header="Close All Tabs"
Command="{Binding DataContext.CloseAllTabsCommand, RelativeSource={RelativeSource AncestorType=TabControl}}" />
</ContextMenu>
</DockPanel.ContextMenu>
<Button
Command="{Binding DataContext.CloseTabCommand, RelativeSource={RelativeSource AncestorType=TabControl}}"
CommandParameter="{Binding ItemId}"
Content="X"
Cursor="Hand"
DockPanel.Dock="Right"
Focusable="False"
FontFamily="Courier"
FontWeight="Bold"
FontSize="10"
VerticalContentAlignment="Center"
Width="15" Height="15" />
<ContentPresenter Content="{Binding HeaderText}" VerticalAlignment="Center" />
</DockPanel>
</DataTemplate>
</TabControl.ItemTemplate>
<TabControl.ItemContainerStyle>
<Style TargetType="TabItem">
<Setter Property="IsSelected" Value="{Binding IsSelected}" />
</Style>
</TabControl.ItemContainerStyle>
</TabControl>
视图模型代码:
private ObservableCollection<TabItemViewModel> _tabItems;
public ObservableCollection<TabItemViewModel> TabItems {
// if _tabItems is null initiate object.
get { return _tabItems; }
set { SetProperty(ref _tabItems, value); }
}
编辑:
绑定到在 TabItemViewModel
(TabControl ItemsSource) class 中声明的命令可以正常工作。但我想将当前 UserControl
的命令绑定到 ViewModel
您是否尝试过将 AncestorType 绑定到 Window 或 UserControl?
Command="{Binding CloseTabCommand, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=UserControl}}"
将DockPanel的Tag属性绑定到视图模型,然后将MenuItem的Command属性绑定到ContextMenu的PlacementTarget:
<DockPanel Width="120" ToolTip="{Binding HeaderText}"
Tag="{Binding DataContext, RelativeSource={RelativeSource AncestorType=TabControl}}">
<DockPanel.ContextMenu>
<ContextMenu>
<MenuItem Header="Close Tab"
Command="{Binding PlacementTarget.Tag.CloseTabCommand, RelativeSource={RelativeSource AncestorType=ContextMenu}}"
CommandParameter="{Binding ItemId}" />
...
ContextMenu 驻留在它自己的可视树中,这就是为什么您不能使用 RelativeSource 绑定到父 TabControl,因为在可视树中没有父 TabControl。
我有一个 ContextMenu
和一个 button
,在 TabControl
里面,我让按钮 Command
可以正常工作,但不知道如何绑定 Context menu items
命令。你能指出我做错了什么吗?
注意:CloseTabCommand
和CloseAllTabsCommand
这两个命令在将它们绑定到按钮时工作正常。
Xaml代码:
<TabControl ItemsSource="{Binding TabItems}">
<TabControl.ItemTemplate>
<DataTemplate>
<DockPanel Width="120" ToolTip="{Binding HeaderText}">
<DockPanel.ContextMenu>
<ContextMenu>
<MenuItem Header="Close Tab"
Command="{Binding DataContext.CloseTabCommand, RelativeSource={RelativeSource AncestorType=TabControl}}"
CommandParameter="{Binding ItemId}" />
<MenuItem Header="Close All Tabs"
Command="{Binding DataContext.CloseAllTabsCommand, RelativeSource={RelativeSource AncestorType=TabControl}}" />
</ContextMenu>
</DockPanel.ContextMenu>
<Button
Command="{Binding DataContext.CloseTabCommand, RelativeSource={RelativeSource AncestorType=TabControl}}"
CommandParameter="{Binding ItemId}"
Content="X"
Cursor="Hand"
DockPanel.Dock="Right"
Focusable="False"
FontFamily="Courier"
FontWeight="Bold"
FontSize="10"
VerticalContentAlignment="Center"
Width="15" Height="15" />
<ContentPresenter Content="{Binding HeaderText}" VerticalAlignment="Center" />
</DockPanel>
</DataTemplate>
</TabControl.ItemTemplate>
<TabControl.ItemContainerStyle>
<Style TargetType="TabItem">
<Setter Property="IsSelected" Value="{Binding IsSelected}" />
</Style>
</TabControl.ItemContainerStyle>
</TabControl>
视图模型代码:
private ObservableCollection<TabItemViewModel> _tabItems;
public ObservableCollection<TabItemViewModel> TabItems {
// if _tabItems is null initiate object.
get { return _tabItems; }
set { SetProperty(ref _tabItems, value); }
}
编辑:
绑定到在 TabItemViewModel
(TabControl ItemsSource) class 中声明的命令可以正常工作。但我想将当前 UserControl
ViewModel
您是否尝试过将 AncestorType 绑定到 Window 或 UserControl?
Command="{Binding CloseTabCommand, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=UserControl}}"
将DockPanel的Tag属性绑定到视图模型,然后将MenuItem的Command属性绑定到ContextMenu的PlacementTarget:
<DockPanel Width="120" ToolTip="{Binding HeaderText}"
Tag="{Binding DataContext, RelativeSource={RelativeSource AncestorType=TabControl}}">
<DockPanel.ContextMenu>
<ContextMenu>
<MenuItem Header="Close Tab"
Command="{Binding PlacementTarget.Tag.CloseTabCommand, RelativeSource={RelativeSource AncestorType=ContextMenu}}"
CommandParameter="{Binding ItemId}" />
...
ContextMenu 驻留在它自己的可视树中,这就是为什么您不能使用 RelativeSource 绑定到父 TabControl,因为在可视树中没有父 TabControl。