I want to display either no context menu or a single item or two items in the context menu. I am using the MVVM pattern.
I have tried linking the context menu visibility to a bool property, this appears to work, but an empty context menu is rendered behind the current control, and becomes visible once the current control is closed. I've tried adding a data trigger bound to the same property - but this does not get fired. examining the visual tree shows that the default property is set for the context menu.
MenuItem Visibility works fine, so I can get 1 or 2 items displaying. But when No context menu is needed, a blank menu appears behind
Note: same results with Visibility Hidden or Collapsed
The context menu is bound to a DataGrid as a static resource:
RowStyle="{StaticResource PagedGridRowStyle}"
<ContextMenu x:Key="BlankMenu" Visibility="Hidden">
</ContextMenu>
<ContextMenu x:Key="PagedGridMenu"
Visibility="{Binding Path=DataContext.ContextMenuEnabled, RelativeSource={RelativeSource AncestorType=UserControl}, Converter={StaticResource VisConverter}}"
DataContext="{Binding PlacementTarget.DataContext, RelativeSource={RelativeSource Self}}">
<MenuItem Header="{Binding Path=DataContext.MenuActionName1, RelativeSource={RelativeSource AncestorType=UserControl}}"
Visibility="{Binding Path=DataContext.ContextMenuEnabled, RelativeSource={RelativeSource AncestorType=UserControl}, Converter={StaticResource VisConverter}}"
CommandParameter="{Binding RelativeSource={RelativeSource AncestorType=UserControl}, Path=DataContext}"
Command="{Binding Path=DataContext.MenuActionCommand1, RelativeSource={RelativeSource AncestorType=UserControl}}"/>
<MenuItem Header="{Binding Path=DataContext.MenuActionName2, RelativeSource={RelativeSource AncestorType=UserControl}}"
Visibility="{Binding Path=DataContext.ContextMenu2Enabled, RelativeSource={RelativeSource AncestorType=UserControl}, Converter={StaticResource VisConverter}}"
CommandParameter="{Binding RelativeSource={RelativeSource AncestorType=UserControl}, Path=DataContext}"
Command="{Binding Path=DataContext.MenuActionCommand2, RelativeSource={RelativeSource AncestorType=UserControl}}"/>
</ContextMenu>
<Style x:Key="PagedGridRowStyle"
TargetType="{x:Type DataGridRow}">
<Setter Property="ContextMenu"
Value="{StaticResource PagedGridMenu}"/>
<Style.Triggers>
<DataTrigger Binding="{Binding ContextMenuEnabled}" Value="false">
<Setter Property="ContextMenu" Value="{StaticResource BlankMenu}"/>
</DataTrigger>
</Style.Triggers>
</Style>
Note VisConverter simply toggles Visibility.Visible and Visibility.Collapsed on the boolean value
Style.Triggers - above: This is an attempt to replace the complete context menu - to try to avoid the blank context menu opening behind control. - but it doesn't get fired.
private bool _contextMenu2Enabled;
public bool ContextMenu2Enabled
{
get => _contextMenu2Enabled;
set
{
_contextMenu2Enabled = value;
OnPropertyChanged();
}
}
private bool _contextMenuEnabled;
public bool ContextMenuEnabled
{
get => _contextMenuEnabled;
set
{
_contextMenuEnabled = value;
OnPropertyChanged();
}
}
Binding Error:
When ContextMenuEnabled = false: (and ContextMenu2Enabled = false)
System.Windows.Data Error: 40 : BindingExpression path error: 'ContextMenuEnabled' property not found on 'object' ''DataRowView' (HashCode=33440573)'. BindingExpression:Path=ContextMenuEnabled; DataItem='DataRowView' (HashCode=33440573); target element is 'DataGridRow' (Name=''); target property is 'NoTarget' (type 'Object')
The Context menu does not appear, but an empty context menu is rendered behind the datagrid, and becomes visible after the datagrid is closed
When ContextMenuEnabled = true (and ContextMenu2Enabled = false) Same BindingExpression Error - but the context menu shows a single item as expected.
When ContextMenuEnabled = true and ContextMenu2Enabled = true Same BindingExpression error, - but Both Context menu items are shown as expected.
ContextMenuEnabled
property defined? And why don't you just set theContextProperty
tonull
instead of setting it to an empty menu with no items:<Setter Property="ContextMenu" Value="{x:Null}"/>
? - mm8ContextMenuEnabled
is on the ViewModel . Thanks for informing me about{x:Null}
I now know how to nullify in xaml :) And I changed the data trigger binding toBinding="{Binding DataContext.ContextMenuEnabled, RelativeSource={RelativeSource AncestorType=UserControl}}"
which has solved the problem and fixed the BindingExpression Errors - TomFp