diff --git a/core/src/main/java/org/geysermc/geyser/entity/type/DisplayBaseEntity.java b/core/src/main/java/org/geysermc/geyser/entity/type/DisplayBaseEntity.java index 16587d125..414ed0541 100644 --- a/core/src/main/java/org/geysermc/geyser/entity/type/DisplayBaseEntity.java +++ b/core/src/main/java/org/geysermc/geyser/entity/type/DisplayBaseEntity.java @@ -66,7 +66,7 @@ public class DisplayBaseEntity extends Entity { this.setRiderSeatPosition(this.baseTranslation); this.moveRelative(this.baseTranslation.getX(), this.baseTranslation.getY(), this.baseTranslation.getZ(), yaw, pitch, headYaw, false); } else { - EntityUtils.updateMountOffset(this, this.vehicle, true, true, false); + EntityUtils.updateMountOffset(this, this.vehicle, true, true, 0, 1); this.updateBedrockMetadata(); } } diff --git a/core/src/main/java/org/geysermc/geyser/entity/type/Entity.java b/core/src/main/java/org/geysermc/geyser/entity/type/Entity.java index fa1f05417..b03dea3ed 100644 --- a/core/src/main/java/org/geysermc/geyser/entity/type/Entity.java +++ b/core/src/main/java/org/geysermc/geyser/entity/type/Entity.java @@ -621,7 +621,7 @@ public class Entity implements GeyserEntity { Entity passenger = passengers.get(i); if (passenger != null) { boolean rider = i == 0; - EntityUtils.updateMountOffset(passenger, this, rider, true, passengers.size() > 1); + EntityUtils.updateMountOffset(passenger, this, rider, true, i, passengers.size()); passenger.updateBedrockMetadata(); } } @@ -633,7 +633,7 @@ public class Entity implements GeyserEntity { protected void updateMountOffset() { if (vehicle != null) { boolean rider = vehicle.getPassengers().get(0) == this; - EntityUtils.updateMountOffset(this, vehicle, rider, true, vehicle.getPassengers().size() > 1); + EntityUtils.updateMountOffset(this, vehicle, rider, true, vehicle.getPassengers().indexOf(this), vehicle.getPassengers().size()); updateBedrockMetadata(); } } diff --git a/core/src/main/java/org/geysermc/geyser/entity/type/living/animal/HappyGhastEntity.java b/core/src/main/java/org/geysermc/geyser/entity/type/living/animal/HappyGhastEntity.java index 44ad0b7e8..99eac9a8b 100644 --- a/core/src/main/java/org/geysermc/geyser/entity/type/living/animal/HappyGhastEntity.java +++ b/core/src/main/java/org/geysermc/geyser/entity/type/living/animal/HappyGhastEntity.java @@ -51,6 +51,9 @@ import java.util.UUID; public class HappyGhastEntity extends AnimalEntity implements ClientVehicle { + public static final float[] X_OFFSETS = {0.0F, -1.7F, 0.0F, 1.7F}; + public static final float[] Z_OFFSETS = {1.7F, 0.0F, -1.7F, 0.0F}; + private final HappyGhastVehicleComponent vehicleComponent = new HappyGhastVehicleComponent(this, 0.0f); private boolean staysStill; private float speed; diff --git a/core/src/main/java/org/geysermc/geyser/translator/protocol/java/entity/JavaSetPassengersTranslator.java b/core/src/main/java/org/geysermc/geyser/translator/protocol/java/entity/JavaSetPassengersTranslator.java index 1ca9e268a..3bc25c986 100644 --- a/core/src/main/java/org/geysermc/geyser/translator/protocol/java/entity/JavaSetPassengersTranslator.java +++ b/core/src/main/java/org/geysermc/geyser/translator/protocol/java/entity/JavaSetPassengersTranslator.java @@ -25,6 +25,7 @@ package org.geysermc.geyser.translator.protocol.java.entity; +import lombok.NonNull; import org.cloudburstmc.protocol.bedrock.data.entity.EntityDataTypes; import org.cloudburstmc.protocol.bedrock.data.entity.EntityLinkData; import org.cloudburstmc.protocol.bedrock.packet.SetEntityLinkPacket; @@ -50,7 +51,10 @@ public class JavaSetPassengersTranslator extends PacketTranslator newPassengers = new ArrayList<>(); - for (int passengerId : packet.getPassengerIds()) { + int @NonNull [] passengerIds = packet.getPassengerIds(); + for (int i = 0; i < passengerIds.length; i++) { + int passengerId = passengerIds[i]; + Entity passenger = session.getEntityCache().getEntityByJavaId(passengerId); if (passenger == session.getPlayerEntity()) { session.getPlayerEntity().setVehicle(entity); @@ -76,13 +80,15 @@ public class JavaSetPassengersTranslator extends PacketTranslator 1)); + EntityUtils.updateMountOffset(passenger, entity, rider, true, i, packet.getPassengerIds().length); // Force an update to the passenger metadata passenger.updateBedrockMetadata(); } // Handle passengers that were removed - for (Entity passenger : entity.getPassengers()) { + List passengers = entity.getPassengers(); + for (int i = 0; i < passengers.size(); i++) { + Entity passenger = passengers.get(i); if (passenger == null) { continue; } @@ -93,7 +99,7 @@ public class JavaSetPassengersTranslator extends PacketTranslator 1)); + EntityUtils.updateMountOffset(passenger, entity, false, false, i, packet.getPassengerIds().length); // Force an update to the passenger metadata passenger.updateBedrockMetadata(); diff --git a/core/src/main/java/org/geysermc/geyser/util/EntityUtils.java b/core/src/main/java/org/geysermc/geyser/util/EntityUtils.java index c6797ab79..9cdcbed9f 100644 --- a/core/src/main/java/org/geysermc/geyser/util/EntityUtils.java +++ b/core/src/main/java/org/geysermc/geyser/util/EntityUtils.java @@ -167,7 +167,7 @@ public final class EntityUtils { /** * Adjust an entity's height if they have mounted/dismounted an entity. */ - public static void updateMountOffset(Entity passenger, Entity mount, boolean rider, boolean riding, boolean moreThanOneEntity) { + public static void updateMountOffset(Entity passenger, Entity mount, boolean rider, boolean riding, int index, int passengers) { passenger.setFlag(EntityFlag.RIDING, riding); if (riding) { // Without the Y offset, Bedrock players will find themselves in the floor when mounting @@ -180,7 +180,7 @@ public final class EntityUtils { switch (mount.getDefinition().entityType()) { case CAMEL -> { zOffset = 0.5f; - if (moreThanOneEntity) { + if (passengers > 1) { if (!rider) { zOffset = -0.7f; } @@ -223,18 +223,18 @@ public final class EntityUtils { } } case HAPPY_GHAST -> { - // TODO seat index matters here, likely // 0.0, 5.02001, 1.7 BDS - xOffset = 0; + int seatingIndex = Math.min(index, 4); + xOffset = HappyGhastEntity.X_OFFSETS[seatingIndex]; yOffset = 3.4f; - zOffset = 1.7f; + zOffset = HappyGhastEntity.Z_OFFSETS[seatingIndex]; } } if (mount instanceof ChestBoatEntity) { xOffset = 0.15F; } else if (mount instanceof BoatEntity) { // Without the X offset, more than one entity on a boat is stacked on top of each other - if (moreThanOneEntity) { + if (passengers > 1) { xOffset = rider ? 0.2f : -0.6f; if (passenger instanceof AnimalEntity) { xOffset += 0.2f;