最新版 |
編集中の文章 |
1行目: |
1行目: |
| + | = 新しいEventSystemの使い方 = |
| + | |
| Minecraft1.1向けのBukkit API以降、新しいイベントの仕組みが提供されています。<BR /> | | Minecraft1.1向けのBukkit API以降、新しいイベントの仕組みが提供されています。<BR /> |
| この新しい仕組みは、シンプルでかつ、汎用性・高速性・可読性等に優れています。<BR /> | | この新しい仕組みは、シンプルでかつ、汎用性・高速性・可読性等に優れています。<BR /> |
14行目: |
16行目: |
| === イベントリスナ === | | === イベントリスナ === |
| まず、イベントを待ち受ける処理(Event Listenerと呼ばれます)が必要です: | | まず、イベントを待ち受ける処理(Event Listenerと呼ばれます)が必要です: |
− | <blockquote><source lang="java"> | + | <blockquote><source lang="java">public void onPlayerLogin(PlayerLoginEvent event) { |
− | @EventHandler
| + | // Your code here... |
− | public void onPlayerLogin(PlayerLoginEvent event) { | + | }</source></blockquote> |
− | // ここに処理を書きます... | |
− | } | |
− | </source></blockquote> | |
| 次に、発生するイベント(Event Handlerと呼ばれます)が必要になります。 | | 次に、発生するイベント(Event Handlerと呼ばれます)が必要になります。 |
| | | |
28行目: |
27行目: |
| | | |
| イベントハンドラには優先度を指定でき、次のような書き方をします: | | イベントハンドラには優先度を指定でき、次のような書き方をします: |
− | <blockquote><source lang="java">@EventHandler(priority = EventPriority.HIGHEST) // 高優先度のイベントハンドラとする | + | <blockquote><source lang="java">@EventHandler(priority = EventPriority.HIGHEST) // 高優先度のイベントとする |
− | @EventHandler(priority = EventPriority.LOW) // 低優先度のイベントハンドラとする</source></blockquote> | + | @EventHandler(priority = EventPriority.LOW) // 低優先度のイベントとする</source></blockquote> |
| | | |
| 以上をまとめると、次のようになります: | | 以上をまとめると、次のようになります: |
| <blockquote><source lang="java">@EventHandler | | <blockquote><source lang="java">@EventHandler |
| public void onPlayerLogin(PlayerLoginEvent event) { | | public void onPlayerLogin(PlayerLoginEvent event) { |
− | // ここに処理を書きます... | + | // Your code here... |
| }</source></blockquote> | | }</source></blockquote> |
| | | |
43行目: |
42行目: |
| @EventHandler | | @EventHandler |
| public void onPlayerLogin(PlayerLoginEvent event) { | | public void onPlayerLogin(PlayerLoginEvent event) { |
− | // ここに処理を書きます... | + | // Your code here... |
| } | | } |
| }</source></blockquote> | | }</source></blockquote> |
53行目: |
52行目: |
| 上記の例で言えば、PlayerLoginEventから読み込みます。 | | 上記の例で言えば、PlayerLoginEventから読み込みます。 |
| | | |
− | :'''Note''': 特定のイベントハンドラを1つも登録していなければ、Bukkitはそのクラスをイベントリスナとして登録することができません。 | + | :'''Note''': 特定のイベントまたはBukkitが登録しないイベントに関しては、手動で指定しなければなりません。(訳が不適切か) |
| | | |
| === イベントハンドラの設定 === | | === イベントハンドラの設定 === |
88行目: |
87行目: |
| </blockquote> | | </blockquote> |
| | | |
− | ==== イベントの優先度 ==== | + | == イベントの登録 == |
− | | + | イベントを記述するクラスは、<BR /> |
− | 上記の表にあるように、イベントの優先度は6種類ありますが、イベントが呼び出される順序は下記のようになっています。
| |
− | | |
− | * EventPriority.LOWEST
| |
− | * EventPriority.LOW
| |
− | * EventPriority.NORMAL
| |
− | * EventPriority.HIGH
| |
− | * EventPriority.HIGHEST
| |
− | * EventPriority.MONITOR
| |
− | | |
− | すべてのプラグインでイベント発生内容を取得できるようにする必要があります。<br>
| |
− | だから、あるプラグインでキャンセルされてしまった後であっても、その他のプラグインにもイベントリスナーが呼び出されます。<br>
| |
− | また、実際に別のプラグインが先にイベントをキャンセルしたとしても、イベントを uncancel することができます。<br>
| |
− | これを理解するには、優先順位の理解が本当に重要になります。
| |
− | | |
− | あるイベントが発生すると、まずLOWESTのリスナーが呼び出され、リスナーから設定内容の変更や、isCancelledの変更を行います。<br>
| |
− | その後、LOWからHIGHESTまで、順にリスナーが行われ、設定内容が書き換わります。<br>
| |
− | 最終的に、MONITORのリスナーが呼び出されます。この時点で、全てのリスナーが設定した内容が最終結果として参照できるようになります。<br>
| |
− | MONITORは、イベントの内容を変更すべきではなく、イベントの結果を確認するためだけに使用してください。
| |
− | | |
− | 例として、BLOCK_PLACE イベントが処理されるとしましょう。<br>
| |
− | 3つのプラグインが有効になっており、1つ目は基本的な領域保護プラグイン、2つ目はカンバンを使った付加価値的プラグイン、3つ目はログ記録プラグインです。<br>
| |
− | 領域保護プラグインはPriority.LOWESTで待機します。
| |
− | そのプラグインは、「この領域内にブロックを配置することはできない」と判断して、イベントをキャンセルします。<br>
| |
− | カンバンを使った付加価値的プラグインはPriority.NORMALで待機します。
| |
− | そのプラグインは、「この領域内にカンバンを置くことができる」と判断したので、イベントをuncancelします(''event.isCancelled(false)'')。<br>
| |
− | ログ記録プラグインはPriority.MONITORで待機します。
| |
− | これは、'''イベント処理が実際に実行された'''(キャンセルされていない)という最終結果を確認し、イベント内容をログに記録します。
| |
− | | |
− | あなたはイベントの結果を変更する場合、LOWESTからHIGHESTの間で、慎重に選択してください。<br>
| |
− | あなたが、イベントの最終結果を受け取りたいが、結果を変更しないときは、MONITORを使用してください。<br>
| |
− | ただし、'''MONITORのリスナーがイベントをキャンセルしたりしないように、イベントの内容を変更したりしないように、十分注意してください。'''最悪、他のプラグインの動作を阻害してしまうことになってしまいます。
| |
− | | |
− | == イベントリスナの登録 ==
| |
− | イベントリスナを記述するクラスは、<BR />
| |
| Listenerインタフェースを実装(implements)し、かつイベントハンドラを含んでいなければなりません。 | | Listenerインタフェースを実装(implements)し、かつイベントハンドラを含んでいなければなりません。 |
| | | |
131行目: |
96行目: |
| }</source></blockquote> | | }</source></blockquote> |
| | | |
− | イベントリスナの登録処理は、PluginManagerインスタンスのregisterEventsメソッドを使って、プラグインクラスと共に記述します。
| + | イベントの登録処理は、PluginManagerインスタンスのregisterEventsメソッドとして、プラグインとリスナに記述します。 |
| <blockquote><source lang="java">getServer().getPluginManager().registerEvents(Listener, Plugin);</source></blockquote> | | <blockquote><source lang="java">getServer().getPluginManager().registerEvents(Listener, Plugin);</source></blockquote> |
| | | |
217行目: |
182行目: |
| } | | } |
| }</source></blockquote> | | }</source></blockquote> |
− |
| |
− | == イベントリスナの登録解除 ==
| |
− |
| |
− | 自分のプラグインから登録したイベントリスナだけでなく、他のプラグインから登録されたイベントリスナであっても、自由に登録を解除することが可能です。
| |
− |
| |
− | ==== 特定のイベントからリスナを登録解除する ====
| |
− |
| |
− | 全てのイベントは、staticメソッドの getHandlerList() を持っています。<br/>
| |
− | HandlerList を取得して unregister() メソッドを実行すれば、イベントに関連するリスナの登録を解除することが可能です。
| |
− |
| |
− | 例:
| |
− |
| |
− | <blockquote><source lang="java">
| |
− | PlayerInteractEvent.getHandlerList().unregister(plugin);
| |
− | // 指定したプラグインから PlayerInteractEvent に登録された、
| |
− | // 全てのイベントリスナを登録解除します。
| |
− | </source></blockquote>
| |
− |
| |
− | getHandlerList() メソッドの詳細については、後述の自作イベントのところで説明します。
| |
− |
| |
− | ==== 全てのイベントリスナの登録解除 ====
| |
− |
| |
− | HandlerList クラスの staticメソッド unregisterAll() を使用すると、指定したプラグイン、または、指定したイベントリスナークラスから登録された全てのイベントリスナを登録解除することができます。
| |
− |
| |
− | 例:
| |
− |
| |
− | <blockquote><source lang="java">
| |
− | HandlerList.unregisterAll(plugin);
| |
− | // 指定したプラグインから登録された
| |
− | // 全てのイベントリスナを登録解除します。
| |
− | </source></blockquote>
| |
− |
| |
| | | |
| == イベントの自作 == | | == イベントの自作 == |
324行目: |
257行目: |
| } | | } |
| }</source></blockquote> | | }</source></blockquote> |
− |
| |
− | === 自作イベントをキャンセル可能にする ===
| |
− |
| |
− | 次に、自作イベントをキャンセル可能に実装してみましょう。Cancellableクラスを実装してください(implements Cancellable)。<br>
| |
− | あとはそのまま利用してください。とっても簡単ですね!<br>
| |
− | では、実例をみてみましょう。
| |
− |
| |
− | <blockquote><source lang="java">import org.bukkit.event.Event;
| |
− | import org.bukkit.event.HandlerList;
| |
− | import org.bukkit.event.Cancellable;
| |
− |
| |
− | public final class CustomEvent extends Event implements Cancellable {
| |
− | private static final HandlerList handlers = new HandlerList();
| |
− | private String message;
| |
− | private boolean cancelled;
| |
− |
| |
− | public CustomEvent(String example) {
| |
− | message = example;
| |
− | }
| |
− |
| |
− | public String getMessage() {
| |
− | return message;
| |
− | }
| |
− |
| |
− | public boolean isCancelled() {
| |
− | return cancelled;
| |
− | }
| |
− |
| |
− | public void setCancelled(boolean cancel) {
| |
− | cancelled = cancel;
| |
− | }
| |
− |
| |
− | public HandlerList getHandlers() {
| |
− | return handlers;
| |
− | }
| |
− |
| |
− | public static HandlerList getHandlerList() {
| |
− | return handlers;
| |
− | }
| |
− | }</source></blockquote>
| |
− |
| |
− | イベントをコールした後に、イベントがリスナーによってキャンセルされているかどうかを調べてください。<br>
| |
− | キャンセルされていないなら、通常通り処理を実行すれば良いのです。
| |
− |
| |
− | <blockquote><source lang="java">
| |
− | // イベントのインスタンス化
| |
− | CustomEvent event = new CustomEvent("Sample Message");
| |
− | // イベントのコール
| |
− | Bukkit.getServer().getPluginManager().callEvent(event);
| |
− | // イベントがキャンセルされていないなら・・・
| |
− | if (!event.isCancelled()) {
| |
− | // イベントからメッセージ内容を取得して処理する
| |
− | Bukkit.getServer().broadcastMessage(event.getMessage());
| |
− | }
| |
− | </source></blockquote>
| |