この記事は"Minecraft Forge4.3x"を前提MODとしています。 |
目次
より自由になったコーディング記法
新しいアノテーション@Modと@NetworkModにより, Modの核となるクラス(従来のBaseModを継承したクラス)は自由なクラス名とパッケージを利用することが可能になった. 以下に何もしない空のMod, Sample.javaを示す.
package mods.sample; import net.minecraft.src.*; import cpw.mods.fml.common.Mod; import cpw.mods.fml.common.network.NetworkMod; @Mod( modid = "sample", name = "sample mod", version = "1.0.0" ) @NetworkMod( clientSideRequired = true, serverSideRequired = false ) public class Sample { }
@Modアノテーション
@ModアノテーションはModに対し最低でも以下の要素を持たせるアノテーションである.
- Mod固有のID(他のModと重複しない文字列)
- Mod名
- Modのバージョン
このアノテーションが付与されたクラスが従来のBaseModに相当することになる. FMLはmodsフォルダ内にあるクラスを走査し, このアノテーションを持つクラスからロードすることになる.
@NetworkModアノテーション
@NetworkModアノテーションはModに対しクライアントとサーバー間の連携を示すためのアノテーションである. 上記の例では
clientSideRequired = true, serverSideRequired = false
のみとなっている. これは「このModはクライアントに導入する必要があり, 導入されていない場合は接続を切断する」ということになる. それ以外にも以下のような要素を持つが, これらは後述のチュートリアルで利用する際に解説する.
channels = {"channelName"}, packetHandler = PacketHandler.class, connectionHandler = ConnectionHandler.class
クライアント, サーバーのコード統一化によるModのUniversal化
Minecraft1.3からクライアント, サーバーのコードの統一化が図れた. これに伴いMinecraftForge 4xから共通部分(common), クライアントのみ(minecraft), サーバーのみ(minecraft_server)と開発環境では整理された. Moddingを行う場合, 通常common以下で作成する. このときnet/minecraft/srcに入れるのではなく, 新しいフォルダを作成し, その中で適切なパッケージを宣言して作成してもよい.
Universal化による注意点
Universal化によってコードは統一されるが, 実行されるコードは同じではないことに注意する必要がある. 特にWorldに対し作用を行う処理(主にEntity)ではサーバー側のワールドでのみ実行する必要がある. forgeインストール後, common以下の各ソースコードを読むとところどころに以下のような条件分岐が多々ある.
if (!world.isRemote) { .... }
このworld.isRemoteとはすなわち,
- クライアントがサーバーに接続しているワールドならtrue
- それ以外はfalse
ひとつの例としてworld.spawnEntityInWorldはサーバー側で行わなければならない. もし上記の条件がなければどうなるかは, 実際にコードを書いてみて試すと分かる.
クライアント側のみの処理を指定するアノテーション
コードが統一化されたと言っても, GUIやレンダー, キーイベントなどはクライアント側でのみ行われる. そのためにひとつのクラスまたはメソッドをクライアント専用にすることでサーバー側で読み込まれないようにすることが可能である.
@SideOnly(Side.CLIENT)
このアノテーションが付与されたクラス/メソッドがクライアント専用であることを示す. なおこのアノテーションとEnumは以下のimportが必要になる.
import cpw.mods.fml.common.Side; import cpw.mods.fml.common.asm.SideOnly;
また, この@SideOnlyアノテーションは当然ながらサーバー専用を明示することも可能である.
@SideOnly(Side.SERVER)
ただし, サーバー側の処理≒共通処理になっているためほとんど使われることはない. バニラのminecraft_server側でも数クラスあるだけである.
ModLoaderとMinecraft Forgeの違い
基本的にMinecraft Forgeに同梱されているForgeModLoader(FML)はModLoaderと互換性を備えている. しかし, FMLの設計思想からか, 従来のテクニックが使えないことがある.
ModLoaderでしか出来ないこと
21/10/2012現在, 分かっていることは
- バニラのItem, Blockのリストにnullを代入し, 自作のものを差し替えるテクニック
- new File((net.minecraft.src.mod_Mannequin.class).getProtectionDomain().getCodeSource().getLocation().toURI());
のような処理である. 逆に言えば, このような処理を行いたい場合はModLoaderを前提にするほかない.
諸注意
- Minecraft Forgeのバージョンはrecommendedを選ぶか, 他のModが前提にしているバージョンを選ぶ
- コーディングの際はファイルの文字コードをUTF-8かUTF-8Nにする