提供: Minecraft Modding Wiki
(新規作成) |
(FML仕様のパケットシステムに変更。) |
||
1行目: | 1行目: | ||
− | {{前提MOD|reqmod="Minecraft Forge Universal 10.12. | + | {{前提MOD|reqmod="Minecraft Forge Universal 10.12.1.1090~"}} |
==パケットについて== | ==パケットについて== | ||
<p>1.7.2でパケット関連のシステムが大幅に変更され、nettyと呼ばれるオープンプロジェクトのシステムを利用したHandshake方式になりました。<br> | <p>1.7.2でパケット関連のシステムが大幅に変更され、nettyと呼ばれるオープンプロジェクトのシステムを利用したHandshake方式になりました。<br> | ||
− | + | 以前ここで解説したパケットシステムはメモリリークを誘発するので、こちらの方法が推奨されています。</p> | |
− | == | + | ==ソースコード== |
− | + | ===PacketHander=== | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | === | ||
<source lang = "java"> | <source lang = "java"> | ||
− | |||
− | + | package mods.samplepacketmod; | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
import cpw.mods.fml.common.network.NetworkRegistry; | import cpw.mods.fml.common.network.NetworkRegistry; | ||
− | import cpw.mods.fml.common.network. | + | import cpw.mods.fml.common.network.simpleimpl.SimpleNetworkWrapper; |
import cpw.mods.fml.relauncher.Side; | import cpw.mods.fml.relauncher.Side; | ||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | public class PacketHandler { | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | //このMOD用のSimpleNetworkWrapperを生成。チャンネルの文字列は固有であれば何でも良い。MODIDの利用を推奨。 | |
− | + | public static final SimpleNetworkWrapper INSTANCE = NetworkRegistry.INSTANCE.newSimpleChannel("SamplePacketMod"); | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | public static void init() { | |
− | |||
− | |||
− | |||
− | |||
− | + | /*IMesssageHandlerクラスとMessageクラスの登録。今回同じクラスにしているが、別々でもよい。 | |
− | + | *第三引数:MessageクラスのMOD内での登録ID。256個登録できる | |
− | + | *第四引数:送り先指定。クライアントかサーバーか、Side.CLIENT Side.SERVER*/ | |
+ | INSTANCE.registerMessage(MessageSample.class, MessageSample.class, 0, Side.SERVER); | ||
+ | } | ||
+ | }</source> | ||
− | + | ===MessageSample=== | |
− | + | <source lang = "java"> | |
− | + | package mods.samplepacketmod; | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | import cpw.mods.fml.client.FMLClientHandler; | |
− | + | import cpw.mods.fml.common.FMLCommonHandler; | |
− | + | import cpw.mods.fml.common.network.simpleimpl.IMessage; | |
− | + | import cpw.mods.fml.common.network.simpleimpl.IMessageHandler; | |
− | + | import cpw.mods.fml.common.network.simpleimpl.MessageContext; | |
− | + | import io.netty.buffer.ByteBuf; | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | public class MessageSample implements IMessage, IMessageHandler<MessageSample, IMessage> { | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | private byte data; | |
− | |||
− | |||
− | |||
− | + | public MessageSample(){} | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | public MessageSample(byte par1) { | |
− | + | this.data= par1; | |
− | + | } | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | @Override//IMessageのメソッド。ByteBufからデータを読み取る。 | |
− | + | public void fromBytes(ByteBuf buf) { | |
− | + | this.data= buf.readByte(); | |
− | + | } | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | @Override//IMessageのメソッド。ByteBufにデータを書き込む。 | |
− | + | public void toBytes(ByteBuf buf) { | |
− | + | buf.writeByte(this.data); | |
− | + | } | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | @Override//IMessageHandlerのメソッド | |
− | + | public IMessage onMessage(MessageKeyPressed message, MessageContext ctx) { | |
− | + | //クライアントへ送った際に、Worldインスタンスはこのように取れる。 | |
− | + | //FMLClientHandler.instance().getClient().theWorld | |
− | + | //サーバーへ送った際に、EntityPlayerインスタンス(EntityPlayerMPインスタンス)はこのように取れる。 | |
− | + | //EntityPlayer entityPlayer = ctx.getServerHandler().playerEntity; | |
− | + | //Do something. | |
− | + | return null;//本来は返答用IMessageインスタンスを返すのだが、旧来のパケットの使い方をするなら必要ない。 | |
− | + | } | |
− | |||
− | |||
} | } | ||
</source> | </source> | ||
− | + | ===@Modクラス内の記述=== | |
− | |||
− | ===@ | ||
<source lang = "java"> | <source lang = "java"> | ||
− | + | package mods.samplepacketmod; | |
− | + | import cpw.mods.fml.common.Mod; | |
− | + | import cpw.mods.fml.common.event.FMLPreInitializationEvent; | |
− | |||
− | |||
− | |||
− | |||
− | @EventHandler | + | @Mod(modid="SamplePacketMod", name="SamplePacketMod", version="1.0.0",dependencies="required-after:Forge@[10.12.1.1090,)") |
− | public void | + | public class SamplePacketMod { |
− | + | @Mod.Instance("SamplePacketMod") | |
+ | public static SamplePacketMod instance; | ||
+ | @Mod.EventHandler | ||
+ | public void preInit(FMLPreInitializationEvent event) | ||
+ | { | ||
+ | PacketHandler.init(); | ||
+ | } | ||
} | } | ||
</source> | </source> | ||
− | == | + | ===パケットを送る際の記述=== |
− | |||
− | == | ||
− | |||
− | |||
− | |||
− | |||
<source lang = "java"> | <source lang = "java"> | ||
− | + | PacketHandler.INSTANCE.sendToServer(new MessageSample(data)); | |
− | + | </source> | |
− | + | ==解説== | |
− | + | Nettyを利用していることには変わりないので、パケット(Message)の書き方が1.6とは大分違ったものとなっている。<br> | |
− | + | ソース内に必要なコメントは載せているので、パケットの流れを解説する。<br> | |
− | / | ||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | PacketHandler.INSTANCE.sendToServer<br> | |
− | + | ↓<br> | |
− | + | IMessageのtoBytesメソッド<br> | |
− | + | ↓<br> | |
− | + | サーバーorクライアントへ<br> | |
− | + | ↓<br> | |
− | + | IMessageのfromBytesメソッド<br> | |
− | + | ↓<br> | |
− | + | IMessageHandlerのonMessageメソッド<br> | |
− | + | IMessageクラスに引数を指定したコンストラクタを用意する必要はないが、例のように、用意したほうが利便性は高い。 | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | < |
2014年5月31日 (土) 21:43時点における版
この記事は"Minecraft Forge Universal 10.12.1.1090~"を前提MODとしています。 |
パケットについて
1.7.2でパケット関連のシステムが大幅に変更され、nettyと呼ばれるオープンプロジェクトのシステムを利用したHandshake方式になりました。
以前ここで解説したパケットシステムはメモリリークを誘発するので、こちらの方法が推奨されています。
ソースコード
PacketHander
package mods.samplepacketmod; import cpw.mods.fml.common.network.NetworkRegistry; import cpw.mods.fml.common.network.simpleimpl.SimpleNetworkWrapper; import cpw.mods.fml.relauncher.Side; public class PacketHandler { //このMOD用のSimpleNetworkWrapperを生成。チャンネルの文字列は固有であれば何でも良い。MODIDの利用を推奨。 public static final SimpleNetworkWrapper INSTANCE = NetworkRegistry.INSTANCE.newSimpleChannel("SamplePacketMod"); public static void init() { /*IMesssageHandlerクラスとMessageクラスの登録。今回同じクラスにしているが、別々でもよい。 *第三引数:MessageクラスのMOD内での登録ID。256個登録できる *第四引数:送り先指定。クライアントかサーバーか、Side.CLIENT Side.SERVER*/ INSTANCE.registerMessage(MessageSample.class, MessageSample.class, 0, Side.SERVER); } }
MessageSample
package mods.samplepacketmod; import cpw.mods.fml.client.FMLClientHandler; import cpw.mods.fml.common.FMLCommonHandler; import cpw.mods.fml.common.network.simpleimpl.IMessage; import cpw.mods.fml.common.network.simpleimpl.IMessageHandler; import cpw.mods.fml.common.network.simpleimpl.MessageContext; import io.netty.buffer.ByteBuf; public class MessageSample implements IMessage, IMessageHandler<MessageSample, IMessage> { private byte data; public MessageSample(){} public MessageSample(byte par1) { this.data= par1; } @Override//IMessageのメソッド。ByteBufからデータを読み取る。 public void fromBytes(ByteBuf buf) { this.data= buf.readByte(); } @Override//IMessageのメソッド。ByteBufにデータを書き込む。 public void toBytes(ByteBuf buf) { buf.writeByte(this.data); } @Override//IMessageHandlerのメソッド public IMessage onMessage(MessageKeyPressed message, MessageContext ctx) { //クライアントへ送った際に、Worldインスタンスはこのように取れる。 //FMLClientHandler.instance().getClient().theWorld //サーバーへ送った際に、EntityPlayerインスタンス(EntityPlayerMPインスタンス)はこのように取れる。 //EntityPlayer entityPlayer = ctx.getServerHandler().playerEntity; //Do something. return null;//本来は返答用IMessageインスタンスを返すのだが、旧来のパケットの使い方をするなら必要ない。 } }
@Modクラス内の記述
package mods.samplepacketmod; import cpw.mods.fml.common.Mod; import cpw.mods.fml.common.event.FMLPreInitializationEvent; @Mod(modid="SamplePacketMod", name="SamplePacketMod", version="1.0.0",dependencies="required-after:Forge@[10.12.1.1090,)") public class SamplePacketMod { @Mod.Instance("SamplePacketMod") public static SamplePacketMod instance; @Mod.EventHandler public void preInit(FMLPreInitializationEvent event) { PacketHandler.init(); } }
パケットを送る際の記述
PacketHandler.INSTANCE.sendToServer(new MessageSample(data));
解説
Nettyを利用していることには変わりないので、パケット(Message)の書き方が1.6とは大分違ったものとなっている。
ソース内に必要なコメントは載せているので、パケットの流れを解説する。
PacketHandler.INSTANCE.sendToServer
↓
IMessageのtoBytesメソッド
↓
サーバーorクライアントへ
↓
IMessageのfromBytesメソッド
↓
IMessageHandlerのonMessageメソッド
IMessageクラスに引数を指定したコンストラクタを用意する必要はないが、例のように、用意したほうが利便性は高い。