1
0
mirror of https://github.com/Minestom/Minestom.git synced 2025-03-31 17:05:54 +02:00

fix: EquipmentSlot ordering was wrong for sending item components e.g. Equippable

This commit is contained in:
steank 2024-12-04 19:34:15 -08:00 committed by Matt Worzala
parent 13d74663f1
commit 0668be90c5
2 changed files with 38 additions and 10 deletions
src/main/java/net/minestom/server
entity
network/packet/server/play

View File

@ -2,23 +2,26 @@ package net.minestom.server.entity;
import net.minestom.server.network.NetworkBuffer; import net.minestom.server.network.NetworkBuffer;
import net.minestom.server.utils.nbt.BinaryTagSerializer; import net.minestom.server.utils.nbt.BinaryTagSerializer;
import org.jetbrains.annotations.ApiStatus;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import java.util.Arrays; import java.util.Arrays;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.stream.Collectors; import java.util.stream.Collectors;
import net.minestom.server.item.component.Equippable;
import net.minestom.server.network.packet.server.play.EntityEquipmentPacket;
import static net.minestom.server.utils.inventory.PlayerInventoryUtils.*; import static net.minestom.server.utils.inventory.PlayerInventoryUtils.*;
public enum EquipmentSlot { public enum EquipmentSlot {
MAIN_HAND(false, -1, "mainhand"), MAIN_HAND(false, -1, "mainhand", 0),
OFF_HAND(false, -1, "offhand"), BOOTS(true, BOOTS_SLOT, "feet", 2),
BOOTS(true, BOOTS_SLOT, "feet"), LEGGINGS(true, LEGGINGS_SLOT, "legs", 3),
LEGGINGS(true, LEGGINGS_SLOT, "legs"), CHESTPLATE(true, CHESTPLATE_SLOT, "chest", 4),
CHESTPLATE(true, CHESTPLATE_SLOT, "chest"), HELMET(true, HELMET_SLOT, "head", 5),
HELMET(true, HELMET_SLOT, "head"), OFF_HAND(false, -1, "offhand", 1),
BODY(false, -1, "body"); BODY(false, -1, "body", 6);
private static final List<EquipmentSlot> ARMORS = List.of(BOOTS, LEGGINGS, CHESTPLATE, HELMET); private static final List<EquipmentSlot> ARMORS = List.of(BOOTS, LEGGINGS, CHESTPLATE, HELMET);
private static final Map<String, EquipmentSlot> BY_NBT_NAME = Arrays.stream(values()) private static final Map<String, EquipmentSlot> BY_NBT_NAME = Arrays.stream(values())
@ -31,11 +34,13 @@ public enum EquipmentSlot {
private final boolean armor; private final boolean armor;
private final int armorSlot; private final int armorSlot;
private final String nbtName; private final String nbtName;
private final int equipmentSlot;
EquipmentSlot(boolean armor, int armorSlot, String nbtName) { EquipmentSlot(boolean armor, int armorSlot, String nbtName, int equipmentSlot) {
this.armor = armor; this.armor = armor;
this.armorSlot = armorSlot; this.armorSlot = armorSlot;
this.nbtName = nbtName; this.nbtName = nbtName;
this.equipmentSlot = equipmentSlot;
} }
public boolean isHand() { public boolean isHand() {
@ -46,6 +51,16 @@ public enum EquipmentSlot {
return armor; return armor;
} }
/**
* Differs from the ordinal only slightly - the ordinal is used for sending components such as {@link Equippable},
* but this value needs to be used instead for {@link EntityEquipmentPacket}.
*
* @return the equipment slot
*/
public int equipmentSlot() {
return equipmentSlot;
}
public int armorSlot() { public int armorSlot() {
return armorSlot; return armorSlot;
} }
@ -58,4 +73,17 @@ public enum EquipmentSlot {
return ARMORS; return ARMORS;
} }
@ApiStatus.Internal
public static @NotNull EquipmentSlot fromEquipmentSlot(int equipmentSlot) {
return switch (equipmentSlot) {
case 0 -> EquipmentSlot.MAIN_HAND;
case 1 -> EquipmentSlot.OFF_HAND;
case 2 -> EquipmentSlot.BOOTS;
case 3 -> EquipmentSlot.LEGGINGS;
case 4 -> EquipmentSlot.CHESTPLATE;
case 5 -> EquipmentSlot.HELMET;
case 6 -> EquipmentSlot.BODY;
default -> throw new IllegalStateException("Unexpected value: " + equipmentSlot);
};
}
} }

View File

@ -28,7 +28,7 @@ public record EntityEquipmentPacket(int entityId,
int index = 0; int index = 0;
for (var entry : value.equipments.entrySet()) { for (var entry : value.equipments.entrySet()) {
final boolean last = index++ == value.equipments.size() - 1; final boolean last = index++ == value.equipments.size() - 1;
byte slotEnum = (byte) entry.getKey().ordinal(); byte slotEnum = (byte) entry.getKey().equipmentSlot();
if (!last) slotEnum |= 0x80; if (!last) slotEnum |= 0x80;
buffer.write(BYTE, slotEnum); buffer.write(BYTE, slotEnum);
buffer.write(ItemStack.NETWORK_TYPE, entry.getValue()); buffer.write(ItemStack.NETWORK_TYPE, entry.getValue());
@ -62,7 +62,7 @@ public record EntityEquipmentPacket(int entityId,
byte slot; byte slot;
do { do {
slot = reader.read(BYTE); slot = reader.read(BYTE);
equipments.put(EquipmentSlot.values()[slot & 0x7F], reader.read(ItemStack.NETWORK_TYPE)); equipments.put(EquipmentSlot.fromEquipmentSlot(slot & 0x7F), reader.read(ItemStack.NETWORK_TYPE));
} while ((slot & 0x80) == 0x80); } while ((slot & 0x80) == 0x80);
return equipments; return equipments;
} }