Freigeben über


Gewusst wie: Erstellen und behandeln Sie Befehle in VSPackages (C#)

Hinzufügen eines Befehls in einem VSPackage ist ein zwei Schritte. Zuerst wird der Befehl wie ein XML-Element in der .vsct-Datei definiert. Anschließend wird es im Code implementiert werden. Die Informationen, die in die .vsct-Datei eingegeben werden, bestimmen die Darstellung des Befehls, dessen Position in der integrierten Entwicklungsumgebung (IDE) und einige seiner Verhalten. Der Befehl wird dann im Code, in der Regel als MenuCommand oder OleMenuCommand-Objekt definiert, und seine Ereignishandler implementiert werden.

Die Befehle, die ein VSPackage der IDE verfügbar macht, müssen sichtbar und aktiviert werden, bevor der Benutzer sie verwenden können. Wenn Befehle in einer .vsct-Datei erstellt werden, indem Sie die Projektvorlage Visual Studio-Paket verwendet, sind sie sichtbar und standardmäßig aktiviert. Das Festlegen einiger Befehls Flags fest, wie DynamicItemStart, kann das Standardverhalten ändern. Die Sichtbarkeit, der aktivierte Status und andere Eigenschaften eines Befehls können im Code auch zur Laufzeit geändert werden, indem das OleMenuCommand-Objekt zugreift, das dem Befehl zugeordnet ist.

Erstellen eines Befehls

Alle Befehle, Befehlsgruppen, Menüs, Symbolleisten und Toolfenster werden in der .vsct-Datei definiert. Wenn ein VSPackage über keine .vsct-Datei verfügt, müssen Sie ein hinzufügen. Weitere Informationen finden Sie unter (Visual Studio-Befehls-Tabelle. Dateien Vsct).

Wenn Sie ein VSPackage erstellen, indem Sie die Vorlage Paket verwenden, wählen Sie Menübefehl aus, um eine .vsct-Datei zu erstellen und einen Menübefehl zu definieren. Weitere Informationen finden Sie unter Exemplarische Vorgehensweise: Wenn Sie einen Menübefehl mit der Visual Studio-Paket-Vorlage erstellen.

So fügen Sie einen Befehl Hinzufügen der IDE

  1. Öffnen Sie die .vsct-Datei.

  2. Im Abschnitt Symbols Suchen Sie das GuidSymbol-Element, das die Gruppen und die Befehle enthält.

  3. Erstellen Sie ein IDSymbol-Element für jedes Menü oder Gruppe, die Sie hinzufügen möchten, wie im folgenden Beispiel gezeigt.

    <GuidSymbol name="guidButtonGroupCmdSet" value="{f69209e9-975a-4543-821d-1f4a2c52d737}">
      <IDSymbol name="MyMenuGroup" value="0x1020" />
      <IDSymbol name="cmdidMyCommand" value="0x0100" />
    </GuidSymbol>
    

    Die name-Attribute der GuidSymbol und IDSymbol-Elemente stellen die GUID: ID-Paare für jedes neue Menü Gruppe oder Command. guid stellt ein Befehl dar, der für ein VSPackage definiert ist. Sie können mehrere Befehle definieren legt ihn fest. Jedes GUID: ID-Paare müssen eindeutig sein.

  4. Im Schaltflächen-Abschnitt erstellen Sie ein Schaltfläche-Element, um den Befehl, wie im folgenden Beispiel gezeigt definiert.

    <Button guid="guidButtonGroupCmdSet" id="cmdidMyCommand" priority="0x0100" type="Button">
      <Parent guid="guidButtonGroupCmdSet" id="MyMenuGroup" />
      <Icon guid="guidImages" id="bmpPic1" />
      <Strings>
        <CommandName>cmdidMyCommand</CommandName>
        <ButtonText>My Command name</ButtonText>
      </Strings>
    </Button>
    
    1. Legen Sie die guid und id Felder fest, um die GUID entspricht: ID des neuen Befehls.

    2. Legen Sie das priority-Attribut fest.

      Das priority-Attribut wird vom .vsct verwendet, um die Position der Schaltfläche unter den anderen Objekten in seiner übergeordneten Gruppe zu bestimmen.

      Befehle, die Werte mit niedrigerer Priorität aufweisen, werden oben oder auf der linken Seite Befehle angezeigt, die prioritärere Werte aufweisen. Doppelte Werte für Priorität sind zulässig, aber die relative Position von Befehlen, die dieselbe Priorität haben, wird durch die Reihenfolge bestimmt, in der VSPackages zur Laufzeit verarbeitet werden und in der Reihenfolge nicht vorbestimmt werden kann.

      Das Weglassen des priority-Attributs dessen Wert auf 0 fest.

    3. Legen Sie das type-Attribut fest. In den meisten Fällen ist der Wert „Button“. Die Beschreibungen anderer gültiger Schaltflächen Typen finden Sie unter Button-Element.

  5. In der Definition der Schaltflächen erstellen Sie ein Zeichenfolgen-Element, das ein ButtonText-Element enthält den Namen des Menüs, wie es in der IDE angezeigt wird, und CommandName-Elements enthalten soll, um den Namen des Befehls, der verwendet wird, um das Befehl im Menü Fenster zuzugreifen.

    Wenn die Schaltflächen Textzeichenfolge dem Namen „&„- Zeichen enthält, kann der Benutzer das Menü zu öffnen, indem er ALT sowie das Zeichen“&drückt, das unmittelbar folgt.“

    Das Hinzufügen eines Tooltip enthaltenden Elements bewirkt, dass der Text, der angezeigt wird, wenn ein Benutzer den Mauszeiger auf die Schaltfläche zeigt.

  6. Fügen Sie ein Symbol-Element hinzu, um das Symbol anzugeben, wenn mit dem Befehl angezeigt werden soll. Symbole sind für Schaltflächen auf Symbolleisten, jedoch nicht für Menüelemente erforderlich. guid und id des Icon-Elements müssen die Bitmap eines Elements übereinstimmen, das im Bitmaps-Abschnitt definiert wird.

  7. Fügen Sie ggf. Flags für Befehle hinzu, um die Darstellung und das Verhalten der Schaltfläche zu ändern. Hierzu fügen Sie ein CommandFlag-Element in der Definition des Menüs hinzu.

  8. Legen Sie für die übergeordnete Gruppe des Befehls fest. Die übergeordnete Gruppe kann eine Gruppe, die Sie erstellen, eine Gruppe von einem anderen Paket oder eine Gruppe über die IDE sein. Um beispielsweise den Befehl Symbolleiste Studio-Bearbeitungs Visual Kommentar neben den Kommentar entfernen Schaltflächen hinzuzufügen, und legen das übergeordnete Element an das guidStdEditor fest: IDG_VS_EDITTOOLBAR_COMMENT. Wenn das übergeordnete Element eine benutzerdefinierte Gruppe ist, muss es sich dabei um das untergeordnete Element eines Menüs der Symbolleiste oder des Toolfensters darstellen, das in der IDE angezeigt wird.

    Dazu haben Sie zwei Möglichkeiten, abhängig vom Entwurf vorgehen:

    • Im Button-Element erstellen Sie ein Das übergeordnete Element-Element, und legen Sie dessen guid und id Felder GUID und ID der Gruppe, die den Host der Befehl wird auch als primäre übergeordneten Gruppefestgelegt.

      Das folgende Beispiel definiert einen Befehl, der bei einem benutzerdefinierten Menü dargestellt wird.

      <Button guid="guidTopLevelMenuCmdSet" id="cmdidTestCommand" priority="0x0100" type="Button">
        <Parent guid="guidTopLevelMenuCmdSet" id="MyMenuGroup" />
        <Icon guid="guidImages" id="bmpPic1" />
        <Strings>
          <CommandName>cmdidTestCommand</CommandName>
          <ButtonText>Test Command</ButtonText>
        </Strings>
      </Button>
      
    • Sie lassen möglicherweise das Parent-Element weg, wenn der Befehl positioniert werden soll, indem er der Befehls verwendet. Erstellen Sie ein CommandPlacements-Element vor dem Symbols-Abschnitt, und fügen Sie ein CommandPlacement-Element, das guid und id des Befehls, der priorityund des übergeordneten Elements hat. Dies wird im folgenden Beispiel veranschaulicht.

      <CommandPlacements>
        <CommandPlacement guid="guidButtonGroupCmdSet" id="cmdidMyCommand" priority="0x105">
          <Parent guid="guidButtonGroupCmdSet" id="MyMenuGroup" />
        </CommandPlacement>
      </CommandPlacements>
      

      Mehrere Befehls platzierungen erstellen, die das gleiche GUID aufweisen: ID und verfügt über verschiedene Ursachen der übergeordneten Elemente, um ein Menü an mehreren Stellen angezeigt wird. Weitere Informationen finden Sie unter CommandPlacements-Element.

    Weitere Informationen über Befehlsgruppen und Parenting finden Sie unter Gewusst wie: Erstellen von wiederverwendbaren Gruppen Schaltflächen.

An diesem Punkt ist der Befehl in der IDE angezeigt, jedoch hat keine Funktion. Wenn der Befehl von der Vorlage Paket erstellt wurde, verfügt sie standardmäßig auf einen Handler, der eine Meldung angezeigt.

Behandeln des neuen Befehl

Die meisten Befehle in verwaltetem Code kann durch das verwaltete Paketframework (MPF), indem Sie den Befehl mit einem MenuCommand-Objekt oder OleMenuCommand-Objekt zuweisen und ihre Ereignishandler behandelt werden.

Für Code, der die IOleCommandTarget-Schnittstelle nicht direkt für Befehls Klassenbehandlung verwendet, müssen Sie die IOleCommandTarget-Schnittstelle und ihre Methoden implementieren. Die beiden wichtigsten Methoden sind QueryStatus und Exec.

Um den neuen Befehl mithilfe von MPF behandeln

  1. Rufen Sie die OleMenuCommandService-Instanz, so wie im folgenden Beispiel gezeigt.

    OleMenuCommandService mcs = 
        GetService(typeof(IMenuCommandService)) as OleMenuCommandService;
    
  2. Erstellen Sie ein CommandID-Objekt, das als Parameter die GUID und ID des Befehls zu behandeln, wie im folgenden Beispiel gezeigt.

    CommandID menuCommandID = 
        new CommandID(GuidList.guidButtonGroupCmdSet, 
            (int)PkgCmdIDList.cmdidMyCommand);
    

    Die Visual Studio-Paket GuidList Vorlage stellt zwei Auflistungen, und PkgCmdIDList, um die GUID und ID der Befehle enthält. Diese werden automatisch für Befehle aufgefüllt, die von der Vorlage hinzugefügt werden, aber für Befehle, die Sie manuell hinzufügen, müssen Sie den Eintrag ID der PkgCmdIdList-Klasse hinzufügen.

    Alternativ können Sie das CommandID-Objekt auffüllen, indem Sie den unformatierten Zeichenfolgenwert des GUIDs und den ganzzahligen Wert der ID verwenden

  3. Instanziieren Sie entweder MenuCommand oder OleMenuCommand-Objekt, das die Methode, die den Befehl zusammen mit CommandIDbehandelt, wie im folgenden Beispiel gezeigt angibt.

    MenuCommand menuItem = 
        new MenuCommand(MenuItemCallback, menuCommandID);
    

    MenuCommand ist für statische Befehle geeignet. Bei dynamischen Menüelements angezeigt werden QueryStatus-Ereignishandler benötigen. OleMenuCommand fügt das BeforeQueryStatus-Ereignis, das auftritt, wenn das Hosten des Befehls im Menü geöffnet wird, und eine Reihe weiterer Eigenschaften, z. B. Texthinzu.

    Die Befehle, die von der Vorlage erstellten Paket werden standardmäßig in einen OleMenuCommand-Objekt in der Initialize()-Methode der Paket Klasse übergeben.

  4. MenuCommand ist für statische Befehle geeignet. Bei dynamischen Menüelements angezeigt werden QueryStatus-Ereignishandler benötigen. OleMenuCommand fügt das BeforeQueryStatus-Ereignis, das auftritt, wenn das Hosten des Befehls im Menü geöffnet wird, und eine Reihe weiterer Eigenschaften, z. B. Texthinzu.

    Die Befehle, die von der Vorlage erstellten Paket werden standardmäßig in einen OleMenuCommand-Objekt in der Initialize()-Methode der Paket Klasse übergeben. Der Visual Studio-Assistent implementiert die Initialize-Methode, indem er MenuCommandverwendet. Bei dynamischen Menüelements angezeigt werden müssen Sie dies auf OleMenuCommandändern, wie im nächsten Schritt gezeigt. Darüber hinaus Menüelement um den Text zu ändern, müssen Sie ein TextChanges-Befehls flag der Schaltfläche Menübefehls in der .vsct-Datei hinzufügen, wie im folgenden Beispiel gezeigt wird

    <Button guid="guidMenuTextCmdSet" id="cmdidMyCommand" priority="0x0100" type="Button">
      <Parent guid="guidMenuTextCmdSet" id="MyMenuGroup" />
      <Icon guid="guidImages" id="bmpPic1" />
      <CommandFlag>TextChanges</CommandFlag>
      <Strings>
        <CommandName>cmdidMyCommand</CommandName>
        <ButtonText>My Command name</ButtonText>
      </Strings>
    </Button>
    
  5. Führen Sie den neuen Menübefehl für die AddCommand-Methode in der IMenuCommandService-Schnittstelle. Dies ist standardmäßig für die Befehle erstellt, die durch die Vorlage Paket, wie im folgenden Beispiel gezeigt erstellt werden

    mcs.AddCommand( menuItem );
    
  6. Implementieren Sie die Methode, die den Befehl behandelt.

So implementieren MPF-Klassen mithilfe der QueryStatus

  1. Das QueryStatus-Ereignis tritt ein, bevor ein Befehl angezeigt wird. Dadurch können Eigenschaften dieses Befehls, festgelegter im Ereignishandler zu sein, bevor der Benutzer erreicht. ONLY-Befehle, die OleMenuCommand-Objekte hinzugefügt werden, während dieser Methode zugreifen können.

    Fügen Sie ein EventHandler-Objekt, das BeforeQueryStatus-Ereignis im OleMenuCommand das erstellte Objekt, um den Befehl zu behandeln, wie im folgenden Beispiel gezeigt hinzu (menuItem ist die OleMenuCommand-Instanz).

    Dim menuCommandID As CommandID = New CommandID(GuidList.guidMenuTextCmdSet, CInt(PkgCmdIDList.cmdidMyTextCommand))
    Dim menuItem As OleMenuCommand = New OleMenuCommand(New EventHandler(AddressOf MenuItemCallback), menuCommandID)
    AddHandler menuItem.BeforeQueryStatus, AddressOf OnBeforeQueryStatus
    mcs.AddCommand(menuItem)
    
    // Create the command for the menu item.
    CommandID menuCommandID = new CommandID(GuidList.guidMenuTextCmdSet, (int)PkgCmdIDList.cmdidMyCommand);
    OleMenuCommand menuItem = new OleMenuCommand(MenuItemCallback, menuCommandID );
    menuItem.BeforeQueryStatus +=
        new EventHandler(OnBeforeQueryStatus);
    mcs.AddCommand(menuItem);
    

    Das EventHandler-Objekt ist der Name einer Methode angegeben, die aufgerufen wird, wenn sich der Status des Menübefehls abgefragt wird.

  2. Implementieren Sie die Abfragen status-Handler Methode für den Befehl. Der Parameter object sender kann zu einem OleMenuCommand-Objekt, das verwendet wird, um verschiedene Attribute des Menübefehls festzulegen, einschließlich der Text umgewandelt werden. Von der folgenden Tabelle werden die Eigenschaften auf der MenuCommand an die MPF-Klasse OleMenuCommand-Klasse (abgeleitet), die den OLECMDF-Flags entsprechen.

    MenuCommand-Eigenschaft

    OLECMDF-Flag

    Checked = true

    OLECMDF_LATCHED

    Visible = false

    OLECMDF_INVISIBLE

    Enabled = true

    OLECMDF_ENABLED

    Um den Text eines Menübefehls zu ändern, verwenden Sie die Text-Eigenschaft auf dem OleMenuCommand-Objekt, wie im folgenden Beispiel gezeigt.

    Private Sub OnBeforeQueryStatus(ByVal sender As Object, ByVal e As EventArgs)
        Dim myCommand As OleMenuCommand = TryCast(sender, OleMenuCommand)
        If myCommand IsNot Nothing Then
            myCommand.Text = "New Text" 
        End If 
    End Sub
    
    private void OnBeforeQueryStatus(object sender, EventArgs e)
    {
        var myCommand = sender as OleMenuCommand;
        if (null != myCommand)
        {
            myCommand.Text = "New Text";
        }
    }
    

Das MPF behandelt automatisch den Fall nicht unterstützt oder unbekannter Gruppen. Sofern ein Befehl OleMenuCommandService hinzugefügt wurde, indem die AddCommand-Methode, wird der Befehl nicht unterstützt.

Behandlungs-Befehle mithilfe der IOleCommandTarget-Schnittstelle

Für Code, der die IOleCommandTarget-Schnittstelle nicht direkt verwendet, muss ein VSPackage das QueryStatus und die Exec-Methode der IOleCommandTarget-Schnittstelle implementieren. Wenn ein VSPackage einer Projekthierarchie implementiert, sollte das QueryStatusCommand und die ExecCommand-Methode der IVsUIHierarchy-Schnittstelle implementiert werden.

QueryStatus sind die Methoden und die Exec im Hinblick auf einen einzelnen Befehl Menge GUID und ein Array von Befehls-IDs als Eingaben zu empfangen. Es wird empfohlen, dass nur VSPackages Unterstützung dieses Konzept der mehrere IDs in einem Aufruf. Solange ein VSPackage jedoch nicht von anderen VSPackages aufgerufen wird, können Sie davon ausgehen, dass nur eine Befehls-ID des Befehls array, da das QueryStatus und die Exec-Methode in einer klar definierte Reihenfolge ausgeführt werden. Informationen zum Routing finden Sie unter Command Routing in VSPackages.

Für Code, der die IOleCommandTarget-Schnittstelle nicht direkt für Befehls Klassenbehandlung verwendet, müssen Sie die QueryStatus-Methode wie folgt in einem VSPackage implementieren, um Befehle zu behandeln.

So implementieren QueryStatus-Methode

  1. Geben Sie S_OK für gültige Befehle.

  2. Legen Sie das cmdf-Element des prgCmds-Parameters fest.

    Der Wert des Elements cmdf ist die logische Gesamtmenge von Werten aus der OLECMDF-Enumeration, kombiniert, indem er das logische OR (|Operator.)

    Verwenden Sie die entsprechende Enumeration auf Grundlage des Status des Befehls:

    • Wenn der Befehl unterstützt wird:

      prgCmds[0].cmdf = OLECMDF_SUPPORTED;

    • Wenn der Befehl zum Zeitpunkt nicht sichtbar ist:

      prgCmds[0].cmdf |= OLECMDF_INVISIBLE;

    • Wenn der Befehl beendet wird und scheint geklickt worden sein:

      prgCmds[0].cmdf |= OLECMDF_LATCHED;

      Bei der Verarbeitung von Befehlen, die in einem Menü des Typs MenuControllerLatchedgehostet werden, ist der erste Befehl, der vom OLECMDF_LATCHED-Flags gekennzeichnet ist, der Standardbefehl, der beim Start im Menü angezeigt werden soll. Weitere Informationen zu MenuController Menü Typen finden Sie unter Menu-Element.

    • Wenn der Befehl derzeit aktiviert ist:

      prgCmds[0].cmdf |= OLECMDF_ENABLED;

    • Wenn der Befehl Teil eines Kontextmenüs und standardmäßig ausgeblendet ist:

      prgCmds[0] cmdf |= OLECMDF_DEFHIDEONCTXMENU

    • Wenn der Befehl das TEXTCHANGES-Flag verwendet wird, legen Sie das rgwz-Element des pCmdText-Parameters an den neuen Text des Befehls fest, und legen Sie das cwActual-Element des pCmdText-Parameters auf die Größe der Befehlszeichenfolge fest.

    Für Fehlerbedingungen muss die QueryStatus-Methode die folgenden Fehler fälle behandeln:

    • Wenn die GUID oder nicht unterstütztes, geben OLECMDERR_E_UNKNOWNGROUPunbekannt ist.

    • Wenn jedoch die GUID bezeichnet, die Befehls-ID ist oder nicht unterstütztes, geben OLECMDERR_E_NOTSUPPORTEDunbekannt.

Die VSPackage-Implementierung der Exec-Methode muss bestimmte Fehlercodes auch zurückgeben, je nachdem, ob der Befehl unterstützt wird und ob der Befehl erfolgreich behandelt wurde.

Um die Leitprogramm Methode implementieren

  • Wenn der Befehl GUID unbekanntes, geben OLECMDERR_E_UNKNOWNGROUPist.

  • Wenn GUID bekannt ist, jedoch ist die Befehls-ID unbekanntes, geben OLECMDERR_E_NOTSUPPORTED.

  • Wenn GUID und die Befehls-ID die GUID entspricht: ID-Paare, die vom Befehl in der .vsct-Datei verwendet wird, führen Code aus, der mit dem Befehl und der Rückgabe S_OKzugeordnet ist.

Siehe auch

Konzepte

VSCT-XML-Schemaverweis

Weitere Ressourcen

Allgemeine Aufgaben mit Befehlen, Menüs und Symbolleisten

Walkthrough: Adding a Command to a Visual Studio Menu