この記事は"Minecraft Forge Universal 10.14.4.x~"及び"ComputerCraft 1.76~"を前提MODとしています。 |
目次
ツールタイプTurtleの追加
ツールタイプのTurtle Upgradeを追加します。
- ITurtleUpgrade(ツールタイプ)の実装
- TurtleUpgradeの登録
ソースコード
Packageは適宜設定してください。
SampleUpgradeCore.java
// package mods.sample.upgrade; import net.minecraftforge.fml.common.Mod; import net.minecraftforge.fml.common.Mod.EventHandler; import net.minecraftforge.fml.common.event.FMLInitializationEvent; import dan200.computercraft.api.ComputerCraftAPI; @Mod( modid = SampleUpgradeCore.MOD_ID, name = SampleUpgradeCore.MOD_NAME, version = SampleUpgradeCore.MOD_VERSION, dependencies = SampleUpgradeCore.MOD_DEPENDENCIES, acceptedMinecraftVersions = SampleUpgradeCore.MOD_ACCEPTED_MC_VERSIONS) public class SampleUpgradeCore { public static final String MOD_ID = "sampleupgrademod"; public static final String MOD_NAME = "Sample Upgrade Mod"; public static final String MOD_VERSION = "1.0"; public static final String MOD_DEPENDENCIES = "after:ComputerCraft"; public static final String MOD_ACCEPTED_MC_VERSIONS = "[1.8,1.8.9]"; @EventHandler public void init(FMLInitializationEvent event) { ComputerCraftAPI.registerTurtleUpgrade(new TurtleSample()); } }
TurtleSample.java
// package mods.sample.upgrade; import javax.vecmath.Matrix4f; import net.minecraft.client.Minecraft; import net.minecraft.client.resources.model.IBakedModel; import net.minecraft.init.Items; import net.minecraft.item.ItemStack; import net.minecraft.util.EnumFacing; import net.minecraft.util.ResourceLocation; import net.minecraftforge.fml.relauncher.Side; import net.minecraftforge.fml.relauncher.SideOnly; import org.apache.commons.lang3.tuple.Pair; import dan200.computercraft.api.peripheral.IPeripheral; import dan200.computercraft.api.turtle.ITurtleAccess; import dan200.computercraft.api.turtle.ITurtleUpgrade; import dan200.computercraft.api.turtle.TurtleCommandResult; import dan200.computercraft.api.turtle.TurtleSide; import dan200.computercraft.api.turtle.TurtleUpgradeType; import dan200.computercraft.api.turtle.TurtleVerb; public class TurtleSample implements ITurtleUpgrade { private ResourceLocation upgradeID = new ResourceLocation(SampleUpgradeCore.MOD_ID, "sample"); private ItemStack upgradeItem = new ItemStack(Items.stick); @Override public ResourceLocation getUpgradeID() { return upgradeID; } @Override public int getLegacyUpgradeID() { return -1; } @Override public String getUnlocalisedAdjective() { return "Sample"; } @Override public TurtleUpgradeType getType() { return TurtleUpgradeType.Tool; } @Override public ItemStack getCraftingItem() { return upgradeItem; } @Override public IPeripheral createPeripheral(ITurtleAccess turtle, TurtleSide side) { return null; } @Override public TurtleCommandResult useTool(ITurtleAccess turtle, TurtleSide side, TurtleVerb verb, EnumFacing direction) { switch(verb) { case Dig: return dig(turtle, direction); case Attack: return attack(turtle, direction); } return TurtleCommandResult.failure("Undefined command"); } @Override @SideOnly(Side.CLIENT) public Pair<IBakedModel, Matrix4f> getModel(ITurtleAccess turtle, TurtleSide side) { float xOffset = (side == TurtleSide.Left) ? -0.40625F : 0.40625F; Matrix4f transform = new Matrix4f( 0.0F, 0.0F, -1.0F, 1.0F + xOffset, 1.0F, 0.0F, 0.0F, 0.0F, 0.0F, -1.0F, 0.0F, 1.0F, 0.0F, 0.0F, 0.0F, 1.0F); Minecraft mc = Minecraft.getMinecraft(); IBakedModel model = mc.getRenderItem().getItemModelMesher().getItemModel(upgradeItem); return Pair.of(model, transform); } @Override public void update(ITurtleAccess turtle, TurtleSide side) { } private TurtleCommandResult dig(ITurtleAccess turtle, EnumFacing direction) { return TurtleCommandResult.success(new Object[] {"DIG to " + direction.getName()}); } private TurtleCommandResult attack(ITurtleAccess turtle, EnumFacing direction) { return TurtleCommandResult.success(new Object[] {"ATTACK to " + direction.getName()}); } }
解説
SampleUpgradeCore.java
Modのコアとなるクラス
- dependencies
@Mod( dependencies = SampleUpgradeCore.MOD_DEPENDENCIES ) public class SampleUpgradeCore { public static final String MOD_DEPENDENCIES = "after:ComputerCraft";
このmodがComputerCraftの後に読み込まれるように設定しています。
- TurtleUpgradeの登録
ComputerCraftAPI.registerTurtleUpgrade(new TurtleSample());
実装したITurtleUpgrade(後述)のインスタンスをComputerCraftに登録します。
これは、実装したTurtleUpgradeをTurtleへ装着するために必須です。
TurtleSample.java
Turtle Upgradeの機能を定義するクラス
- ITurtleUpgradeの実装
public class TurtleSample implements ITurtleUpgrade {
ITurtleUpgradeを実装します。
前述の通り、このクラスのインスタンスをComputerCraftへ登録します。
- getUpgradeID()
private ResourceLocation upgradeID = new ResourceLocation(SampleUpgradeCore.MOD_ID, "sample"); @Override public ResourceLocation getUpgradeID() { return upgradeID; }
ComputerCraftがTurtle Upgradeを識別するためのIDを返します。戻り値のResourceLocationに設定する文字列は、他のTurtle Upgradeと重複しないものである必要があります。
今回はUpgradeIDとして"sampleupgrademod:sample"という文字列を設定しています。
- getLegacyUpgradeID()
@Override public int getLegacyUpgradeID() { return -1; }
MC1.8以前のワールドで使用されていたTurtle UpgradeをMC1.8以降へ引き継ぎたい場合、MC1.8以前(CC1.75まで)のgetUpgradeIDと同じ値を返すようにします。
旧バージョンとの互換性を考えない場合は -1 を返します。
- getUnlocalisedAdjective()
@Override public String getUnlocalisedAdjective() { return "Sample"; }
Turtle Upgradeを装着した際にTurtleのアイテム名に付与される形容詞を指定します。
今回の例では“Sample Turtle”のようになります。
戻り値は表示される前にStatCollector#translateToLocalで処理されるため、langファイルによる翻訳も可能です。
例えば次のようなlangファイル(UTF-8で保存)を assets\<mod_id>\lang\ja_JP.lang に置いてこのメソッドで"Sample"を返した場合、Minecraftの言語設定を日本語にしたときに「サンプル Turtle」のように表示されます。
Sample=サンプル
- getType()
@Override public TurtleUpgradeType getType() { return TurtleUpgradeType.Tool; }
Turtle Upgradeの種類をTurtleUpgradeTypeの値で指定します。
今回はツールタイプなので TurtleUpgradeType.Tool を返しています。
- getCraftingItem()
private ItemStack upgradeItem = new ItemStack(Items.stick); @Override public ItemStack getCraftingItem() { return upgradeItem; }
Turtle Upgradeを装着するためのアイテムをItemStackで指定します。
今回はバニラアイテムの棒を指定していますが、modで追加した独自アイテムも同様に指定できます。
- createPeripheral()
@Override public IPeripheral createPeripheral(ITurtleAccess turtle, TurtleSide side) { return null; }
周辺機器タイプのTurtle Upgradeでは周辺機器のインスタンスを返します。
今回のようなツールタイプのTurtle Upgradeではそもそも呼び出されないため、nullを返しています。
- useTool()
@Override public TurtleCommandResult useTool(ITurtleAccess turtle, TurtleSide side, TurtleVerb verb, EnumFacing direction) { switch(verb) { case Dig: return dig(turtle, direction); case Attack: return attack(turtle, direction); } return TurtleCommandResult.failure("Undefined command"); }
ツールタイプのTurtle Upgradeでゲーム内のLuaからturtle.dig()やturtle.attack()が呼ばれたときに呼び出されます。
digとattackのどちらが呼ばれたのかは引数verbの値で判別可能です。
戻り値は行動成功時にはTurtleCommandResult.success()、失敗時にはTurtleCommandResult.failure()を返します。
TurtleCommandResult.success()ではObject[]で追加パラメータ(値はIPeripheral#callMethodと同様にLuaの型へ変換されます)を、TurtleCommandResult.failure()では文字列で失敗理由を同時に返すことも可能です。
今回はdigとattackの処理をそれぞれ別のprivateメソッドで行っています。
private TurtleCommandResult dig(ITurtleAccess turtle, EnumFacing direction) { return TurtleCommandResult.success(new Object[] {"DIG to " + direction.getName()}); } private TurtleCommandResult attack(ITurtleAccess turtle, EnumFacing direction) { return TurtleCommandResult.success(new Object[] {"ATTACK to " + direction.getName()}); }
無条件に行動成功とし、呼び出した行動の種類と方向が分かる文字列を返しています。
例えばLua側からturtle.digDown()を呼び出したときは、Lua側への次のような値が返ります。
true, "DIG to down"
- getModel()
@Override @SideOnly(Side.CLIENT) public Pair<IBakedModel, Matrix4f> getModel(ITurtleAccess turtle, TurtleSide side) { float xOffset = (side == TurtleSide.Left) ? -0.40625F : 0.40625F; Matrix4f transform = new Matrix4f( 0.0F, 0.0F, -1.0F, 1.0F + xOffset, 1.0F, 0.0F, 0.0F, 0.0F, 0.0F, -1.0F, 0.0F, 1.0F, 0.0F, 0.0F, 0.0F, 1.0F); Minecraft mc = Minecraft.getMinecraft(); IBakedModel model = mc.getRenderItem().getItemModelMesher().getItemModel(upgradeItem); return Pair.of(model, transform); }
Turtleに装着されたTurtle Upgradeの外観を指定します。
戻り値はPair<IBakedModel, Matrix4f>で、IBakedModelがモデル、Matrix4fがモデルを変形する座標変換行列です。
今回はCC1.76の実装を参考にしています。
- update()
@Override public void update(ITurtleAccess turtle, TurtleSide side) { }
Turtle UpgradeがTurtleに装着されている間、毎tick呼び出されます。
ロードされているワールド上で装着されている数だけ呼び出されますが、各パラメータでどれに対する呼び出しなのかが判別が可能です。
また、サーバ側とクライアント側でそれぞれ別に呼び出されますが、どちら側の呼び出しなのかはturtle.getWorld().isRemoteの値で判別可能です。
今回は何もしていません。