From bdc856edf5c675c5300a29ba29a0f066db33b6c0 Mon Sep 17 00:00:00 2001 From: ChampionAsh5357 Date: Fri, 14 Jul 2023 22:06:07 -0400 Subject: [PATCH] Properly Handle Fluid Updates while in a Boat Fix #9256 (#9428) --- .../minecraft/world/entity/Entity.java.patch | 33 ++++++++++++++++--- .../common/extensions/IForgeBoat.java | 14 ++++++++ .../common/extensions/IForgeEntity.java | 14 ++++++++ .../common/extensions/IForgeFluid.java | 15 +++++++++ .../common/extensions/IForgeFluidState.java | 14 ++++++++ .../net/minecraftforge/fluids/FluidType.java | 14 ++++++++ 6 files changed, 99 insertions(+), 5 deletions(-) diff --git a/patches/minecraft/net/minecraft/world/entity/Entity.java.patch b/patches/minecraft/net/minecraft/world/entity/Entity.java.patch index 79e9e4a958..4dfba4e346 100644 --- a/patches/minecraft/net/minecraft/world/entity/Entity.java.patch +++ b/patches/minecraft/net/minecraft/world/entity/Entity.java.patch @@ -160,7 +160,7 @@ this.m_5496_(soundtype.m_56776_(), soundtype.m_56773_() * 0.15F, soundtype.m_56774_()); } } -@@ -1074,19 +_,22 @@ +@@ -1074,31 +_,38 @@ public void m_5844_() { if (this.m_6069_()) { @@ -188,6 +188,24 @@ } void m_20074_() { + Entity entity = this.m_20202_(); ++ java.util.function.BooleanSupplier updateFluidHeight = () -> this.m_204031_(FluidTags.f_13131_, 0.014D); + if (entity instanceof Boat boat) { + if (!boat.m_5842_()) { + this.f_19798_ = false; +- return; ++ updateFluidHeight = () -> { ++ this.updateFluidHeightAndDoFluidPushing(state -> this.shouldUpdateFluidWhileBoating(state, boat)); ++ return false; ++ }; + } + } + +- if (this.m_204031_(FluidTags.f_13131_, 0.014D)) { ++ if (updateFluidHeight.getAsBoolean()) { + if (!this.f_19798_ && !this.f_19803_) { + this.m_5841_(); + } @@ -1115,6 +_,7 @@ private void m_20323_() { this.f_19800_ = this.m_204029_(FluidTags.f_13131_); @@ -414,19 +432,24 @@ }); } -@@ -2861,9 +_,17 @@ +@@ -2861,9 +_,22 @@ this.f_19859_ = this.m_146908_(); } -+ @Deprecated // Forge: Use no parameter version instead, only for vanilla Tags ++ @Deprecated // Forge: Use predicate version instead, only for vanilla Tags public boolean m_204031_(TagKey p_204032_, double p_204033_) { -+ this.updateFluidHeightAndDoFluidPushing(); ++ this.updateFluidHeightAndDoFluidPushing(com.google.common.base.Predicates.alwaysTrue()); + if(p_204032_ == FluidTags.f_13131_) return this.isInFluidType(net.minecraftforge.common.ForgeMod.WATER_TYPE.get()); + else if (p_204032_ == FluidTags.f_13132_) return this.isInFluidType(net.minecraftforge.common.ForgeMod.LAVA_TYPE.get()); + else return false; + } + ++ @Deprecated(forRemoval = true, since = "1.19.4") + public void updateFluidHeightAndDoFluidPushing() { ++ this.updateFluidHeightAndDoFluidPushing(com.google.common.base.Predicates.alwaysTrue()); ++ } ++ ++ public void updateFluidHeightAndDoFluidPushing(Predicate shouldUpdate) { if (this.m_146899_()) { - return false; + return; @@ -446,7 +469,7 @@ FluidState fluidstate = this.f_19853_.m_6425_(blockpos$mutableblockpos); - if (fluidstate.m_205070_(p_204032_)) { + net.minecraftforge.fluids.FluidType fluidType = fluidstate.getFluidType(); -+ if (!fluidType.isAir()) { ++ if (!fluidType.isAir() && shouldUpdate.test(fluidstate)) { double d1 = (double)((float)i2 + fluidstate.m_76155_(this.f_19853_, blockpos$mutableblockpos)); if (d1 >= aabb.f_82289_) { flag1 = true; diff --git a/src/main/java/net/minecraftforge/common/extensions/IForgeBoat.java b/src/main/java/net/minecraftforge/common/extensions/IForgeBoat.java index 7399873a38..e7011c9462 100644 --- a/src/main/java/net/minecraftforge/common/extensions/IForgeBoat.java +++ b/src/main/java/net/minecraftforge/common/extensions/IForgeBoat.java @@ -5,6 +5,7 @@ package net.minecraftforge.common.extensions; +import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.vehicle.Boat; import net.minecraft.world.level.material.FluidState; import net.minecraftforge.fluids.FluidType; @@ -37,4 +38,17 @@ public interface IForgeBoat { return type.supportsBoating(self()); } + + /** + * When {@code false}, the fluid will no longer update its height value while + * within a boat while it is not within a fluid ({@link Boat#isUnderWater()}. + * + * @param state the state of the fluid the rider is within + * @param rider the rider of the boat + * @return {@code true} if the fluid height should be updated, {@code false} otherwise + */ + default boolean shouldUpdateFluidWhileRiding(FluidState state, Entity rider) + { + return state.shouldUpdateWhileBoating(self(), rider); + } } diff --git a/src/main/java/net/minecraftforge/common/extensions/IForgeEntity.java b/src/main/java/net/minecraftforge/common/extensions/IForgeEntity.java index 7d2f9d6041..c62d5a7b95 100644 --- a/src/main/java/net/minecraftforge/common/extensions/IForgeEntity.java +++ b/src/main/java/net/minecraftforge/common/extensions/IForgeEntity.java @@ -13,6 +13,7 @@ import net.minecraft.world.entity.LivingEntity; import net.minecraft.world.entity.ai.attributes.AttributeInstance; import net.minecraft.world.entity.boss.enderdragon.EnderDragon; import net.minecraft.world.entity.player.Player; +import net.minecraft.world.entity.vehicle.Boat; import net.minecraft.world.level.block.Block; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.entity.Entity; @@ -424,4 +425,17 @@ public interface IForgeEntity extends ICapabilitySerializable { return false; } + + /** + * When {@code false}, the fluid will no longer update its height value while + * within a boat while it is not within a fluid ({@link Boat#isUnderWater()}. + * + * @param state the state of the fluid the rider is within + * @param boat the boat the rider is within that is not inside a fluid + * @return {@code true} if the fluid height should be updated, {@code false} otherwise + */ + default boolean shouldUpdateFluidWhileBoating(FluidState state, Boat boat) + { + return boat.shouldUpdateFluidWhileRiding(state, self()); + } } diff --git a/src/main/java/net/minecraftforge/common/extensions/IForgeFluid.java b/src/main/java/net/minecraftforge/common/extensions/IForgeFluid.java index 9f463a7a55..f2cfd0d364 100644 --- a/src/main/java/net/minecraftforge/common/extensions/IForgeFluid.java +++ b/src/main/java/net/minecraftforge/common/extensions/IForgeFluid.java @@ -6,6 +6,7 @@ package net.minecraftforge.common.extensions; import net.minecraft.core.BlockPos; +import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.LivingEntity; import net.minecraft.world.entity.Mob; import net.minecraft.world.entity.vehicle.Boat; @@ -94,6 +95,20 @@ public interface IForgeFluid return getFluidType().supportsBoating(state, boat); } + /** + * When {@code false}, the fluid will no longer update its height value while + * within a boat while it is not within a fluid ({@link Boat#isUnderWater()}. + * + * @param state the state of the fluid the rider is within + * @param boat the boat the rider is within that is not inside a fluid + * @param rider the rider of the boat + * @return {@code true} if the fluid height should be updated, {@code false} otherwise + */ + default boolean shouldUpdateWhileBoating(FluidState state, Boat boat, Entity rider) + { + return getFluidType().shouldUpdateWhileBoating(state, boat, rider); + } + /** * Gets the path type of this fluid when an entity is pathfinding. When * {@code null}, uses vanilla behavior. diff --git a/src/main/java/net/minecraftforge/common/extensions/IForgeFluidState.java b/src/main/java/net/minecraftforge/common/extensions/IForgeFluidState.java index d461607851..ed463157af 100644 --- a/src/main/java/net/minecraftforge/common/extensions/IForgeFluidState.java +++ b/src/main/java/net/minecraftforge/common/extensions/IForgeFluidState.java @@ -6,6 +6,7 @@ package net.minecraftforge.common.extensions; import net.minecraft.core.BlockPos; +import net.minecraft.world.entity.Entity; import net.minecraft.world.entity.LivingEntity; import net.minecraft.world.entity.Mob; import net.minecraft.world.entity.vehicle.Boat; @@ -88,6 +89,19 @@ public interface IForgeFluidState return self().getType().supportsBoating(self(), boat); } + /** + * When {@code false}, the fluid will no longer update its height value while + * within a boat while it is not within a fluid ({@link Boat#isUnderWater()}. + * + * @param boat the boat the rider is within that is not inside a fluid + * @param rider the rider of the boat + * @return {@code true} if the fluid height should be updated, {@code false} otherwise + */ + default boolean shouldUpdateWhileBoating(Boat boat, Entity rider) + { + return self().getType().shouldUpdateWhileBoating(self(), boat, rider); + } + /** * Gets the path type of this fluid when an entity is pathfinding. When * {@code null}, uses vanilla behavior. diff --git a/src/main/java/net/minecraftforge/fluids/FluidType.java b/src/main/java/net/minecraftforge/fluids/FluidType.java index a2a308a5ef..1a6dde3a0f 100644 --- a/src/main/java/net/minecraftforge/fluids/FluidType.java +++ b/src/main/java/net/minecraftforge/fluids/FluidType.java @@ -355,6 +355,20 @@ public class FluidType return this.supportsBoating(boat); } + /** + * When {@code false}, the fluid will no longer update its height value while + * within a boat while it is not within a fluid ({@link Boat#isUnderWater()}. + * + * @param state the state of the fluid the rider is within + * @param boat the boat the rider is within that is not inside a fluid + * @param rider the rider of the boat + * @return {@code true} if the fluid height should be updated, {@code false} otherwise + */ + public boolean shouldUpdateWhileBoating(FluidState state, Boat boat, Entity rider) + { + return !this.supportsBoating(state, boat); + } + /** * Returns whether the entity can ride in this vehicle under the fluid. *