Расширение меню и контекстных меню в приложении .NET с помощью MEF - PullRequest
1 голос
/ 09 августа 2011

Я пытаюсь придумать архитектуру меню и контекстного меню, аналогичную той, что предлагает Visual Studio 2010, чтобы я мог расширить свое текущее меню дополнительными подпунктами, предоставляемыми расширениями. Я использую MEF ( Managed Extensibility Framework ). Например, расширение Resharper добавляет пункты меню и элементы контекстного меню в любой возможной позиции (вверху, в середине или внизу контекстного меню или пункта меню) Как можно обеспечить такую ​​функциональность? Должен ли я индексировать каждый элемент меню оболочки, и нужно ли, чтобы расширение ссылалось на индекс, чтобы расположить его в подэлементах? Я надеюсь, что мой вопрос достаточно ясен. В противном случае я был бы более чем рад добавить некоторые разъяснения.

1 Ответ

0 голосов
/ 11 августа 2011

Я не уверен, что есть лучший способ сделать это. Но вот несколько идей для рассмотрения:

Довольно простое решение состоит в том, чтобы использовать один контракт (т. Е. IMenuIten) и использовать метаданные для управления тем, в каком меню появляется команда и в какой позиции. Один из способов сделать это - иметь индекс, хотя он, вероятно, должен быть двойным и использоваться для сортировки элементов в меню, чтобы каждому элементу не нужно было знать его абсолютную позицию в меню. Другой способ заключается в том, чтобы иметь метаданные в пунктах меню, которые дают список других элементов, которые должны быть до и после текущего элемента. Затем вы можете выполнить топологическую сортировку пунктов меню, чтобы получить порядок их отображения.

В зависимости от того, насколько сложным / динамичным должно быть ваше поведение в меню, вы можете обнаружить, что вы не можете выразить его с помощью метаданных экспорта. В этом случае вы можете переместить функциональность в сам контракт, т. Е. Добавить свойства или методы в свой контракт IMenuItem. Таким образом, вы можете запустить код для вычисления необходимых вам значений.

Другое решение - не экспортировать пункты меню напрямую. Вместо этого вы можете иметь службу меню, которая импортируется компонентом. Служба будет иметь метод Register, который будет добавлять пункт меню в меню. По моему мнению, это делает добавление пунктов меню немного более громоздким, поэтому я бы не рекомендовал его, если бы не была причина, по которой он вам нужен. Возможно, будет целесообразно изменить доступные пункты меню в зависимости от текущего контекста приложения. Обратите внимание, что если вы пойдете по этому пути, просто наличие класса, который импортирует службу меню, не приведет к тому, что класс будет создан и составлен. Класс должен экспортировать то, что импортировано где-то еще в системе.

...