Search code examples
visual-studio-2010idevb.net-2010visual-studio-macros

Can I Programatically Modify the IDE's Context Menu's?


I am trying to create an additional menu item for the "Project and Solutions Context Menus>Solution" menu. However, I wanted this context menu to appear ONLY when a certain solution was opened, otherwise I don't want it to show. I figured I could use the MACROS within the Visual Studio IDE. There are events that run on the opening of solutions & projects, etc.

My question is, can I create the Context Menu I want programatically, point it to the MACRO I want it to run, and then programatically attach it to the CONTEXT menu inside the IDE that I want to display it in?


Solution

  • I found the answer to my question. I used the following code to create the menu items I needed:

    Private WithEvents _objSolutionExplorer_ContextMenu_ItemHandler As EnvDTE.CommandBarEvents
    Private _objHash_ContextMenuItemHandlers As New Hashtable
    
    Private Function CreateContextMenuButtonItem(ByVal p_objMenuItem As Object, ByVal p_strMenuItemCaption As String) As CommandBarButton
        '************************************************************************
        ' Procedure/Function: CreateContextMenuButtonItem()
        ' Author: Ben Santiago
        ' Created On: 08/18/2011
        ' Description:
        '       Creates specified MenuButton item.
        '************************************************************************
    
        '***************************************
        ' Initialize Variables
        '***************************************
        Dim objMenuButton As CommandBarButton
        Dim objClickEventHandler As EnvDTE.CommandBarEvents
    
        '***************************************
        ' If MenuItem Exists, Delete It
        '***************************************
        For intCounter As Integer = 1 To p_objMenuItem.Controls.Count
            If p_objMenuItem.Controls.Item(intCounter).Caption = p_strMenuItemCaption Then
                p_objMenuItem.Controls.Item(intCounter).Delete()
                Exit For
            End If
        Next
        If EnvironmentEvents._objHash_ContextMenuItemHandlers.Contains(p_strMenuItemCaption) Then
            EnvironmentEvents._objHash_ContextMenuItemHandlers.Remove(p_strMenuItemCaption)
        End If
    
        '***************************************
        ' Create New Menu Item w/ Click Event Handling
        '***************************************
        objNewMenuItem = p_objMenuItem.Controls.Add(MsoControlType.msoControlButton, System.Reflection.Missing.Value, System.Reflection.Missing.Value, 1, True)
        objNewMenuItem.Caption = p_strMenuItemCaption
        objClickEventHandler = DTE.Events.CommandBarEvents(objNewMenuItem)
        AddHandler objClickEventHandler.Click, AddressOf TestScoring_objSolutionExplorer_ContextMenu_ItemHandler_Click
        If EnvironmentEvents._objHash_ContextMenuItemHandlers.Contains(p_strMenuItemCaption) Then
            EnvironmentEvents._objHash_ContextMenuItemHandlers.Remove(p_strMenuItemCaption)
        End If
        EnvironmentEvents._objHash_ContextMenuItemHandlers.Add(p_strMenuItemCaption, objClickEventHandler)
    
        '***************************************
        ' Return Reference To MenuButton Item
        '***************************************
        Return objNewMenuItem
    End Function
    
    Private Function CreateContextMenuPopupItem(ByVal p_strCommandBarName As String, ByVal p_strMenuCaption As String) As CommandBarPopup
        '************************************************************************
        ' Procedure/Function: CreateContextMenuPopupItem()
        ' Author: Ben Santiago
        ' Created On: 08/18/2011
        ' Description:
        '       Creates specified MenuPopup item.
        '************************************************************************
    
        '***************************************
        ' Initialize Variables
        '***************************************
        Dim objCommandBar As CommandBar = DTE.CommandBars(p_strCommandBarName)
        Dim objMenuPopup As CommandBarPopup
    
        '***************************************
        ' Search For Existing ContextMenuPopup
        '***************************************
        For intCounter As Integer = 1 To objCommandBar.Controls.Count
            If objCommandBar.Controls.Item(intCounter).Caption = p_strMenuCaption Then
                objMenuPopup = objCommandBar.Controls.Item(intCounter)
                Exit For
            End If
        Next
    
        If objMenuPopup Is Nothing Then
            '***************************************
            ' Create Menu If Needed
            '***************************************
            objMenuPopup = objCommandBar.Controls.Add(MsoControlType.msoControlPopup, System.Reflection.Missing.Value, System.Reflection.Missing.Value, 1, True)
            objMenuPopup.Caption = p_strMenuCaption
        Else
            '***************************************
            ' Delete All Child Menu Items
            '***************************************
            For intCounter As Integer = objMenuPopup.Controls.Count To 1 Step -1
                If EnvironmentEvents._objHash_ContextMenuItemHandlers.Contains(objMenuPopup.Controls.Item(intCounter).Caption) Then
                    EnvironmentEvents._objHash_ContextMenuItemHandlers.Remove(objMenuPopup.Controls.Item(intCounter).Caption)
                End If
                objMenuPopup.Controls.Item(intCounter).Delete()
            Next
        End If
    
        '***************************************
        ' Return Reference To MenuPopup Item
        '***************************************
        Return objMenuPopup
    End Function