【ScriptAPI】オフハンドのアイテム・インベントリのアイテムを検知する方法を解説! – getComponent関数とgetEquipment関数の概要と使い方

はじめに

本記事ではインベントリ内・オフハンドにあるアイテムをScriptAPIで取得・編集(書き換え)する方法についてスクリプトを示しながら解説します。

Character
結構こういうことをやりたくなること、あるのでは?

なお、ScriptAPIの環境構築や基本的な事項については以下の記事をご覧ください:

インベントリ内のアイテムの取得

インベントリ内のアイテムを取得するにはgetComponent関数でエンティティのインベントリ情報を取得した上で、getSlot(引数番号)で特定のスロットに存在するアイテムスタックを取得する必要があります。

const inventoryItem =  player.getComponent(server.EntityComponentTypes.Inventory).container.getSlot(0)
Copied!

これはプレイヤーのインベントリ番号0のアイテムを取得し、変数inventoryItemに格納する例です。これはItemStackクラスですので、実際にこのアイテムのidを使う場合には別途typeIdプロパティが必要です。使用にあたってはプレイヤークラスの変数playerが必須なので注意しましょう。

使用例

以下はホットバーの一番右にダイアモンドがあるときにツルハシでブロックを壊した際、そのダイアモンドを失う代わりにstrengthのエフェクトを付与する例です:

import * as server from "@minecraft/server";
server.world.afterEvents.playerBreakBlock.subscribe(ev => {
    if (ev.itemStackAfterBreak.typeId.endsWith("pickaxe")){ // ピッケルで壊したことを検知
        if(ev.player.getComponent(server.EntityComponentTypes.Inventory).
        container.getSlot(0).typeId == "minecraft:diamond"){ // ダイアモンドが0番目のスロットに存在するならば
            ev.player.runCommand("clear @s diamond 1") // ダイアモンドを1つ減らして
            ev.player.runCommand("effect @s strength 1") // エフェクトを付与
        }
    }
})
Copied!

このように、getComponent関数でインベントリ情報を取得することができます。

オフハンドのアイテムの取得

オフハンドのアイテムは同様の方法では取得することができません。getSlot関数はインベントリ内にあるアイテムしか取得することができないからです。このような場合には、EntityEquippableComponentクラスのgetEquipment関数を使用する必要があります

const offhandItem = ev.player.getComponent(server.EntityComponentTypes.Equippable)
.getEquipment(server.EquipmentSlot.Offhand);
Copied!

基本的な構成は先とあまり変わりませんが、getComponent関数の引数が”minecraft:equippable”となっている点には注意しましょう。これはEntityEquippableComponentクラスを返します。また、ここで取得されるoffhandItemは先と同じくItemStackクラスです。

使用例

import * as server from "@minecraft/server";
server.world.afterEvents.playerBreakBlock.subscribe(ev => {
    if (ev.itemStackAfterBreak.typeId.endsWith("pickaxe")){ // ピッケルで壊したことを検知
        const offhandItem = ev.player.getComponent(server.EntityComponentTypes.Equippable).getEquipment(server.EquipmentSlot.Offhand);
        const triggerItem = "minecraft:firework_rocket"
        if(offhandItem == undefined){return;}
        if(offhandItem.typeId == triggerItem){
            ev.player.getComponent(server.EntityComponentTypes.Equippable).
            setEquipment(server.EquipmentSlot.Offhand, new server.ItemStack(triggerItem, offhandItem.amount - 1));
            ev.player.runCommand("effect @s strength 1") // エフェクトを付与
        }
    }
})
Copied!

これはオフハンドに花火があるときにツルハシでブロックを壊した際、その花火を消費する代わりにstrengthを付与する例です。なお、ここではオフハンドにあるアイテムをclearコマンドで減らすことはできないので、ここではsetEquipment関数でオフハンドアイテムの書き換えを行っています。setEquipment関数の第一引数はスロットのid、第二引数はItemStack(アイテムidと個数の情報を持つアイテム)となっています。

今回解説したスクリプトを使って、友人・コミュニティー内で24時間いつでも遊べるマルチサーバーを構築したい場合は、VPS(レンタルサーバー)の導入が近道です。

私の開発・検証環境では「シンVPS」を使用しています。

シンVPS コントロールパネル画像

以前は自宅PCでホストしていましたが、PCの電源を切り忘れるストレスや、電気代を考慮して移行しました。シンVPSを選んだ決め手は、圧倒的なコストパフォーマンスです。

  • 月額の安さ 4GBプランでも月額1,200円程度(長期契約なら1,000円以下)と維持費が安く済みます。
  • 高速な読み込み 全プランでNVMe SSDを採用しており、ワールドの読み込みや重いコマンド処理でもラグを感じにくいです。
※最低利用期間が3ヶ月からという縛りはありますが、サーバーを長期で安定運用するならむしろ割安になります。

以下のリンクから申し込むと初回利用料金が10%OFFになります。
(1ヶ月以上の契約対象。「安くて速い」サーバーを探している方はぜひ試してみてください)

シンVPS 公式サイトを見てみる
(10%OFF適用)
マルチサーバーの立て方はこちら
最新情報をチェックしよう!