Xtextでクリップボードにコピーするメニューのメモ。
Xtextで作ったエディターでは、右クリックして出るコンテキストメニューに「Copy Qualified Name」というメニューがある。
これはEditorCopyQualifiedNameHandler(アウトラインページの場合はOutlineCopyQualifiedNameHandler)で実装されている。(Xtext2.4)
また、これらのハンドラーを呼び出す為の記述は、uiプロジェクトのplugin.xmlに(最初に生成されたときに)書かれている。
したがって、これらの記述を真似すると、自分独自のコピーメニューを実装できる。
Xtextで作ったエディター用の「Copy Qualified Name」メニューのハンドラー。
DMDL EditorXの場合、以下のようになっている。
<extension
point="org.eclipse.ui.handlers">
〜
<!-- copy qualified name -->
<handler
class="jp.hishidama.xtext.dmdl_editor.ui.DMDLExecutableExtensionFactory:org.eclipse.xtext.ui.editor.copyqualifiedname.EditorCopyQualifiedNameHandler"
commandId="org.eclipse.xtext.ui.editor.copyqualifiedname.EditorCopyQualifiedName">
<activeWhen>
<reference definitionId="jp.hishidama.xtext.dmdl_editor.DMDL.Editor.opened" />
</activeWhen>
</handler>
〜
</extension>
Xtextのplugin.xmlにちょくちょく出てくるのが、「jp.hishidama.xtext.dmdl_editor.ui.DMDLExecutableExtensionFactory:org.eclipse.xtext.ui.editor.copyqualifiedname.EditorCopyQualifiedNameHandler」といった、コロン「:」で区切ったクラス名指定。
前半部が実際に呼ばれるファクトリークラスで、後半部はインスタンスを生成したいクラス。
前半部のファクトリークラス(のソース)は自動生成されている。
このファクトリークラスを使って後半部のクラスのインスタンスが生成される。その際、後半部クラスのインジェクションの初期設定をしてくれる。
(したがって、インジェクションを使っていない場合はファクトリークラスを経由する必要は無く、インスタンス生成したいクラス名のみを書けばよい)
<extension
point="org.eclipse.ui.commands">
〜
<!-- copy qualified name -->
<command
id="org.eclipse.xtext.ui.editor.copyqualifiedname.EditorCopyQualifiedName"
categoryId="org.eclipse.ui.category.edit"
description="Copy the qualified name for the selected element"
name="Copy Qualified Name">
</command>
〜
</extension>
<extension point="org.eclipse.ui.menus">
〜
<!-- copy qualified name -->
<menuContribution locationURI="popup:#TextEditorContext?after=copy">
<command commandId="org.eclipse.xtext.ui.editor.copyqualifiedname.EditorCopyQualifiedName"
style="push" tooltip="Copy Qualified Name">
<visibleWhen checkEnabled="false">
<reference definitionId="jp.hishidama.xtext.dmdl_editor.DMDL.Editor.opened" />
</visibleWhen>
</command>
</menuContribution>
<menuContribution locationURI="menu:edit?after=copy">
<command commandId="org.eclipse.xtext.ui.editor.copyqualifiedname.EditorCopyQualifiedName"
style="push" tooltip="Copy Qualified Name">
<visibleWhen checkEnabled="false">
<reference definitionId="jp.hishidama.xtext.dmdl_editor.DMDL.Editor.opened" />
</visibleWhen>
</command>
</menuContribution>
〜
</extension>
メニューは2種類定義されている。
| locationURI | 説明 |
|---|---|
popup:#TextEditorContext?after=copy |
エディター上で右クリックして出るコンテキストメニュー。 「Copy」メニューの後ろに追加される。 |
menu:edit?after=copy |
メニューバーの「Edit」メニュー。 「Copy」メニューの後ろに追加される。 |
Xtextのアウトラインページ用の「Copy Qualified Name」メニューのハンドラー。
plugin.xml上のほとんどの定義はEditorCopyQualifiedNameHandlerと同様で、メニュー定義部分だけ明確に異なる。
<extension point="org.eclipse.ui.menus">
〜
<menuContribution locationURI="popup:org.eclipse.xtext.ui.outline?after=additions">
<command commandId="org.eclipse.xtext.ui.editor.copyqualifiedname.OutlineCopyQualifiedName"
style="push" tooltip="Copy Qualified Name">
<visibleWhen checkEnabled="false">
<and>
<reference definitionId="jp.hishidama.xtext.dmdl_editor.DMDL.XtextEditor.opened" />
<iterate>
<adapt type="org.eclipse.xtext.ui.editor.outline.IOutlineNode" />
</iterate>
</and>
</visibleWhen>
</command>
</menuContribution>
</extension>
EditorCopyQualifiedNameHandlerおよびOutlineCopyQualifiedNameHandlerの共通の親クラス。
基本的には非常にシンプル。
import org.eclipse.core.commands.AbstractHandler; import org.eclipse.core.commands.ExecutionEvent; import org.eclipse.core.commands.ExecutionException;
public abstract class AbstractCopyQualifiedNameHandler extends AbstractHandler {
〜
// @Override
public Object execute(ExecutionEvent event) throws ExecutionException {
String qualifiedName = getQualifiedName(event);
return ClipboardUtil.copy(qualifiedName);
}
protected abstract String getQualifiedName(ExecutionEvent event);
〜
}
ここに出てくるClipboardUtilはXtext専用のクラスだが、内部ではSWTのClipboard機構を使っている。