User Tools

Site Tools


zh_cn:tutorial:networking

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
zh_cn:tutorial:networking [2024/05/28 08:52] solidblockzh_cn:tutorial:networking [2024/07/05 10:58] (current) solidblock
Line 43: Line 43:
 要修复崩溃,你需要了解 Minecraft 如何在客户端和专用服务器之间通信(communication)。 要修复崩溃,你需要了解 Minecraft 如何在客户端和专用服务器之间通信(communication)。
  
-[[Minecraft 的逻辑|{{tutorial:sides.png?700}}]]+[[Minecraft 的逻辑|{{tutorial:sides.png?700}}]]
  
 从上面这张图可以看到,游戏客户端和专用服务器是相互分离的系统,并使用数据包(packets,注意不是 datapack)桥接在一起。这个数据包桥(packet bridge)不仅存在于游戏客户端和专用服务器之间,还存在于您的客户端和通过 LAN 连接的另一个客户端之间。注意即使是单人游戏也有数据包桥,这是因为游戏客户端会启动一个特殊的集成服务器实例来运行游戏。下表显示了三种连接类型之间的主要区别: 从上面这张图可以看到,游戏客户端和专用服务器是相互分离的系统,并使用数据包(packets,注意不是 datapack)桥接在一起。这个数据包桥(packet bridge)不仅存在于游戏客户端和专用服务器之间,还存在于您的客户端和通过 LAN 连接的另一个客户端之间。注意即使是单人游戏也有数据包桥,这是因为游戏客户端会启动一个特殊的集成服务器实例来运行游戏。下表显示了三种连接类型之间的主要区别:
Line 74: Line 74:
 </code> </code>
  
-接下来,我们需要将数据包发送到游戏客户端。首先需要定义一个用于识别数据包的 ''Identifier''。对于本例,我们的标识符为 ''wiki_example:highlight_block''。为将数据包发送到游戏客户端,需要指定要哪个玩家的游戏客户端接收数据包。由于该操作发生在逻辑服务器上,所以可以将 ''player'' 向上强转为 ''ServerPlayerEntity''+接下来,我们需要将数据包发送到游戏客户端。首先需要定义一个用于识别数据包的 ''Identifier''。对于本例,我们的标识符为 ''tutorial:highlight_block''。为将数据包发送到游戏客户端,需要指定要哪个玩家的游戏客户端接收数据包。由于该操作发生在逻辑服务器上,所以可以将 ''player'' 向上强转为 ''ServerPlayerEntity'' 
 +<code java> 
 +public class TutorialNetworkingConstants { 
 +    // 存储数据包的 id 以便后面引用 
 +    public static final Identifier HIGHLIGHT_PACKET_ID = Identifier.of("tutorial", "highlight_block"); 
 +
 +</code>
  
 要将数据包发送到玩家,我们使用 ''ServerPlayerNetworking'' 中的一些方法。我们使用该类中的以下方法: 要将数据包发送到玩家,我们使用 ''ServerPlayerNetworking'' 中的一些方法。我们使用该类中的以下方法:
Line 83: Line 89:
 </code> </code>
  
-数据包将会被发送到此方法中的玩家。通道名称是你之前决定用来识别数据包的 ''Identifier''。''PacketByteBuf'' 用于存储数据包的数据。We will return later to writing data to the packet's payload via the buf.+数据包将会被发送到此方法中的玩家。通道名称是你之前决定用来识别数据包的 ''Identifier''。''PacketByteBuf'' 用于存储数据包的数据。然后我们返回,以通过 buf 将数据写入数据包的有效负载。
  
 由于我们没有向数据包写入任何数据,所以现在,我们将发送带有空有效负载的数据包。可以使用 ''PacketByteBufs.empty()'' 创建带有空有效负载的 buf。 由于我们没有向数据包写入任何数据,所以现在,我们将发送带有空有效负载的数据包。可以使用 ''PacketByteBufs.empty()'' 创建带有空有效负载的 buf。
Line 205: Line 211:
  
 ===== 1.20.5 中的网络通信 ===== ===== 1.20.5 中的网络通信 =====
-自 1.20.5 开始,网络通信的逻辑被大改。在 1.20.5 中,你需要定义一个 ''Payload''。首先,定义一个包含了 ''BlockPos'' 的 ''Payload''+自 1.20.5 开始,网络通信的逻辑被大改。在 1.20.5 中,''RegistryByteBuf'' 现在用于游玩阶段网络,你需要定义一个 ''Payload''。首先,定义一个包含了 ''BlockPos'' 的 ''Payload''
  
 <code java> <code java>
 public record BlockHighlightPayload(BlockPos blockPos) implements CustomPayload { public record BlockHighlightPayload(BlockPos blockPos) implements CustomPayload {
-  public static final Id<BlockHighlightPayload> ID = CustomPayload.id("tutorial:block_highlight");+  public static final Id<BlockHighlightPayload> ID = new CustomPayload.Id<>(TutorialNetworkingConstants.HIGHLIGHT_PACKET_ID);
   public static final PacketCodec<PacketByteBuf, BlockHighlightPayload> CODEC = PacketCodec.tuple(BlockPos.PACKET_CODEC, BlockHighlightPayload::blockPos, BlockHighlightPayload::new);   public static final PacketCodec<PacketByteBuf, BlockHighlightPayload> CODEC = PacketCodec.tuple(BlockPos.PACKET_CODEC, BlockHighlightPayload::blockPos, BlockHighlightPayload::new);
   // 或者,你也可以这样写:   // 或者,你也可以这样写:
zh_cn/tutorial/networking.1716886362.txt.gz · Last modified: 2024/05/28 08:52 by solidblock