Fixed Player Carrying, closes #774

This commit is contained in:
Tschipp 2025-07-22 23:48:52 +02:00
parent d1227d3d87
commit 45a2b32c97
10 changed files with 120 additions and 5 deletions

View File

@ -40,6 +40,7 @@ import tschipp.carryon.common.carry.CarryOnDataManager;
import tschipp.carryon.common.carry.PlacementHandler;
import tschipp.carryon.common.command.CommandCarryOn;
import tschipp.carryon.config.ConfigLoader;
import tschipp.carryon.networking.clientbound.ClientboundStartRidingOtherPlayerPacket;
import tschipp.carryon.networking.clientbound.ClientboundStartRidingPacket;
import tschipp.carryon.networking.clientbound.ClientboundSyncScriptsPacket;
import tschipp.carryon.networking.serverbound.ServerboundCarryKeyPressedPacket;
@ -83,6 +84,14 @@ public class CarryOnCommon
ClientboundSyncScriptsPacket::handle,
args
);
Services.PLATFORM.registerClientboundPacket(
ClientboundStartRidingOtherPlayerPacket.TYPE,
ClientboundStartRidingOtherPlayerPacket.class,
ClientboundStartRidingOtherPlayerPacket.CODEC,
ClientboundStartRidingOtherPlayerPacket::handle,
args
);
}
public static void registerConfig()
@ -160,6 +169,16 @@ public class CarryOnCommon
}
}
public static void onRiderDisconnected(Player rider)
{
if(rider.getVehicle() instanceof ServerPlayer vehicle) {
CarryOnData data = CarryOnDataManager.getCarryData(vehicle);
if(data.isCarrying(CarryType.PLAYER)) {
PlacementHandler.placeCarried(vehicle);
}
}
}
private static int potionLevel(CarryOnData carry, Level level)
{

View File

@ -37,5 +37,6 @@ public class Constants {
public static final ResourceLocation PACKET_ID_KEY_PRESSED = ResourceLocation.fromNamespaceAndPath(Constants.MOD_ID, "key_pressed");
public static final ResourceLocation PACKET_ID_START_RIDING = ResourceLocation.fromNamespaceAndPath(Constants.MOD_ID, "start_riding");
public static final ResourceLocation PACKET_ID_SYNC_SCRIPTS = ResourceLocation.fromNamespaceAndPath(Constants.MOD_ID, "sync_scripts");
public static final ResourceLocation PACKET_ID_START_RIDING_OTHER = ResourceLocation.fromNamespaceAndPath(Constants.MOD_ID, "start_riding_other");
}

View File

@ -44,6 +44,7 @@ import tschipp.carryon.common.pickupcondition.PickupCondition;
import tschipp.carryon.common.pickupcondition.PickupConditionHandler;
import tschipp.carryon.common.scripting.CarryOnScript;
import tschipp.carryon.common.scripting.ScriptManager;
import tschipp.carryon.networking.clientbound.ClientboundStartRidingOtherPlayerPacket;
import tschipp.carryon.networking.clientbound.ClientboundStartRidingPacket;
import tschipp.carryon.platform.Services;
@ -224,8 +225,8 @@ public class PickupHandler {
player.getServer().getCommands().performPrefixedCommand(player.getServer().createCommandSourceStack(), "/execute as " + player.getGameProfile().getName() + " run " + cmd);
}
otherPlayer.startRiding(player);
Services.PLATFORM.sendPacketToPlayer(Constants.PACKET_ID_START_RIDING, new ClientboundStartRidingPacket(otherPlayer.getId(), true), player);
otherPlayer.startRiding(player, true);
Services.PLATFORM.sendPacketToAllPlayers(Constants.PACKET_ID_START_RIDING_OTHER, new ClientboundStartRidingOtherPlayerPacket(player.getId(), otherPlayer.getId(), true), player.serverLevel());
carry.setCarryingPlayer();
player.swing(InteractionHand.MAIN_HAND, true);
player.level().playSound(null, player.getOnPos(), SoundEvents.ARMOR_EQUIP_GENERIC.value(), SoundSource.AMBIENT, 1.0f, 0.5f);

View File

@ -46,6 +46,8 @@ import tschipp.carryon.Constants;
import tschipp.carryon.common.carry.CarryOnData.CarryType;
import tschipp.carryon.common.config.ListHandler;
import tschipp.carryon.common.scripting.CarryOnScript.ScriptEffects;
import tschipp.carryon.networking.clientbound.ClientboundStartRidingOtherPlayerPacket;
import tschipp.carryon.platform.Services;
import javax.annotation.Nullable;
import java.util.ArrayList;
@ -173,10 +175,9 @@ public class PlacementHandler
if (carry.isCarrying(CarryType.PLAYER)) {
Entity otherPlayer = player.getFirstPassenger();
player.ejectPassengers();
Services.PLATFORM.sendPacketToAllPlayers(Constants.PACKET_ID_START_RIDING_OTHER, new ClientboundStartRidingOtherPlayerPacket(player.getId(), otherPlayer.getId(), false), player.serverLevel());
carry.clear();
CarryOnDataManager.setCarryData(player, carry);
if (otherPlayer == null)
return true;
otherPlayer.teleportTo(placementPos.x, placementPos.y, placementPos.z);
player.swing(InteractionHand.MAIN_HAND, true);
return true;
@ -222,6 +223,8 @@ public class PlacementHandler
else
entityHeld = player.getFirstPassenger();
if(entityHeld == null)
return;
double sizeHeldEntity = entityHeld.getBbHeight() * entityHeld.getBbWidth();
double distance = entityClicked.blockPosition().distSqr(player.blockPosition());

View File

@ -20,6 +20,7 @@
package tschipp.carryon.mixin;
import com.llamalad7.mixinextras.injector.ModifyExpressionValue;
import net.minecraft.server.level.ServerPlayer;
import net.minecraft.util.Mth;
import net.minecraft.world.entity.Entity;
@ -49,6 +50,12 @@ public abstract class EntityMixin
@Shadow public abstract void onPassengerTurned(Entity $$0);
@ModifyExpressionValue(method = "startRiding(Lnet/minecraft/world/entity/Entity;Z)Z", at = @At(value = "INVOKE", target = "Lnet/minecraft/world/entity/EntityType;canSerialize()Z"))
private boolean onStartRidingCheck(boolean original, Entity entity, boolean force) {
if (force && entity instanceof Player) return true;
return original;
}
@Inject(method = "positionRider(Lnet/minecraft/world/entity/Entity;Lnet/minecraft/world/entity/Entity$MoveFunction;)V", at = @At("HEAD"), cancellable = true)
private void onPositionPassenger(Entity entity, MoveFunction move, CallbackInfo ci)
{

View File

@ -0,0 +1,59 @@
/*
* GNU Lesser General Public License v3
* Copyright (C) 2024 Tschipp
* mrtschipp@gmail.com
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
package tschipp.carryon.networking.clientbound;
import net.minecraft.network.RegistryFriendlyByteBuf;
import net.minecraft.network.codec.ByteBufCodecs;
import net.minecraft.network.codec.StreamCodec;
import net.minecraft.world.entity.Entity;
import net.minecraft.world.entity.player.Player;
import tschipp.carryon.Constants;
import tschipp.carryon.networking.PacketBase;
public record ClientboundStartRidingOtherPlayerPacket(int mount, int rider, boolean ride) implements PacketBase
{
public static final StreamCodec<RegistryFriendlyByteBuf, ClientboundStartRidingOtherPlayerPacket> CODEC = StreamCodec.composite(
ByteBufCodecs.INT, ClientboundStartRidingOtherPlayerPacket::mount,
ByteBufCodecs.INT, ClientboundStartRidingOtherPlayerPacket::rider,
ByteBufCodecs.BOOL, ClientboundStartRidingOtherPlayerPacket::ride,
ClientboundStartRidingOtherPlayerPacket::new
);
public static final Type<ClientboundStartRidingOtherPlayerPacket> TYPE = new Type<>(Constants.PACKET_ID_START_RIDING_OTHER);
@Override
public void handle(Player player)
{
Entity mount = player.level().getEntity(this.mount);
Entity rider = player.level().getEntity(this.rider);
if(mount != null && rider != null)
if(ride)
rider.startRiding(mount, true);
else
rider.stopRiding();
}
@Override
public Type<ClientboundStartRidingOtherPlayerPacket> type() {
return TYPE;
}
}

View File

@ -26,6 +26,7 @@ import net.minecraft.network.RegistryFriendlyByteBuf;
import net.minecraft.network.codec.StreamCodec;
import net.minecraft.network.protocol.common.custom.CustomPacketPayload;
import net.minecraft.resources.ResourceLocation;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.server.level.ServerPlayer;
import net.minecraft.world.entity.player.Player;
import tschipp.carryon.config.BuiltConfig;
@ -67,4 +68,10 @@ public interface IPlatformHelper {
void sendPacketToServer(ResourceLocation id, PacketBase packet);
void sendPacketToPlayer(ResourceLocation id, PacketBase packet, ServerPlayer player);
default void sendPacketToAllPlayers(ResourceLocation id, PacketBase packet, ServerLevel level) {
for(ServerPlayer p : level.players())
sendPacketToPlayer(id, packet, p);
}
}

View File

@ -26,6 +26,7 @@ import net.fabricmc.fabric.api.event.lifecycle.v1.CommonLifecycleEvents;
import net.fabricmc.fabric.api.event.lifecycle.v1.ServerLifecycleEvents;
import net.fabricmc.fabric.api.event.lifecycle.v1.ServerTickEvents;
import net.fabricmc.fabric.api.event.player.*;
import net.fabricmc.fabric.api.networking.v1.ServerPlayConnectionEvents;
import net.fabricmc.fabric.api.resource.ResourceManagerHelper;
import net.minecraft.core.BlockPos;
import net.minecraft.core.Direction;
@ -155,6 +156,10 @@ public class CommonEvents {
return InteractionResult.PASS;
}));
ServerPlayConnectionEvents.DISCONNECT.register((handler, server) -> {
CarryOnCommon.onRiderDisconnected(handler.getPlayer());
});
//TODO: drop carried when attacked
}

View File

@ -40,6 +40,7 @@ import net.minecraftforge.event.TickEvent.ServerTickEvent;
import net.minecraftforge.event.entity.living.LivingAttackEvent;
import net.minecraftforge.event.entity.living.MobSpawnEvent.FinalizeSpawn;
import net.minecraftforge.event.entity.player.AttackEntityEvent;
import net.minecraftforge.event.entity.player.PlayerEvent;
import net.minecraftforge.event.entity.player.PlayerEvent.BreakSpeed;
import net.minecraftforge.event.entity.player.PlayerEvent.Clone;
import net.minecraftforge.event.entity.player.PlayerInteractEvent;
@ -218,4 +219,10 @@ public class CommonEvents
CarryOnCommon.onPlayerAttacked(player);
}
@SubscribeEvent
public static void onPlayerLoggedOut(PlayerEvent.PlayerLoggedOutEvent event) {
if(event.getEntity() instanceof ServerPlayer player)
CarryOnCommon.onRiderDisconnected(player);
}
}

View File

@ -213,4 +213,10 @@ public class CommonEvents
CarryOnCommon.onPlayerAttacked(player);
}
@SubscribeEvent
public static void onPlayerLoggedOut(PlayerEvent.PlayerLoggedOutEvent event) {
if(event.getEntity() instanceof ServerPlayer player)
CarryOnCommon.onRiderDisconnected(player);
}
}