Back to Devexpress

How to Customize a Context Menu with the PopupMenuShowing Event

wpf-401122-controls-and-libraries-pivot-grid-examples-menu-how-to-customize-menu-with-popupmenushowing-event.md

latest13.0 KB
Original Source

How to Customize a Context Menu with the PopupMenuShowing Event

  • Jul 15, 2019
  • 5 minutes to read

This example demonstrates how to use the PivotGridControl.PopupMenuShowing event to add custom items to the built-in context menu.

The event is handled automatically if the field’s AllowFieldSummaryTypeChanging or AllowFieldSummaryDisplayTypeChanging attached properties are true. The properties are defined in the HeaderMenuHelper class.

xaml
<Window x:Class="HeaderMenuCustomizationExample.MainWindow"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:dxpg="http://schemas.devexpress.com/winfx/2008/xaml/pivotgrid"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:local="clr-namespace:HeaderMenuCustomizationExample"
         Title="Data Header Context Menu Customization" Height="450" Width="800"
         Loaded="Window_Loaded">
    <Grid>
        <dxpg:PivotGridControl Name="pivotGridControl1"
                               local:HeaderMenuHelper.AllowPopupMenuCustomization="True"
                               RowTreeWidth="130">

            <dxpg:PivotGridControl.Fields>
                <dxpg:PivotGridField Area="RowArea" FieldName="Name" />
                <dxpg:PivotGridField Area="RowArea" FieldName="Owner" />
                <dxpg:PivotGridField Area="ColumnArea" FieldName="Type" />
                <dxpg:PivotGridField Area="DataArea" FieldName="Value" Name="fieldValue"
                                     local:HeaderMenuHelper.AllowFieldSummaryTypeChanging="True"
                                     local:HeaderMenuHelper.AllowFieldSummaryDisplayTypeChanging="True" />
                <dxpg:PivotGridField Area="DataArea" FieldName="Target" Name="fieldTarget"
                                     local:HeaderMenuHelper.AllowFieldSummaryTypeChanging="True"
                                     local:HeaderMenuHelper.AllowFieldSummaryDisplayTypeChanging="True" />
            </dxpg:PivotGridControl.Fields>

        </dxpg:PivotGridControl>
    </Grid>
</Window>
csharp
using DevExpress.Xpf.Bars;
using DevExpress.Xpf.PivotGrid;
using System;
using System.Reflection;
using System.Windows;

namespace HeaderMenuCustomizationExample
{
    class HeaderMenuHelper
    {
        #region AttachedProperties
        public static readonly DependencyProperty AllowFieldSummaryTypeChangingProperty =
               DependencyProperty.RegisterAttached("AllowFieldSummaryTypeChanging", typeof(Boolean), typeof(HeaderMenuHelper));
        public static void SetAllowFieldSummaryTypeChanging(DependencyObject element, Boolean value)
        {
            element.SetValue(AllowFieldSummaryTypeChangingProperty, value);
        }
        public static Boolean GetAllowFieldSummaryTypeChanging(DependencyObject element)
        {
            return (Boolean)element.GetValue(AllowFieldSummaryTypeChangingProperty);
        }

        public static readonly DependencyProperty AllowFieldSummaryDisplayTypeChangingProperty =
              DependencyProperty.RegisterAttached("AllowFieldSummaryDisplayTypeChanging", typeof(Boolean), typeof(HeaderMenuHelper));
        public static void SetAllowFieldSummaryDisplayTypeChanging(DependencyObject element, Boolean value)
        {
            element.SetValue(AllowFieldSummaryDisplayTypeChangingProperty, value);
        }
        public static Boolean GetAllowFieldSummaryDisplayTypeChanging(DependencyObject element)
        {
            return (Boolean)element.GetValue(AllowFieldSummaryDisplayTypeChangingProperty);
        }

        public static readonly DependencyProperty AllowPopupMenuCustomizationProperty =
              DependencyProperty.RegisterAttached("AllowPopupMenuCustomization", typeof(Boolean), typeof(HeaderMenuHelper),
              new FrameworkPropertyMetadata(false, new PropertyChangedCallback(OnAllowPopupMenuCustomization)));
        public static void SetAllowPopupMenuCustomization(DependencyObject element, Boolean value)
        {
            element.SetValue(AllowPopupMenuCustomizationProperty, value);
        }
        public static Boolean GetAllowPopupMenuCustomization(DependencyObject element)
        {
            return (Boolean)element.GetValue(AllowPopupMenuCustomizationProperty);
        }
        #endregion AttachedProperties

