diff --git a/MinecraftClient/Mapping/World.cs b/MinecraftClient/Mapping/World.cs index b6240ffc..8add5c23 100644 --- a/MinecraftClient/Mapping/World.cs +++ b/MinecraftClient/Mapping/World.cs @@ -1,4 +1,4 @@ -using System; +using System; using System.Collections.Concurrent; using System.Collections.Generic; using System.Linq; @@ -23,6 +23,11 @@ namespace MinecraftClient.Mapping private static readonly Dictionary dimensionList = new(); + /// + /// VarInt ID → dimension name mapping, populated from RegistryData in 1.20.6+ + /// + private static Dictionary dimensionIdMap = new(); + /// /// Chunk data parsing progress /// @@ -212,6 +217,21 @@ namespace MinecraftClient.Mapping StoreDimensionList(defaultRegistryCodec); } + public static void SetDimensionIdMap(Dictionary idMap) + { + dimensionIdMap = idMap; + } + + public static string GetDimensionNameById(int id) + { + return dimensionIdMap.TryGetValue(id, out var name) ? name : "minecraft:overworld"; + } + + public static bool HasAnyDimension() + { + return dimensionList.Count > 0; + } + /// /// Store one dimension - Directly used in 1.16.2 to 1.18.2 /// diff --git a/MinecraftClient/Protocol/Handlers/Protocol18.cs b/MinecraftClient/Protocol/Handlers/Protocol18.cs index a274b6e4..3a0abe27 100644 --- a/MinecraftClient/Protocol/Handlers/Protocol18.cs +++ b/MinecraftClient/Protocol/Handlers/Protocol18.cs @@ -458,40 +458,41 @@ namespace MinecraftClient.Protocol.Handlers } else { - // TODO: Implement proper parsing for 1.20.6 / 1.21 when there is a custom data pack on the server - // THis is a temporary workaround to get the client to be useable asap - var registryId = dataTypes.ReadNextString(packetData); var entryCount = dataTypes.ReadNextVarInt(packetData); - // Ignore other registries to save on time, we need only these 2 - if(registryId is not ("minecraft:dimension_type" or "minecraft:chat_type")) - break; + var isChat = registryId == "minecraft:chat_type"; + var isDimension = registryId == "minecraft:dimension_type"; - var avaliableChats = new Dictionary(); - var dimensionType = new Dictionary(); + var availableChats = isChat ? new Dictionary() : null; + var dimensionIdMap = isDimension ? new Dictionary() : null; for (var i = 0; i < entryCount; i++) { var entryId = dataTypes.ReadNextString(packetData); var hasData = dataTypes.ReadNextBool(packetData); - - if (hasData) - { - // TODO: Parse in case when the server data packs differ from the client - dataTypes.ReadNextNbt(packetData); - } - if (registryId == "minecraft:chat_type") - avaliableChats.Add(i, entryId); - else dimensionType.Add(i, entryId); + Dictionary? nbtData = null; + if (hasData) + nbtData = dataTypes.ReadNextNbt(packetData); + + if (isChat) + availableChats!.Add(i, entryId); + else if (isDimension) + { + dimensionIdMap!.Add(i, entryId); + if (nbtData != null && handler.GetTerrainEnabled()) + World.StoreOneDimension(entryId, nbtData); + } } - if (registryId == "minecraft:chat_type") - ChatParser.ReadChatType(avaliableChats); - else + if (isChat) + ChatParser.ReadChatType(availableChats!); + else if (isDimension) { - World.LoadDefaultDimensions1206Plus(); + World.SetDimensionIdMap(dimensionIdMap!); + if (!handler.GetTerrainEnabled() || !World.HasAnyDimension()) + World.LoadDefaultDimensions1206Plus(); } } @@ -531,7 +532,10 @@ namespace MinecraftClient.Protocol.Handlers knownDataPacks.Add((nameSpace, id, version)); } - SendKnownDataPacks(knownDataPacks); + var vanillaPacks = knownDataPacks + .Where(p => p.Item1 == "minecraft") + .ToList(); + SendKnownDataPacks(vanillaPacks); break; // Ignore other packets at this stage