Поделиться через


Изменение стандартной команды меню в предметно-ориентированном языке

Поведение некоторых стандартных команд, определенных в доменном языке автоматически, можно изменять. Например, можно изменить "Вырезать ", чтобы исключить конфиденциальную информацию. Для этого необходимо переопределить методы в классе наборов команд. Эти классы определяются в файле CommandSet.cs проекта DslPackage project и являются производными от класса CommandSet.

Примечание.

Если вы хотите создать собственные команды меню, см . статью "Практическое руководство. Добавление команды в контекстное меню".

Какие команды можно изменять?

Поиск команд, доступных для изменения

  1. В проекте DslPackage откройте GeneratedCode\CommandSet.cs. Этот файл C# можно найти в Обозреватель решений в качестве дочерней CommandSet.ttкомпании.

  2. Найдите классы в этом файле, имена которых заканчиваются "CommandSet", например Language1CommandSet и Language1ClipboardCommandSet.

  3. В каждом классе наборов команд введите "override" и пробел. IntelliSense отобразит список методов, которые можно переопределить. Каждая команда имеет пару методов, имена которых начинаются с "ProcessOnStatus" и "ProcessOnMenu".

  4. Запомните, какой класс наборов команд содержит команду, подлежащую изменению.

  5. Закройте файл без сохранения изменений.

    Примечание.

    Обычно генерируемые файлы не редактируются. При следующей генерации файлов все изменения будут утеряны.

Расширение соответствующего класса наборов команд

Создайте новый файл, содержащий частичное описание класса наборов команд.

Расширение класса наборов команд

  1. В Обозревателе решений в проекте DslPackage откройте папку GeneratedCode, найдите раздел CommandSet.tt и откройте созданный в нем файл CommandSet.cs. Запомните пространство имен и имя первого определенного здесь класса. Например:

    namespace Company.Language1

    { ... internal partial class Language1CommandSet : ...

  2. В DslPackage создайте папку с именем Custom Code. В этой папке создайте файл класса с именем CommandSet.cs.

  3. В новом файле напишите частичное объявление, используя то же пространство имен и имя, что и в созданном частичном классе. Рассмотрим пример.

    using System;
    using System.Collections.Generic;
    using System.ComponentModel.Design;
    namespace Company.Language1 /* Make sure this is correct */
    { internal partial class Language1CommandSet { ...
    

    Примечание.

    Если вы использовали шаблон файла класса для создания нового файла, необходимо исправить пространство имен и имя класса.

Переопределение методов команд

Большинство команд имеют два связанных метода: метод с именем, например ProcessOnStatus... определяет, должна ли команда быть видимой и включенной. Она вызывается, когда пользователь щелкает схему правой кнопкой мыши, и должна выполняться быстро и не вносить изменений. ProcessOnMenu... вызывается, когда пользователь щелкает команду и должен выполнять функцию команды. Возможно, потребуется переопределение одного или двух этих методов.

Изменение условий отображения команды в меню

Переопределите ProcessOnStatus... Метод. Он должен задавать свойства Visible и Enabled своего параметра MenuCommand. Обычно команда проверяет this.CurrentSelection, чтобы определить, применяется ли команда к выбранным элементам, а также может проверить их свойства, чтобы определить возможность применения команды в их текущем состоянии.

Как правило, свойство Visible должно определяться выбранными элементами. Свойство Enabled, определяющее цвет отображения команды в меню (черный или серый), должно зависеть от текущего состояния выделения.

В следующем примере элемент меню "Удалить" отключается, когда пользователь выбирает больше одной фигуры.

Примечание.

Этот метод не влияет на доступность команды при нажатии клавиши. Например, отключение элемента меню "Удалить" не запрещает вызов команды с помощью клавиши Delete.

/// <summary>
/// Called when user right-clicks on the diagram or clicks the Edit menu.
/// </summary>
/// <param name="command">Set Visible and Enabled properties.</param>
protected override void ProcessOnStatusDeleteCommand (MenuCommand command)
{
  // Default settings from the base method.
  base.ProcessOnStatusDeleteCommand(command);
  if (this.CurrentSelection.Count > 1)
  {
    // If user has selected more than one item, Delete is greyed out.
    command.Enabled = false;
  }
}

Рекомендуется вначале вызвать базовый метод, чтобы обработать все случаи и настройки, которые вас не беспокоят.

Метод ProcessOnStatus не должен создавать, удалять или обновлять элементы в Магазине.

Изменение поведения команды

Переопределите ProcessOnMenu... Метод. В следующем примере код запрещает пользователю удалять больше одного элемента за один раз даже с помощью клавиши Delete.

/// <summary>
/// Called when user presses Delete key
/// or clicks the Delete command on a menu.
/// </summary>
protected override void ProcessOnMenuDeleteCommand()
{
  // Allow users to delete only one thing at a time.
  if (this.CurrentSelection.Count <= 1)
  {
    base.ProcessOnMenuDeleteCommand();
  }
}

Если код вносит в Магазин такие изменения, как создание, удаление или обновление элементов и ссылок, необходимо делать это внутри транзакции. Дополнительные сведения см. в разделе "Создание и обновление элементов модели".

Написание кода методов

В этих методах часто используются следующие фрагменты:

  • this.CurrentSelection. Фигура, которую пользователь щелкает правой кнопкой мыши, всегда включается в этот список фигур и соединителей. Если пользователь щелкает пустую область схемы, схема становится единственным членом списка.

  • this.IsDiagramSelected() - true Если пользователь щелкнул пустую часть схемы.

  • this.IsCurrentDiagramEmpty()

  • this.IsSingleSelection() — пользователь не выбирает несколько фигур

  • this.SingleSelection — фигура или схема, щелкнув правой кнопкой мыши пользователя

  • shape.ModelElement as MyLanguageElement — элемент модели, представленный фигурой.

Дополнительные сведения о том, как переходить от элемента к элементу и о том, как создавать объекты и ссылки, см. в статье "Навигация и обновление модели в программном коде".