Add /npc hitbox, WIP packet NPCs

This commit is contained in:
fullwall 2023-01-03 20:55:27 +08:00
parent 26bf39c328
commit e21681fa26
101 changed files with 1070 additions and 291 deletions

View File

@ -119,7 +119,7 @@ public class Citizens extends JavaPlugin implements CitizensPlugin {
}
@Override
public void setTexture(String string, SkullMeta meta) {
public void setTexture(String texture, SkullMeta meta) {
GameProfile profile = NMS.getProfile(meta);
if (profile == null) {
if (SUPPORT_OWNER_PROFILE) {
@ -134,7 +134,7 @@ public class Citizens extends JavaPlugin implements CitizensPlugin {
profile = new GameProfile(UUID.randomUUID(), null);
}
}
profile.getProperties().put("textures", new Property("textures", string));
profile.getProperties().put("textures", new Property("textures", texture));
NMS.setProfile(meta, profile);
}
};

View File

@ -55,6 +55,7 @@ import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.plugin.PluginDescriptionFile;
import org.bukkit.scheduler.BukkitRunnable;
import com.google.common.base.Joiner;
import com.google.common.base.Predicates;
import com.google.common.collect.ArrayListMultimap;
import com.google.common.collect.Iterables;
@ -349,14 +350,12 @@ public class EventListen implements Listener {
public void onNPCDespawn(NPCDespawnEvent event) {
if (event.getReason() == DespawnReason.PLUGIN || event.getReason() == DespawnReason.REMOVAL
|| event.getReason() == DespawnReason.RELOAD) {
if (Messaging.isDebugging()) {
Messaging.debug("Preventing further respawns of", event.getNPC(),
"due to DespawnReason." + event.getReason());
}
Messaging.idebug(() -> Joiner.on(' ').join("Preventing further respawns of", event.getNPC(),
"due to DespawnReason." + event.getReason()));
toRespawn.values().remove(event.getNPC());
} else if (Messaging.isDebugging()) {
Messaging.debug("Removing", event.getNPC(),
"from skin tracker due to DespawnReason." + event.getReason().name());
} else {
Messaging.idebug(() -> Joiner.on(' ').join("Removing", event.getNPC(),
"from skin tracker due to DespawnReason." + event.getReason().name()));
}
skinUpdateTracker.onNPCDespawn(event.getNPC());
}
@ -369,9 +368,8 @@ public class EventListen implements Listener {
@EventHandler(priority = EventPriority.MONITOR, ignoreCancelled = true)
public void onNPCSpawn(NPCSpawnEvent event) {
skinUpdateTracker.onNPCSpawn(event.getNPC());
if (Messaging.isDebugging()) {
Messaging.debug("Removing respawns of", event.getNPC(), "due to SpawnReason." + event.getReason());
}
Messaging.idebug(() -> Joiner.on(' ').join("Removing respawns of", event.getNPC(),
"due to SpawnReason." + event.getReason()));
toRespawn.values().remove(event.getNPC());
}
@ -631,28 +629,20 @@ public class EventListen implements Listener {
for (int i = 0; i < ids.size(); i++) {
NPC npc = ids.get(i);
if (npc.getOwningRegistry().getById(npc.getId()) != npc) {
if (Messaging.isDebugging()) {
Messaging.debug("Prevented deregistered NPC from respawning", npc);
}
Messaging.idebug(() -> "Prevented deregistered NPC from respawning " + npc);
continue;
}
if (npc.isSpawned()) {
if (Messaging.isDebugging()) {
Messaging.debug("Can't respawn NPC", npc, ": already spawned");
}
Messaging.idebug(() -> "Can't respawn NPC " + npc + ": already spawned");
continue;
}
boolean success = spawn(npc);
if (!success) {
ids.remove(i--);
if (Messaging.isDebugging()) {
Messaging.debug("Couldn't respawn", npc, "during", event, "at", coord);
}
Messaging.idebug(() -> Joiner.on(' ').join("Couldn't respawn", npc, "during", event, "at", coord));
continue;
}
if (Messaging.isDebugging()) {
Messaging.debug("Spawned", npc, "during", event, "at", coord);
}
Messaging.idebug(() -> Joiner.on(' ').join("Spawned", npc, "during", event, "at", coord));
}
for (NPC npc : ids) {
toRespawn.remove(coord, npc);
@ -662,9 +652,7 @@ public class EventListen implements Listener {
private boolean spawn(NPC npc) {
Location spawn = npc.getOrAddTrait(CurrentLocation.class).getLocation();
if (spawn == null) {
if (Messaging.isDebugging()) {
Messaging.debug("Couldn't find a spawn location for despawned NPC", npc);
}
Messaging.idebug(() -> Joiner.on(' ').join("Couldn't find a spawn location for despawned NPC", npc));
return false;
}
return npc.spawn(spawn, SpawnReason.CHUNK_LOAD);
@ -687,9 +675,7 @@ public class EventListen implements Listener {
for (NPC npc : toDespawn) {
if (!npc.despawn(DespawnReason.CHUNK_UNLOAD)) {
if (!(event instanceof Cancellable)) {
if (Messaging.isDebugging()) {
Messaging.debug("Reloading chunk because", npc, "couldn't despawn");
}
Messaging.idebug(() -> Joiner.on(' ').join("Reloading chunk because", npc, "couldn't despawn"));
loadChunk = true;
toRespawn.put(coord, npc);
continue;
@ -700,17 +686,13 @@ public class EventListen implements Listener {
return;
}
toRespawn.put(coord, npc);
if (Messaging.isDebugging()) {
Messaging.debug("Despawned", npc, "due to chunk unload at", coord);
}
Messaging.idebug(() -> Joiner.on(' ').join("Despawned", npc, "due to chunk unload at", coord));
}
if (Messaging.isDebugging() && Setting.DEBUG_CHUNK_LOADS.asBoolean()) {
new Exception("CITIZENS CHUNK UNLOAD DEBUG " + coord).printStackTrace();
}
if (loadChunk) {
if (Messaging.isDebugging()) {
Messaging.debug("Loading chunk in 10 ticks due to forced chunk load at", coord);
}
Messaging.idebug(() -> Joiner.on(' ').join("Loading chunk in 10 ticks due to forced chunk load at", coord));
Bukkit.getScheduler().scheduleSyncDelayedTask(CitizensAPI.getPlugin(), new Runnable() {
@Override
public void run() {
@ -722,6 +704,5 @@ public class EventListen implements Listener {
}
}
private static boolean SUPPORT_OWNING_PLAYER = true;
private static boolean SUPPORT_STOP_USE_ITEM = true;
}

View File

@ -29,7 +29,6 @@ public class Settings {
}
}
updateMessagingSettings();
save();
}

View File

@ -86,6 +86,7 @@ import net.citizensnpcs.api.trait.trait.MobType;
import net.citizensnpcs.api.trait.trait.Owner;
import net.citizensnpcs.api.trait.trait.Spawned;
import net.citizensnpcs.api.trait.trait.Speech;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.api.util.Paginator;
import net.citizensnpcs.api.util.Placeholders;
@ -100,6 +101,7 @@ import net.citizensnpcs.npc.Template;
import net.citizensnpcs.trait.Age;
import net.citizensnpcs.trait.Anchors;
import net.citizensnpcs.trait.ArmorStandTrait;
import net.citizensnpcs.trait.BoundingBoxTrait;
import net.citizensnpcs.trait.ClickRedirectTrait;
import net.citizensnpcs.trait.CommandTrait;
import net.citizensnpcs.trait.CommandTrait.CommandTraitError;
@ -1047,6 +1049,29 @@ public class NPCCommands {
InventoryMenu.createSelfRegistered(new NPCConfigurator(npc)).present(sender);
}
@Command(
aliases = { "npc" },
usage = "hitbox --scale [scale] --width/height [value]",
desc = "Sets the NPC hitbox",
modifiers = { "hitbox" },
min = 1,
max = 1,
permission = "citizens.npc.hitbox")
public void hitbox(CommandContext args, CommandSender sender, NPC npc, @Flag("scale") Float scale,
@Flag("width") Float width, @Flag("height") Float height) {
if (scale != null) {
npc.getOrAddTrait(BoundingBoxTrait.class).setScale(scale);
}
if (width != null) {
npc.getOrAddTrait(BoundingBoxTrait.class).setWidth(width);
}
if (height != null) {
npc.getOrAddTrait(BoundingBoxTrait.class).setHeight(height);
}
EntityDim dim = npc.getOrAddTrait(BoundingBoxTrait.class).getAdjustedBoundingBox();
Messaging.sendTr(sender, Messages.BOUNDING_BOX_SET, "width " + dim.width + " height " + dim.height);
}
@Command(
aliases = { "npc" },
usage = "hologram add [text] | set [line #] [text] | remove [line #] | clear | lineheight [height] | direction [up|down]",

View File

@ -3,9 +3,11 @@ package net.citizensnpcs.npc;
import org.bukkit.Location;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import org.bukkit.event.entity.CreatureSpawnEvent;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.util.NMS;
import net.citizensnpcs.util.Util;
public abstract class AbstractEntityController implements EntityController {
private Entity bukkitEntity;
@ -17,8 +19,18 @@ public abstract class AbstractEntityController implements EntityController {
NMS.registerEntityClass(clazz);
}
@Override
public void create(Location at, NPC npc) {
bukkitEntity = createEntity(at, npc);
}
protected abstract Entity createEntity(Location at, NPC npc);
@Override
public void die() {
bukkitEntity = null;
}
@Override
public Entity getBukkitEntity() {
return bukkitEntity;
@ -31,7 +43,7 @@ public abstract class AbstractEntityController implements EntityController {
if (bukkitEntity instanceof Player) {
NMS.removeFromWorld(bukkitEntity);
NMS.remove(bukkitEntity);
setEntity(null);
bukkitEntity = null;
} else {
bukkitEntity.remove();
bukkitEntity = null;
@ -39,12 +51,7 @@ public abstract class AbstractEntityController implements EntityController {
}
@Override
public void setEntity(Entity entity) {
this.bukkitEntity = entity;
}
@Override
public void spawn(Location at, NPC npc) {
bukkitEntity = createEntity(at, npc);
public boolean spawn(Location at) {
return !Util.isLoaded(at) ? false : NMS.addEntityToWorld(bukkitEntity, CreatureSpawnEvent.SpawnReason.CUSTOM);
}
}

View File

@ -12,7 +12,6 @@ import org.bukkit.entity.Entity;
import org.bukkit.entity.EntityType;
import org.bukkit.entity.LivingEntity;
import org.bukkit.entity.Player;
import org.bukkit.event.entity.CreatureSpawnEvent;
import org.bukkit.event.player.PlayerTeleportEvent.TeleportCause;
import org.bukkit.metadata.FixedMetadataValue;
import org.bukkit.scheduler.BukkitRunnable;
@ -47,6 +46,7 @@ import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.CurrentLocation;
import net.citizensnpcs.trait.Gravity;
import net.citizensnpcs.trait.HologramTrait;
import net.citizensnpcs.trait.PacketNPC;
import net.citizensnpcs.trait.ScoreboardTrait;
import net.citizensnpcs.trait.SitTrait;
import net.citizensnpcs.trait.SneakTrait;
@ -63,10 +63,9 @@ public class CitizensNPC extends AbstractNPC {
private final CitizensNavigator navigator = new CitizensNavigator(this);
private int updateCounter = 0;
public CitizensNPC(UUID uuid, int id, String name, EntityController entityController, NPCRegistry registry) {
public CitizensNPC(UUID uuid, int id, String name, EntityController controller, NPCRegistry registry) {
super(uuid, id, name, registry);
Preconditions.checkNotNull(entityController);
this.entityController = entityController;
setEntityController(controller);
}
@Override
@ -109,7 +108,7 @@ public class CitizensNPC extends AbstractNPC {
}
if (reason == DespawnReason.DEATH) {
entityController.setEntity(null);
entityController.die();
} else {
entityController.remove();
}
@ -139,6 +138,10 @@ public class CitizensNPC extends AbstractNPC {
return entityController == null ? null : entityController.getBukkitEntity();
}
public EntityController getEntityController() {
return entityController;
}
@Override
public Navigator getNavigator() {
return navigator;
@ -157,7 +160,7 @@ public class CitizensNPC extends AbstractNPC {
@Override
public boolean isSpawned() {
return getEntity() != null && NMS.isValid(getEntity());
return getEntity() != null && (hasTrait(PacketNPC.class) || NMS.isValid(getEntity()));
}
@Override
@ -225,7 +228,7 @@ public class CitizensNPC extends AbstractNPC {
public void setEntityController(EntityController newController) {
Preconditions.checkNotNull(newController);
boolean wasSpawned = isSpawned();
boolean wasSpawned = entityController == null ? false : isSpawned();
Location prev = null;
if (wasSpawned) {
prev = getEntity().getLocation(CACHE_LOCATION);
@ -287,7 +290,7 @@ public class CitizensNPC extends AbstractNPC {
}
getOrAddTrait(CurrentLocation.class).setLocation(at);
entityController.spawn(at.clone(), this);
entityController.create(at.clone(), this);
getEntity().setMetadata(NPC_METADATA_MARKER, new FixedMetadataValue(CitizensAPI.getPlugin(), true));
Collection<Trait> onPreSpawn = traits.values();
@ -300,8 +303,8 @@ public class CitizensNPC extends AbstractNPC {
}
}
boolean loaded = Util.isLoaded(at);
boolean couldSpawn = !loaded ? false : NMS.addEntityToWorld(getEntity(), CreatureSpawnEvent.SpawnReason.CUSTOM);
boolean loaded = Messaging.isDebugging() ? false : Util.isLoaded(at);
boolean couldSpawn = entityController.spawn(at);
if (!couldSpawn) {
if (Messaging.isDebugging()) {
@ -598,7 +601,6 @@ public class CitizensNPC extends AbstractNPC {
private static boolean SUPPORT_GLOWING = true;
private static boolean SUPPORT_NODAMAGE_TICKS = true;
private static boolean SUPPORT_PICKUP_ITEMS = true;
private static boolean SUPPORT_SILENT = true;
private static boolean SUPPORT_USE_ITEM = true;

View File

@ -21,6 +21,7 @@ import net.citizensnpcs.api.trait.trait.Speech;
import net.citizensnpcs.trait.Age;
import net.citizensnpcs.trait.Anchors;
import net.citizensnpcs.trait.ArmorStandTrait;
import net.citizensnpcs.trait.BoundingBoxTrait;
import net.citizensnpcs.trait.ClickRedirectTrait;
import net.citizensnpcs.trait.CommandTrait;
import net.citizensnpcs.trait.Controllable;
@ -37,6 +38,7 @@ import net.citizensnpcs.trait.LookClose;
import net.citizensnpcs.trait.MirrorTrait;
import net.citizensnpcs.trait.MountTrait;
import net.citizensnpcs.trait.OcelotModifiers;
import net.citizensnpcs.trait.PacketNPC;
import net.citizensnpcs.trait.Poses;
import net.citizensnpcs.trait.Powered;
import net.citizensnpcs.trait.RabbitType;
@ -66,6 +68,7 @@ public class CitizensTraitFactory implements TraitFactory {
registerTrait(TraitInfo.create(Age.class));
registerTrait(TraitInfo.create(ArmorStandTrait.class));
registerTrait(TraitInfo.create(Anchors.class));
registerTrait(TraitInfo.create(BoundingBoxTrait.class));
registerTrait(TraitInfo.create(ClickRedirectTrait.class));
registerTrait(TraitInfo.create(CommandTrait.class));
registerTrait(TraitInfo.create(Controllable.class));
@ -86,6 +89,7 @@ public class CitizensTraitFactory implements TraitFactory {
registerTrait(TraitInfo.create(MobType.class).asDefaultTrait());
registerTrait(TraitInfo.create(OcelotModifiers.class));
registerTrait(TraitInfo.create(Owner.class));
registerTrait(TraitInfo.create(PacketNPC.class));
registerTrait(TraitInfo.create(Poses.class));
registerTrait(TraitInfo.create(Powered.class));
registerTrait(TraitInfo.create(RabbitType.class));

View File

@ -6,11 +6,13 @@ import org.bukkit.entity.Entity;
import net.citizensnpcs.api.npc.NPC;
public interface EntityController {
void create(Location at, NPC npc);
void die();
Entity getBukkitEntity();
void remove();
void setEntity(Entity entity);
void spawn(Location at, NPC npc);
boolean spawn(Location at);
}

View File

@ -155,9 +155,7 @@ class ProfileFetchThread implements Runnable {
@Override
public void onProfileLookupSucceeded(final GameProfile profile) {
if (Messaging.isDebugging()) {
Messaging.debug("Fetched profile " + profile.getId() + " for player " + profile.getName());
}
Messaging.idebug(() -> "Fetched profile " + profile.getId() + " for player " + profile.getName());
ProfileRequest request = findRequest(profile.getName(), requests);
if (request == null)

View File

@ -192,9 +192,7 @@ public class Skin {
}
}, delay);
if (Messaging.isDebugging()) {
Messaging.debug("Retrying skin fetch for '" + skinName + "' in " + delay + " ticks.");
}
Messaging.idebug(() -> "Retrying skin fetch for '" + skinName + "' in " + delay + " ticks.");
break;
case SUCCESS:
GameProfile profile = request.getProfile();
@ -210,15 +208,11 @@ public class Skin {
private void fetchForced() {
final int maxRetries = Setting.MAX_NPC_SKIN_RETRIES.asInt();
if (maxRetries > -1 && fetchRetries >= maxRetries) {
if (Messaging.isDebugging()) {
Messaging.debug("Reached max skin fetch retries for '" + skinName + "'");
}
Messaging.idebug(() -> "Reached max skin fetch retries for '" + skinName + "'");
return;
}
if (skinName.length() < 3 || skinName.length() > 16) {
if (Messaging.isDebugging()) {
Messaging.debug("Skin name invalid length '" + skinName + "'");
}
Messaging.idebug(() -> "Skin name invalid length '" + skinName + "'");
return;
}
@ -250,9 +244,7 @@ public class Skin {
}
}, delay);
if (Messaging.isDebugging()) {
Messaging.debug("Retrying skin fetch for '" + skinName + "' in " + delay + " ticks.");
}
Messaging.idebug(() -> "Retrying skin fetch for '" + skinName + "' in " + delay + " ticks.");
break;
case SUCCESS:
GameProfile profile = request.getProfile();

View File

@ -0,0 +1,60 @@
package net.citizensnpcs.trait;
import net.citizensnpcs.api.npc.NPC.NPCUpdate;
import net.citizensnpcs.api.persistence.Persist;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitName;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.util.NMS;
// TODO: could set a function instead which replaces makeBoundingBox
@TraitName("boundingbox")
public class BoundingBoxTrait extends Trait {
private EntityDim base;
@Persist
private float height = -1;
@Persist
private float scale = -1;
@Persist
private float width = -1;
public BoundingBoxTrait() {
super("boundingbox");
}
public EntityDim getAdjustedBoundingBox() {
EntityDim desired = base.clone();
if (scale != -1) {
desired = desired.mul(scale);
}
return new EntityDim(width == -1 ? desired.width : width, height == -1 ? desired.height : height);
}
@Override
public void onSpawn() {
base = EntityDim.from(npc.getEntity());
}
@Override
public void run() {
if (!npc.isUpdating(NPCUpdate.PACKET) || !npc.isSpawned())
return;
EntityDim desired = getAdjustedBoundingBox();
if (!desired.equals(EntityDim.from(npc.getEntity()))) {
NMS.setDimensions(npc.getEntity(), desired);
}
}
public void setHeight(float height) {
this.height = height;
}
public void setScale(float s) {
this.scale = s;
}
public void setWidth(float width) {
this.width = width;
}
}

View File

@ -0,0 +1,93 @@
package net.citizensnpcs.trait;
import org.bukkit.Location;
import org.bukkit.entity.Entity;
import org.bukkit.entity.Player;
import org.bukkit.metadata.FixedMetadataValue;
import net.citizensnpcs.api.CitizensAPI;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitName;
import net.citizensnpcs.npc.CitizensNPC;
import net.citizensnpcs.npc.EntityController;
import net.citizensnpcs.util.NMS;
import net.citizensnpcs.util.PlayerUpdateTask;
@TraitName("packet")
public class PacketNPC extends Trait {
private EntityPacketTracker playerTracker;
public PacketNPC() {
super("packet");
}
@Override
public void onSpawn() {
playerTracker = NMS.getPlayerTracker(npc.getEntity());
}
@Override
public void run() {
wrap((CitizensNPC) npc);
if (!npc.isSpawned())
return;
for (Player nearby : CitizensAPI.getLocationLookup().getNearbyPlayers(npc.getStoredLocation(), 64)) {
if (!nearby.hasMetadata(npc.getUniqueId().toString())) {
playerTracker.link(nearby);
nearby.setMetadata(npc.getUniqueId().toString(), new FixedMetadataValue(CitizensAPI.getPlugin(), true));
}
}
playerTracker.run();
}
private void wrap(CitizensNPC npc) {
if (!(npc.getEntityController() instanceof PacketController)) {
npc.setEntityController(new PacketController(npc.getEntityController()));
}
}
private class PacketController implements EntityController {
private final EntityController base;
public PacketController(EntityController controller) {
this.base = controller;
}
@Override
public void create(Location at, NPC npc) {
base.create(at, npc);
}
@Override
public void die() {
}
@Override
public Entity getBukkitEntity() {
return base.getBukkitEntity();
}
@Override
public void remove() {
PlayerUpdateTask.deregisterPlayer(getBukkitEntity());
playerTracker.remove();
base.remove();
}
@Override
public boolean spawn(Location at) {
base.getBukkitEntity().teleport(at);
PlayerUpdateTask.registerPlayer(getBukkitEntity());
return true;
}
}
public static interface EntityPacketTracker extends Runnable {
public void link(Player player);
public void remove();
public void unlink(Player player);
}
}

View File

@ -17,6 +17,7 @@ import org.bukkit.entity.Player;
import com.google.common.base.Splitter;
import com.google.common.collect.Lists;
import com.google.common.primitives.Doubles;
import net.citizensnpcs.Settings.Setting;
import net.citizensnpcs.api.CitizensAPI;
@ -137,15 +138,16 @@ public class BossBarTrait extends Trait {
}
}
bar.setProgress(entity.getHealth() / maxHealth);
} else {
} else if (track != null && !track.isEmpty()) {
String replaced = Placeholders.replace(track,
npc.getEntity() instanceof Player ? (Player) npc.getEntity() : null);
if (!track.equals(replaced)) {
try {
bar.setProgress(Double.parseDouble(replaced));
} catch (NumberFormatException ex) {
}
Double number = Doubles.tryParse(replaced);
if (number == null)
return;
if (number >= 1 && number <= 100) {
number /= 100.0;
}
bar.setProgress(number);
}
}
bar.setTitle(title);

View File

@ -32,6 +32,7 @@ public class Messages {
public static final String BEHAVIOUR_HELP = "citizens.commands.npc.behaviour.help";
public static final String BEHAVIOURS_ADDED = "citizens.commands.npc.behaviour.added";
public static final String BEHAVIOURS_REMOVED = "citizens.commands.npc.behaviour.removed";
public static final String BOUNDING_BOX_SET = "citizens.commands.npc.hitbox.set";
public static final String CAMEL_POSE_SET = "citizens.commands.npc.camel.pose-set";
public static final String CANNOT_TELEPORT_ACROSS_WORLDS = "citizens.commands.npc.tphere.multiworld-not-allowed";
public static final String CAT_COLLAR_COLOR_SET = "citizens.commands.npc.cat.collar-color-set";

View File

@ -40,10 +40,12 @@ import net.citizensnpcs.api.npc.BlockBreaker.BlockBreakerConfiguration;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.versioned.CamelTrait.CamelPose;
public class NMS {
@ -346,6 +348,10 @@ public class NMS {
return BRIDGE.getPassengers(entity);
}
public static EntityPacketTracker getPlayerTracker(Entity entity) {
return BRIDGE.createPacketTracker(entity);
}
public static GameProfile getProfile(Player player) {
return BRIDGE.getProfile(player);
}
@ -546,6 +552,10 @@ public class NMS {
BRIDGE.setBodyYaw(entity, yaw);
}
public static void setBoundingBox(Entity entity, BoundingBox box) {
BRIDGE.setBoundingBox(entity, box);
}
public static void setCamelPose(Entity entity, CamelPose pose) {
BRIDGE.setCamelPose(entity, pose);
}
@ -558,6 +568,10 @@ public class NMS {
BRIDGE.setDestination(entity, x, y, z, speed);
}
public static void setDimensions(Entity entity, EntityDim desired) {
BRIDGE.setDimensions(entity, desired);
}
public static void setEndermanAngry(Enderman enderman, boolean angry) {
BRIDGE.setEndermanAngry(enderman, angry);
}
@ -685,7 +699,6 @@ public class NMS {
private static Object UNSAFE;
private static MethodHandle UNSAFE_FIELD_OFFSET;
private static MethodHandle UNSAFE_PUT_OBJECT;
private static MethodHandle UNSAFE_STATIC_FIELD_OFFSET;
static {

View File

@ -34,9 +34,11 @@ import net.citizensnpcs.api.npc.BlockBreaker.BlockBreakerConfiguration;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.versioned.CamelTrait.CamelPose;
public interface NMSBridge {
@ -51,6 +53,10 @@ public interface NMSBridge {
public void cancelMoveDestination(Entity entity);
default public EntityPacketTracker createPacketTracker(Entity entity) {
throw new UnsupportedOperationException();
}
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable;
public BlockBreaker getBlockBreaker(Entity entity, Block targetBlock, BlockBreakerConfiguration config);
@ -75,7 +81,7 @@ public interface NMSBridge {
public CompoundTag getNBT(ItemStack item);
public NPC getNPC(Entity entity);
public NPC getNPC(Entity entity);;
public List<Entity> getPassengers(Entity entity);
@ -142,11 +148,11 @@ public interface NMSBridge {
public void removeHookIfNecessary(NPCRegistry npcRegistry, FishHook entity);
public void replaceTrackerEntry(Player player);
public void replaceTrackerEntry(Player player);;
public void sendPositionUpdate(Player excluding, Entity from, Location location);
public void sendRotationNearby(Entity from, float bodyYaw, float headYaw, float pitch);;
public void sendRotationNearby(Entity from, float bodyYaw, float headYaw, float pitch);
public boolean sendTabListAdd(Player recipient, Player listPlayer);
@ -160,7 +166,9 @@ public interface NMSBridge {
throw new UnsupportedOperationException();
}
public void setBodyYaw(Entity entity, float yaw);
public void setBodyYaw(Entity entity, float yaw);;
public void setBoundingBox(Entity entity, BoundingBox box);
public default void setCamelPose(Entity entity, CamelPose pose) {
throw new UnsupportedOperationException();
@ -168,21 +176,23 @@ public interface NMSBridge {
public void setCustomName(Entity entity, Object component, String string);;
public void setDestination(Entity entity, double x, double y, double z, float speed);
public void setDestination(Entity entity, double x, double y, double z, float speed);;
public void setDimensions(Entity entity, EntityDim desired);;
public void setEndermanAngry(Enderman enderman, boolean angry);
public void setHeadYaw(Entity entity, float yaw);;
public void setKnockbackResistance(LivingEntity entity, double d);;
public void setKnockbackResistance(LivingEntity entity, double d);
public default void setLyingDown(Entity cat, boolean lying) {
throw new UnsupportedOperationException();
};
}
public void setNavigationTarget(Entity handle, Entity target, float speed);
public void setNoGravity(Entity entity, boolean nogravity);;
public void setNoGravity(Entity entity, boolean nogravity);
public default void setPandaSitting(Entity entity, boolean sitting) {
throw new UnsupportedOperationException();
@ -234,5 +244,5 @@ public interface NMSBridge {
public void updateNavigationWorld(Entity entity, World world);
public void updatePathfindingRange(NPC npc, float pathfindingRange);;
public void updatePathfindingRange(NPC npc, float pathfindingRange);
}

View File

@ -12,7 +12,9 @@ import org.bukkit.scheduler.BukkitRunnable;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.npc.CitizensNPC;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.trait.PacketNPC;
public class PlayerUpdateTask extends BukkitRunnable {
@Override
@ -28,14 +30,18 @@ public class PlayerUpdateTask extends BukkitRunnable {
}
for (Entity entity : PLAYERS_PENDING_ADD) {
PlayerTick rm = PLAYERS.remove(entity.getUniqueId());
NPC next = ((NPCHolder) entity).getNPC();
if (rm != null) {
NPC old = ((NPCHolder) rm).getNPC();
NPC next = ((NPCHolder) entity).getNPC();
NPC old = ((NPCHolder) rm.entity).getNPC();
Messaging.severe(old == next ? "Player registered twice"
: "Player registered twice with different NPC instances", rm.entity.getUniqueId());
rm.entity.remove();
}
PLAYERS.put(entity.getUniqueId(), new PlayerTick((Player) entity));
if (next.hasTrait(PacketNPC.class)) {
PLAYERS.put(entity.getUniqueId(), new PlayerTick(entity, () -> ((CitizensNPC) next).update()));
} else {
PLAYERS.put(entity.getUniqueId(), new PlayerTick((Player) entity));
}
}
PLAYERS_PENDING_ADD.clear();
PLAYERS_PENDING_REMOVE.clear();
@ -44,19 +50,25 @@ public class PlayerUpdateTask extends BukkitRunnable {
}
private static class PlayerTick implements Runnable {
Player entity;
Runnable tick;
private final Entity entity;
private final Runnable tick;
public PlayerTick(Entity entity, Runnable tick) {
this.entity = entity;
this.tick = tick;
}
public PlayerTick(Player player) {
entity = player;
tick = NMS.playerTicker(player);
this(player, () -> {
if (player.isValid()) {
NMS.playerTicker(player);
}
});
}
@Override
public void run() {
if (entity.isValid()) {
tick.run();
}
tick.run();
}
}

View File

@ -351,10 +351,8 @@ public class Util {
cmd += " --id <id>";
}
String interpolatedCommand = Placeholders.replace(cmd, clicker, npc);
if (Messaging.isDebugging()) {
Messaging.debug("Running command " + interpolatedCommand + " on NPC " + (npc == null ? -1 : npc.getId())
+ " clicker " + clicker);
}
Messaging.idebug(() -> "Running command " + interpolatedCommand + " on NPC " + (npc == null ? -1 : npc.getId())
+ " clicker " + clicker);
if (!player) {
Bukkit.getServer().dispatchCommand(Bukkit.getConsoleSender(), interpolatedCommand);

View File

@ -114,6 +114,7 @@ citizens.commands.npc.glowing.color-set=[[{0}]]''s glowing color set to {1}]].
citizens.commands.npc.goat.horns-set=[[{0}]]''s horns set to left: [[{1}]] right: [[{2}]]
citizens.commands.npc.guardian.elder-unset=[[{0}]] is no longer an elder guardian.
citizens.commands.npc.guardian.elder-set=[[{0}]] is now an elder guardian.
citizens.commands.npc.hitbox.set=Hitbox set to [[{0}]].
citizens.commands.npc.hologram.text-set=Set hologram text line [[{0}]] to [[{1}]].
citizens.commands.npc.hologram.text-removed=Removed hologram text.
citizens.commands.npc.hologram.text-missing=Missing text to add.

View File

@ -36,9 +36,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -94,6 +94,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_10_R1.entity.BatController;
import net.citizensnpcs.nms.v1_10_R1.entity.BlazeController;
@ -167,6 +168,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
import net.citizensnpcs.trait.versioned.PolarBearTrait;
@ -315,6 +317,45 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
// TODO: configuration / use minecraft defaults for this
int visibleDistance = handle instanceof EntityPlayer ? 512 : 80;
int updateInterval = handle instanceof EntityPlayer ? 2 : 3;
boolean deltaTracking = handle instanceof EntityPlayer ? false : true;
EntityTrackerEntry tracker = new EntityTrackerEntry(handle, visibleDistance,
handle.world.getMinecraftServer().getPlayerList().d(), updateInterval, deltaTracking);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.updatePlayer(p);
tracker.trackedPlayers.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : tracker.trackedPlayers) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
tracker.trackedPlayers.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Exception {
if (Bukkit.isPrimaryThread())
@ -582,10 +623,8 @@ public class NMSImpl implements NMSBridge {
@Override
public boolean update() {
if (params.speed() != lastSpeed && lastSpeed > 0) {
if (Messaging.isDebugging()) {
Messaging.debug(
"Repathfinding " + ((NPCHolder) entity).getNPC().getId() + " due to speed change");
}
Messaging.idebug(
() -> "Repathfinding " + ((NPCHolder) entity).getNPC().getId() + " due to speed change");
Entity handle = getHandle(entity);
float oldWidth = handle.width;
if (handle instanceof EntityHorse) {
@ -1082,6 +1121,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName(string);
@ -1099,6 +1143,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity bentity, EntityDim desired) {
setSize(getHandle(bentity), desired.width, desired.height, false);
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)

View File

@ -36,9 +36,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -36,9 +36,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends EntityHorseDonkey implements NPCHolder {

View File

@ -36,9 +36,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends EntityHorseMule implements NPCHolder {

View File

@ -36,9 +36,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends EntityHorseSkeleton implements NPCHolder {

View File

@ -36,9 +36,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends EntityHorseZombie implements NPCHolder {

View File

@ -36,9 +36,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends EntityLlama implements NPCHolder {

View File

@ -94,6 +94,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_11_R1.entity.BatController;
import net.citizensnpcs.nms.v1_11_R1.entity.BlazeController;
@ -182,6 +183,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
import net.citizensnpcs.trait.versioned.LlamaTrait;
@ -336,6 +338,45 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
// TODO: configuration / use minecraft defaults for this
int visibleDistance = handle instanceof EntityPlayer ? 512 : 80;
int updateInterval = handle instanceof EntityPlayer ? 2 : 3;
boolean deltaTracking = handle instanceof EntityPlayer ? false : true;
EntityTrackerEntry tracker = new EntityTrackerEntry(handle, visibleDistance,
handle.world.getMinecraftServer().getPlayerList().d(), updateInterval, deltaTracking);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.updatePlayer(p);
tracker.trackedPlayers.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : tracker.trackedPlayers) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
tracker.trackedPlayers.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Exception {
if (Bukkit.isPrimaryThread())
@ -613,10 +654,8 @@ public class NMSImpl implements NMSBridge {
@Override
public boolean update() {
if (params.speed() != lastSpeed && lastSpeed > 0) {
if (Messaging.isDebugging()) {
Messaging.debug(
"Repathfinding " + ((NPCHolder) entity).getNPC().getId() + " due to speed change");
}
Messaging.idebug(
() -> "Repathfinding " + ((NPCHolder) entity).getNPC().getId() + " due to speed change");
Entity handle = getHandle(entity);
float oldWidth = handle.width;
if (handle instanceof EntityHorse) {
@ -1141,6 +1180,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName(string);
@ -1158,6 +1202,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity bentity, EntityDim desired) {
setSize(getHandle(bentity), desired.width, desired.height, false);
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)

View File

@ -39,9 +39,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -39,9 +39,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends EntityHorseDonkey implements NPCHolder {

View File

@ -39,9 +39,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends EntityHorseMule implements NPCHolder {

View File

@ -39,9 +39,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends EntityHorseSkeleton implements NPCHolder {

View File

@ -39,9 +39,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends EntityHorseZombie implements NPCHolder {

View File

@ -37,9 +37,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends EntityLlama implements NPCHolder {

View File

@ -94,6 +94,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_12_R1.entity.BatController;
import net.citizensnpcs.nms.v1_12_R1.entity.BlazeController;
@ -184,6 +185,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
import net.citizensnpcs.trait.versioned.LlamaTrait;
@ -341,6 +343,45 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
// TODO: configuration / use minecraft defaults for this
int visibleDistance = handle instanceof EntityPlayer ? 512 : 80;
int updateInterval = handle instanceof EntityPlayer ? 2 : 3;
boolean deltaTracking = handle instanceof EntityPlayer ? false : true;
EntityTrackerEntry tracker = new EntityTrackerEntry(handle, visibleDistance,
handle.world.getMinecraftServer().getPlayerList().d(), updateInterval, deltaTracking);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.updatePlayer(p);
tracker.trackedPlayers.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : tracker.trackedPlayers) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
tracker.trackedPlayers.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Exception {
if (Bukkit.isPrimaryThread())
@ -1146,6 +1187,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName(string);
@ -1163,6 +1209,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity bentity, EntityDim desired) {
setSize(getHandle(bentity), desired.width, desired.height, false);
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)

View File

@ -43,9 +43,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -43,9 +43,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends EntityHorseDonkey implements NPCHolder {

View File

@ -43,9 +43,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends EntityHorseMule implements NPCHolder {

View File

@ -43,9 +43,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends EntityHorseSkeleton implements NPCHolder {

View File

@ -43,9 +43,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends EntityHorseZombie implements NPCHolder {

View File

@ -41,9 +41,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends EntityLlama implements NPCHolder {

View File

@ -96,6 +96,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_13_R2.entity.BatController;
import net.citizensnpcs.nms.v1_13_R2.entity.BlazeController;
@ -195,6 +196,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
import net.citizensnpcs.trait.versioned.LlamaTrait;
@ -361,6 +363,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
// TODO: configuration / use minecraft defaults for this
int visibleDistance = handle instanceof EntityPlayer ? 512 : 80;
int updateInterval = handle instanceof EntityPlayer ? 2 : 3;
boolean deltaTracking = handle instanceof EntityPlayer ? false : true;
EntityTrackerEntry tracker = new EntityTrackerEntry(handle, visibleDistance,
handle.world.getMinecraftServer().getPlayerList().getFurthestViewableBlock(), updateInterval,
deltaTracking);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.updatePlayer(p);
tracker.trackedPlayers.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : tracker.trackedPlayers) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
tracker.trackedPlayers.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Exception {
if (Bukkit.isPrimaryThread())
@ -1188,6 +1230,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName((IChatBaseComponent) component);
@ -1205,6 +1252,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity bentity, EntityDim desired) {
setSize(getHandle(bentity), desired.width, desired.height, false);
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)

View File

@ -46,9 +46,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends EntityHorseDonkey implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends EntityHorseMule implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends EntityHorseSkeleton implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends EntityHorseZombie implements NPCHolder {

View File

@ -44,9 +44,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends EntityLlama implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class TraderLlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityTraderLlamaNPC extends EntityLlamaTrader implements NPCHolder {

View File

@ -57,6 +57,7 @@ import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.mojang.authlib.GameProfile;
import com.mojang.authlib.GameProfileRepository;
import com.mojang.authlib.HttpAuthenticationService;
@ -93,6 +94,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_14_R1.entity.BatController;
import net.citizensnpcs.nms.v1_14_R1.entity.BlazeController;
@ -199,6 +201,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
import net.citizensnpcs.trait.versioned.CatTrait;
@ -264,6 +267,7 @@ import net.minecraft.server.v1_14_R1.EntityRabbit;
import net.minecraft.server.v1_14_R1.EntityShulker;
import net.minecraft.server.v1_14_R1.EntitySize;
import net.minecraft.server.v1_14_R1.EntityTameableAnimal;
import net.minecraft.server.v1_14_R1.EntityTrackerEntry;
import net.minecraft.server.v1_14_R1.EntityTurtle;
import net.minecraft.server.v1_14_R1.EntityTypes;
import net.minecraft.server.v1_14_R1.EntityWither;
@ -400,6 +404,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
Set<EntityPlayer> linked = Sets.newIdentityHashSet();
EntityTrackerEntry tracker = new EntityTrackerEntry((WorldServer) handle.world, handle,
handle.getEntityType().getUpdateInterval(), handle.getEntityType().isDeltaTracking(), packet -> {
for (EntityPlayer link : linked) {
link.playerConnection.sendPacket(packet);
}
}, linked);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.b(p);
linked.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : linked) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
linked.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable {
if (Bukkit.isPrimaryThread())
@ -1205,6 +1249,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName((IChatBaseComponent) component);
@ -1222,6 +1271,18 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity bentity, EntityDim desired) {
EntitySize entitysize = new EntitySize(desired.width, desired.height, true);
Entity entity = getHandle(bentity);
try {
SIZE_FIELD_SETTER.invoke(entity, entitysize);
HEAD_HEIGHT.invoke(entity, HEAD_HEIGHT_METHOD.invoke(entity, entity.getPose(), entity.a(entity.getPose())));
} catch (Throwable ex) {
ex.printStackTrace();
}
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)

View File

@ -42,14 +42,14 @@ public class HorseController extends MobEntityController {
}
@Override
public Horse getBukkitEntity() {
return (Horse) super.getBukkitEntity();
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.create(at, npc);
}
@Override
public void spawn(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
public Horse getBukkitEntity() {
return (Horse) super.getBukkitEntity();
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends EntityHorseDonkey implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends EntityHorseMule implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends EntityHorseSkeleton implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends EntityHorseZombie implements NPCHolder {

View File

@ -45,9 +45,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends EntityLlama implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class TraderLlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityTraderLlamaNPC extends EntityLlamaTrader implements NPCHolder {

View File

@ -2,6 +2,8 @@ package net.citizensnpcs.nms.v1_15_R1.util;
import org.bukkit.entity.Entity;
import com.google.common.base.Joiner;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.npc.ai.NPCHolder;
@ -11,9 +13,8 @@ public interface ForwardingNPCHolder extends NPCHolder, Entity {
default NPC getNPC() {
net.minecraft.server.v1_15_R1.Entity handle = NMSImpl.getHandle(this);
if (!(handle instanceof NPCHolder)) {
if (Messaging.isDebugging()) {
Messaging.debug("ForwardingNPCHolder with an improper bukkit entity", this, handle);
}
Messaging.idebug(
() -> Joiner.on(' ').join("ForwardingNPCHolder with an improper bukkit entity", this, handle));
return null;
}
return ((NPCHolder) handle).getNPC();

View File

@ -57,6 +57,7 @@ import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.mojang.authlib.GameProfile;
import com.mojang.authlib.GameProfileRepository;
import com.mojang.authlib.HttpAuthenticationService;
@ -93,6 +94,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_15_R1.entity.BatController;
import net.citizensnpcs.nms.v1_15_R1.entity.BeeController;
@ -200,6 +202,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BeeTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
@ -268,6 +271,7 @@ import net.minecraft.server.v1_15_R1.EntityRabbit;
import net.minecraft.server.v1_15_R1.EntityShulker;
import net.minecraft.server.v1_15_R1.EntitySize;
import net.minecraft.server.v1_15_R1.EntityTameableAnimal;
import net.minecraft.server.v1_15_R1.EntityTrackerEntry;
import net.minecraft.server.v1_15_R1.EntityTurtle;
import net.minecraft.server.v1_15_R1.EntityTypes;
import net.minecraft.server.v1_15_R1.EntityWither;
@ -415,6 +419,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
Set<EntityPlayer> linked = Sets.newIdentityHashSet();
EntityTrackerEntry tracker = new EntityTrackerEntry((WorldServer) handle.world, handle,
handle.getEntityType().getUpdateInterval(), handle.getEntityType().isDeltaTracking(), packet -> {
for (EntityPlayer link : linked) {
link.playerConnection.sendPacket(packet);
}
}, linked);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.b(p);
linked.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : linked) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
linked.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable {
if (Bukkit.isPrimaryThread())
@ -1223,6 +1267,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName((IChatBaseComponent) component);
@ -1240,6 +1289,18 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity bentity, EntityDim desired) {
EntitySize entitysize = new EntitySize(desired.width, desired.height, true);
Entity entity = getHandle(bentity);
try {
SIZE_FIELD_SETTER.invoke(entity, entitysize);
HEAD_HEIGHT.invoke(entity, HEAD_HEIGHT_METHOD.invoke(entity, entity.getPose(), entity.a(entity.getPose())));
} catch (Throwable ex) {
ex.printStackTrace();
}
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)

View File

@ -47,9 +47,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends EntityHorseDonkey implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends EntityHorseMule implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends EntityHorseSkeleton implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends EntityHorseZombie implements NPCHolder {

View File

@ -45,9 +45,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends EntityLlama implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class TraderLlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityTraderLlamaNPC extends EntityLlamaTrader implements NPCHolder {

View File

@ -58,6 +58,7 @@ import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.mojang.authlib.GameProfile;
import com.mojang.authlib.GameProfileRepository;
import com.mojang.authlib.HttpAuthenticationService;
@ -94,6 +95,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_16_R3.entity.BatController;
import net.citizensnpcs.nms.v1_16_R3.entity.BeeController;
@ -206,6 +208,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.BeeTrait;
import net.citizensnpcs.trait.versioned.BossBarTrait;
@ -276,6 +279,7 @@ import net.minecraft.server.v1_16_R3.EntityRabbit;
import net.minecraft.server.v1_16_R3.EntityShulker;
import net.minecraft.server.v1_16_R3.EntitySize;
import net.minecraft.server.v1_16_R3.EntityTameableAnimal;
import net.minecraft.server.v1_16_R3.EntityTrackerEntry;
import net.minecraft.server.v1_16_R3.EntityTurtle;
import net.minecraft.server.v1_16_R3.EntityTypes;
import net.minecraft.server.v1_16_R3.EntityWither;
@ -424,6 +428,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
Set<EntityPlayer> linked = Sets.newIdentityHashSet();
EntityTrackerEntry tracker = new EntityTrackerEntry((WorldServer) handle.world, handle,
handle.getEntityType().getUpdateInterval(), handle.getEntityType().isDeltaTracking(), packet -> {
for (EntityPlayer link : linked) {
link.playerConnection.sendPacket(packet);
}
}, linked);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
handle.dead = false;
tracker.b(p);
linked.add(p);
}
@Override
public void remove() {
for (EntityPlayer link : linked) {
unlink(link.getBukkitEntity());
}
}
@Override
public void run() {
tracker.a();
}
@Override
public void unlink(Player player) {
EntityPlayer p = (EntityPlayer) getHandle(player);
tracker.a(p);
linked.remove(p);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable {
if (Bukkit.isPrimaryThread())
@ -1253,6 +1297,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).yaw = yaw;
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).a(new AxisAlignedBB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName((IChatBaseComponent) component);
@ -1270,6 +1319,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity entity, EntityDim desired) {
setSize(getHandle(entity), new EntitySize(desired.width, desired.height, true));
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_ANGRY == null)
@ -2136,6 +2190,7 @@ public class NMSImpl implements NMSBridge {
public static void setSize(Entity entity, EntitySize size) {
try {
SIZE_FIELD_SETTER.invoke(entity, size);
HEAD_HEIGHT.invoke(entity, HEAD_HEIGHT_METHOD.invoke(entity, entity.getPose(), entity.a(entity.getPose())));
} catch (Throwable e) {
e.printStackTrace();
}

View File

@ -46,9 +46,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends Horse implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends Donkey implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends Mule implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends SkeletonHorse implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends ZombieHorse implements NPCHolder {

View File

@ -44,9 +44,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends Llama implements NPCHolder {

View File

@ -44,9 +44,9 @@ public class TraderLlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityTraderLlamaNPC extends TraderLlama implements NPCHolder {

View File

@ -2,6 +2,8 @@ package net.citizensnpcs.nms.v1_17_R1.util;
import org.bukkit.entity.Entity;
import com.google.common.base.Joiner;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.npc.ai.NPCHolder;
@ -11,9 +13,8 @@ public interface ForwardingNPCHolder extends NPCHolder, Entity {
default NPC getNPC() {
net.minecraft.world.entity.Entity handle = NMSImpl.getHandle(this);
if (!(handle instanceof NPCHolder)) {
if (Messaging.isDebugging()) {
Messaging.debug("ForwardingNPCHolder with an improper bukkit entity", this, handle);
}
Messaging.idebug(
() -> Joiner.on(' ').join("ForwardingNPCHolder with an improper bukkit entity", this, handle));
return null;
}
return ((NPCHolder) handle).getNPC();

View File

@ -8,13 +8,6 @@ public class NMSBoundingBox {
}
public static BoundingBox wrap(AABB bb) {
double minX = 0, minY = 0, minZ = 0, maxX = 0, maxY = 0, maxZ = 0;
minX = bb.minX;
minY = bb.minY;
minZ = bb.minZ;
maxX = bb.maxX;
maxY = bb.maxY;
maxZ = bb.maxZ;
return new BoundingBox(minX, minY, minZ, maxX, maxY, maxZ);
return new BoundingBox(bb.minX, bb.minY, bb.minZ, bb.maxX, bb.maxY, bb.maxZ);
}
}

View File

@ -55,6 +55,7 @@ import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.mojang.authlib.GameProfile;
import com.mojang.authlib.GameProfileRepository;
import com.mojang.authlib.HttpAuthenticationService;
@ -91,6 +92,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_17_R1.entity.AxolotlController;
import net.citizensnpcs.nms.v1_17_R1.entity.BatController;
@ -208,6 +210,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.AxolotlTrait;
import net.citizensnpcs.trait.versioned.BeeTrait;
@ -253,8 +256,10 @@ import net.minecraft.server.level.ChunkMap;
import net.minecraft.server.level.ChunkMap.TrackedEntity;
import net.minecraft.server.level.ServerBossEvent;
import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.server.level.ServerEntity;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.server.level.ServerPlayer;
import net.minecraft.server.network.ServerPlayerConnection;
import net.minecraft.sounds.SoundEvent;
import net.minecraft.tags.FluidTags;
import net.minecraft.util.Mth;
@ -439,6 +444,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
Set<ServerPlayerConnection> linked = Sets.newIdentityHashSet();
ServerEntity tracker = new ServerEntity((ServerLevel) handle.level, handle, handle.getType().updateInterval(),
handle.getType().trackDeltas(), packet -> {
for (ServerPlayerConnection link : linked) {
link.send(packet);
}
}, linked);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
ServerPlayer p = (ServerPlayer) getHandle(player);
handle.unsetRemoved();
tracker.addPairing(p);
linked.add(p.connection);
}
@Override
public void remove() {
for (ServerPlayerConnection link : linked) {
unlink(link.getPlayer().getBukkitEntity());
}
}
@Override
public void run() {
tracker.sendChanges();
}
@Override
public void unlink(Player player) {
ServerPlayer p = (ServerPlayer) getHandle(player);
tracker.removePairing(p);
linked.remove(p.connection);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable {
if (Bukkit.isPrimaryThread())
@ -1249,6 +1294,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).setYRot(yaw);
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).setBoundingBox(new AABB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName((Component) component);
@ -1266,6 +1316,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity entity, EntityDim desired) {
setSize(getHandle(entity), new EntityDimensions(desired.width, desired.height, true));
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_CREEPY == null)
@ -2139,6 +2194,9 @@ public class NMSImpl implements NMSBridge {
public static void setSize(Entity entity, EntityDimensions size) {
try {
SIZE_FIELD_SETTER.invoke(entity, size);
HEAD_HEIGHT.invoke(entity,
HEAD_HEIGHT_METHOD.invoke(entity, entity.getPose(), entity.getDimensions(entity.getPose())));
} catch (Throwable e) {
e.printStackTrace();
}
@ -2185,7 +2243,6 @@ public class NMSImpl implements NMSBridge {
EntityType.SHULKER, EntityType.PHANTOM);
private static final MethodHandle BEHAVIOR_MAP = NMS.getGetter(Brain.class, "f");
private static final MethodHandle BUKKITENTITY_FIELD_SETTER = NMS.getSetter(Entity.class, "bukkitEntity");
private static final MethodHandle CHUNKMAP_UPDATE_PLAYER_STATUS = NMS.getMethodHandle(ChunkMap.class, "a", true,
ServerPlayer.class, boolean.class);

View File

@ -47,9 +47,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends Horse implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends Donkey implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends Mule implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends SkeletonHorse implements NPCHolder {

View File

@ -47,9 +47,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends ZombieHorse implements NPCHolder {

View File

@ -45,9 +45,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends Llama implements NPCHolder {

View File

@ -45,9 +45,9 @@ public class TraderLlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityTraderLlamaNPC extends TraderLlama implements NPCHolder {

View File

@ -2,6 +2,8 @@ package net.citizensnpcs.nms.v1_18_R2.util;
import org.bukkit.entity.Entity;
import com.google.common.base.Joiner;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.npc.ai.NPCHolder;
@ -11,9 +13,9 @@ public interface ForwardingNPCHolder extends NPCHolder, Entity {
default NPC getNPC() {
net.minecraft.world.entity.Entity handle = NMSImpl.getHandle(this);
if (!(handle instanceof NPCHolder)) {
if (Messaging.isDebugging()) {
Messaging.debug("ForwardingNPCHolder with an improper bukkit entity", this, handle);
}
Messaging.idebug(
() -> Joiner.on(' ').join("ForwardingNPCHolder with an improper bukkit entity", this, handle));
return null;
}
return ((NPCHolder) handle).getNPC();

View File

@ -8,13 +8,6 @@ public class NMSBoundingBox {
}
public static BoundingBox wrap(AABB bb) {
double minX = 0, minY = 0, minZ = 0, maxX = 0, maxY = 0, maxZ = 0;
minX = bb.minX;
minY = bb.minY;
minZ = bb.minZ;
maxX = bb.maxX;
maxY = bb.maxY;
maxZ = bb.maxZ;
return new BoundingBox(minX, minY, minZ, maxX, maxY, maxZ);
return new BoundingBox(bb.minX, bb.minY, bb.minZ, bb.maxX, bb.maxY, bb.maxZ);
}
}

View File

@ -55,6 +55,7 @@ import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.mojang.authlib.GameProfile;
import com.mojang.authlib.GameProfileRepository;
import com.mojang.authlib.HttpAuthenticationService;
@ -92,6 +93,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_18_R2.entity.AxolotlController;
import net.citizensnpcs.nms.v1_18_R2.entity.BatController;
@ -209,6 +211,7 @@ import net.citizensnpcs.npc.ai.MCNavigationStrategy.MCNavigator;
import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.AxolotlTrait;
import net.citizensnpcs.trait.versioned.BeeTrait;
@ -254,8 +257,10 @@ import net.minecraft.server.level.ChunkMap;
import net.minecraft.server.level.ChunkMap.TrackedEntity;
import net.minecraft.server.level.ServerBossEvent;
import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.server.level.ServerEntity;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.server.level.ServerPlayer;
import net.minecraft.server.network.ServerPlayerConnection;
import net.minecraft.sounds.SoundEvent;
import net.minecraft.tags.FluidTags;
import net.minecraft.util.Mth;
@ -443,6 +448,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
Set<ServerPlayerConnection> linked = Sets.newIdentityHashSet();
ServerEntity tracker = new ServerEntity((ServerLevel) handle.level, handle, handle.getType().updateInterval(),
handle.getType().trackDeltas(), packet -> {
for (ServerPlayerConnection link : linked) {
link.send(packet);
}
}, linked);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
ServerPlayer p = (ServerPlayer) getHandle(player);
handle.unsetRemoved();
tracker.addPairing(p);
linked.add(p.connection);
}
@Override
public void remove() {
for (ServerPlayerConnection link : linked) {
unlink(link.getPlayer().getBukkitEntity());
}
}
@Override
public void run() {
tracker.sendChanges();
}
@Override
public void unlink(Player player) {
ServerPlayer p = (ServerPlayer) getHandle(player);
tracker.removePairing(p);
linked.remove(p.connection);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable {
if (Bukkit.isPrimaryThread())
@ -1257,6 +1302,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).setYRot(yaw);
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).setBoundingBox(new AABB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ));
}
@Override
public void setCustomName(org.bukkit.entity.Entity entity, Object component, String string) {
getHandle(entity).setCustomName((Component) component);
@ -1274,6 +1324,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity entity, EntityDim desired) {
setSize(getHandle(entity), new EntityDimensions(desired.width, desired.height, true));
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_CREEPY == null)
@ -2155,6 +2210,8 @@ public class NMSImpl implements NMSBridge {
public static void setSize(Entity entity, EntityDimensions size) {
try {
SIZE_FIELD_SETTER.invoke(entity, size);
HEAD_HEIGHT.invoke(entity,
HEAD_HEIGHT_METHOD.invoke(entity, entity.getPose(), entity.getDimensions(entity.getPose())));
} catch (Throwable e) {
e.printStackTrace();
}
@ -2222,7 +2279,6 @@ public class NMSImpl implements NMSBridge {
}
private static final MethodHandle ADVANCEMENTS_PLAYER_FIELD = NMS.getFinalSetter(ServerPlayer.class, "cr");
private static final Set<EntityType> BAD_CONTROLLER_LOOK = EnumSet.of(EntityType.POLAR_BEAR, EntityType.BEE,
EntityType.SILVERFISH, EntityType.SHULKER, EntityType.ENDERMITE, EntityType.ENDER_DRAGON, EntityType.BAT,
EntityType.SLIME, EntityType.DOLPHIN, EntityType.MAGMA_CUBE, EntityType.HORSE, EntityType.GHAST,

View File

@ -46,9 +46,9 @@ public class CamelController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class CamelNPC extends CraftCamel implements ForwardingNPCHolder {

View File

@ -5,7 +5,6 @@ import java.lang.invoke.MethodHandle;
import java.net.Socket;
import java.util.List;
import java.util.Map;
import java.util.function.Consumer;
import org.bukkit.Bukkit;
import org.bukkit.Location;
@ -339,14 +338,10 @@ public class EntityHumanNPC extends ServerPlayer implements NPCHolder, Skinnable
AttributeSupplier provider = (AttributeSupplier) ATTRIBUTE_SUPPLIER.invoke(getAttributes());
Map<Attribute, AttributeInstance> all = Maps
.newHashMap((Map<Attribute, AttributeInstance>) ATTRIBUTE_PROVIDER_MAP.invoke(provider));
all.put(Attributes.FOLLOW_RANGE,
new AttributeInstance(Attributes.FOLLOW_RANGE, new Consumer<AttributeInstance>() {
@Override
public void accept(AttributeInstance att) {
throw new UnsupportedOperationException(
"Tried to change value for default attribute instance FOLLOW_RANGE");
}
}));
all.put(Attributes.FOLLOW_RANGE, new AttributeInstance(Attributes.FOLLOW_RANGE, att -> {
throw new UnsupportedOperationException(
"Tried to change value for default attribute instance FOLLOW_RANGE");
}));
ATTRIBUTE_PROVIDER_MAP_SETTER.invoke(provider, ImmutableMap.copyOf(all));
} catch (Throwable e) {
e.printStackTrace();

View File

@ -48,9 +48,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends Horse implements NPCHolder {

View File

@ -48,9 +48,9 @@ public class HorseDonkeyController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.addTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseDonkeyNPC extends Donkey implements NPCHolder {

View File

@ -48,9 +48,9 @@ public class HorseMuleController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseMuleNPC extends Mule implements NPCHolder {

View File

@ -48,9 +48,9 @@ public class HorseSkeletonController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseSkeletonNPC extends SkeletonHorse implements NPCHolder {

View File

@ -48,9 +48,9 @@ public class HorseZombieController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseZombieNPC extends ZombieHorse implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class LlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityLlamaNPC extends Llama implements NPCHolder {

View File

@ -46,9 +46,9 @@ public class TraderLlamaController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityTraderLlamaNPC extends TraderLlama implements NPCHolder {

View File

@ -2,6 +2,8 @@ package net.citizensnpcs.nms.v1_19_R2.util;
import org.bukkit.entity.Entity;
import com.google.common.base.Joiner;
import net.citizensnpcs.api.npc.NPC;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.npc.ai.NPCHolder;
@ -11,9 +13,8 @@ public interface ForwardingNPCHolder extends NPCHolder, Entity {
default NPC getNPC() {
net.minecraft.world.entity.Entity handle = NMSImpl.getHandle(this);
if (!(handle instanceof NPCHolder)) {
if (Messaging.isDebugging()) {
Messaging.debug("ForwardingNPCHolder with an improper bukkit entity", this, handle);
}
Messaging.idebug(
() -> Joiner.on(' ').join("ForwardingNPCHolder with an improper bukkit entity", this, handle));
return null;
}
return ((NPCHolder) handle).getNPC();

View File

@ -7,14 +7,11 @@ public class NMSBoundingBox {
private NMSBoundingBox() {
}
public static AABB convert(BoundingBox box) {
return new AABB(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ);
}
public static BoundingBox wrap(AABB bb) {
double minX = 0, minY = 0, minZ = 0, maxX = 0, maxY = 0, maxZ = 0;
minX = bb.minX;
minY = bb.minY;
minZ = bb.minZ;
maxX = bb.maxX;
maxY = bb.maxY;
maxZ = bb.maxZ;
return new BoundingBox(minX, minY, minZ, maxX, maxY, maxZ);
return new BoundingBox(bb.minX, bb.minY, bb.minZ, bb.maxX, bb.maxY, bb.maxZ);
}
}

View File

@ -56,6 +56,7 @@ import com.google.common.base.Preconditions;
import com.google.common.collect.Iterables;
import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.google.common.collect.Sets;
import com.mojang.authlib.GameProfile;
import com.mojang.authlib.GameProfileRepository;
import com.mojang.authlib.HttpAuthenticationService;
@ -95,6 +96,7 @@ import net.citizensnpcs.api.npc.NPCRegistry;
import net.citizensnpcs.api.trait.Trait;
import net.citizensnpcs.api.trait.TraitInfo;
import net.citizensnpcs.api.util.BoundingBox;
import net.citizensnpcs.api.util.EntityDim;
import net.citizensnpcs.api.util.Messaging;
import net.citizensnpcs.nms.v1_19_R2.entity.AllayController;
import net.citizensnpcs.nms.v1_19_R2.entity.AxolotlController;
@ -219,6 +221,7 @@ import net.citizensnpcs.npc.ai.MCTargetStrategy.TargetNavigator;
import net.citizensnpcs.npc.ai.NPCHolder;
import net.citizensnpcs.npc.skin.SkinnableEntity;
import net.citizensnpcs.trait.MirrorTrait;
import net.citizensnpcs.trait.PacketNPC.EntityPacketTracker;
import net.citizensnpcs.trait.RotationTrait;
import net.citizensnpcs.trait.versioned.AllayTrait;
import net.citizensnpcs.trait.versioned.AxolotlTrait;
@ -272,8 +275,10 @@ import net.minecraft.server.level.ChunkMap;
import net.minecraft.server.level.ChunkMap.TrackedEntity;
import net.minecraft.server.level.ServerBossEvent;
import net.minecraft.server.level.ServerChunkCache;
import net.minecraft.server.level.ServerEntity;
import net.minecraft.server.level.ServerLevel;
import net.minecraft.server.level.ServerPlayer;
import net.minecraft.server.network.ServerPlayerConnection;
import net.minecraft.sounds.SoundEvent;
import net.minecraft.tags.FluidTags;
import net.minecraft.util.Mth;
@ -463,6 +468,46 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public EntityPacketTracker createPacketTracker(org.bukkit.entity.Entity entity) {
Entity handle = getHandle(entity);
Set<ServerPlayerConnection> linked = Sets.newIdentityHashSet();
ServerEntity tracker = new ServerEntity((ServerLevel) handle.level, handle, handle.getType().updateInterval(),
handle.getType().trackDeltas(), packet -> {
for (ServerPlayerConnection link : linked) {
link.send(packet);
}
}, linked);
return new EntityPacketTracker() {
@Override
public void link(Player player) {
ServerPlayer p = (ServerPlayer) getHandle(player);
handle.unsetRemoved();
tracker.addPairing(p);
linked.add(p.connection);
}
@Override
public void remove() {
for (ServerPlayerConnection link : linked) {
unlink(link.getPlayer().getBukkitEntity());
}
}
@Override
public void run() {
tracker.sendChanges();
}
@Override
public void unlink(Player player) {
ServerPlayer p = (ServerPlayer) getHandle(player);
tracker.removePairing(p);
linked.remove(p.connection);
}
};
}
@Override
public GameProfile fillProfileProperties(GameProfile profile, boolean requireSecure) throws Throwable {
if (Bukkit.isPrimaryThread())
@ -1363,6 +1408,11 @@ public class NMSImpl implements NMSBridge {
getHandle(entity).setYRot(yaw);
}
@Override
public void setBoundingBox(org.bukkit.entity.Entity entity, BoundingBox box) {
NMSImpl.getHandle(entity).setBoundingBox(NMSBoundingBox.convert(box));
}
@Override
public void setCamelPose(org.bukkit.entity.Entity entity, CamelPose pose) {
if (entity.getType() != EntityType.CAMEL)
@ -1404,6 +1454,11 @@ public class NMSImpl implements NMSBridge {
}
}
@Override
public void setDimensions(org.bukkit.entity.Entity entity, EntityDim desired) {
setSize(getHandle(entity), new EntityDimensions(desired.width, desired.height, true));
}
@Override
public void setEndermanAngry(org.bukkit.entity.Enderman enderman, boolean angry) {
if (ENDERMAN_CREEPY == null)
@ -2298,6 +2353,8 @@ public class NMSImpl implements NMSBridge {
public static void setSize(Entity entity, EntityDimensions size) {
try {
SIZE_FIELD_SETTER.invoke(entity, size);
HEAD_HEIGHT.invoke(entity,
HEAD_HEIGHT_METHOD.invoke(entity, entity.getPose(), entity.getDimensions(entity.getPose())));
} catch (Throwable e) {
e.printStackTrace();
}
@ -2372,9 +2429,7 @@ public class NMSImpl implements NMSBridge {
EntityType.SHULKER, EntityType.PHANTOM);
private static final MethodHandle BEHAVIOR_TREE_MAP = NMS.getGetter(Brain.class, "f");
private static final MethodHandle BUKKITENTITY_FIELD_SETTER = NMS.getSetter(Entity.class, "bukkitEntity");
private static final MethodHandle CHUNKMAP_UPDATE_PLAYER_STATUS = NMS.getMethodHandle(ChunkMap.class, "a", true,
ServerPlayer.class, boolean.class);
private static final Map<Class<?>, net.minecraft.world.entity.EntityType<?>> CITIZENS_ENTITY_TYPES = Maps

View File

@ -35,9 +35,9 @@ public class HorseController extends MobEntityController {
}
@Override
public void spawn(Location at, NPC npc) {
public void create(Location at, NPC npc) {
npc.getOrAddTrait(HorseModifiers.class);
super.spawn(at, npc);
super.create(at, npc);
}
public static class EntityHorseNPC extends EntityHorse implements NPCHolder {

Some files were not shown because too many files have changed in this diff Show More