diff --git a/src/main/java/net/citizensnpcs/EventListen.java b/src/main/java/net/citizensnpcs/EventListen.java index 4dda9be7a..6b9f1ec1d 100644 --- a/src/main/java/net/citizensnpcs/EventListen.java +++ b/src/main/java/net/citizensnpcs/EventListen.java @@ -83,14 +83,14 @@ public class EventListen implements Listener { @EventHandler(ignoreCancelled = true) public void onChunkUnload(ChunkUnloadEvent event) { ChunkCoord coord = toCoord(event.getChunk()); - Location cachedLocation = new Location(null, 0, 0, 0); + Location location = new Location(null, 0, 0, 0); for (NPC npc : npcRegistry) { if (!npc.isSpawned()) continue; - cachedLocation = npc.getBukkitEntity().getLocation(cachedLocation); - boolean sameChunkCoordinates = coord.z == cachedLocation.getBlockZ() >> 4 - && coord.x == cachedLocation.getBlockX() >> 4; - if (sameChunkCoordinates && event.getWorld().equals(cachedLocation.getWorld())) { + location = npc.getBukkitEntity().getLocation(location); + boolean sameChunkCoordinates = coord.z == location.getBlockZ() >> 4 + && coord.x == location.getBlockX() >> 4; + if (sameChunkCoordinates && event.getWorld().equals(location.getWorld())) { npc.despawn(DespawnReason.CHUNK_UNLOAD); toRespawn.put(coord, npc.getId()); Messaging.debug("Despawned", npc.getId(), "due to chunk unload at [" + coord.x + "," diff --git a/src/main/java/net/citizensnpcs/npc/ai/AStarNavigationStrategy.java b/src/main/java/net/citizensnpcs/npc/ai/AStarNavigationStrategy.java index 15e70b8b3..054219884 100644 --- a/src/main/java/net/citizensnpcs/npc/ai/AStarNavigationStrategy.java +++ b/src/main/java/net/citizensnpcs/npc/ai/AStarNavigationStrategy.java @@ -8,36 +8,38 @@ import net.citizensnpcs.api.astar.pathfinder.ChunkBlockSource; import net.citizensnpcs.api.astar.pathfinder.Path; import net.citizensnpcs.api.astar.pathfinder.VectorGoal; import net.citizensnpcs.api.astar.pathfinder.VectorNode; -import net.citizensnpcs.npc.CitizensNPC; +import net.citizensnpcs.api.npc.NPC; import net.citizensnpcs.util.NMS; +import org.bukkit.Effect; import org.bukkit.Location; import org.bukkit.util.Vector; public class AStarNavigationStrategy extends AbstractPathStrategy { - private final Location dest; - private final CitizensNPC npc; + private final Location destination; + private final NPC npc; private final NavigatorParameters params; private Path plan; private Vector vector; - AStarNavigationStrategy(CitizensNPC npc, Location dest, NavigatorParameters params) { + AStarNavigationStrategy(NPC npc, Location dest, NavigatorParameters params) { super(TargetType.LOCATION); this.params = params; - this.dest = dest; + this.destination = dest; this.npc = npc; Location location = npc.getBukkitEntity().getEyeLocation(); plan = (Path) ASTAR.runFully(new VectorGoal(dest), new VectorNode(location, new ChunkBlockSource( location, params.range()), params.examiners()), (int) (params.range() * 10)); - if (plan == null || plan.isComplete()) + if (plan == null || plan.isComplete()) { setCancelReason(CancelReason.STUCK); - else + } else { vector = plan.getCurrentVector(); + } } @Override public Location getTargetAsLocation() { - return dest; + return destination; } @Override @@ -47,19 +49,24 @@ public class AStarNavigationStrategy extends AbstractPathStrategy { @Override public boolean update() { - if (getCancelReason() != null) + if (getCancelReason() != null || plan == null || plan.isComplete()) return true; - if (plan == null || plan.isComplete()) - return true; - if (npc.getBukkitEntity().getVelocity().distanceSquared(vector) <= params.distanceMargin()) { + if (npc.getBukkitEntity().getLocation(NPC_LOCATION).toVector().distanceSquared(vector) <= params + .distanceMargin()) { plan.update(npc); if (plan.isComplete()) return true; vector = plan.getCurrentVector(); + npc.getBukkitEntity() + .getWorld() + .playEffect(vector.toLocation(npc.getBukkitEntity().getWorld()), Effect.STEP_SOUND, + org.bukkit.Material.STONE.getId()); } NMS.setDestination(npc.getBukkitEntity(), vector.getX(), vector.getY(), vector.getZ(), params.speed()); return false; } private static final AStarMachine ASTAR = AStarMachine.createWithDefaultStorage(); -} + + private static final Location NPC_LOCATION = new Location(null, 0, 0, 0); +} \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/npc/ai/AbstractPathStrategy.java b/src/main/java/net/citizensnpcs/npc/ai/AbstractPathStrategy.java index 378017260..5058d1aa8 100644 --- a/src/main/java/net/citizensnpcs/npc/ai/AbstractPathStrategy.java +++ b/src/main/java/net/citizensnpcs/npc/ai/AbstractPathStrategy.java @@ -29,4 +29,4 @@ public abstract class AbstractPathStrategy implements PathStrategy { protected void setCancelReason(CancelReason reason) { cancelReason = reason; } -} +} \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/npc/ai/CitizensNavigator.java b/src/main/java/net/citizensnpcs/npc/ai/CitizensNavigator.java index f36e94972..c13245476 100644 --- a/src/main/java/net/citizensnpcs/npc/ai/CitizensNavigator.java +++ b/src/main/java/net/citizensnpcs/npc/ai/CitizensNavigator.java @@ -15,7 +15,6 @@ import net.citizensnpcs.api.ai.event.NavigationReplaceEvent; import net.citizensnpcs.api.astar.pathfinder.MinecraftBlockExaminer; import net.citizensnpcs.api.npc.NPC; import net.citizensnpcs.api.util.DataKey; -import net.citizensnpcs.npc.CitizensNPC; import net.citizensnpcs.util.NMS; import org.bukkit.Bukkit; @@ -31,12 +30,11 @@ public class CitizensNavigator implements Navigator, Runnable { private PathStrategy executing; private int lastX, lastY, lastZ; private NavigatorParameters localParams = defaultParams; - private final CitizensNPC npc; - private final Location stationaryLocation = new Location(null, 0, 0, 0); + private final NPC npc; private int stationaryTicks; - public CitizensNavigator(CitizensNPC npc) { + public CitizensNavigator(NPC npc) { this.npc = npc; } @@ -213,19 +211,21 @@ public class CitizensNavigator implements Navigator, Runnable { private boolean updateStationaryStatus() { if (localParams.stationaryTicks() < 0) return false; - npc.getBukkitEntity().getLocation(stationaryLocation); - if (lastX == stationaryLocation.getBlockX() && lastY == stationaryLocation.getBlockY() - && lastZ == stationaryLocation.getBlockZ()) { + Location current = npc.getBukkitEntity().getLocation(STATIONARY_LOCATION); + if (lastX == current.getBlockX() && lastY == current.getBlockY() && lastZ == current.getBlockZ()) { if (++stationaryTicks >= localParams.stationaryTicks()) { stopNavigating(CancelReason.STUCK); return true; } } else stationaryTicks = 0; - lastX = stationaryLocation.getBlockX(); - lastY = stationaryLocation.getBlockY(); - lastZ = stationaryLocation.getBlockZ(); + lastX = current.getBlockX(); + lastY = current.getBlockY(); + lastZ = current.getBlockZ(); return false; } + + private static final Location STATIONARY_LOCATION = new Location(null, 0, 0, 0); + private static int UNINITIALISED_SPEED = Integer.MIN_VALUE; } diff --git a/src/main/java/net/citizensnpcs/npc/ai/MCTargetStrategy.java b/src/main/java/net/citizensnpcs/npc/ai/MCTargetStrategy.java index e650d17d6..91c89d550 100644 --- a/src/main/java/net/citizensnpcs/npc/ai/MCTargetStrategy.java +++ b/src/main/java/net/citizensnpcs/npc/ai/MCTargetStrategy.java @@ -22,12 +22,8 @@ public class MCTargetStrategy implements PathStrategy, EntityTarget { private CancelReason cancelReason; private final EntityLiving handle, target; private final Navigation navigation; - private final Location npcLocation = new Location(null, 0, 0, 0); - private final NavigatorParameters parameters; - private final Location targetLocation = new Location(null, 0, 0, 0); - public MCTargetStrategy(NPC handle, LivingEntity target, boolean aggro, NavigatorParameters params) { this.handle = ((CraftLivingEntity) handle.getBukkitEntity()).getHandle(); this.target = ((CraftLivingEntity) target).getHandle(); @@ -42,16 +38,16 @@ public class MCTargetStrategy implements PathStrategy, EntityTarget { && (handle.boundingBox.e > target.boundingBox.b && handle.boundingBox.b < target.boundingBox.e) && distanceSquared() <= ATTACK_DISTANCE && hasLineOfSight(); } + @Override public void clearCancelReason() { cancelReason = null; } private double distanceSquared() { - return handle.getBukkitEntity().getLocation(npcLocation) - .distanceSquared(target.getBukkitEntity().getLocation(targetLocation)); + return handle.getBukkitEntity().getLocation(HANDLE_LOCATION) + .distanceSquared(target.getBukkitEntity().getLocation(TARGET_LOCATION)); } - @Override public CancelReason getCancelReason() { return cancelReason; @@ -120,5 +116,9 @@ public class MCTargetStrategy implements PathStrategy, EntityTarget { } private static final int ATTACK_DELAY_TICKS = 20; + private static final double ATTACK_DISTANCE = 1.75 * 1.75; + + private static final Location HANDLE_LOCATION = new Location(null, 0, 0, 0); + private static final Location TARGET_LOCATION = new Location(null, 0, 0, 0); } \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/npc/entity/EntityHumanNPC.java b/src/main/java/net/citizensnpcs/npc/entity/EntityHumanNPC.java index 50273ae7a..92a1b2ca2 100644 --- a/src/main/java/net/citizensnpcs/npc/entity/EntityHumanNPC.java +++ b/src/main/java/net/citizensnpcs/npc/entity/EntityHumanNPC.java @@ -32,9 +32,7 @@ import org.bukkit.plugin.Plugin; import org.bukkit.util.Vector; public class EntityHumanNPC extends EntityPlayer implements NPCHolder { - private final Location loadedLocation = new Location(null, 0, 0, 0); private final CitizensNPC npc; - private final net.minecraft.server.v1_4_5.ItemStack[] previousEquipment = { null, null, null, null, null }; public EntityHumanNPC(MinecraftServer minecraftServer, World world, String string, @@ -128,7 +126,7 @@ public class EntityHumanNPC extends EntityPlayer implements NPCHolder { if (npc == null) return; - if (getBukkitEntity() != null && Util.isLoaded(getBukkitEntity().getLocation(loadedLocation))) { + if (getBukkitEntity() != null && Util.isLoaded(getBukkitEntity().getLocation(LOADED_LOCATION))) { if (!npc.getNavigator().isNavigating() && !NMS.inWater(this)) move(0, -0.2, 0); // gravity. also works around an entity.onGround not updating issue @@ -227,4 +225,6 @@ public class EntityHumanNPC extends EntityPlayer implements NPCHolder { } private static final float EPSILON = 0.005F; + + private static final Location LOADED_LOCATION = new Location(null, 0, 0, 0); } \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/trait/LookClose.java b/src/main/java/net/citizensnpcs/trait/LookClose.java index b00a03afb..9f2bf9d27 100644 --- a/src/main/java/net/citizensnpcs/trait/LookClose.java +++ b/src/main/java/net/citizensnpcs/trait/LookClose.java @@ -21,7 +21,6 @@ import org.bukkit.entity.Player; public class LookClose extends Trait implements Toggleable, CommandConfigurable { private boolean enabled = Setting.DEFAULT_LOOK_CLOSE.asBoolean(); private Player lookingAt; - private final Location npcLocation = new Location(null, 0, 0, 0); private double range = Setting.DEFAULT_LOOK_CLOSE_RANGE.asDouble(); private boolean realisticLooking = Setting.DEFAULT_REALISTIC_LOOKING.asBoolean(); @@ -43,7 +42,7 @@ public class LookClose extends Trait implements Toggleable, CommandConfigurable private void findNewTarget() { List nearby = npc.getBukkitEntity().getNearbyEntities(range, range, range); - npc.getBukkitEntity().getLocation(npcLocation); + final Location npcLocation = npc.getBukkitEntity().getLocation(NPC_LOCATION); Collections.sort(nearby, new Comparator() { @Override public int compare(Entity o1, Entity o2) { @@ -125,4 +124,6 @@ public class LookClose extends Trait implements Toggleable, CommandConfigurable public String toString() { return "LookClose{" + enabled + "}"; } + + private static final Location NPC_LOCATION = new Location(null, 0, 0, 0); } \ No newline at end of file diff --git a/src/main/java/net/citizensnpcs/util/Util.java b/src/main/java/net/citizensnpcs/util/Util.java index 7407f26e1..e5361d923 100644 --- a/src/main/java/net/citizensnpcs/util/Util.java +++ b/src/main/java/net/citizensnpcs/util/Util.java @@ -22,14 +22,13 @@ import org.bukkit.util.Vector; import com.google.common.base.Splitter; public class Util { - // Static class for small (emphasis small) utility methods private Util() { } - private static final Location atLocation = new Location(null, 0, 0, 0); + private static final Location AT_LOCATION = new Location(null, 0, 0, 0); - private static final Location fromLocation = new Location(null, 0, 0, 0); + private static final Location FROM_LOCATION = new Location(null, 0, 0, 0); private static Class RNG_CLASS = null; @@ -42,7 +41,6 @@ public class Util { if (NPCCollisionEvent.getHandlerList().getRegisteredListeners().length > 0) Bukkit.getPluginManager().callEvent(new NPCCollisionEvent(npc, entity.getBukkitEntity())); } - public static NPCPushEvent callPushEvent(NPC npc, Vector vector) { NPCPushEvent event = new NPCPushEvent(npc, vector); event.setCancelled(npc.data().get(NPC.DEFAULT_PROTECTED_METADATA, true)); @@ -54,15 +52,11 @@ public class Util { if (from.getWorld() != at.getWorld()) return; double xDiff, yDiff, zDiff; - synchronized (fromLocation) { - from.getLocation(fromLocation); - synchronized (atLocation) { - at.getLocation(atLocation); - xDiff = atLocation.getX() - fromLocation.getX(); - yDiff = atLocation.getY() - fromLocation.getY(); - zDiff = atLocation.getZ() - fromLocation.getZ(); - } - } + Location atLocation = at.getLocation(AT_LOCATION); + Location fromLocation = from.getLocation(FROM_LOCATION); + xDiff = atLocation.getX() - fromLocation.getX(); + yDiff = atLocation.getY() - fromLocation.getY(); + zDiff = atLocation.getZ() - fromLocation.getZ(); double distanceXZ = Math.sqrt(xDiff * xDiff + zDiff * zDiff); double distanceY = Math.sqrt(distanceXZ * distanceXZ + yDiff * yDiff);