mirror of
https://github.com/CitizensDev/Citizens2.git
synced 2025-01-26 01:51:40 +01:00
Add custom tag parsing to shop, add /npc hologram insert, add /npc text send text to chat toggle
This commit is contained in:
parent
81794f5ece
commit
d0ff1d147e
@ -467,7 +467,6 @@ public class Citizens extends JavaPlugin implements CitizensPlugin {
|
||||
|
||||
shops.loadFromDisk();
|
||||
shops.load();
|
||||
|
||||
getServer().getPluginManager().callEvent(new CitizensReloadEvent());
|
||||
}
|
||||
|
||||
|
@ -1286,7 +1286,7 @@ public class NPCCommands {
|
||||
|
||||
@Command(
|
||||
aliases = { "npc" },
|
||||
usage = "hologram add [text] | set [line #] [text] | remove [line #] | bgcolor [line #] (red,green,blue(,alpha)) | clear | lineheight [height] | viewrange [range] | margintop [line #] [margin] | marginbottom [line #] [margin]",
|
||||
usage = "hologram add [text] | insert [line #] [text] | set [line #] [text] | remove [line #] | bgcolor [line #] (red,green,blue(,alpha)) | clear | lineheight [height] | viewrange [range] | margintop [line #] [margin] | marginbottom [line #] [margin]",
|
||||
desc = "",
|
||||
modifiers = { "hologram" },
|
||||
min = 1,
|
||||
@ -1295,8 +1295,8 @@ public class NPCCommands {
|
||||
public void hologram(CommandContext args, CommandSender sender, NPC npc,
|
||||
@Arg(
|
||||
value = 1,
|
||||
completions = { "add", "set", "bgcolor", "remove", "clear", "lineheight", "viewrange", "margintop",
|
||||
"marginbottom" }) String action,
|
||||
completions = { "add", "insert", "set", "bgcolor", "remove", "clear", "lineheight", "viewrange",
|
||||
"margintop", "marginbottom" }) String action,
|
||||
@Arg(value = 2, completionsProvider = HologramTrait.TabCompletions.class) String secondCompletion)
|
||||
throws CommandException {
|
||||
HologramTrait trait = npc.getOrAddTrait(HologramTrait.class);
|
||||
@ -1314,7 +1314,8 @@ public class NPCCommands {
|
||||
if (args.argsLength() == 2)
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
int idx = Math.max(0, args.getInteger(2));
|
||||
int idx = args.getString(2).equals("bottom") ? 0
|
||||
: args.getString(2).equals("top") ? trait.getLines().size() - 1 : Math.max(0, args.getInteger(2));
|
||||
if (idx >= trait.getLines().size())
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
@ -1328,7 +1329,9 @@ public class NPCCommands {
|
||||
trait.setDefaultBackgroundColor(Util.parseColor(args.getString(2)));
|
||||
Messaging.sendTr(sender, Messages.HOLOGRAM_DEFAULT_BACKGROUND_COLOR_SET, args.getString(2));
|
||||
} else {
|
||||
int idx = Math.max(0, args.getInteger(2));
|
||||
int idx = args.getString(2).equals("bottom") ? 0
|
||||
: args.getString(2).equals("top") ? trait.getLines().size() - 1
|
||||
: Math.max(0, args.getInteger(2));
|
||||
if (idx >= trait.getLines().size())
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
trait.setBackgroundColor(idx, Util.parseColor(args.getString(3)));
|
||||
@ -1346,11 +1349,26 @@ public class NPCCommands {
|
||||
|
||||
trait.addLine(args.getJoinedStrings(2));
|
||||
Messaging.sendTr(sender, Messages.HOLOGRAM_LINE_ADD, args.getJoinedStrings(2));
|
||||
} else if (action.equalsIgnoreCase("insert")) {
|
||||
if (args.argsLength() == 2)
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
if (args.argsLength() == 3)
|
||||
throw new CommandException(Messages.HOLOGRAM_TEXT_MISSING);
|
||||
|
||||
int idx = args.getString(2).equals("bottom") ? 0
|
||||
: args.getString(2).equals("top") ? trait.getLines().size() - 1 : Math.max(0, args.getInteger(2));
|
||||
if (idx > trait.getLines().size())
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
trait.insertLine(idx, args.getJoinedStrings(3));
|
||||
Messaging.sendTr(sender, Messages.HOLOGRAM_LINE_ADD, args.getJoinedStrings(3));
|
||||
} else if (action.equalsIgnoreCase("remove")) {
|
||||
if (args.argsLength() == 2)
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
int idx = Math.max(0, args.getInteger(2));
|
||||
int idx = args.getString(2).equals("bottom") ? 0
|
||||
: args.getString(2).equals("top") ? trait.getLines().size() - 1 : Math.max(0, args.getInteger(2));
|
||||
if (idx >= trait.getLines().size())
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
@ -1369,7 +1387,8 @@ public class NPCCommands {
|
||||
if (args.argsLength() == 2)
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
int idx = Math.max(0, args.getInteger(2));
|
||||
int idx = args.getString(2).equals("bottom") ? 0
|
||||
: args.getString(2).equals("top") ? trait.getLines().size() - 1 : Math.max(0, args.getInteger(2));
|
||||
if (idx >= trait.getLines().size())
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
@ -1382,7 +1401,8 @@ public class NPCCommands {
|
||||
if (args.argsLength() == 2)
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
int idx = Math.max(0, args.getInteger(2));
|
||||
int idx = args.getString(2).equals("bottom") ? 0
|
||||
: args.getString(2).equals("top") ? trait.getLines().size() - 1 : Math.max(0, args.getInteger(2));
|
||||
if (idx >= trait.getLines().size())
|
||||
throw new CommandException(Messages.HOLOGRAM_INVALID_LINE);
|
||||
|
||||
@ -2725,7 +2745,7 @@ public class NPCCommands {
|
||||
|
||||
@Command(
|
||||
aliases = { "npc" },
|
||||
usage = "rotate (--towards [x,y,z]) (--body [yaw]) (--head [yaw]) (--pitch [pitch]) (-s(mooth))",
|
||||
usage = "rotate (--towards [x,y,z]) (--toentity [name|uuid|me]) (--body [yaw]) (--head [yaw]) (--pitch [pitch]) (-s(mooth))",
|
||||
desc = "",
|
||||
flags = "s",
|
||||
modifiers = { "rotate" },
|
||||
@ -2733,7 +2753,8 @@ public class NPCCommands {
|
||||
max = 1,
|
||||
permission = "citizens.npc.rotate")
|
||||
public void rotate(CommandContext args, CommandSender sender, NPC npc, @Flag("body") Float yaw,
|
||||
@Flag("head") Float head, @Flag("pitch") Float pitch, @Flag("towards") Location towards) {
|
||||
@Flag("head") Float head, @Flag("pitch") Float pitch, @Flag("towards") Location towards,
|
||||
@Flag("toentity") String entity) throws CommandException {
|
||||
if (args.hasFlag('s')) {
|
||||
if (pitch == null) {
|
||||
pitch = npc.getStoredLocation().getPitch();
|
||||
@ -2748,6 +2769,18 @@ public class NPCCommands {
|
||||
npc.getOrAddTrait(RotationTrait.class).getPhysicalSession().rotateToHave(yaw, pitch);
|
||||
return;
|
||||
}
|
||||
if (entity != null) {
|
||||
if (entity.equals("me")) {
|
||||
towards = args.getSenderLocation();
|
||||
} else {
|
||||
try {
|
||||
UUID uuid = UUID.fromString(entity);
|
||||
towards = Bukkit.getPlayer(uuid).getLocation();
|
||||
} catch (IllegalArgumentException ex) {
|
||||
towards = Bukkit.getPlayerExact(entity).getLocation();
|
||||
}
|
||||
}
|
||||
}
|
||||
if (towards != null) {
|
||||
npc.getOrAddTrait(RotationTrait.class).getPhysicalSession().rotateToFace(towards);
|
||||
return;
|
||||
|
@ -220,6 +220,11 @@ public class HologramTrait extends Trait {
|
||||
return viewRange;
|
||||
}
|
||||
|
||||
public void insertLine(int idx, String text) {
|
||||
lines.add(idx, new HologramLine(text, true, -1, createDefaultHologramRenderer()));
|
||||
reloadLineHolograms();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load(DataKey root) {
|
||||
clear();
|
||||
|
@ -49,6 +49,8 @@ public class Text extends Trait implements Runnable, Listener {
|
||||
private double range = Setting.DEFAULT_TALK_CLOSE_RANGE.asDouble();
|
||||
@Persist(value = "realistic-looking")
|
||||
private boolean realisticLooker = Setting.DEFAULT_REALISTIC_LOOKING.asBoolean();
|
||||
@Persist(value = "send-text-to-chat")
|
||||
private boolean sendTextToChat = true;
|
||||
@Persist(value = "speech-bubble-duration")
|
||||
private int speechBubbleDuration = Setting.DEFAULT_TEXT_SPEECH_BUBBLE_DURATION.asTicks();
|
||||
@Persist(value = "speech-bubbles")
|
||||
@ -56,7 +58,7 @@ public class Text extends Trait implements Runnable, Listener {
|
||||
@Persist(value = "talk-close")
|
||||
private boolean talkClose = Setting.DEFAULT_TALK_CLOSE.asBoolean();
|
||||
@Persist
|
||||
private volatile List<String> text = new ArrayList<>();
|
||||
private final List<String> text = new ArrayList<>();
|
||||
|
||||
public Text() {
|
||||
super("text");
|
||||
@ -211,10 +213,16 @@ public class Text extends Trait implements Runnable, Listener {
|
||||
HologramTrait trait = npc.getOrAddTrait(HologramTrait.class);
|
||||
trait.addTemporaryLine(Placeholders.replace(text.get(index), player, npc), speechBubbleDuration);
|
||||
}
|
||||
npc.getDefaultSpeechController().speak(new SpeechContext(text.get(index), player));
|
||||
if (sendTextToChat) {
|
||||
npc.getDefaultSpeechController().speak(new SpeechContext(text.get(index), player));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean sendTextToChat() {
|
||||
return sendTextToChat;
|
||||
}
|
||||
|
||||
/**
|
||||
* Set the text delay between messages.
|
||||
*
|
||||
@ -288,6 +296,13 @@ public class Text extends Trait implements Runnable, Listener {
|
||||
return realisticLooker = !realisticLooker;
|
||||
}
|
||||
|
||||
/**
|
||||
* Toggles sending text through chat
|
||||
*/
|
||||
public boolean toggleSendTextToChat() {
|
||||
return sendTextToChat = !sendTextToChat;
|
||||
}
|
||||
|
||||
/**
|
||||
* Toggles using speech bubbles instead of messages.
|
||||
*/
|
||||
|
@ -74,6 +74,8 @@ public class TextBasePrompt extends StringPrompt {
|
||||
}
|
||||
} else if (input.equalsIgnoreCase("random")) {
|
||||
text.toggleRandomTalker();
|
||||
} else if (original.trim().equalsIgnoreCase("send text to chat")) {
|
||||
text.toggleSendTextToChat();
|
||||
} else if (original.trim().equalsIgnoreCase("realistic looking")) {
|
||||
text.toggleRealisticLooking();
|
||||
} else if (original.trim().equalsIgnoreCase("speech bubbles")) {
|
||||
@ -121,7 +123,7 @@ public class TextBasePrompt extends StringPrompt {
|
||||
Messaging.send((Player) context.getForWhom(),
|
||||
Messaging.tr(Messages.TEXT_EDITOR_START_PROMPT, colorToggleableText(text.shouldTalkClose()),
|
||||
colorToggleableText(text.isRandomTalker()), colorToggleableText(text.useSpeechBubbles()),
|
||||
colorToggleableText(text.useRealisticLooking())));
|
||||
colorToggleableText(text.useRealisticLooking()), colorToggleableText(text.sendTextToChat())));
|
||||
int page = context.getSessionData("page") == null ? 1 : (int) context.getSessionData("page");
|
||||
text.sendPage((Player) context.getForWhom(), page);
|
||||
return "";
|
||||
|
@ -709,7 +709,7 @@
|
||||
"citizens.editors.text.range-set" : "[[Range]] set to [[{0}]].",
|
||||
"citizens.editors.text.realistic-looking-set" : "[[Realistic looking]] set to [[{0}]].",
|
||||
"citizens.editors.text.speech-bubbles-set" : "[[Speech bubbles]] set to [[{0}]].",
|
||||
"citizens.editors.text.start-prompt" : "<click:suggest_command:add ><yellow><u>Add text</u></click> | <click:suggest_command:item ><hover:show_text:\"Set the talk item in hand pattern (set to <yellow>default</yellow> to clear)\"><yellow><u>item</hover></click> | <click:suggest_command:range ><hover:show_text:Set the talking range in blocks><yellow><u>range</hover></click> | <click:suggest_command:delay ><hover:show_text:Set the talking delay in ticks><yellow><u>delay</u></yellow></hover></click><br><click:run_command:/npc text close><hover:show_text:Toggle sending messages when players get close>{0}<u>talk close</hover></click> | <click:run_command:/npc text random><hover:show_text:Toggle random talking>{1}<u>random</hover></click> | <click:suggest_command:/npc text speech bubbles duration ><hover:show_text:Set speech bubble duration>{2}<u>speech bubble duration</hover></click> | <click:run_command:/npc text speech bubbles><hover:show_text:Toggle showing text as holograms instead of chat messages>{2}<u>speech bubbles</hover></click> | <click:run_command:/npc text realistic looking><hover:show_text:Toggle requiring line of sight before speaking>{3}<u>realistic</hover></click>",
|
||||
"citizens.editors.text.start-prompt" : "<click:suggest_command:add ><yellow><u>Add text</u></click> | <click:suggest_command:item ><hover:show_text:\"Set the talk item in hand pattern (set to <yellow>default</yellow> to clear)\"><yellow><u>item</hover></click> | <click:suggest_command:range ><hover:show_text:Set the talking range in blocks><yellow><u>range</hover></click> | <click:suggest_command:delay ><hover:show_text:Set the talking delay in ticks><yellow><u>delay</u></yellow></hover></click><br><click:run_command:/npc text close><hover:show_text:Toggle sending messages when players get close>{0}<u>talk close</hover></click> | <click:run_command:/npc text random><hover:show_text:Toggle random talking>{1}<u>random</hover></click> | <click:suggest_command:/npc text speech bubbles duration ><hover:show_text:Set speech bubble duration>{2}<u>speech bubble duration</hover></click> | <click:run_command:/npc text speech bubbles><hover:show_text:Toggle showing text as holograms instead of chat messages>{2}<u>speech bubbles</hover></click> | <click:run_command:/npc text realistic looking><hover:show_text:Toggle requiring line of sight before speaking>{3}<u>realistic</hover></click> | <click:run_command:/npc text send text to chat><hover:show_text:Toggle sending text to chat>{4}<u>send to chat</hover></click>",
|
||||
"citizens.editors.text.talk-item-set" : "[[Talk item pattern]] set to [[{0}]].",
|
||||
"citizens.editors.text.text-list-header" : "Current text:",
|
||||
"citizens.editors.waypoints.guided.added-available" : "Added a [[destination]] waypoint which the NPC will randomly pathfind between.",
|
||||
|
@ -84,6 +84,7 @@ 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.api.util.SpigotUtil;
|
||||
import net.citizensnpcs.api.util.SpigotUtil.InventoryViewAPI;
|
||||
import net.citizensnpcs.nms.v1_20_R4.entity.AllayController;
|
||||
import net.citizensnpcs.nms.v1_20_R4.entity.ArmadilloController;
|
||||
@ -260,6 +261,14 @@ import net.citizensnpcs.util.Util;
|
||||
import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.core.Holder;
|
||||
import net.minecraft.core.registries.BuiltInRegistries;
|
||||
import net.minecraft.nbt.ByteArrayTag;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.nbt.IntArrayTag;
|
||||
import net.minecraft.nbt.ListTag;
|
||||
import net.minecraft.nbt.LongArrayTag;
|
||||
import net.minecraft.nbt.NumericTag;
|
||||
import net.minecraft.nbt.StringTag;
|
||||
import net.minecraft.nbt.Tag;
|
||||
import net.minecraft.network.Connection;
|
||||
import net.minecraft.network.chat.Component;
|
||||
import net.minecraft.network.chat.MutableComponent;
|
||||
@ -621,6 +630,35 @@ public class NMSImpl implements NMSBridge {
|
||||
return shape.isEmpty() ? BoundingBox.EMPTY : NMSBoundingBox.wrap(shape.bounds());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, Object> getComponentMap(org.bukkit.inventory.ItemStack item) {
|
||||
if (META_COMPOUND_TAG == null) {
|
||||
try {
|
||||
META_COMPOUND_TAG = NMS.getGetter(Class.forName(
|
||||
"org.bukkit.craftbukkit." + SpigotUtil.getMinecraftPackage() + ".inventory.CraftMetaItem"),
|
||||
"customTag");
|
||||
} catch (ClassNotFoundException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
Map<String, Object> base = Maps.newHashMap(NMSBridge.super.getComponentMap(item));
|
||||
CompoundTag ct;
|
||||
try {
|
||||
ct = (CompoundTag) META_COMPOUND_TAG.invoke(item.getItemMeta());
|
||||
} catch (Throwable e) {
|
||||
e.printStackTrace();
|
||||
return base;
|
||||
}
|
||||
if (ct == null)
|
||||
return base;
|
||||
Map<String, Object> custom = Maps.newHashMap();
|
||||
for (String key : ct.getAllKeys()) {
|
||||
custom.put(key, deserialiseNBT(ct.get(key)));
|
||||
}
|
||||
base.put("custom", custom);
|
||||
return base;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Location getDestination(org.bukkit.entity.Entity entity) {
|
||||
Entity handle = getHandle(entity);
|
||||
@ -2085,6 +2123,42 @@ public class NMSImpl implements NMSBridge {
|
||||
}
|
||||
}
|
||||
|
||||
private static Object deserialiseNBT(Tag tag) {
|
||||
switch (tag.getId()) {
|
||||
case Tag.TAG_COMPOUND:
|
||||
CompoundTag ct = (CompoundTag) tag;
|
||||
Map<String, Object> map = Maps.newHashMapWithExpectedSize(ct.size());
|
||||
for (String key : ct.getAllKeys()) {
|
||||
map.put(key, deserialiseNBT(ct.get(key)));
|
||||
}
|
||||
return map;
|
||||
case Tag.TAG_LIST:
|
||||
ListTag list = (ListTag) tag;
|
||||
List<Object> res = Lists.newArrayList(list.size());
|
||||
for (int i = 0; i < list.size(); i++) {
|
||||
res.add(deserialiseNBT(list.get(i)));
|
||||
}
|
||||
return res;
|
||||
case Tag.TAG_BYTE_ARRAY:
|
||||
return ((ByteArrayTag) tag).getAsByteArray();
|
||||
case Tag.TAG_INT_ARRAY:
|
||||
return ((IntArrayTag) tag).getAsIntArray();
|
||||
case Tag.TAG_LONG_ARRAY:
|
||||
return ((LongArrayTag) tag).getAsLongArray();
|
||||
case Tag.TAG_STRING:
|
||||
return ((StringTag) tag).getAsString();
|
||||
case Tag.TAG_ANY_NUMERIC:
|
||||
case Tag.TAG_LONG:
|
||||
case Tag.TAG_FLOAT:
|
||||
case Tag.TAG_DOUBLE:
|
||||
case Tag.TAG_INT:
|
||||
case Tag.TAG_BYTE:
|
||||
case Tag.TAG_SHORT:
|
||||
return ((NumericTag) tag).getAsNumber();
|
||||
}
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
|
||||
public static void flyingMoveLogic(LivingEntity entity, Vec3 vec3d) {
|
||||
if (entity.isEffectiveAi() || entity.isControlledByLocalInstance()) {
|
||||
double d0 = 0.08D;
|
||||
@ -2564,6 +2638,7 @@ public class NMSImpl implements NMSBridge {
|
||||
|
||||
private static final MethodHandle ATTRIBUTE_PROVIDER_MAP_SETTER = NMS.getFirstFinalSetter(AttributeSupplier.class,
|
||||
Map.class);
|
||||
|
||||
private static final MethodHandle ATTRIBUTE_SUPPLIER = NMS.getFirstGetter(AttributeMap.class,
|
||||
AttributeSupplier.class);
|
||||
private static final MethodHandle AVAILABLE_BEHAVIORS_BY_PRIORITY = NMS.getGetter(Brain.class, "f");
|
||||
@ -2610,6 +2685,7 @@ public class NMSImpl implements NMSBridge {
|
||||
private static EntityDataAccessor<Float> INTERACTION_WIDTH = null;
|
||||
private static final MethodHandle JUMP_FIELD = NMS.getGetter(LivingEntity.class, "bn");
|
||||
private static final MethodHandle LOOK_CONTROL_SETTER = NMS.getFirstSetter(Mob.class, LookControl.class);
|
||||
private static MethodHandle META_COMPOUND_TAG;
|
||||
private static final MethodHandle MINECRAFT_CLIENT = NMS.getFirstGetter(YggdrasilMinecraftSessionService.class,
|
||||
MinecraftClient.class);
|
||||
private static final MethodHandle MOVE_CONTROLLER_OPERATION = NMS.getSetter(MoveControl.class, "k");
|
||||
|
@ -84,6 +84,7 @@ 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.api.util.SpigotUtil;
|
||||
import net.citizensnpcs.api.util.SpigotUtil.InventoryViewAPI;
|
||||
import net.citizensnpcs.nms.v1_21_R1.entity.AllayController;
|
||||
import net.citizensnpcs.nms.v1_21_R1.entity.ArmadilloController;
|
||||
@ -260,6 +261,14 @@ import net.citizensnpcs.util.Util;
|
||||
import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.core.Holder;
|
||||
import net.minecraft.core.registries.BuiltInRegistries;
|
||||
import net.minecraft.nbt.ByteArrayTag;
|
||||
import net.minecraft.nbt.CompoundTag;
|
||||
import net.minecraft.nbt.IntArrayTag;
|
||||
import net.minecraft.nbt.ListTag;
|
||||
import net.minecraft.nbt.LongArrayTag;
|
||||
import net.minecraft.nbt.NumericTag;
|
||||
import net.minecraft.nbt.StringTag;
|
||||
import net.minecraft.nbt.Tag;
|
||||
import net.minecraft.network.Connection;
|
||||
import net.minecraft.network.chat.Component;
|
||||
import net.minecraft.network.chat.MutableComponent;
|
||||
@ -601,6 +610,35 @@ public class NMSImpl implements NMSBridge {
|
||||
return shape.isEmpty() ? BoundingBox.EMPTY : NMSBoundingBox.wrap(shape.bounds());
|
||||
}
|
||||
|
||||
@Override
|
||||
public Map<String, Object> getComponentMap(org.bukkit.inventory.ItemStack item) {
|
||||
if (META_COMPOUND_TAG == null) {
|
||||
try {
|
||||
META_COMPOUND_TAG = NMS.getGetter(Class.forName(
|
||||
"org.bukkit.craftbukkit." + SpigotUtil.getMinecraftPackage() + ".inventory.CraftMetaItem"),
|
||||
"customTag");
|
||||
} catch (ClassNotFoundException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
Map<String, Object> base = Maps.newHashMap(NMSBridge.super.getComponentMap(item));
|
||||
CompoundTag ct;
|
||||
try {
|
||||
ct = (CompoundTag) META_COMPOUND_TAG.invoke(item.getItemMeta());
|
||||
} catch (Throwable e) {
|
||||
e.printStackTrace();
|
||||
return base;
|
||||
}
|
||||
if (ct == null)
|
||||
return base;
|
||||
Map<String, Object> custom = Maps.newHashMap();
|
||||
for (String key : ct.getAllKeys()) {
|
||||
custom.put(key, deserialiseNBT(ct.get(key)));
|
||||
}
|
||||
base.put("custom", custom);
|
||||
return base;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Location getDestination(org.bukkit.entity.Entity entity) {
|
||||
Entity handle = getHandle(entity);
|
||||
@ -2079,6 +2117,42 @@ public class NMSImpl implements NMSBridge {
|
||||
}
|
||||
}
|
||||
|
||||
private static Object deserialiseNBT(Tag tag) {
|
||||
switch (tag.getId()) {
|
||||
case Tag.TAG_COMPOUND:
|
||||
CompoundTag ct = (CompoundTag) tag;
|
||||
Map<String, Object> map = Maps.newHashMapWithExpectedSize(ct.size());
|
||||
for (String key : ct.getAllKeys()) {
|
||||
map.put(key, deserialiseNBT(ct.get(key)));
|
||||
}
|
||||
return map;
|
||||
case Tag.TAG_LIST:
|
||||
ListTag list = (ListTag) tag;
|
||||
List<Object> res = Lists.newArrayList(list.size());
|
||||
for (int i = 0; i < list.size(); i++) {
|
||||
res.add(deserialiseNBT(list.get(i)));
|
||||
}
|
||||
return res;
|
||||
case Tag.TAG_BYTE_ARRAY:
|
||||
return ((ByteArrayTag) tag).getAsByteArray();
|
||||
case Tag.TAG_INT_ARRAY:
|
||||
return ((IntArrayTag) tag).getAsIntArray();
|
||||
case Tag.TAG_LONG_ARRAY:
|
||||
return ((LongArrayTag) tag).getAsLongArray();
|
||||
case Tag.TAG_STRING:
|
||||
return ((StringTag) tag).getAsString();
|
||||
case Tag.TAG_ANY_NUMERIC:
|
||||
case Tag.TAG_LONG:
|
||||
case Tag.TAG_FLOAT:
|
||||
case Tag.TAG_DOUBLE:
|
||||
case Tag.TAG_INT:
|
||||
case Tag.TAG_BYTE:
|
||||
case Tag.TAG_SHORT:
|
||||
return ((NumericTag) tag).getAsNumber();
|
||||
}
|
||||
throw new IllegalArgumentException();
|
||||
}
|
||||
|
||||
public static void flyingMoveLogic(LivingEntity entity, Vec3 vec3d) {
|
||||
if (entity.isEffectiveAi() || entity.isControlledByLocalInstance()) {
|
||||
double d0 = 0.08D;
|
||||
@ -2541,9 +2615,12 @@ public class NMSImpl implements NMSBridge {
|
||||
}
|
||||
|
||||
private static final MethodHandle ARMADILLO_SCUTE_TIME = NMS.getSetter(Armadillo.class, "cn");
|
||||
|
||||
private static final MethodHandle ATTRIBUTE_PROVIDER_MAP = NMS.getFirstGetter(AttributeSupplier.class, Map.class);
|
||||
|
||||
private static final MethodHandle ATTRIBUTE_PROVIDER_MAP_SETTER = NMS.getFirstFinalSetter(AttributeSupplier.class,
|
||||
Map.class);
|
||||
|
||||
private static final MethodHandle ATTRIBUTE_SUPPLIER = NMS.getFirstGetter(AttributeMap.class,
|
||||
AttributeSupplier.class);
|
||||
private static final MethodHandle AVAILABLE_BEHAVIORS_BY_PRIORITY = NMS.getGetter(Brain.class, "f");
|
||||
@ -2589,6 +2666,7 @@ public class NMSImpl implements NMSBridge {
|
||||
private static EntityDataAccessor<Float> INTERACTION_WIDTH = null;
|
||||
private static final MethodHandle JUMP_FIELD = NMS.getGetter(LivingEntity.class, "bn");
|
||||
private static final MethodHandle LOOK_CONTROL_SETTER = NMS.getFirstSetter(Mob.class, LookControl.class);
|
||||
private static MethodHandle META_COMPOUND_TAG;
|
||||
private static final MethodHandle MINECRAFT_CLIENT = NMS.getFirstGetter(YggdrasilMinecraftSessionService.class,
|
||||
MinecraftClient.class);
|
||||
private static final MethodHandle MOVE_CONTROLLER_OPERATION = NMS.getSetter(MoveControl.class, "k");
|
||||
|
Loading…
Reference in New Issue
Block a user