向菜单添加子菜单

本演练基于“向 Visual Studio 菜单栏添加菜单”中的演示为基础,演示如何向 TestMenu 菜单添加子菜单

子菜单是另一个菜单中显示的辅助菜单。 子菜单可由其名称后面的箭头标识。 单击该名称会导致显示子菜单及其命令。

本演练在 Visual Studio 菜单栏的菜单中创建子菜单,并在子菜单中添加新命令。 该演练还实现了新命令。

向菜单添加子菜单

  1. 按照“向 Visual Studio 菜单栏添加菜单”中的步骤创建项目和菜单项。 本演练中的步骤假定 VSIX 项目的名称为 TopLevelMenu.

  2. 打开 TestCommandPackage.vsct。 在 <Symbols> 节中,为子菜单添加一个 <IDSymbol> 元素,一个用于子菜单组,一个用于命令,所有节点都 <GuidSymbol> 名为“guidTopLevelMenuCmdSet”。这是包含 <IDSymbol> 顶级菜单元素的同一节点。

    <IDSymbol name="SubMenu" value="0x1100"/>
    <IDSymbol name="SubMenuGroup" value="0x1150"/>
    <IDSymbol name="cmdidTestSubCommand" value="0x0105"/>
    
  3. 将新创建的子菜单添加到 <Menus> 节。

    <Menu guid="guidTestCommandPackageCmdSet" id="SubMenu" priority="0x0100" type="Menu">
        <Parent guid="guidTestCommandPackageCmdSet" id="MyMenuGroup"/>
        <Strings>
            <ButtonText>Sub Menu</ButtonText>
            <CommandName>Sub Menu</CommandName>
        </Strings>
    </Menu>
    

    父级的 GUID/ID 对指定在“向 Visual Studio 菜单栏添加菜单”中生成的菜单组,并且是顶级菜单的子级。

  4. 将步骤 2 中定义的菜单组添加到 <Groups> 分区,并将其设为子菜单的子菜单。

    <Group guid="guidTestCommandPackageCmdSet" id="SubMenuGroup" priority="0x0000">
        <Parent guid="guidTestCommandPackageCmdSet" id="SubMenu"/>
    </Group>
    
  5. 将新 <Button> 元素添加到 <Buttons> 节,以将步骤 2 中创建的命令定义为子菜单上的项。

    <Button guid="guidTestCommandPackageCmdSet" id="cmdidTestSubCommand" priority="0x0000" type="Button">
        <Parent guid="guidTestCommandPackageCmdSet" id="SubMenuGroup" />
        <Icon guid="guidImages" id="bmpPic2" />
        <Strings>
           <CommandName>cmdidTestSubCommand</CommandName>
           <ButtonText>Test Sub Command</ButtonText>
        </Strings>
    </Button>
    
  6. 生成解决方案并开始调试。 应会看到实验实例。

  7. 单击 TestMenu 可查看名为“子菜单” 的新子菜单。 单击“子菜单”打开子菜单,并查看新命令“测试子命令”。 请注意,单击“测试子命令不会执行任何操作。

添加命令

  1. 打开 TestCommand.cs ,并在现有命令 ID 后面添加以下命令 ID。

    public const int cmdidTestSubCmd = 0x0105;
    
  2. 添加子命令。 查找命令构造函数。 在调用 AddCommand 方法后添加以下行。

    CommandID subCommandID = new CommandID(CommandSet, cmdidTestSubCmd);
    MenuCommand subItem = new MenuCommand(new EventHandler(SubItemCallback), subCommandID);
    commandService.AddCommand(subItem);
    

    稍后 SubItemCallback 将定义命令处理程序。 构造函数现在应如下所示:

    private TestCommand(Package package)
    {
        if (package == null)
        {
            throw new ArgumentNullException("package");
        }
    
        this.package = package;
    
        OleMenuCommandService commandService = this.ServiceProvider.GetService(typeof(IMenuCommandService)) as OleMenuCommandService;
        if (commandService != null)
        {
            var menuCommandID = new CommandID(CommandSet, CommandId);
            var menuItem = new MenuCommand(this.MenuItemCallback, menuCommandID);
            commandService.AddCommand(menuItem);
    
            CommandID subCommandID = new CommandID(CommandSet, cmdidTestSubCmd);
            MenuCommand subItem = new MenuCommand(new EventHandler(SubItemCallback), subCommandID);
            commandService.AddCommand(subItem);
        }
    }
    
  3. 添加 SubItemCallback()。 这是单击子菜单中的新命令时调用的方法。

    private void SubItemCallback(object sender, EventArgs e)
    {
        ThreadHelper.ThrowIfNotOnUIThread();
        IVsUIShell uiShell = this.package.GetService<SVsUIShell, IVsUIShell>();
        Guid clsid = Guid.Empty;
        int result;
        uiShell.ShowMessageBox(
            0,
            ref clsid,
            "TestCommand",
            string.Format(CultureInfo.CurrentCulture,
            "Inside TestCommand.SubItemCallback()",
            this.ToString()),
            string.Empty,
            0,
            OLEMSGBUTTON.OLEMSGBUTTON_OK,
            OLEMSGDEFBUTTON.OLEMSGDEFBUTTON_FIRST,
            OLEMSGICON.OLEMSGICON_INFO,
            0,
            out result);
    }
    
  4. 生成项目并启动调试。 应显示实验实例。

  5. 在 TestMenu 菜单上,单击“子菜单”,然后单击“测试子命令”。 此时会显示消息框并显示文本“Test Command Inside TestCommand.SubItemCallback()”。