From bd9d56943ebc9c8fcaf822fc10dd78f01c8a1435 Mon Sep 17 00:00:00 2001 From: Kam Date: Wed, 4 Mar 2026 04:32:54 -0500 Subject: [PATCH] Fix Push Through wall Teleport Logic for Barriers --- .../npcs/entity/EntityEnergyBarrier.java | 33 +++++++++++++++++ .../kamkeel/npcs/entity/EntityEnergyDome.java | 33 ++++++++++------- .../npcs/entity/EntityEnergyPanel.java | 36 ++++++++++++------- 3 files changed, 78 insertions(+), 24 deletions(-) diff --git a/src/main/java/kamkeel/npcs/entity/EntityEnergyBarrier.java b/src/main/java/kamkeel/npcs/entity/EntityEnergyBarrier.java index 9111e7dd8..b6e190fe7 100644 --- a/src/main/java/kamkeel/npcs/entity/EntityEnergyBarrier.java +++ b/src/main/java/kamkeel/npcs/entity/EntityEnergyBarrier.java @@ -9,6 +9,7 @@ import net.minecraft.entity.EntityLivingBase; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.util.AxisAlignedBB; import net.minecraft.util.DamageSource; import net.minecraft.world.World; import noppes.npcs.CustomNpcs; @@ -672,8 +673,11 @@ public abstract class EntityEnergyBarrier extends EntityEnergyAbility { /** * Teleport an entity to a position. Uses network handler for players * to ensure reliable client synchronization. + * Skips teleport if destination intersects solid blocks. */ protected void teleportEntity(EntityLivingBase ent, double x, double y, double z) { + if (!isPositionClear(ent, x, y, z)) return; + if (ent instanceof EntityPlayerMP) { EntityPlayerMP player = (EntityPlayerMP) ent; player.playerNetServerHandler.setPlayerLocation(x, y, z, player.rotationYaw, player.rotationPitch); @@ -682,6 +686,35 @@ public abstract class EntityEnergyBarrier extends EntityEnergyAbility { } } + /** + * Returns true if placing the entity at (x, y, z) would not intersect solid blocks. + */ + protected boolean isPositionClear(EntityLivingBase ent, double x, double y, double z) { + double halfW = ent.width * 0.5; + AxisAlignedBB box = AxisAlignedBB.getBoundingBox( + x - halfW, y, z - halfW, + x + halfW, y + ent.height, z + halfW + ); + return worldObj.getCollidingBoundingBoxes(ent, box).isEmpty(); + } + + /** + * Returns true if the entity can be pushed in the given direction without hitting solid blocks. + * Probes a small distance (0.3 blocks) ahead in the push direction. + */ + protected boolean canPushInDirection(EntityLivingBase ent, double dirX, double dirY, double dirZ) { + double probe = 0.3; + double halfW = ent.width * 0.5; + double px = ent.posX + dirX * probe; + double py = ent.posY + dirY * probe; + double pz = ent.posZ + dirZ * probe; + AxisAlignedBB box = AxisAlignedBB.getBoundingBox( + px - halfW, py, pz - halfW, + px + halfW, py + ent.height, pz + halfW + ); + return worldObj.getCollidingBoundingBoxes(ent, box).isEmpty(); + } + // ==================== GETTERS ==================== public EnergyBarrierData getBarrierData() { diff --git a/src/main/java/kamkeel/npcs/entity/EntityEnergyDome.java b/src/main/java/kamkeel/npcs/entity/EntityEnergyDome.java index 535d1cdff..2c0277a65 100644 --- a/src/main/java/kamkeel/npcs/entity/EntityEnergyDome.java +++ b/src/main/java/kamkeel/npcs/entity/EntityEnergyDome.java @@ -371,8 +371,10 @@ public class EntityEnergyDome extends EntityEnergyBarrier { ent.motionY -= radialVel * ny; ent.motionZ -= radialVel * nz; double pushForce = wasInside ? -0.15 : 0.15; - ent.motionX += nx * pushForce; - ent.motionZ += nz * pushForce; + if (canPushInDirection(ent, nx * pushForce, 0, nz * pushForce)) { + ent.motionX += nx * pushForce; + ent.motionZ += nz * pushForce; + } ent.velocityChanged = true; } else { // Preemptive: near surface and moving toward it — cancel radial velocity @@ -385,8 +387,10 @@ public class EntityEnergyDome extends EntityEnergyBarrier { ent.motionY -= radialVel * ny; ent.motionZ -= radialVel * nz; double pushForce = isInside ? -0.05 : 0.05; - ent.motionX += nx * pushForce; - ent.motionZ += nz * pushForce; + if (canPushInDirection(ent, nx * pushForce, 0, nz * pushForce)) { + ent.motionX += nx * pushForce; + ent.motionZ += nz * pushForce; + } ent.velocityChanged = true; } } @@ -400,16 +404,21 @@ public class EntityEnergyDome extends EntityEnergyBarrier { double proximity = 1.0 - (surfaceDist / knockbackMargin); double force = proximity * strength * 0.06; + double pushX, pushY, pushZ; if (isInside) { - // Push toward center (away from surface) - ent.motionX += -nx * force; - ent.motionY += -ny * force * 0.5; - ent.motionZ += -nz * force; + pushX = -nx * force; + pushY = -ny * force * 0.5; + pushZ = -nz * force; } else { - // Push outward (away from surface) - ent.motionX += nx * force; - ent.motionY += ny * force * 0.5; - ent.motionZ += nz * force; + pushX = nx * force; + pushY = ny * force * 0.5; + pushZ = nz * force; + } + + if (canPushInDirection(ent, pushX, pushY, pushZ)) { + ent.motionX += pushX; + ent.motionY += pushY; + ent.motionZ += pushZ; } ent.velocityChanged = true; } diff --git a/src/main/java/kamkeel/npcs/entity/EntityEnergyPanel.java b/src/main/java/kamkeel/npcs/entity/EntityEnergyPanel.java index eab43440f..ec77f8248 100644 --- a/src/main/java/kamkeel/npcs/entity/EntityEnergyPanel.java +++ b/src/main/java/kamkeel/npcs/entity/EntityEnergyPanel.java @@ -257,12 +257,12 @@ public class EntityEnergyPanel extends EntityEnergyBarrier { double dz = target.posZ - posZ; double len = Math.sqrt(dx * dx + dz * dz); if (len > 0) { - target.addVelocity( - (dx / len) * panelData.launchKnockback * 0.5, - 0.1, - (dz / len) * panelData.launchKnockback * 0.5 - ); - target.velocityChanged = true; + double kbX = (dx / len) * panelData.launchKnockback * 0.5; + double kbZ = (dz / len) * panelData.launchKnockback * 0.5; + if (canPushInDirection(target, kbX, 0.1, kbZ)) { + target.addVelocity(kbX, 0.1, kbZ); + target.velocityChanged = true; + } } } } @@ -580,8 +580,12 @@ public class EntityEnergyPanel extends EntityEnergyBarrier { // Cancel normal velocity and add corrective push ent.motionX -= normalVel * normalX; ent.motionZ -= normalVel * normalZ; - ent.motionX += normalX * prevSide * 0.15; - ent.motionZ += normalZ * prevSide * 0.15; + double pushX = normalX * prevSide * 0.15; + double pushZ = normalZ * prevSide * 0.15; + if (canPushInDirection(ent, pushX, 0, pushZ)) { + ent.motionX += pushX; + ent.motionZ += pushZ; + } ent.velocityChanged = true; } else { // Preemptive: near the plane and moving toward it — cancel normal velocity @@ -592,8 +596,12 @@ public class EntityEnergyPanel extends EntityEnergyBarrier { if (movingToward) { ent.motionX -= normalVel * normalX; ent.motionZ -= normalVel * normalZ; - ent.motionX += normalX * side * 0.05; - ent.motionZ += normalZ * side * 0.05; + double pushX = normalX * side * 0.05; + double pushZ = normalZ * side * 0.05; + if (canPushInDirection(ent, pushX, 0, pushZ)) { + ent.motionX += pushX; + ent.motionZ += pushZ; + } ent.velocityChanged = true; } } @@ -606,8 +614,12 @@ public class EntityEnergyPanel extends EntityEnergyBarrier { if (absDist < searchExtension) { double proximity = 1.0 - (absDist / searchExtension); double force = proximity * strength * 0.06; - ent.motionX += normalX * side * force; - ent.motionZ += normalZ * side * force; + double pushX = normalX * side * force; + double pushZ = normalZ * side * force; + if (canPushInDirection(ent, pushX, 0, pushZ)) { + ent.motionX += pushX; + ent.motionZ += pushZ; + } ent.velocityChanged = true; } }