Context Menus
- 8 minutes to read
The GridControl can display pop-up menus that allow users to manage data (apply grouping and sorting, display summaries, and so on) and customize the View (show or hide its UI elements). These context menus can be customized.
Context Menus Overview
To obtain the context menu displayed within a View, use the GridViewBase.GridMenu property.
Customize Context Menus
In XAML
Use the View’s properties:
Menu Type | Property |
---|---|
TableView TableView.CompactModeFilterElementMenuCustomizations | |
TreeListView TreeListView.CompactModeFilterElementMenuCustomizations TreeListView.CompactModeFilterMergeElementMenuCustomizations |
These properties return a BarManagerActionCollection object (bar items, links, and actions).
In Code
Handle the DataViewBase.ShowGridMenu event.
Examples
Bind to a Column, Row, and TableView in RowCellMenuCustomizations
To bind a cell’s context menu to a column, row, or TableView, use the default binding source or the attached GridPopupMenu.GridMenuInfo property.
<Window ...
xmlns:dxg="http://schemas.devexpress.com/winfx/2008/xaml/grid"
xmlns:dxb="http://schemas.devexpress.com/winfx/2008/xaml/bars">
<!-- ... -->
<dxg:TableView Tag="Test value">
<dxg:TableView.RowCellMenuCustomizations>
<dxb:BarButtonItem Content="{Binding Path=Column.FieldName}" />
<dxb:BarButtonItem Content="{Binding Path=Row.Row.Name}" />
<dxb:BarButtonItem Content="{Binding Path=View.Tag}" />
</dxg:TableView.RowCellMenuCustomizations>
</dxg:TableView>
<!-- OR -->
<dxg:TableView Tag="Test value">
<dxg:TableView.RowCellMenuCustomizations>
<dxb:BarButtonItem Content="{Binding Path=(dxg:GridPopupMenu.GridMenuInfo).Column.FieldName, RelativeSource={RelativeSource Self}}" />
<dxb:BarButtonItem Content="{Binding Path=(dxg:GridPopupMenu.GridMenuInfo).Row.Row.Name, RelativeSource={RelativeSource Self}}" />
<dxb:BarButtonItem Content="{Binding Path=(dxg:GridPopupMenu.GridMenuInfo).View.Tag, RelativeSource={RelativeSource Self}}" />
</dxg:TableView.RowCellMenuCustomizations>
</dxg:TableView>
Rename Standard Menu Items
The following example renames the “Customize…” item in the summary panel:
In XAML
Use the bar‘s UpdateAction and specify the item name.
<dxg:TableView.TotalSummaryMenuCustomizations>
<dxb:UpdateAction ElementName="{x:Static dxg:DefaultSummaryMenuItemNames.Customize}" PropertyName="Content" Value="Edit..." />
</dxg:TableView.TotalSummaryMenuCustomizations>
In Code
Subscribe to the DataViewBase.ShowGridMenu event and change the item name.
<dxg:TableView ShowGridMenu="ShowGridMenu" />
using DevExpress.Xpf.Grid;
using DevExpress.Xpf.Bars;
//...
void ShowGridMenu(object sender, GridMenuEventArgs e) {
if (e.MenuType != GridMenuType.TotalSummary)
return;
BarItem item = e.Items.FirstOrDefault(x => x.Name == DefaultSummaryMenuItemNames.Customize);
if (item != null)
item.Content = "Edit...";
}
Add Cell and Column Menu Items to a Column
In XAML
Use the RowCellMenuCustomizations/ColumnMenuCustomizations properties and binding paths from the Bind to a Column, Row, and TableView in RowCellMenuCustomizations example.
<Window.Resources>
<dxmvvm:ObjectToObjectConverter x:Key="fieldNameToVisibleConverter" DefaultTarget="False">
<dxmvvm:MapItem Source="Visits" Target="True" />
</dxmvvm:ObjectToObjectConverter>
</Window.Resources>
...
<dxg:TableView>
<dxg:TableView.RowCellMenuCustomizations>
<dxb:BarButtonItem Content="Item 1" IsVisible="{Binding Column.FieldName, Converter={StaticResource fieldNameToVisibleConverter}}" />
</dxg:TableView.RowCellMenuCustomizations>
<dxg:TableView.ColumnMenuCustomizations>
<dxb:BarButtonItem Content="Item 2" IsVisible="{Binding Column.FieldName, Converter={StaticResource fieldNameToVisibleConverter}}" />
</dxg:TableView.ColumnMenuCustomizations>
</dxg:TableView>
In Code
Subscribe to the DataViewBase.ShowGridMenu event and specify e.MenuInfo.Column.FieldName in the event handler.
<dxg:TableView ShowGridMenu="TableView_ShowGridMenu" />
void TableView_ShowGridMenu(object sender, GridMenuEventArgs e) {
if (e.MenuInfo.Column.FieldName != "Visits")
return;
switch (e.MenuType) {
case GridMenuType.RowCell:
e.Customizations.Add(new BarButtonItem { Content = "Item 1" });
break;
case GridMenuType.Column:
e.Customizations.Add(new BarButtonItem { Content = "Item 2" });
break;
}
}
Show Different Cell Menu Items Depending on a Property Value
The following example demonstrates how to show the row cell’s context menu item if you sort data against the current column:
In XAML
Use RowCellMenuCustomizations and binding paths from the Bind to a Column, Row, and TableView in RowCellMenuCustomizations example.
<dxg:TableView>
<dxg:TableView.RowCellMenuCustomizations>
<dxb:BarButtonItem Content="Item 1" IsVisible="{Binding Column.IsSorted}" />
<dxb:BarButtonItem Content="Item 2" />
</dxg:TableView.RowCellMenuCustomizations>
</dxg:TableView>
In Code
Subscribe to the DataViewBase.ShowGridMenu event and get column objects from e.MenuInfo.
<dxg:TableView ShowGridMenu="TableView_ShowGridMenu" />
void TableView_ShowGridMenu(object sender, GridMenuEventArgs e)
{
if (e.MenuType != GridMenuType.RowCell)
return;
GridCellMenuInfo info = (GridCellMenuInfo)e.MenuInfo;
ColumnBase item = (ColumnBase)info.Column;
if (item.IsSorted)
e.Customizations.Add(new BarButtonItem { Content = "Item 1" });
e.Customizations.Add(new BarButtonItem { Content = "Item 2" });
}
Show Different Cell Menu Items Depending on a Node Level
The following example demonstrates how to show a row cell’s context menu for a node level:
In XAML
Use the RowCellMenuCustomizations property and bind the BarItem.IsVisible property to the current node’s level.
<Window.Resources>
<dxmvvm:ObjectToObjectConverter x:Key="levelToVisibleConverter" DefaultTarget="False">
<dxmvvm:MapItem Source="1" Target="True" />
</dxmvvm:ObjectToObjectConverter>
</Window.Resources>
...
<dxg:TreeListView>
<dxg:TreeListView.RowCellMenuCustomizations>
<dxb:BarButtonItem Content="Item 1" IsVisible="{Binding Row.Level, Converter={StaticResource levelToVisibleConverter}}" />
</dxg:TreeListView.RowCellMenuCustomizations>
</dxg:TreeListView>
In Code
Subscribe to the DataViewBase.ShowGridMenu event and get the current node from the e.MenuInfo object.
<dxg:TreeListView ShowGridMenu="TreeListView_ShowGridMenu" />
void TreeListView_ShowGridMenu(object sender, GridMenuEventArgs e) {
if (e.MenuType != GridMenuType.RowCell)
return;
GridCellMenuInfo info = (GridCellMenuInfo)e.MenuInfo;
TreeListRowData rowData = (TreeListRowData)info.Row;
if (rowData.Level == 1)
e.Customizations.Add(new BarButtonItem { Content = "Item 1" });
}
Remove Menu Items
The following example removes an item from the Total Summary panel‘s context menu:
In XAML
Add the RemoveBarItemAndLinkAction object to the DataViewBase.TotalSummaryMenuCustomizations collection. Specify the BarItemActionBase.ItemName property with the menu item name from the DefaultSummaryMenuItemNames class.
<dxg:TableView.TotalSummaryMenuCustomizations>
<dxb:RemoveBarItemAndLinkAction ItemName="{x:Static dxg:DefaultSummaryMenuItemNames.Customize}"/>
</dxg:TableView.TotalSummaryMenuCustomizations>
In Code
Handle the DataViewBase.ShowGridMenu event.
<dxg:TableView ShowGridMenu="ShowGridMenu"/>
void ShowGridMenu(object sender, GridMenuEventArgs e) {
if (e.MenuType == GridMenuType.TotalSummary) {
e.Customizations.Add(new RemoveAction { ElementName = DefaultSummaryMenuItemNames.Customize });
}
}
Add Menu Items to a Specific Position
The following example demonstrates how to add a custom menu item to a grid column’s context menu:
In XAML
Add a bar item (for example, BarCheckItem) to the DataViewBase.ColumnMenuCustomizations collection and specify item properties. Attach the BarItemLinkActionBase.ItemLinkIndex property to this item to insert it into a specific position.
<dxg:TableView.ColumnMenuCustomizations>
<dxb:BarCheckItem Content="Checked" IsChecked="True" dxb:BarItemLinkActionBase.ItemLinkIndex="0"/>
<dxb:BarItemLinkSeparator dxb:BarItemLinkActionBase.ItemLinkIndex="1"/>
</dxg:TableView.ColumnMenuCustomizations>
In Code
Handle the ShowGridMenu event.
<dxg:TableView ShowGridMenu="ShowGridMenu"/>
void ShowGridMenu(object sender, GridMenuEventArgs e) {
if (e.MenuType == GridMenuType.Column) {
BarCheckItem item1 = new BarCheckItem { Content = "Checked", IsChecked = true };
BarItemLinkActionBase.SetItemLinkIndex(item1, 0);
e.Customizations.Add(item1);
BarItemLinkSeparator item2 = new BarItemLinkSeparator();
BarItemLinkActionBase.SetItemLinkIndex(item2, 1);
e.Customizations.Add(item2);
}
}
Add Custom Row Cell’s Context Menu
This example shows how to define a cell’s context menu. The context menu allows users to delete a row or copy its data to the clipboard.
<dxg:GridControl.View>
<dxg:TableView x:Name="view" AutoWidth="True">
<dxg:TableView.RowCellMenuCustomizations>
<dxb:BarButtonItem Name="deleteRowItem" Content="Delete"
IsEnabled="{Binding Row.Row.CanBeDeleted}"
ItemClick="OnDeleteRow"/>
<dxb:BarButtonItem Name="copyCellDataItem" Content="Copy"
ItemClick="OnCopyRow" />
</dxg:TableView.RowCellMenuCustomizations>
</dxg:TableView>
</dxg:GridControl.View>
void OnCopyRow(object sender, ItemClickEventArgs e) {
if (view.GridMenu.MenuInfo is GridCellMenuInfo menuInfo && menuInfo.Row != null)
grid.CopyCurrentItemToClipboard();
}
void OnDeleteRow(object sender, ItemClickEventArgs e) {
if (view.GridMenu.MenuInfo is GridCellMenuInfo menuInfo && menuInfo.Row != null)
view.DeleteRow(menuInfo.Row.RowHandle.Value);
}
Add a Context Menu to an Empty Grid
The following example shows how to add a context menu for an empty GridControl:
- Create the BarManager.DXContextMenu object.
- Create a new instance of the PopupMenu class and assign it to the BarManager.DXContextMenu object.
- Add bar items (for example, BarButtonItem objects) to the PopupMenu.Items collection.
<Window xmlns:dxg="http://schemas.devexpress.com/winfx/2008/xaml/grid"
xmlns:dxb="http://schemas.devexpress.com/winfx/2008/xaml/bars">
<dxg:GridControl ...>
<dxb:BarManager.DXContextMenu>
<dxb:PopupMenu>
<dxb:PopupMenu.Items>
<dxb:BarButtonItem Content="Item 1"/>
<dxb:BarButtonItem Content="Item 2"/>
</dxb:PopupMenu.Items>
</dxb:PopupMenu>
</dxb:BarManager.DXContextMenu>
</dxg:GridControl>
</Window>
Disable all the GridControl’s Context Menus
If you do not want to display any of the GridControl‘s context menus, follow the steps below:
- Handle the DataViewBase.ShowGridMenu event.
- In the event handler, set the e.Handled property to true.
<dxg:GridControl.View>
<dxg:TableView ShowGridMenu="view_ShowGridMenu"/>
</dxg:GridControl.View>