        #region PivotPopupMenuCustomization
        public static void OnAllowPopupMenuCustomization(DependencyObject o, DependencyPropertyChangedEventArgs args)
        {
            PivotGridControl pivotGrid = o as PivotGridControl;
            if (pivotGrid == null) return;
            if( (Boolean)args.NewValue == true && (Boolean)args.OldValue == false )
                pivotGrid.PopupMenuShowing += pivotGrid_PopupMenuShowing;
            else if ( (Boolean)args.NewValue == false && (Boolean)args.OldValue == true )
                pivotGrid.PopupMenuShowing -= pivotGrid_PopupMenuShowing;

        }

        static void pivotGrid_PopupMenuShowing(object sender, PopupMenuShowingEventArgs e)
        {
            if (e.MenuType == PivotGridMenuType.Header)
            {
                PivotGridControl pivot = (PivotGridControl)sender;
                PivotGridField field = e.GetFieldInfo().Field;
                if (Convert.ToBoolean(field.GetValue(HeaderMenuHelper.AllowFieldSummaryTypeChangingProperty)))
                    e.Customizations.Add(CreateBarSubItem("Summary Type", "SummaryType", field));
                if (Convert.ToBoolean(field.GetValue(HeaderMenuHelper.AllowFieldSummaryDisplayTypeChangingProperty)))
                    e.Customizations.Add(CreateBarSubItem("Summary Display Type", "SummaryDisplayType", field));

            }
        }
        #endregion

        #region CustomBarItemsCreation

        private static BarSubItem CreateBarSubItem(string displayText, string propertyName, PivotGridField field)
        {
            BarSubItem barSubItem = new BarSubItem();
            barSubItem.Name = "bsi" + propertyName;
            barSubItem.Content = displayText;

            PropertyInfo property = typeof(PivotGridField).GetProperty(propertyName);

            foreach (object enumValue in Enum.GetValues(property.PropertyType))
            {
                BarCheckItem checkItem = new BarCheckItem();
                checkItem.Name = "bci" + propertyName + enumValue;
                checkItem.Content = enumValue.ToString();
                checkItem.IsChecked = Object.Equals(property.GetValue(field, new object[0]), enumValue);
                checkItem.Tag = new object[] { field, property, enumValue };
                checkItem.ItemClick += itemClickEventHandler;

                barSubItem.ItemLinks.Add(checkItem);
            }
            return barSubItem;
        }

        static void itemClickEventHandler(object sender, ItemClickEventArgs e)
        {
            BarItem barItem = sender as BarItem;
            object[] barItemInfo = (object[])barItem.Tag;
            PivotGridField field = (PivotGridField)barItemInfo[0];
            PropertyInfo property = (PropertyInfo)barItemInfo[1];
            object newValue = barItemInfo[2];
            property.SetValue(field, newValue, new object[0]);

        }
        #endregion CommonMethods
    }
}
vb
Imports DevExpress.Xpf.Bars
Imports DevExpress.Xpf.PivotGrid
Imports System
Imports System.Reflection
Imports System.Windows

