From ae5464b758ce4680db341542c26a52ccb89f757d Mon Sep 17 00:00:00 2001 From: Sollace Date: Mon, 12 Feb 2024 13:14:29 +0000 Subject: [PATCH] Fixed shapeshifting and fixed disguise entities not playing animations --- .../ability/magic/spell/SpellReference.java | 6 +++- .../render/spell/ShieldSpellRenderer.java | 2 +- .../unicopia/entity/behaviour/Disguise.java | 10 +++++- .../entity/behaviour/EntityAppearance.java | 2 ++ .../unicopia/entity/duck/RotatedView.java | 2 ++ .../unicopia/mixin/MixinWorld.java | 15 ++++++++ .../client/MixinClientPlayNetworkHandler.java | 35 +++++++++++++++++++ .../datasync/SpellNetworkedReference.java | 2 +- src/main/resources/unicopia.mixin.json | 1 + 9 files changed, 71 insertions(+), 4 deletions(-) create mode 100644 src/main/java/com/minelittlepony/unicopia/mixin/client/MixinClientPlayNetworkHandler.java diff --git a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/SpellReference.java b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/SpellReference.java index c8b504f8..cca32178 100644 --- a/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/SpellReference.java +++ b/src/main/java/com/minelittlepony/unicopia/ability/magic/spell/SpellReference.java @@ -50,6 +50,10 @@ public final class SpellReference implements NbtSerialisable { @Override public void fromNBT(NbtCompound compound) { + fromNBT(compound, true); + } + + public void fromNBT(NbtCompound compound, boolean force) { final int hash = compound.hashCode(); if (nbtHash == hash) { return; @@ -58,7 +62,7 @@ public final class SpellReference implements NbtSerialisable { if (spell == null || !Objects.equals(Spell.getUuid(compound), spell.getUuid())) { spell = Spell.readNbt(compound); - } else { + } else if (force || !spell.isDirty()) { spell.fromNBT(compound); } } diff --git a/src/main/java/com/minelittlepony/unicopia/client/render/spell/ShieldSpellRenderer.java b/src/main/java/com/minelittlepony/unicopia/client/render/spell/ShieldSpellRenderer.java index aa96a28f..d6f236de 100644 --- a/src/main/java/com/minelittlepony/unicopia/client/render/spell/ShieldSpellRenderer.java +++ b/src/main/java/com/minelittlepony/unicopia/client/render/spell/ShieldSpellRenderer.java @@ -51,7 +51,7 @@ public class ShieldSpellRenderer extends SpellRenderer { model.render(matrices, buffer, light, 1, radius, colors[0], colors[1], colors[2], alpha * 0.2F); } else { matrices.multiply(RotationAxis.POSITIVE_X.rotationDegrees(180)); - matrices.scale(1, radius == 0 ? 1 : 2.6F / radius, 1); + matrices.scale(1, radius == 0 ? 1 : MathHelper.clamp(2.6F / radius, 0.7F, 1), 1); SphereModel.SPHERE.render(matrices, buffer, light, 1, radius + thickness, colors[0], colors[1], colors[2], alpha * 0.08F); SphereModel.SPHERE.render(matrices, buffer, light, 1, radius - thickness, colors[0], colors[1], colors[2], alpha * 0.05F); SphereModel.SPHERE.render(matrices, buffer, light, 1, radius + thickness * 2, colors[0], colors[1], colors[2], alpha * 0.05F); diff --git a/src/main/java/com/minelittlepony/unicopia/entity/behaviour/Disguise.java b/src/main/java/com/minelittlepony/unicopia/entity/behaviour/Disguise.java index 272cde97..7041b6e7 100644 --- a/src/main/java/com/minelittlepony/unicopia/entity/behaviour/Disguise.java +++ b/src/main/java/com/minelittlepony/unicopia/entity/behaviour/Disguise.java @@ -9,6 +9,7 @@ import com.minelittlepony.unicopia.Owned; import com.minelittlepony.unicopia.ability.magic.Caster; import com.minelittlepony.unicopia.entity.Living; import com.minelittlepony.unicopia.entity.duck.LivingEntityDuck; +import com.minelittlepony.unicopia.entity.duck.RotatedView; import com.minelittlepony.unicopia.entity.player.PlayerDimensions; import com.minelittlepony.unicopia.entity.player.Pony; @@ -100,7 +101,14 @@ public interface Disguise extends FlightType.Provider, PlayerDimensions.Provider behaviour.copyBaseAttributes(owner, entity); if (tick && !getDisguise().skipsUpdate()) { - entity.tick(); + ((RotatedView)entity.getWorld()).setMirrorEntityStatuses(entity.getWorld().isClient); + if (entity.getWorld().isClient) { + entity.tick(); + } else { + entity.tick(); + } + + ((RotatedView)entity.getWorld()).setMirrorEntityStatuses(false); } if (!(owner instanceof PlayerEntity) && !((LivingEntityDuck)owner).isJumping()) { diff --git a/src/main/java/com/minelittlepony/unicopia/entity/behaviour/EntityAppearance.java b/src/main/java/com/minelittlepony/unicopia/entity/behaviour/EntityAppearance.java index 15c8fee6..7a5d4c96 100644 --- a/src/main/java/com/minelittlepony/unicopia/entity/behaviour/EntityAppearance.java +++ b/src/main/java/com/minelittlepony/unicopia/entity/behaviour/EntityAppearance.java @@ -211,6 +211,8 @@ public class EntityAppearance implements NbtSerialisable, PlayerDimensions.Provi if (source.isClient()) { source.asWorld().spawnEntity(entity); + } else { + entity.setId(source.asEntity().getId()); } } diff --git a/src/main/java/com/minelittlepony/unicopia/entity/duck/RotatedView.java b/src/main/java/com/minelittlepony/unicopia/entity/duck/RotatedView.java index 33e09463..e5c60d40 100644 --- a/src/main/java/com/minelittlepony/unicopia/entity/duck/RotatedView.java +++ b/src/main/java/com/minelittlepony/unicopia/entity/duck/RotatedView.java @@ -10,6 +10,8 @@ public interface RotatedView { boolean hasTransform(); + void setMirrorEntityStatuses(boolean enable); + default void pushRotation(int y) { getRotations().add(y); } diff --git a/src/main/java/com/minelittlepony/unicopia/mixin/MixinWorld.java b/src/main/java/com/minelittlepony/unicopia/mixin/MixinWorld.java index eda9c5b4..04db071b 100644 --- a/src/main/java/com/minelittlepony/unicopia/mixin/MixinWorld.java +++ b/src/main/java/com/minelittlepony/unicopia/mixin/MixinWorld.java @@ -6,11 +6,13 @@ import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.injection.At; import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.ModifyVariable; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; import com.minelittlepony.unicopia.entity.duck.RotatedView; import com.minelittlepony.unicopia.server.world.BlockDestructionManager; import net.minecraft.block.BlockState; +import net.minecraft.entity.Entity; import net.minecraft.util.math.BlockPos; import net.minecraft.world.World; import net.minecraft.world.WorldAccess; @@ -22,6 +24,7 @@ abstract class MixinWorld implements WorldAccess, BlockDestructionManager.Source private int recurseCount = 0; private final Stack rotations = new Stack<>(); + private boolean mirrorEntityStatuses; @Override public Stack getRotations() { @@ -33,11 +36,23 @@ abstract class MixinWorld implements WorldAccess, BlockDestructionManager.Source return recurseCount <= 0; } + @Override + public void setMirrorEntityStatuses(boolean enable) { + mirrorEntityStatuses = enable; + } + @Override public BlockDestructionManager getDestructionManager() { return destructions.get(); } + @Inject(method = "sendEntityStatus(Lnet/minecraft/entity/Entity;B)V", at = @At("HEAD")) + private void onSendEntityStatus(Entity entity, byte status, CallbackInfo info) { + if (mirrorEntityStatuses) { + entity.handleStatus(status); + } + } + @ModifyVariable(method = "setBlockState(Lnet/minecraft/util/math/BlockPos;Lnet/minecraft/block/BlockState;II)Z", at = @At("HEAD")) private BlockPos modifyBlockPos(BlockPos pos) { pos = applyRotation(pos); diff --git a/src/main/java/com/minelittlepony/unicopia/mixin/client/MixinClientPlayNetworkHandler.java b/src/main/java/com/minelittlepony/unicopia/mixin/client/MixinClientPlayNetworkHandler.java new file mode 100644 index 00000000..06821d12 --- /dev/null +++ b/src/main/java/com/minelittlepony/unicopia/mixin/client/MixinClientPlayNetworkHandler.java @@ -0,0 +1,35 @@ +package com.minelittlepony.unicopia.mixin.client; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Shadow; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; + +import com.minelittlepony.unicopia.ability.magic.SpellPredicate; +import com.minelittlepony.unicopia.entity.Living; +import com.minelittlepony.unicopia.entity.behaviour.Disguise; +import com.minelittlepony.unicopia.entity.behaviour.EntityAppearance; + +import net.minecraft.client.network.ClientPlayNetworkHandler; +import net.minecraft.client.world.ClientWorld; +import net.minecraft.network.packet.s2c.play.EntityStatusS2CPacket; + +@Mixin(ClientPlayNetworkHandler.class) +abstract class MixinClientPlayNetworkHandler { + @Shadow private ClientWorld world; + + @Inject(method = "onEntityStatus", at = @At("TAIL")) + private void onOnEntityStatus(EntityStatusS2CPacket packet, CallbackInfo info) { + Living living = Living.living(packet.getEntity(world)); + if (living != null) { + living.getSpellSlot() + .get(SpellPredicate.IS_DISGUISE, false) + .map(Disguise::getDisguise) + .map(EntityAppearance::getAppearance) + .ifPresent(appearance -> { + appearance.handleStatus(packet.getStatus()); + }); + } + } +} diff --git a/src/main/java/com/minelittlepony/unicopia/network/datasync/SpellNetworkedReference.java b/src/main/java/com/minelittlepony/unicopia/network/datasync/SpellNetworkedReference.java index 9ae9f29a..fbc8ba3b 100644 --- a/src/main/java/com/minelittlepony/unicopia/network/datasync/SpellNetworkedReference.java +++ b/src/main/java/com/minelittlepony/unicopia/network/datasync/SpellNetworkedReference.java @@ -31,7 +31,7 @@ public class SpellNetworkedReference implements NetworkedRefere @Override public boolean fromNbt(NbtCompound comp) { dirty = false; - currentValue.fromNBT(comp); + currentValue.fromNBT(comp, owner.isClient()); return isDirty(); } diff --git a/src/main/resources/unicopia.mixin.json b/src/main/resources/unicopia.mixin.json index 549625a7..20a09367 100644 --- a/src/main/resources/unicopia.mixin.json +++ b/src/main/resources/unicopia.mixin.json @@ -67,6 +67,7 @@ "client.MixinBackgroundRenderer", "client.MixinCamera", "client.MixinClientWorld", + "client.MixinClientPlayNetworkHandler", "client.MixinEntityRenderDispatcher", "client.MixinGameRenderer", "client.MixinHeldItemRenderer",