BeforeItemUseOnEvent クラス

BeforeItemUseOnEventは、エンティティ(プレイヤーを含む)がブロックに対してアイテムを使おうとしたときに発火するイベントです。実際にアイテムをブロックに対して使う前に何かしらの処理を挟むときなどに利用できます。

更新履歴
  • 2023/02/17
    • サンプルコードを修正

プロパティ

blockFace

read-only blockFace: Direction;

アイテムが使われているブロックの面に関する情報。

Type: Direction(公式サイト)

blockLocation

read-only blockLocation: BlockLocation;

アイテムを使われるブロック(影響を受けるブロック)の位置。

Type: BlockLocation(公式サイト)

cancel

cancel: boolean;

アイテム使用時の動作をキャンセルするかどうか。trueにセットするとアイテムの使用をキャンセルします。

Type: boolean

faceLocationX

read-only faceLocationX: number;

対象ブロックに対してアイテムが使われる際のX座標(カーソル位置のX座標)。

Type: number

faceLocationY

read-only faceLocationY: number;

対象ブロックに対してアイテムが使われる際のY座標(カーソル位置のY座標)。

Type: number

item

item: ItemStack;

ブロックに対して使用したアイテム(アイテムスタック)。

Type: ItemStack (公式サイト)

source

read-only source: Entity;

このイベントを発生させたエンティティ。エンティティはプレイヤーを含む。

Type: Entity (公式サイト)

サンプルコード

棒を持った状態でしかチェストを開けなくする

BeforeItemUseOnEventイベントは実際にアイテムが使われてその効果が出る「前」にイベントを挟み込むことができるのが特徴です。これにより「特定のアイテムを持っていない場合にイベントをキャンセルする」こともできます。

例えば以下のようなコードで「棒を持った状態でしかチェストを開けなくする」といった機能を実現できます。

import { world } from "@minecraft/server";
 
world.events.beforeItemUseOn.subscribe(ev => {
  // アイテムを使ったのがプレイヤーの場合のみ
  if (ev.source.typeId === "minecraft:player") {
    // そのアイテムが棒(minecraft:stick)以外の場合、
    if (ev.item.typeId !== "minecraft:stick") {
      // アイテムを使った先のブロックの座標からブロックを取得し、
      // そのブロックがチェスト(minecraft:chest)だったらイベントをキャンセルする。
      // = 棒以外のアイテムではチェストが開かなくなる。
      const block = ev.source.dimension.getBlock(ev.blockLocation);
      if (block.typeId === "minecraft:chest") {
        ev.cancel = true;
      }
    }
  }
});

使ったアイテムのネームタグが特定の文字列の場合しかチェストを開けない、みたいにすればマルチで謎解きクエストみたいなことが実現できそうですね!

上のコードを定数クラスを使って書く場合は次の通り。こちらの方が打ち間違えが発生しにくくバグも少なくなるでしょう。

import { MinecraftBlockTypes, MinecraftEntityTypes, MinecraftItemTypes, world } from "@minecraft/server";
 
world.events.beforeItemUseOn.subscribe(ev => {
  // アイテムを使ったのがプレイヤーの場合のみ
  if (ev.source.typeId === MinecraftEntityTypes.player.id) {
    // そのアイテムが棒(minecraft:stick)以外の場合、
    if (ev.item.typeId !== MinecraftItemTypes.stick.id) {
      // アイテムを使った先のブロックの座標からブロックを取得し、
      // そのブロックがチェスト(minecraft:chest)だったらイベントをキャンセルする。
      // = 棒以外のアイテムではチェストが開かなくなる。
      const block = ev.source.dimension.getBlock(ev.blockLocation);
      if (block.typeId === MinecraftBlockTypes.chest.id) {
        ev.cancel = true;
      }
    }
  }
});

関数型プログラミングではこんな感じでしょうか。慣れればこれの方が見やすいかも。

import { MinecraftBlockTypes, MinecraftEntityTypes, MinecraftItemTypes, world } from "@minecraft/server";
 
world.events.beforeItemUseOn.subscribe(ev => {
  [ev]
    .filter(e => e.source.typeId === MinecraftEntityTypes.player.id)
    .filter(e => e.item.typeId !== MinecraftItemTypes.stick.id)
    .map(e => e.source.dimension.getBlock(e.blockLocation))
    .filter(block => block.typeId === MinecraftBlockTypes.chest.id)
    .map(() => ev.cancel = true);
});

まとめ

BeforeItemUseOnEventイベントはアイテムをブロックに対して使った際に、その効果が表れる「前」に処理を挟むことができることを解説しました。特定の条件の時のみアイテムやブロックのイベントを続行できるようにできるとアドオンの幅が広がると思いますのでチャレンジしてみてください。