Namespace HeaderMenuCustomizationExample
    Friend Class HeaderMenuHelper
        #Region "AttachedProperties"
        Public Shared ReadOnly AllowFieldSummaryTypeChangingProperty As DependencyProperty = DependencyProperty.RegisterAttached("AllowFieldSummaryTypeChanging", GetType(Boolean), GetType(HeaderMenuHelper))
        Public Shared Sub SetAllowFieldSummaryTypeChanging(ByVal element As DependencyObject, ByVal value As Boolean)
            element.SetValue(AllowFieldSummaryTypeChangingProperty, value)
        End Sub
        Public Shared Function GetAllowFieldSummaryTypeChanging(ByVal element As DependencyObject) As Boolean
            Return DirectCast(element.GetValue(AllowFieldSummaryTypeChangingProperty), Boolean)
        End Function

        Public Shared ReadOnly AllowFieldSummaryDisplayTypeChangingProperty As DependencyProperty = DependencyProperty.RegisterAttached("AllowFieldSummaryDisplayTypeChanging", GetType(Boolean), GetType(HeaderMenuHelper))
        Public Shared Sub SetAllowFieldSummaryDisplayTypeChanging(ByVal element As DependencyObject, ByVal value As Boolean)
            element.SetValue(AllowFieldSummaryDisplayTypeChangingProperty, value)
        End Sub
        Public Shared Function GetAllowFieldSummaryDisplayTypeChanging(ByVal element As DependencyObject) As Boolean
            Return DirectCast(element.GetValue(AllowFieldSummaryDisplayTypeChangingProperty), Boolean)
        End Function

        Public Shared ReadOnly AllowPopupMenuCustomizationProperty As DependencyProperty = DependencyProperty.RegisterAttached("AllowPopupMenuCustomization", GetType(Boolean), GetType(HeaderMenuHelper), New FrameworkPropertyMetadata(False, New PropertyChangedCallback(AddressOf OnAllowPopupMenuCustomization)))
        Public Shared Sub SetAllowPopupMenuCustomization(ByVal element As DependencyObject, ByVal value As Boolean)
            element.SetValue(AllowPopupMenuCustomizationProperty, value)
        End Sub
        Public Shared Function GetAllowPopupMenuCustomization(ByVal element As DependencyObject) As Boolean
            Return DirectCast(element.GetValue(AllowPopupMenuCustomizationProperty), Boolean)
        End Function
        #End Region ' AttachedProperties

        #Region "PivotPopupMenuCustomization"
        Public Shared Sub OnAllowPopupMenuCustomization(ByVal o As DependencyObject, ByVal args As DependencyPropertyChangedEventArgs)
            Dim pivotGrid As PivotGridControl = TryCast(o, PivotGridControl)
            If pivotGrid Is Nothing Then
                Return
            End If
            If DirectCast(args.NewValue, Boolean) = True AndAlso DirectCast(args.OldValue, Boolean) = False Then
                AddHandler pivotGrid.PopupMenuShowing, AddressOf pivotGrid_PopupMenuShowing
            ElseIf DirectCast(args.NewValue, Boolean) = False AndAlso DirectCast(args.OldValue, Boolean) = True Then
                RemoveHandler pivotGrid.PopupMenuShowing, AddressOf pivotGrid_PopupMenuShowing
            End If

        End Sub

        Private Shared Sub pivotGrid_PopupMenuShowing(ByVal sender As Object, ByVal e As PopupMenuShowingEventArgs)
            If e.MenuType = PivotGridMenuType.Header Then
                Dim pivot As PivotGridControl = DirectCast(sender, PivotGridControl)
                Dim field As PivotGridField = e.GetFieldInfo().Field
                If Convert.ToBoolean(field.GetValue(HeaderMenuHelper.AllowFieldSummaryTypeChangingProperty)) Then
                    e.Customizations.Add(CreateBarSubItem("Summary Type", "SummaryType", field))
                End If
                If Convert.ToBoolean(field.GetValue(HeaderMenuHelper.AllowFieldSummaryDisplayTypeChangingProperty)) Then
                    e.Customizations.Add(CreateBarSubItem("Summary Display Type", "SummaryDisplayType", field))
                End If

            End If
        End Sub
        #End Region

        #Region "CustomBarItemsCreation"

        Private Shared Function CreateBarSubItem(ByVal displayText As String, ByVal propertyName As String, ByVal field As PivotGridField) As BarSubItem
            Dim barSubItem As New BarSubItem()
            barSubItem.Name = "bsi" & propertyName
            barSubItem.Content = displayText

            Dim [property] As PropertyInfo = GetType(PivotGridField).GetProperty(propertyName)

            For Each enumValue As Object In System.Enum.GetValues([property].PropertyType)
                Dim checkItem As New BarCheckItem()
                checkItem.Name = "bci" + propertyName.ToString() + enumValue.ToString()
                checkItem.Content = enumValue.ToString()
                checkItem.IsChecked = Object.Equals([property].GetValue(field, New Object(){}), enumValue)
                checkItem.Tag = New Object() { field, [property], enumValue }
                AddHandler checkItem.ItemClick, AddressOf itemClickEventHandler

                barSubItem.ItemLinks.Add(checkItem)
            Next enumValue
            Return barSubItem
        End Function

        Private Shared Sub itemClickEventHandler(ByVal sender As Object, ByVal e As ItemClickEventArgs)
            Dim barItem As BarItem = TryCast(sender, BarItem)
            Dim barItemInfo() As Object = DirectCast(barItem.Tag, Object())
            Dim field As PivotGridField = DirectCast(barItemInfo(0), PivotGridField)
            Dim [property] As PropertyInfo = DirectCast(barItemInfo(1), PropertyInfo)
            Dim newValue As Object = barItemInfo(2)
            [property].SetValue(field, newValue, New Object(){})

        End Sub
        #End Region ' CommonMethods
    End Class
End Namespace