问题描述
我知道之前曾有人问过这个问题,但是我无法解决最少的代码示例。我要求对整件事进行审查。
我有一个WPF DataGrid,它显示了一堆行。每行都有一个右键单击ContextMenu及其自己的命令。
我无法正确使用ContextMenu部分。抱怨“ ContextMenu不能具有逻辑或可视的父级。”任何帮助将不胜感激。
谢谢。
-
XAML文件:
<DataGrid ItemsSource="{Binding MyModules}" AutoGenerateColumns="False"> <!-- Begin uncertain part --> <ContextMenu ItemsSource="{Binding Configuration.Commands}"> <ContextMenu.ItemContainerStyle> <Style targettype="x:Type ContextMenuItem"> <Setter Property="Command" Value="Binding Command}" /> </Style> </ContextMenu.ItemContainerStyle> </ContextMenu> <!-- End uncertain part --> <DataGrid.Columns> <DataGridTemplateColumn Header="Module Name" Width="*" IsReadOnly="True"> <DataGridTemplateColumn.CellTemplate> <DataTemplate> <TextBlock Text="{Binding Configuration.Name}" /> </DataTemplate> </DataGridTemplateColumn.CellTemplate> </DataGridTemplateColumn> <DataGridTemplateColumn Header="Module Description" Width="3*" IsReadOnly="True"> <DataGridTemplateColumn.CellTemplate> <DataTemplate> <TextBlock Text="{Binding Configuration.Description}" /> </DataTemplate> </DataGridTemplateColumn.CellTemplate> </DataGridTemplateColumn> </DataGrid.Columns>
-
public ObservableCollection<IModule> MyModules { get; set; } // ... public interface IModule { Configuration Configuration { get; } void ExecuteCommand(Command command); } public class Configuration { public Guid Id { get; private set; } public string Name { get; private set; } public string Description { get; private set; } public List<Command> Commands = new List<Command>(); public Configuration(string name,string description,List<Command> commands) { Id = new Guid(); Name = name; Description= description; Commands = commands; } }
编辑1:
我从很多地方拿来样品。现在可以编译了。但是,右键单击上下文菜单是完全空白的。
<DataGrid ItemsSource="{Binding MyModules}" AutoGenerateColumns="False">
<DataGrid.Columns>
<DataGridTemplateColumn Header="Configuration Name" Width="*" IsReadOnly="True">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding Configuration.Name}">
<TextBlock.ContextMenu>
<ContextMenu ItemsSource="{Binding Configuration.Commands}">
<ContextMenu.ItemContainerStyle>
<Style targettype="MenuItem">
<Setter Property="Command" Value="{Binding ItemAction}" />
<Setter Property="Header" Value="{Binding ItemHeader}" />
</Style>
</ContextMenu.ItemContainerStyle>
</ContextMenu>
</TextBlock.ContextMenu>
</TextBlock>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
<DataGridTemplateColumn Header="Description" Width="3*" IsReadOnly="True">
<DataGridTemplateColumn.CellTemplate>
<DataTemplate>
<TextBlock Text="{Binding Configuration.MainMenuDescription}">
<TextBlock.ContextMenu>
<ContextMenu ItemsSource="{Binding Configuration.Commands}">
<ContextMenu.ItemContainerStyle>
<Style targettype="MenuItem">
<Setter Property="Command" Value="{Binding ItemAction}" />
<Setter Property="Header" Value="{Binding ItemHeader}" />
</Style>
</ContextMenu.ItemContainerStyle>
</ContextMenu>
</TextBlock.ContextMenu>
</TextBlock>
</DataTemplate>
</DataGridTemplateColumn.CellTemplate>
</DataGridTemplateColumn>
</DataGrid.Columns>
</DataGrid>
尽管我不太喜欢第二种方法。我必须为每列重复ContextMenu标记...
解决方法
您可以定义一个ItemContainerStyle
,在其中为所有行设置ContextMenu
属性:
<DataGrid ItemsSource="{Binding MyModules}" AutoGenerateColumns="False">
<DataGrid.ItemContainerStyle>
<Style TargetType="DataGridRow">
<Setter Property="ContextMenu">
<Setter.Value>
<ContextMenu ItemsSource="{Binding Configuration.Commands}">
<ContextMenu.ItemContainerStyle>
<Style TargetType="{x:Type ContextMenuItem}">
<Setter Property="Command" Value="{Binding Command}" />
</Style>
</ContextMenu.ItemContainerStyle>
</ContextMenu>
</Setter.Value>
</Setter>
</Style>
</DataGrid.ItemContainerStyle>
<DataGrid.Columns>
...
</DataGrid.Columns>
</DataGrid>