Mirror von
https://github.com/St3venAU/ArmorStandTools.git
synchronisiert 2024-12-28 04:20:08 +01:00
Update to v2.0
Dieser Commit ist enthalten in:
Ursprung
71d3b27315
Commit
0c3417e08e
255
src/com/gmail/St3venAU/plugins/ArmorStandTools/ArmorStandGUI.java
Normale Datei
255
src/com/gmail/St3venAU/plugins/ArmorStandTools/ArmorStandGUI.java
Normale Datei
@ -0,0 +1,255 @@
|
||||
package com.gmail.St3venAU.plugins.ArmorStandTools;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.entity.ArmorStand;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.EventHandler;
|
||||
import org.bukkit.event.HandlerList;
|
||||
import org.bukkit.event.Listener;
|
||||
import org.bukkit.event.inventory.ClickType;
|
||||
import org.bukkit.event.inventory.InventoryClickEvent;
|
||||
import org.bukkit.event.inventory.InventoryCloseEvent;
|
||||
import org.bukkit.event.inventory.InventoryDragEvent;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.inventory.meta.ItemMeta;
|
||||
import org.bukkit.inventory.meta.SkullMeta;
|
||||
import org.bukkit.scheduler.BukkitRunnable;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.UUID;
|
||||
|
||||
class ArmorStandGUI implements Listener {
|
||||
|
||||
private static final HashSet<Integer> inUse = new HashSet<Integer>();
|
||||
private static final HashSet<Integer> invSlots = new HashSet<Integer>();
|
||||
private static ItemStack filler;
|
||||
|
||||
private Inventory i;
|
||||
private ArmorStand as;
|
||||
private Main plugin;
|
||||
|
||||
ArmorStandGUI(Main plugin, ArmorStand as, Player p) {
|
||||
if(inUse.contains(as.getEntityId())) {
|
||||
p.sendMessage(ChatColor.RED + "This armor stand's GUI is in use");
|
||||
return;
|
||||
}
|
||||
if(filler == null) {
|
||||
filler = new ItemStack(Material.STAINED_GLASS_PANE, 1, (short) 15);
|
||||
ItemMeta im = filler.getItemMeta();
|
||||
im.setDisplayName(" ");
|
||||
filler.setItemMeta(im);
|
||||
invSlots.add(0);
|
||||
invSlots.add(9);
|
||||
invSlots.add(10);
|
||||
invSlots.add(18);
|
||||
invSlots.add(27);
|
||||
}
|
||||
this.plugin = plugin;
|
||||
plugin.getServer().getPluginManager().registerEvents(this, plugin);
|
||||
this.as = as;
|
||||
String name = as.getCustomName();
|
||||
if(name == null) {
|
||||
name = "Armor Stand";
|
||||
}
|
||||
i = Bukkit.createInventory(null, 36, name);
|
||||
for(int slot = 0; slot < i.getSize(); slot++) {
|
||||
i.setItem(slot, filler);
|
||||
}
|
||||
for(ArmorStandTool tool : ArmorStandTool.values()) {
|
||||
if(tool.isForGui() && tool.isEnabled()) {
|
||||
i.setItem(tool.getSlot(), updateLore(tool));
|
||||
}
|
||||
}
|
||||
i.setItem(0, as.getHelmet());
|
||||
i.setItem(9, as.getChestplate());
|
||||
i.setItem(10, as.getItemInHand());
|
||||
i.setItem(18, as.getLeggings());
|
||||
i.setItem(27, as.getBoots());
|
||||
inUse.add(as.getEntityId());
|
||||
p.openInventory(i);
|
||||
}
|
||||
|
||||
ItemStack updateLore(ArmorStandTool tool) {
|
||||
ItemStack item = tool.getItem();
|
||||
switch (tool) {
|
||||
case INVIS:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.asVisible + ": " + (as.isVisible() ? (ChatColor.GREEN + Config.isTrue) : (ChatColor.RED + Config.isFalse)));
|
||||
case SIZE:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.size + ": " + (as.isSmall() ? (ChatColor.BLUE + Config.small) : (ChatColor.GREEN + Config.normal)));
|
||||
case BASE:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.basePlate + ": " + (as.hasBasePlate() ? (ChatColor.GREEN + Config.isOn) : (ChatColor.RED + Config.isOff)));
|
||||
case GRAV:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.gravity + ": " + (as.hasGravity() ? (ChatColor.GREEN + Config.isOn) : (ChatColor.RED + Config.isOff)));
|
||||
case ARMS:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.arms + ": " + (as.hasArms() ? (ChatColor.GREEN + Config.isOn) : (ChatColor.RED + Config.isOff)));
|
||||
case INVUL:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.invul + ": " + (NBT.isInvulnerable(as) ? (ChatColor.GREEN + Config.isOn) : (ChatColor.RED + Config.isOff)));
|
||||
case SLOTS:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.equip + ": " + (NBT.getDisabledSlots(as) == 2039583 ? (ChatColor.GREEN + Config.locked) : (ChatColor.RED + Config.unLocked)));
|
||||
case NODEL:
|
||||
return Utils.setLore(item, ChatColor.AQUA + "Deletion Protection: " + (as.getMaxHealth() == 50 ? (ChatColor.GREEN + "Enabled") : (ChatColor.RED + "Disabled")));
|
||||
case NAME:
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.currently + ": " + (as.getCustomName() == null ? (ChatColor.BLUE + "None") : (ChatColor.GREEN + as.getCustomName())));
|
||||
case PHEAD:
|
||||
String name = plrHeadName(as);
|
||||
return Utils.setLore(item, ChatColor.AQUA + Config.currently + ": " + (name == null ? (ChatColor.BLUE + "None") : (ChatColor.GREEN + name)));
|
||||
default:
|
||||
return item;
|
||||
}
|
||||
}
|
||||
|
||||
String plrHeadName(ArmorStand as) {
|
||||
if(as.getHelmet() == null) return null;
|
||||
if(!(as.getHelmet().getItemMeta() instanceof SkullMeta)) return null;
|
||||
SkullMeta meta = (SkullMeta) as.getHelmet().getItemMeta();
|
||||
if(!meta.hasOwner()) return null;
|
||||
return meta.getOwner();
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void inInventoryClose(InventoryCloseEvent event) {
|
||||
if(!event.getInventory().equals(i)) return;
|
||||
HandlerList.unregisterAll(this);
|
||||
inUse.remove(as.getEntityId());
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onInventoryClick(InventoryClickEvent event) {
|
||||
if(!event.getInventory().equals(i)) return;
|
||||
Player p = (Player) event.getWhoClicked();
|
||||
if(event.getClick() == ClickType.SHIFT_LEFT || event.getClick() == ClickType.SHIFT_RIGHT || event.getClick() == ClickType.NUMBER_KEY) {
|
||||
event.setCancelled(true);
|
||||
return;
|
||||
}
|
||||
int slot = event.getRawSlot();
|
||||
if(slot > i.getSize()) return;
|
||||
if(invSlots.contains(slot)) {
|
||||
if(plugin.checkPermission(p, as.getLocation().getBlock())) {
|
||||
updateInventory();
|
||||
} else {
|
||||
event.setCancelled(true);
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
}
|
||||
return;
|
||||
}
|
||||
event.setCancelled(true);
|
||||
if(!(event.getWhoClicked() instanceof Player)) return;
|
||||
ArmorStandTool t = ArmorStandTool.get(event.getCurrentItem());
|
||||
if(t == null) return;
|
||||
if (!plugin.playerHasPermission(p, as.getLocation().getBlock(), t)) {
|
||||
p.sendMessage(ChatColor.RED + Config.generalNoPerm);
|
||||
return;
|
||||
}
|
||||
switch (t) {
|
||||
case INVIS:
|
||||
as.setVisible(!as.isVisible());
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.asVisible + ": " + (as.isVisible() ? Config.isTrue : Config.isFalse));
|
||||
break;
|
||||
case CLONE:
|
||||
p.closeInventory();
|
||||
plugin.pickUpArmorStand(plugin.clone(as), p, true);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.carrying);
|
||||
break;
|
||||
case SAVE:
|
||||
plugin.generateCmdBlock(p.getLocation(), as);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.cbCreated);
|
||||
break;
|
||||
case SIZE:
|
||||
as.setSmall(!as.isSmall());
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.size + ": " + (as.isSmall() ? Config.small : Config.normal));
|
||||
break;
|
||||
case BASE:
|
||||
as.setBasePlate(!as.hasBasePlate());
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.basePlate + ": " + (as.hasBasePlate() ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case GRAV:
|
||||
as.setGravity(!as.hasGravity());
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.gravity + ": " + (as.hasGravity() ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case ARMS:
|
||||
as.setArms(!as.hasArms());
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.arms + ": " + (as.hasArms() ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case NAME:
|
||||
p.closeInventory();
|
||||
plugin.setName(p, as);
|
||||
break;
|
||||
case PHEAD:
|
||||
p.closeInventory();
|
||||
plugin.setPlayerSkull(p, as);
|
||||
break;
|
||||
case INVUL:
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.invul + ": " + (NBT.toggleInvulnerability(as) ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case SLOTS:
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.equip + ": " + (NBT.toggleSlotsDisabled(as) ? Config.locked : Config.unLocked));
|
||||
break;
|
||||
case MOVE:
|
||||
p.closeInventory();
|
||||
UUID uuid = p.getUniqueId();
|
||||
if(plugin.carryingArmorStand.containsKey(uuid)) {
|
||||
plugin.carryingArmorStand.remove(uuid);
|
||||
Utils.actionBarMsg(p, Config.asDropped);
|
||||
} else {
|
||||
plugin.pickUpArmorStand(as, p, false);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.carrying);
|
||||
}
|
||||
break;
|
||||
case NODEL: // Developer tool - do not use
|
||||
if(as.getMaxHealth() == 50) {
|
||||
as.setMaxHealth(20);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + "Deletion Protection: Disabled");
|
||||
} else {
|
||||
as.setMaxHealth(50);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + "Deletion Protection: Enabled");
|
||||
}
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
i.setItem(t.getSlot(), updateLore(t));
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onInventoryDrag(InventoryDragEvent event) {
|
||||
if(!event.getInventory().equals(i) || !(event.getWhoClicked() instanceof Player)) return;
|
||||
Player p = (Player) event.getWhoClicked();
|
||||
boolean invModified = false;
|
||||
for(int slot : event.getRawSlots()) {
|
||||
if(slot < i.getSize()) {
|
||||
if(invSlots.contains(slot)) {
|
||||
invModified = true;
|
||||
} else {
|
||||
event.setCancelled(true);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
if(invModified) {
|
||||
if(plugin.checkPermission(p, as.getLocation().getBlock())) {
|
||||
updateInventory();
|
||||
} else {
|
||||
event.setCancelled(true);
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void updateInventory() {
|
||||
new BukkitRunnable() {
|
||||
@Override
|
||||
public void run() {
|
||||
if(as == null || i == null) return;
|
||||
as.setHelmet(i.getItem(0));
|
||||
as.setChestplate(i.getItem(9));
|
||||
as.setItemInHand(i.getItem(10));
|
||||
as.setLeggings(i.getItem(18));
|
||||
as.setBoots(i.getItem(27));
|
||||
}
|
||||
}.runTaskLater(plugin, 1L);
|
||||
}
|
||||
|
||||
}
|
@ -9,52 +9,55 @@ import org.bukkit.inventory.PlayerInventory;
|
||||
import org.bukkit.inventory.meta.ItemMeta;
|
||||
|
||||
public enum ArmorStandTool {
|
||||
HEADX ("headX", Material.JACK_O_LANTERN, (short) 0, 27, true),
|
||||
HEADY ("headY", Material.JACK_O_LANTERN, (short) 0, 28, true),
|
||||
HEADZ ("headZ", Material.JACK_O_LANTERN, (short) 0, 29, true),
|
||||
LARMX ("lArmX", Material.TORCH, (short) 0, 30, true),
|
||||
LARMY ("lArmY", Material.TORCH, (short) 0, 31, true),
|
||||
LARMZ ("lArmZ", Material.TORCH, (short) 0, 32, true),
|
||||
RARMX ("rArmX", Material.REDSTONE_TORCH_ON, (short) 0, 33, true),
|
||||
RARMY ("rArmY", Material.REDSTONE_TORCH_ON, (short) 0, 34, true),
|
||||
RARMZ ("rArmZ", Material.REDSTONE_TORCH_ON, (short) 0, 35, true),
|
||||
MOVEX ("moveX", Material.SHEARS, (short) 0, 24, true),
|
||||
MOVEY ("moveY", Material.SHEARS, (short) 0, 25, true),
|
||||
MOVEZ ("moveZ", Material.SHEARS, (short) 0, 26, true),
|
||||
ROTAT ("rotat", Material.MAGMA_CREAM, (short) 0, 6, true),
|
||||
INVIS ("invis", Material.GOLD_NUGGET, (short) 0, 5, true),
|
||||
SUMMON ("summon", Material.ARMOR_STAND, (short) 0, 0, true),
|
||||
CLONE ("clone", Material.GLOWSTONE_DUST, (short) 0, 16, true),
|
||||
SAVE ("save", Material.DIAMOND, (short) 0, 17, true),
|
||||
LLEGX ("lLegX", Material.BONE, (short) 0, 18, true),
|
||||
LLEGY ("lLegY", Material.BONE, (short) 0, 19, true),
|
||||
LLEGZ ("lLegZ", Material.BONE, (short) 0, 20, true),
|
||||
RLEGX ("rLegX", Material.BLAZE_ROD, (short) 0, 21, true),
|
||||
RLEGY ("rLegY", Material.BLAZE_ROD, (short) 0, 22, true),
|
||||
RLEGZ ("rLegZ", Material.BLAZE_ROD, (short) 0, 23, true),
|
||||
BODYX ("bodyX", Material.NETHER_BRICK_ITEM, (short) 0, 9, true),
|
||||
BODYY ("bodyY", Material.NETHER_BRICK_ITEM, (short) 0, 10, true),
|
||||
BODYZ ("bodyZ", Material.NETHER_BRICK_ITEM, (short) 0, 11, true),
|
||||
SIZE ("size", Material.EMERALD, (short) 0, 3, true),
|
||||
BASE ("base", Material.BOOK, (short) 0, 4, true),
|
||||
GRAV ("grav", Material.GHAST_TEAR, (short) 0, 1, true),
|
||||
ARMS ("arms", Material.ARROW, (short) 0, 2, true),
|
||||
NAME ("name", Material.NAME_TAG, (short) 0, 7, true),
|
||||
SLOTS ("slots", Material.IRON_HOE, (short) 0, 13, true),
|
||||
PHEAD ("pHead", Material.SKULL_ITEM, (short) 3, 8, true),
|
||||
INVUL ("invul", Material.GOLDEN_CARROT, (short) 0, 12, true),
|
||||
MOVE ("move", Material.FEATHER, (short) 0, 14, true),
|
||||
NODEL ("noDel", Material.WOOD_SPADE, (short) 0, 15, false); // Developer tool, disabled by default
|
||||
HEADX ("headX", Material.JACK_O_LANTERN, (short) 0, 12, false, true),
|
||||
HEADY ("headY", Material.JACK_O_LANTERN, (short) 0, 13, false, true),
|
||||
HEADZ ("headZ", Material.JACK_O_LANTERN, (short) 0, 14, false, true),
|
||||
LARMX ("lArmX", Material.TORCH, (short) 0, 27, false, true),
|
||||
LARMY ("lArmY", Material.TORCH, (short) 0, 28, false, true),
|
||||
LARMZ ("lArmZ", Material.TORCH, (short) 0, 29, false, true),
|
||||
RARMX ("rArmX", Material.REDSTONE_TORCH_ON, (short) 0, 30, false, true),
|
||||
RARMY ("rArmY", Material.REDSTONE_TORCH_ON, (short) 0, 31, false, true),
|
||||
RARMZ ("rArmZ", Material.REDSTONE_TORCH_ON, (short) 0, 32, false, true),
|
||||
MOVEX ("moveX", Material.SHEARS, (short) 0, 3, false, true),
|
||||
MOVEY ("moveY", Material.SHEARS, (short) 0, 4, false, true),
|
||||
MOVEZ ("moveZ", Material.SHEARS, (short) 0, 5, false, true),
|
||||
LLEGX ("lLegX", Material.BONE, (short) 0, 18, false, true),
|
||||
LLEGY ("lLegY", Material.BONE, (short) 0, 19, false, true),
|
||||
LLEGZ ("lLegZ", Material.BONE, (short) 0, 20, false, true),
|
||||
RLEGX ("rLegX", Material.BLAZE_ROD, (short) 0, 21, false, true),
|
||||
RLEGY ("rLegY", Material.BLAZE_ROD, (short) 0, 22, false, true),
|
||||
RLEGZ ("rLegZ", Material.BLAZE_ROD, (short) 0, 23, false, true),
|
||||
BODYX ("bodyX", Material.NETHER_BRICK_ITEM, (short) 0, 9, false, true),
|
||||
BODYY ("bodyY", Material.NETHER_BRICK_ITEM, (short) 0, 10, false, true),
|
||||
BODYZ ("bodyZ", Material.NETHER_BRICK_ITEM, (short) 0, 11, false, true),
|
||||
SUMMON ("summon", Material.ARMOR_STAND, (short) 0, 0, false, true),
|
||||
GUI ("gui", Material.NETHER_STAR, (short) 0, 1, false, true),
|
||||
ROTAT ("rotat", Material.MAGMA_CREAM, (short) 0, 2, false, true),
|
||||
CLONE ("gui_clone", Material.GLOWSTONE_DUST, (short) 0, 16, true, true),
|
||||
SAVE ("gui_save", Material.DIAMOND, (short) 0, 17, true, true),
|
||||
INVIS ("gui_invis", Material.GOLD_NUGGET, (short) 0, 14, true, true),
|
||||
SIZE ("gui_size", Material.EMERALD, (short) 0, 23, true, true),
|
||||
BASE ("gui_base", Material.BOOK, (short) 0, 22, true, true),
|
||||
GRAV ("gui_grav", Material.GHAST_TEAR, (short) 0, 24, true, true),
|
||||
ARMS ("gui_arms", Material.ARROW, (short) 0, 21, true, true),
|
||||
NAME ("gui_name", Material.NAME_TAG, (short) 0, 12, true, true),
|
||||
SLOTS ("gui_slots", Material.IRON_HOE, (short) 0, 26, true, true),
|
||||
PHEAD ("gui_pHead", Material.SKULL_ITEM, (short) 3, 13, true, true),
|
||||
INVUL ("gui_invul", Material.GOLDEN_CARROT, (short) 0, 25, true, true),
|
||||
MOVE ("gui_move", Material.FEATHER, (short) 0, 15, true, true),
|
||||
NODEL ("gui_noDel", Material.WOOD_SPADE, (short) 0, 35, true, false); // Developer tool, disabled by default
|
||||
|
||||
private final ItemStack item;
|
||||
private final String id;
|
||||
private final int slot;
|
||||
private final boolean enabled;
|
||||
|
||||
ArmorStandTool(String id, Material m, short data, int slot, boolean enabled) {
|
||||
private final boolean forGui;
|
||||
|
||||
ArmorStandTool(String id, Material m, short data, int slot, boolean forGui, boolean enabled) {
|
||||
item = new ItemStack(m, 1, data);
|
||||
this.id = id;
|
||||
this.slot = slot;
|
||||
this.forGui = forGui;
|
||||
this.enabled = enabled;
|
||||
}
|
||||
|
||||
@ -64,14 +67,26 @@ public enum ArmorStandTool {
|
||||
|
||||
boolean is(ItemStack is) {
|
||||
return is != null && is.getType() == item.getType() && is.hasItemMeta() &&
|
||||
is.getItemMeta().hasDisplayName() &&
|
||||
is.getItemMeta().getDisplayName().equals(item.getItemMeta().getDisplayName());
|
||||
is.getItemMeta().hasDisplayName() &&
|
||||
is.getItemMeta().getDisplayName().equals(item.getItemMeta().getDisplayName());
|
||||
}
|
||||
|
||||
boolean isForGui() {
|
||||
return forGui;
|
||||
}
|
||||
|
||||
boolean isEnabled() {
|
||||
return enabled;
|
||||
}
|
||||
|
||||
int getSlot() {
|
||||
return slot;
|
||||
}
|
||||
|
||||
static void updateTools(FileConfiguration config) {
|
||||
for(ArmorStandTool t : values()) {
|
||||
ItemMeta im = t.item.getItemMeta();
|
||||
im.setDisplayName(ChatColor.GREEN + config.getString("tool." + t.id + ".name"));
|
||||
im.setDisplayName(ChatColor.YELLOW + config.getString("tool." + t.id + ".name"));
|
||||
im.setLore(config.getStringList("tool." + t.id + ".lore"));
|
||||
t.item.setItemMeta(im);
|
||||
}
|
||||
@ -80,7 +95,7 @@ public enum ArmorStandTool {
|
||||
static void give(Player p) {
|
||||
PlayerInventory i = p.getInventory();
|
||||
for(ArmorStandTool t : values()) {
|
||||
if(t.enabled) {
|
||||
if(t.enabled && !t.forGui) {
|
||||
i.setItem(t.slot, t.item);
|
||||
}
|
||||
}
|
||||
@ -97,4 +112,4 @@ public enum ArmorStandTool {
|
||||
static boolean isTool(ItemStack is) {
|
||||
return get(is) != null;
|
||||
}
|
||||
}
|
||||
}
|
@ -25,6 +25,7 @@ class Commands implements CommandExecutor {
|
||||
Player p = (Player) sender;
|
||||
if (!Utils.hasPermissionNode(p, "astools.command")) {
|
||||
p.sendMessage(ChatColor.RED + Config.noCommandPerm);
|
||||
return true;
|
||||
}
|
||||
if(args.length == 0) {
|
||||
UUID uuid = p.getUniqueId();
|
||||
|
@ -31,12 +31,13 @@ class Config {
|
||||
|
||||
public static String
|
||||
invReturned, asDropped, asVisible, isTrue, isFalse,
|
||||
asCloned, carrying, noPerm, cbCreated, size, small,
|
||||
carrying, cbCreated, size, small,
|
||||
normal, basePlate, isOn, isOff, gravity, arms, invul,
|
||||
equip, locked, unLocked, notConsole, giveMsg1,
|
||||
giveMsg2, conReload, noRelPerm, noAirError,
|
||||
pleaseWait, appliedHead, noHead, invalidName,
|
||||
wgNoPerm, noCommandPerm;
|
||||
wgNoPerm, currently, headFailed, noCommandPerm,
|
||||
generalNoPerm;
|
||||
|
||||
public static void reload(Main main) {
|
||||
plugin = main;
|
||||
@ -53,9 +54,7 @@ class Config {
|
||||
asVisible = languageConfig.getString("asVisible");
|
||||
isTrue = languageConfig.getString("isTrue");
|
||||
isFalse = languageConfig.getString("isFalse");
|
||||
asCloned = languageConfig.getString("asCloned");
|
||||
carrying = languageConfig.getString("carrying");
|
||||
noPerm = languageConfig.getString("noPerm");
|
||||
cbCreated = languageConfig.getString("cbCreated");
|
||||
size = languageConfig.getString("size");
|
||||
small = languageConfig.getString("small");
|
||||
@ -81,6 +80,9 @@ class Config {
|
||||
invalidName = languageConfig.getString("invalidName");
|
||||
wgNoPerm = languageConfig.getString("wgNoPerm");
|
||||
noCommandPerm = languageConfig.getString("noCommandPerm");
|
||||
currently = languageConfig.getString("currently");
|
||||
headFailed = languageConfig.getString("headFailed");
|
||||
generalNoPerm = languageConfig.getString("generalNoPerm");
|
||||
}
|
||||
|
||||
private static void reloadMainConfig() {
|
||||
|
@ -1,13 +1,22 @@
|
||||
package com.gmail.St3venAU.plugins.ArmorStandTools;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.block.CommandBlock;
|
||||
import org.bukkit.command.CommandExecutor;
|
||||
import org.bukkit.entity.ArmorStand;
|
||||
import org.bukkit.entity.EntityType;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.event.block.BlockBreakEvent;
|
||||
import org.bukkit.event.block.BlockPlaceEvent;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.metadata.FixedMetadataValue;
|
||||
import org.bukkit.metadata.MetadataValue;
|
||||
import org.bukkit.plugin.java.JavaPlugin;
|
||||
import org.bukkit.util.EulerAngle;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.UUID;
|
||||
@ -16,6 +25,7 @@ public class Main extends JavaPlugin {
|
||||
|
||||
public final HashMap<UUID, ArmorStand> carryingArmorStand = new HashMap<UUID, ArmorStand>();
|
||||
public final HashMap<UUID, ItemStack[]> savedInventories = new HashMap<UUID, ItemStack[]>();
|
||||
private final EulerAngle zero = new EulerAngle(0D, 0D, 0D);
|
||||
static String NMS_VERSION;
|
||||
|
||||
@Override
|
||||
@ -56,4 +66,156 @@ public class Main extends JavaPlugin {
|
||||
}
|
||||
as.remove();
|
||||
}
|
||||
|
||||
void pickUpArmorStand(ArmorStand as, Player p, boolean newlySummoned) {
|
||||
carryingArmorStand.put(p.getUniqueId(), as);
|
||||
if(newlySummoned) return;
|
||||
as.setMetadata("startLoc", new FixedMetadataValue(this, as.getLocation()));
|
||||
}
|
||||
|
||||
@SuppressWarnings({"deprecation", "ConstantConditions"})
|
||||
void generateCmdBlock(Location l, ArmorStand as) {
|
||||
Location loc = as.getLocation();
|
||||
int dSlots = NBT.getDisabledSlots(as);
|
||||
int hand = as.getItemInHand() == null ? 0 : as.getItemInHand().getTypeId();
|
||||
int handDmg = as.getItemInHand() == null ? 0 : as.getItemInHand().getDurability();
|
||||
int boots = as.getBoots() == null ? 0 : as.getBoots().getTypeId();
|
||||
int bootsDmg = as.getBoots() == null ? 0 : as.getBoots().getDurability();
|
||||
int legs = as.getLeggings() == null ? 0 : as.getLeggings().getTypeId();
|
||||
int legsDmg = as.getLeggings() == null ? 0 : as.getLeggings().getDurability();
|
||||
int chest = as.getChestplate() == null ? 0 : as.getChestplate().getTypeId();
|
||||
int chestDmg = as.getChestplate() == null ? 0 : as.getChestplate().getDurability();
|
||||
int helm = as.getHelmet() == null ? 0 : as.getHelmet().getTypeId();
|
||||
int helmDmg = as.getHelmet() == null ? 0 : as.getHelmet().getDurability();
|
||||
EulerAngle he = as.getHeadPose();
|
||||
EulerAngle ll = as.getLeftLegPose();
|
||||
EulerAngle rl = as.getRightLegPose();
|
||||
EulerAngle la = as.getLeftArmPose();
|
||||
EulerAngle ra = as.getRightArmPose();
|
||||
EulerAngle bo = as.getBodyPose();
|
||||
String cmd =
|
||||
"summon ArmorStand " + Utils.twoDec(loc.getX()) + " " + Utils.twoDec(loc.getY()) + " " + Utils.twoDec(loc.getZ()) + " {"
|
||||
+ (as.getMaxHealth() != 20 ? "Attributes:[{Name:\"generic.maxHealth\", Base:" + as.getMaxHealth() + "}]," : "")
|
||||
+ (as.isVisible() ? "" : "Invisible:1,")
|
||||
+ (as.hasBasePlate() ? "" : "NoBasePlate:1,")
|
||||
+ (as.hasGravity() ? "" : "NoGravity:1,")
|
||||
+ (as.hasArms() ? "ShowArms:1," : "")
|
||||
+ (as.isSmall() ? "Small:1," : "")
|
||||
+ (NBT.isInvulnerable(as) ? "Invulnerable:1," : "")
|
||||
+ (dSlots == 0 ? "" : ("DisabledSlots:" + dSlots + ","))
|
||||
+ (as.isCustomNameVisible() ? "CustomNameVisible:1," : "")
|
||||
+ (as.getCustomName() == null ? "" : ("CustomName:\"" + as.getCustomName() + "\","))
|
||||
+ (loc.getYaw() == 0F ? "" : ("Rotation:[" + Utils.twoDec(loc.getYaw()) + "f],"))
|
||||
+ (hand == 0 && boots == 0 && legs == 0 && chest == 0 && helm == 0 ? "" : (
|
||||
"Equipment:["
|
||||
+ "{id:" + hand + ",Count:" + as.getItemInHand().getAmount() + ",Damage:" + handDmg + NBT.getItemStackTags(as.getItemInHand()) + "},"
|
||||
+ "{id:" + boots + ",Count:" + as.getBoots().getAmount() + ",Damage:" + bootsDmg + NBT.getItemStackTags(as.getBoots()) + "},"
|
||||
+ "{id:" + legs + ",Count:" + as.getLeggings().getAmount() + ",Damage:" + legsDmg + NBT.getItemStackTags(as.getLeggings()) + "},"
|
||||
+ "{id:" + chest + ",Count:" + as.getChestplate().getAmount() + ",Damage:" + chestDmg + NBT.getItemStackTags(as.getChestplate()) + "},"
|
||||
+ "{id:" + helm + ",Count:" + as.getHelmet().getAmount() + ",Damage:" + helmDmg + NBT.getItemStackTags(as.getHelmet()) + NBT.skullOwner(as.getHelmet()) + "}],"))
|
||||
+ "Pose:{"
|
||||
+ (bo.equals(zero) ? "" : ("Body:[" + Utils.angle(bo.getX()) + "f," + Utils.angle(bo.getY()) + "f," + Utils.angle(bo.getZ()) + "f],"))
|
||||
+ (he.equals(zero) ? "" : ("Head:[" + Utils.angle(he.getX()) + "f," + Utils.angle(he.getY()) + "f," + Utils.angle(he.getZ()) + "f],"))
|
||||
+ (ll.equals(zero) ? "" : ("LeftLeg:[" + Utils.angle(ll.getX()) + "f," + Utils.angle(ll.getY()) + "f," + Utils.angle(ll.getZ()) + "f],"))
|
||||
+ (rl.equals(zero) ? "" : ("RightLeg:[" + Utils.angle(rl.getX()) + "f," + Utils.angle(rl.getY()) + "f," + Utils.angle(rl.getZ()) + "f],"))
|
||||
+ (la.equals(zero) ? "" : ("LeftArm:[" + Utils.angle(la.getX()) + "f," + Utils.angle(la.getY()) + "f," + Utils.angle(la.getZ()) + "f],"))
|
||||
+ "RightArm:[" + Utils.angle(ra.getX()) + "f," + Utils.angle(ra.getY()) + "f," + Utils.angle(ra.getZ()) + "f]}}";
|
||||
Block b = l.getBlock();
|
||||
b.setType(Material.COMMAND);
|
||||
b.setData((byte) 0);
|
||||
CommandBlock cb = (CommandBlock) b.getState();
|
||||
cb.setCommand(cmd);
|
||||
cb.update();
|
||||
}
|
||||
|
||||
ArmorStand clone(ArmorStand as) {
|
||||
ArmorStand clone = (ArmorStand) as.getWorld().spawnEntity(as.getLocation().add(1, 0, 0), EntityType.ARMOR_STAND);
|
||||
clone.setGravity(as.hasGravity());
|
||||
clone.setHelmet(as.getHelmet());
|
||||
clone.setChestplate(as.getChestplate());
|
||||
clone.setLeggings(as.getLeggings());
|
||||
clone.setBoots(as.getBoots());
|
||||
clone.setItemInHand(as.getItemInHand());
|
||||
clone.setHeadPose(as.getHeadPose());
|
||||
clone.setBodyPose(as.getBodyPose());
|
||||
clone.setLeftArmPose(as.getLeftArmPose());
|
||||
clone.setRightArmPose(as.getRightArmPose());
|
||||
clone.setLeftLegPose(as.getLeftLegPose());
|
||||
clone.setRightLegPose(as.getRightLegPose());
|
||||
clone.setVisible(as.isVisible());
|
||||
clone.setBasePlate(as.hasBasePlate());
|
||||
clone.setArms(as.hasArms());
|
||||
clone.setCustomName(as.getCustomName());
|
||||
clone.setCustomNameVisible(as.isCustomNameVisible());
|
||||
clone.setSmall(as.isSmall());
|
||||
clone.setMaxHealth(as.getMaxHealth());
|
||||
NBT.setSlotsDisabled(clone, NBT.getDisabledSlots(as) == 2039583);
|
||||
NBT.setInvulnerable(clone, NBT.isInvulnerable(as));
|
||||
return clone;
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
void setName(Player p, ArmorStand as) {
|
||||
Block b = Utils.findAnAirBlock(p.getLocation());
|
||||
if(b == null) {
|
||||
p.sendMessage(ChatColor.RED + Config.noAirError);
|
||||
return;
|
||||
}
|
||||
b.setData((byte) 0);
|
||||
b.setType(Material.SIGN_POST);
|
||||
Utils.openSign(p, b);
|
||||
b.setMetadata("armorStand", new FixedMetadataValue(this, as.getUniqueId()));
|
||||
b.setMetadata("setName", new FixedMetadataValue(this, true));
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
void setPlayerSkull(Player p, ArmorStand as) {
|
||||
Block b = Utils.findAnAirBlock(p.getLocation());
|
||||
if(b == null) {
|
||||
p.sendMessage(ChatColor.RED + Config.noAirError);
|
||||
return;
|
||||
}
|
||||
b.setData((byte) 0);
|
||||
b.setType(Material.SIGN_POST);
|
||||
Utils.openSign(p, b);
|
||||
b.setMetadata("armorStand", new FixedMetadataValue(this, as.getUniqueId()));
|
||||
b.setMetadata("setSkull", new FixedMetadataValue(this, true));
|
||||
}
|
||||
|
||||
boolean checkPermission(Player player, Block block) {
|
||||
|
||||
if(block == null) return true;
|
||||
|
||||
// Check PlotSquared
|
||||
Location loc = block.getLocation();
|
||||
if (PlotSquaredHook.api != null) {
|
||||
if (PlotSquaredHook.isPlotWorld(loc)) {
|
||||
return PlotSquaredHook.checkPermission(player, loc);
|
||||
}
|
||||
}
|
||||
|
||||
// check WorldGuard
|
||||
if(Config.worldGuardPlugin != null) {
|
||||
return Config.worldGuardPlugin.canBuild(player, block);
|
||||
}
|
||||
|
||||
// Use standard permission checking (will support basically any plugin)
|
||||
BlockBreakEvent myBreak = new BlockBreakEvent(block, player);
|
||||
Bukkit.getServer().getPluginManager().callEvent(myBreak);
|
||||
boolean hasPerm = !myBreak.isCancelled();
|
||||
BlockPlaceEvent place = new BlockPlaceEvent(block, block.getState(), block, null, player, true);
|
||||
Bukkit.getServer().getPluginManager().callEvent(place);
|
||||
if (place.isCancelled()) {
|
||||
hasPerm = false;
|
||||
}
|
||||
return hasPerm;
|
||||
}
|
||||
|
||||
boolean playerHasPermission(Player p, Block b, ArmorStandTool tool) {
|
||||
return !(tool != null && !p.isOp()
|
||||
&& (!Utils.hasPermissionNode(p, "astools.use")
|
||||
|| (ArmorStandTool.SAVE == tool && !Utils.hasPermissionNode(p, "astools.cmdblock"))
|
||||
|| (ArmorStandTool.CLONE == tool && !Utils.hasPermissionNode(p, "astools.clone"))))
|
||||
&& checkPermission(p, b);
|
||||
}
|
||||
}
|
@ -1,14 +1,13 @@
|
||||
package com.gmail.St3venAU.plugins.ArmorStandTools;
|
||||
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.ChatColor;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.SkullType;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.block.CommandBlock;
|
||||
import org.bukkit.block.Skull;
|
||||
import org.bukkit.entity.ArmorStand;
|
||||
import org.bukkit.entity.Entity;
|
||||
import org.bukkit.entity.EntityType;
|
||||
import org.bukkit.entity.ItemFrame;
|
||||
import org.bukkit.entity.Player;
|
||||
@ -30,10 +29,10 @@ import org.bukkit.event.player.PlayerInteractEvent;
|
||||
import org.bukkit.event.player.PlayerMoveEvent;
|
||||
import org.bukkit.event.player.PlayerQuitEvent;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.inventory.meta.SkullMeta;
|
||||
import org.bukkit.metadata.FixedMetadataValue;
|
||||
import org.bukkit.metadata.MetadataValue;
|
||||
import org.bukkit.scheduler.BukkitRunnable;
|
||||
import org.bukkit.util.EulerAngle;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
@ -43,7 +42,6 @@ import java.util.regex.Pattern;
|
||||
public class MainListener implements Listener {
|
||||
|
||||
private final Pattern MC_USERNAME_PATTERN = Pattern.compile("^[a-zA-Z0-9_]{3,16}$");
|
||||
private final EulerAngle zero = new EulerAngle(0D, 0D, 0D);
|
||||
private final Main plugin;
|
||||
|
||||
MainListener(Main main) {
|
||||
@ -56,7 +54,7 @@ public class MainListener implements Listener {
|
||||
if (event.getRightClicked() instanceof ArmorStand) {
|
||||
Player p = event.getPlayer();
|
||||
if(plugin.carryingArmorStand.containsKey(p.getUniqueId())) {
|
||||
if (playerHasPermission(p, plugin.carryingArmorStand.get(p.getUniqueId()).getLocation().getBlock(), null)) {
|
||||
if (plugin.playerHasPermission(p, plugin.carryingArmorStand.get(p.getUniqueId()).getLocation().getBlock(), null)) {
|
||||
plugin.carryingArmorStand.remove(p.getUniqueId());
|
||||
Utils.actionBarMsg(p, Config.asDropped);
|
||||
event.setCancelled(true);
|
||||
@ -68,8 +66,9 @@ public class MainListener implements Listener {
|
||||
ArmorStandTool tool = ArmorStandTool.get(p.getItemInHand());
|
||||
if(tool == null) return;
|
||||
ArmorStand as = (ArmorStand) event.getRightClicked();
|
||||
if (!playerHasPermission(p, event.getRightClicked().getLocation().getBlock(), tool)) {
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
if (!plugin.playerHasPermission(p, event.getRightClicked().getLocation().getBlock(), tool)) {
|
||||
p.sendMessage(ChatColor.RED + Config.generalNoPerm);
|
||||
event.setCancelled(true);
|
||||
return;
|
||||
}
|
||||
double num = event.getClickedPosition().getY() - 0.05;
|
||||
@ -151,65 +150,8 @@ public class MainListener implements Listener {
|
||||
l.setYaw(((float) num) * 180F);
|
||||
as.teleport(l);
|
||||
break;
|
||||
case INVIS:
|
||||
as.setVisible(!as.isVisible());
|
||||
p.sendMessage(ChatColor.GREEN + Config.asVisible + ": " + (as.isVisible() ? Config.isTrue : Config.isFalse));
|
||||
break;
|
||||
case CLONE:
|
||||
pickUpArmorStand(clone(as), p, true);
|
||||
p.sendMessage(ChatColor.GREEN + Config.asCloned);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.carrying);
|
||||
break;
|
||||
case SAVE:
|
||||
generateCmdBlock(p.getLocation(), as);
|
||||
p.sendMessage(ChatColor.GREEN + Config.cbCreated);
|
||||
break;
|
||||
case SIZE:
|
||||
as.setSmall(!as.isSmall());
|
||||
p.sendMessage(ChatColor.GREEN + Config.size + ": " + (as.isSmall() ? Config.small : Config.normal));
|
||||
break;
|
||||
case BASE:
|
||||
as.setBasePlate(!as.hasBasePlate());
|
||||
p.sendMessage(ChatColor.GREEN + Config.basePlate + ": " + (as.hasBasePlate() ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case GRAV:
|
||||
as.setGravity(!as.hasGravity());
|
||||
p.sendMessage(ChatColor.GREEN + Config.gravity + ": " + (as.hasGravity() ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case ARMS:
|
||||
as.setArms(!as.hasArms());
|
||||
p.sendMessage(ChatColor.GREEN + Config.arms + ": " + (as.hasArms() ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case NAME:
|
||||
setName(p, as);
|
||||
break;
|
||||
case PHEAD:
|
||||
setPlayerSkull(p, as);
|
||||
break;
|
||||
case INVUL:
|
||||
p.sendMessage(ChatColor.GREEN + Config.invul + ": " + (NBT.toggleInvulnerability(as) ? Config.isOn : Config.isOff));
|
||||
break;
|
||||
case SLOTS:
|
||||
p.sendMessage(ChatColor.GREEN + Config.equip + ": " + (NBT.toggleSlotsDisabled(as) ? Config.locked : Config.unLocked));
|
||||
break;
|
||||
case MOVE:
|
||||
UUID uuid = p.getUniqueId();
|
||||
if(plugin.carryingArmorStand.containsKey(uuid)) {
|
||||
plugin.carryingArmorStand.remove(uuid);
|
||||
Utils.actionBarMsg(p, Config.asDropped);
|
||||
} else {
|
||||
pickUpArmorStand(as, p, false);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.carrying);
|
||||
}
|
||||
break;
|
||||
case NODEL: // Developer tool - do not use
|
||||
if(as.getMaxHealth() == 50) {
|
||||
as.setMaxHealth(20);
|
||||
p.sendMessage(ChatColor.GREEN + "Deletion Protection: Disabled");
|
||||
} else {
|
||||
as.setMaxHealth(50);
|
||||
p.sendMessage(ChatColor.GREEN + "Deletion Protection: Enabled");
|
||||
}
|
||||
case GUI:
|
||||
new ArmorStandGUI(plugin, as, p);
|
||||
break;
|
||||
default:
|
||||
cancel = tool == ArmorStandTool.SUMMON || tool == ArmorStandTool.SAVE || event.isCancelled();
|
||||
@ -224,37 +166,9 @@ public class MainListener implements Listener {
|
||||
if (event.getRightClicked() instanceof ItemFrame && ArmorStandTool.isTool(event.getPlayer().getItemInHand())) {
|
||||
event.setCancelled(true);
|
||||
event.getPlayer().updateInventory();
|
||||
} else if(!(event.getRightClicked() instanceof ArmorStand) && ArmorStandTool.NAME.is(event.getPlayer().getItemInHand())) {
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
|
||||
private ArmorStand clone(ArmorStand as) {
|
||||
ArmorStand clone = (ArmorStand) as.getWorld().spawnEntity(as.getLocation().add(1, 0, 0), EntityType.ARMOR_STAND);
|
||||
clone.setGravity(as.hasGravity());
|
||||
clone.setHelmet(as.getHelmet());
|
||||
clone.setChestplate(as.getChestplate());
|
||||
clone.setLeggings(as.getLeggings());
|
||||
clone.setBoots(as.getBoots());
|
||||
clone.setItemInHand(as.getItemInHand());
|
||||
clone.setHeadPose(as.getHeadPose());
|
||||
clone.setBodyPose(as.getBodyPose());
|
||||
clone.setLeftArmPose(as.getLeftArmPose());
|
||||
clone.setRightArmPose(as.getRightArmPose());
|
||||
clone.setLeftLegPose(as.getLeftLegPose());
|
||||
clone.setRightLegPose(as.getRightLegPose());
|
||||
clone.setVisible(as.isVisible());
|
||||
clone.setBasePlate(as.hasBasePlate());
|
||||
clone.setArms(as.hasArms());
|
||||
clone.setCustomName(as.getCustomName());
|
||||
clone.setCustomNameVisible(as.isCustomNameVisible());
|
||||
clone.setSmall(as.isSmall());
|
||||
clone.setMaxHealth(as.getMaxHealth());
|
||||
NBT.setSlotsDisabled(clone, NBT.getDisabledSlots(as) == 2039583);
|
||||
NBT.setInvulnerable(clone, NBT.isInvulnerable(as));
|
||||
return clone;
|
||||
}
|
||||
|
||||
@EventHandler
|
||||
public void onBlockPlace(BlockPlaceEvent event) {
|
||||
if (ArmorStandTool.isTool(event.getItemInHand())) {
|
||||
@ -347,39 +261,31 @@ public class MainListener implements Listener {
|
||||
public void onPlayerInteract(PlayerInteractEvent event) {
|
||||
Player p = event.getPlayer();
|
||||
if(plugin.carryingArmorStand.containsKey(p.getUniqueId())) {
|
||||
boolean perm = playerHasPermission(p, plugin.carryingArmorStand.get(p.getUniqueId()).getLocation().getBlock(), null);
|
||||
if (perm) {
|
||||
if (plugin.playerHasPermission(p, plugin.carryingArmorStand.get(p.getUniqueId()).getLocation().getBlock(), null)) {
|
||||
plugin.carryingArmorStand.remove(p.getUniqueId());
|
||||
Utils.actionBarMsg(p, Config.asDropped);
|
||||
p.setMetadata("lastDrop", new FixedMetadataValue(plugin, System.currentTimeMillis()));
|
||||
event.setCancelled(true);
|
||||
} else {
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
}
|
||||
return;
|
||||
}
|
||||
Action action = event.getAction();
|
||||
ArmorStandTool tool = ArmorStandTool.get(event.getItem());
|
||||
if(tool == null) return;
|
||||
event.setCancelled(true);
|
||||
Action action = event.getAction();
|
||||
if(action == Action.LEFT_CLICK_AIR || action == Action.LEFT_CLICK_BLOCK) {
|
||||
event.setCancelled(true);
|
||||
Utils.cycleInventory(p);
|
||||
} else if(action == Action.RIGHT_CLICK_BLOCK) {
|
||||
if (!playerHasPermission(p, event.getClickedBlock(), tool)) {
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
} else if((action == Action.RIGHT_CLICK_BLOCK || action == Action.RIGHT_CLICK_AIR) && tool == ArmorStandTool.SUMMON) {
|
||||
if (!plugin.playerHasPermission(p, event.getClickedBlock(), tool)) {
|
||||
p.sendMessage(ChatColor.RED + Config.generalNoPerm);
|
||||
return;
|
||||
}
|
||||
switch (tool) {
|
||||
case SUMMON:
|
||||
event.setCancelled(true);
|
||||
Location l = Utils.getLocationFacingPlayer(p);
|
||||
pickUpArmorStand(spawnArmorStand(l), p, true);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.carrying);
|
||||
p.updateInventory();
|
||||
break;
|
||||
case NAME:
|
||||
event.setCancelled(true);
|
||||
break;
|
||||
}
|
||||
Location l = Utils.getLocationFacingPlayer(p);
|
||||
plugin.pickUpArmorStand(spawnArmorStand(l), p, true);
|
||||
Utils.actionBarMsg(p, ChatColor.GREEN + Config.carrying);
|
||||
p.updateInventory();
|
||||
}
|
||||
}
|
||||
|
||||
@ -387,10 +293,21 @@ public class MainListener implements Listener {
|
||||
public void onEntityDamageByEntity(EntityDamageByEntityEvent event) {
|
||||
if(event.getEntity() instanceof ArmorStand && event.getDamager() instanceof Player && ArmorStandTool.isTool(((Player) event.getDamager()).getItemInHand())) {
|
||||
event.setCancelled(true);
|
||||
Utils.cycleInventory((Player) event.getDamager());
|
||||
if(noCooldown(event.getDamager())) {
|
||||
Utils.cycleInventory((Player) event.getDamager());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private boolean noCooldown(Entity e) {
|
||||
for(MetadataValue meta : e.getMetadata("lastDrop")) {
|
||||
if(meta.getOwningPlugin() == plugin) {
|
||||
return System.currentTimeMillis() - meta.asFloat() > 100;
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
private ArmorStand spawnArmorStand(Location l) {
|
||||
ArmorStand as = (ArmorStand) l.getWorld().spawnEntity(l, EntityType.ARMOR_STAND);
|
||||
as.setHelmet(Config.helmet);
|
||||
@ -412,59 +329,12 @@ public class MainListener implements Listener {
|
||||
return as;
|
||||
}
|
||||
|
||||
@SuppressWarnings({"deprecation", "ConstantConditions"})
|
||||
private void generateCmdBlock(Location l, ArmorStand as) {
|
||||
Location loc = as.getLocation();
|
||||
int dSlots = NBT.getDisabledSlots(as);
|
||||
int hand = as.getItemInHand() == null ? 0 : as.getItemInHand().getTypeId();
|
||||
int handDmg = as.getItemInHand() == null ? 0 : as.getItemInHand().getDurability();
|
||||
int boots = as.getBoots() == null ? 0 : as.getBoots().getTypeId();
|
||||
int bootsDmg = as.getBoots() == null ? 0 : as.getBoots().getDurability();
|
||||
int legs = as.getLeggings() == null ? 0 : as.getLeggings().getTypeId();
|
||||
int legsDmg = as.getLeggings() == null ? 0 : as.getLeggings().getDurability();
|
||||
int chest = as.getChestplate() == null ? 0 : as.getChestplate().getTypeId();
|
||||
int chestDmg = as.getChestplate() == null ? 0 : as.getChestplate().getDurability();
|
||||
int helm = as.getHelmet() == null ? 0 : as.getHelmet().getTypeId();
|
||||
int helmDmg = as.getHelmet() == null ? 0 : as.getHelmet().getDurability();
|
||||
EulerAngle he = as.getHeadPose();
|
||||
EulerAngle ll = as.getLeftLegPose();
|
||||
EulerAngle rl = as.getRightLegPose();
|
||||
EulerAngle la = as.getLeftArmPose();
|
||||
EulerAngle ra = as.getRightArmPose();
|
||||
EulerAngle bo = as.getBodyPose();
|
||||
String cmd =
|
||||
"summon ArmorStand " + Utils.twoDec(loc.getX()) + " " + Utils.twoDec(loc.getY()) + " " + Utils.twoDec(loc.getZ()) + " {"
|
||||
+ (as.getMaxHealth() != 20 ? "Attributes:[{Name:\"generic.maxHealth\", Base:" + as.getMaxHealth() + "}]," : "")
|
||||
+ (as.isVisible() ? "" : "Invisible:1,")
|
||||
+ (as.hasBasePlate() ? "" : "NoBasePlate:1,")
|
||||
+ (as.hasGravity() ? "" : "NoGravity:1,")
|
||||
+ (as.hasArms() ? "ShowArms:1," : "")
|
||||
+ (as.isSmall() ? "Small:1," : "")
|
||||
+ (NBT.isInvulnerable(as) ? "Invulnerable:1," : "")
|
||||
+ (dSlots == 0 ? "" : ("DisabledSlots:" + dSlots + ","))
|
||||
+ (as.isCustomNameVisible() ? "CustomNameVisible:1," : "")
|
||||
+ (as.getCustomName() == null ? "" : ("CustomName:\"" + as.getCustomName() + "\","))
|
||||
+ (loc.getYaw() == 0F ? "" : ("Rotation:[" + Utils.twoDec(loc.getYaw()) + "f],"))
|
||||
+ (hand == 0 && boots == 0 && legs == 0 && chest == 0 && helm == 0 ? "" : (
|
||||
"Equipment:["
|
||||
+ "{id:" + hand + ",Damage:" + handDmg + NBT.getItemStackTags(as.getItemInHand()) + "},"
|
||||
+ "{id:" + boots + ",Damage:" + bootsDmg + NBT.getItemStackTags(as.getBoots()) + "},"
|
||||
+ "{id:" + legs + ",Damage:" + legsDmg + NBT.getItemStackTags(as.getLeggings()) + "},"
|
||||
+ "{id:" + chest + ",Damage:" + chestDmg + NBT.getItemStackTags(as.getChestplate()) + "},"
|
||||
+ "{id:" + helm + ",Damage:" + helmDmg + NBT.getItemStackTags(as.getHelmet()) + NBT.skullOwner(as.getHelmet()) + "}],"))
|
||||
+ "Pose:{"
|
||||
+ (bo.equals(zero) ? "" : ("Body:[" + Utils.angle(bo.getX()) + "f," + Utils.angle(bo.getY()) + "f," + Utils.angle(bo.getZ()) + "f],"))
|
||||
+ (he.equals(zero) ? "" : ("Head:[" + Utils.angle(he.getX()) + "f," + Utils.angle(he.getY()) + "f," + Utils.angle(he.getZ()) + "f],"))
|
||||
+ (ll.equals(zero) ? "" : ("LeftLeg:[" + Utils.angle(ll.getX()) + "f," + Utils.angle(ll.getY()) + "f," + Utils.angle(ll.getZ()) + "f],"))
|
||||
+ (rl.equals(zero) ? "" : ("RightLeg:[" + Utils.angle(rl.getX()) + "f," + Utils.angle(rl.getY()) + "f," + Utils.angle(rl.getZ()) + "f],"))
|
||||
+ (la.equals(zero) ? "" : ("LeftArm:[" + Utils.angle(la.getX()) + "f," + Utils.angle(la.getY()) + "f," + Utils.angle(la.getZ()) + "f],"))
|
||||
+ "RightArm:[" + Utils.angle(ra.getX()) + "f," + Utils.angle(ra.getY()) + "f," + Utils.angle(ra.getZ()) + "f]}}";
|
||||
Block b = l.getBlock();
|
||||
b.setType(Material.COMMAND);
|
||||
b.setData((byte) 0);
|
||||
CommandBlock cb = (CommandBlock) b.getState();
|
||||
cb.setCommand(cmd);
|
||||
cb.update();
|
||||
@EventHandler
|
||||
public void onBlockBreak(BlockBreakEvent event) {
|
||||
Block b = event.getBlock();
|
||||
if((b.getType() == Material.SKULL && b.hasMetadata("protected")) || (b.getType() == Material.SIGN_POST && b.hasMetadata("armorStand"))) {
|
||||
event.setCancelled(true);
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
@ -493,6 +363,7 @@ public class MainListener implements Listener {
|
||||
} else if(b.hasMetadata("setSkull")) {
|
||||
if(MC_USERNAME_PATTERN.matcher(input).matches()) {
|
||||
final String name = input;
|
||||
b.setMetadata("protected", new FixedMetadataValue(plugin, true));
|
||||
b.setType(Material.SKULL);
|
||||
final Skull s = (Skull) b.getState();
|
||||
s.setSkullType(SkullType.PLAYER);
|
||||
@ -508,13 +379,39 @@ public class MainListener implements Listener {
|
||||
if (ok) {
|
||||
s.setOwner(name);
|
||||
s.update();
|
||||
as.setHelmet(b.getDrops().iterator().next());
|
||||
event.getPlayer().sendMessage(ChatColor.GREEN + Config.appliedHead + ChatColor.GOLD + " " + name);
|
||||
new BukkitRunnable() {
|
||||
int n = 0;
|
||||
ItemStack skull;
|
||||
@Override
|
||||
public void run() {
|
||||
if(++n > 20) {
|
||||
this.cancel();
|
||||
event.getPlayer().sendMessage(ChatColor.RED + Config.headFailed);
|
||||
b.setType(Material.AIR);
|
||||
b.setData((byte) 0);
|
||||
b.removeMetadata("protected", plugin);
|
||||
return;
|
||||
}
|
||||
skull = b.getDrops().iterator().next();
|
||||
if(skull.getType() == Material.SKULL_ITEM && skull.getData().getData() == (byte) 3) {
|
||||
SkullMeta meta = (SkullMeta) skull.getItemMeta();
|
||||
if(meta.hasOwner() && meta.getOwner().equalsIgnoreCase(name)) {
|
||||
as.setHelmet(skull);
|
||||
event.getPlayer().sendMessage(ChatColor.GREEN + Config.appliedHead + ChatColor.GOLD + " " + name);
|
||||
b.setType(Material.AIR);
|
||||
b.setData((byte) 0);
|
||||
b.removeMetadata("protected", plugin);
|
||||
this.cancel();
|
||||
}
|
||||
}
|
||||
}
|
||||
}.runTaskTimer(plugin, 10L, 10L);
|
||||
} else {
|
||||
event.getPlayer().sendMessage(ChatColor.RED + Config.noHead + ChatColor.GOLD + " " + name);
|
||||
b.setType(Material.AIR);
|
||||
b.setData((byte) 0);
|
||||
b.removeMetadata("protected", plugin);
|
||||
}
|
||||
b.setType(Material.AIR);
|
||||
b.setData((byte) 0);
|
||||
}
|
||||
}.runTask(plugin);
|
||||
}
|
||||
@ -534,42 +431,6 @@ public class MainListener implements Listener {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private void setName(Player p, ArmorStand as) {
|
||||
Block b = Utils.findAnAirBlock(p.getLocation());
|
||||
if(b == null) {
|
||||
p.sendMessage(ChatColor.RED + Config.noAirError);
|
||||
return;
|
||||
}
|
||||
if(!checkPermission(p, b)) {
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
return;
|
||||
}
|
||||
b.setData((byte) 0);
|
||||
b.setType(Material.SIGN_POST);
|
||||
Utils.openSign(p, b);
|
||||
b.setMetadata("armorStand", new FixedMetadataValue(plugin, as.getUniqueId()));
|
||||
b.setMetadata("setName", new FixedMetadataValue(plugin, true));
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
private void setPlayerSkull(Player p, ArmorStand as) {
|
||||
Block b = Utils.findAnAirBlock(p.getLocation());
|
||||
if(b == null) {
|
||||
p.sendMessage(ChatColor.RED + Config.noAirError);
|
||||
return;
|
||||
}
|
||||
if(!checkPermission(p, b)) {
|
||||
p.sendMessage(ChatColor.RED + Config.wgNoPerm);
|
||||
return;
|
||||
}
|
||||
b.setData((byte) 0);
|
||||
b.setType(Material.SIGN_POST);
|
||||
Utils.openSign(p, b);
|
||||
b.setMetadata("armorStand", new FixedMetadataValue(plugin, as.getUniqueId()));
|
||||
b.setMetadata("setSkull", new FixedMetadataValue(plugin, true));
|
||||
}
|
||||
|
||||
private ArmorStand getArmorStand(Block b) {
|
||||
UUID uuid = null;
|
||||
@ -588,48 +449,5 @@ public class MainListener implements Listener {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
private static boolean checkPermission(Player player, Block block) {
|
||||
|
||||
// Check PlotSquared
|
||||
Location loc = block.getLocation();
|
||||
if (PlotSquaredHook.api != null) {
|
||||
if (PlotSquaredHook.isPlotWorld(loc)) {
|
||||
return PlotSquaredHook.checkPermission(player, loc);
|
||||
}
|
||||
}
|
||||
|
||||
// check WorldGuard
|
||||
if(Config.worldGuardPlugin != null) {
|
||||
return Config.worldGuardPlugin.canBuild(player, block);
|
||||
}
|
||||
|
||||
// Use standard permission checking (will support basically any plugin)
|
||||
BlockBreakEvent myBreak = new BlockBreakEvent(block, player);
|
||||
Bukkit.getServer().getPluginManager().callEvent(myBreak);
|
||||
boolean hasPerm = !myBreak.isCancelled();
|
||||
BlockPlaceEvent place = new BlockPlaceEvent(block, block.getState(), block, null, player, true);
|
||||
Bukkit.getServer().getPluginManager().callEvent(place);
|
||||
if (place.isCancelled()) {
|
||||
hasPerm = false;
|
||||
}
|
||||
return hasPerm;
|
||||
}
|
||||
|
||||
private static boolean playerHasPermission(Player p, Block b, ArmorStandTool tool) {
|
||||
if(tool != null && !p.isOp() && (!Utils.hasPermissionNode(p, "astools.use")
|
||||
||(ArmorStandTool.SAVE == tool && !Utils.hasPermissionNode(p, "astools.cmdblock"))
|
||||
||(ArmorStandTool.CLONE == tool && !Utils.hasPermissionNode(p, "astools.clone")))) {
|
||||
p.sendMessage(ChatColor.RED + Config.noPerm);
|
||||
return false;
|
||||
}
|
||||
return checkPermission(p, b);
|
||||
}
|
||||
|
||||
void pickUpArmorStand(ArmorStand as, Player p, boolean newlySummoned) {
|
||||
plugin.carryingArmorStand.put(p.getUniqueId(), as);
|
||||
if(newlySummoned) return;
|
||||
as.setMetadata("startLoc", new FixedMetadataValue(plugin, as.getLocation()));
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -6,10 +6,12 @@ import org.bukkit.block.Block;
|
||||
import org.bukkit.entity.Player;
|
||||
import org.bukkit.inventory.Inventory;
|
||||
import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.inventory.meta.ItemMeta;
|
||||
import org.bukkit.util.Vector;
|
||||
|
||||
import java.text.DecimalFormat;
|
||||
import java.text.DecimalFormatSymbols;
|
||||
import java.util.Arrays;
|
||||
import java.util.Collection;
|
||||
|
||||
class Utils {
|
||||
@ -18,7 +20,7 @@ class Utils {
|
||||
|
||||
static boolean containsItems(Collection<ItemStack> items) {
|
||||
for(ItemStack i : items) {
|
||||
if(items.contains(i)) {
|
||||
if(ArmorStandTool.get(i) != null) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@ -159,4 +161,11 @@ class Utils {
|
||||
return l.getY() < 255 && l.getBlock().getType() == Material.AIR ? l.getBlock() : null;
|
||||
}
|
||||
|
||||
static ItemStack setLore(ItemStack is, String... lore) {
|
||||
ItemMeta meta = is.getItemMeta();
|
||||
meta.setLore(Arrays.asList(lore));
|
||||
is.setItemMeta(meta);
|
||||
return is;
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
# Armor Stand Tools v1.7
|
||||
# Armor Stand Tools v2.0
|
||||
#
|
||||
# by St3venAU (St3venAU@gmail.com)
|
||||
#
|
||||
@ -7,6 +7,7 @@
|
||||
# - Name armor stands
|
||||
# - Toggle: Gravity, Visibility, Arms, Base, Size, Invulnerability, Equipment Lock
|
||||
# - Manipulate the position of the Head, Body, Arms and Legs
|
||||
# - Full control over armor stand's inventory (armor & item in hand)
|
||||
# - Clone armor stand tool
|
||||
# - Create command block tool: Creates a command block with the command that will summon this
|
||||
# armor stand in its current state
|
||||
|
128
src/language.yml
128
src/language.yml
@ -18,12 +18,11 @@
|
||||
####################
|
||||
invReturned: 'Inventory contents returned'
|
||||
asDropped: 'Armor stand dropped'
|
||||
asVisible: 'Armor stand visible'
|
||||
asVisible: 'Visible'
|
||||
isTrue: 'True'
|
||||
isFalse: 'False'
|
||||
asCloned: 'Armor stand cloned'
|
||||
carrying: 'Carrying armor stand. Click to drop.'
|
||||
noPerm: 'You do not have permission to use this tool'
|
||||
generalNoPerm: 'No permission for this tool and/or region'
|
||||
cbCreated: 'Command block created'
|
||||
size: 'Size'
|
||||
small: 'Small'
|
||||
@ -37,6 +36,7 @@ invul: 'Invulnerability'
|
||||
equip: 'Equipment'
|
||||
locked: 'Locked'
|
||||
unLocked: 'Un-Locked'
|
||||
currently: 'Currently'
|
||||
notConsole: 'This command can not be run from console'
|
||||
giveMsg1: 'Given armor stand tools. L-click any tool to cycle through tools.'
|
||||
giveMsg2: 'Run this command again to return your inventory.'
|
||||
@ -47,13 +47,30 @@ pleaseWait: 'Please wait, this may take a few seconds...'
|
||||
appliedHead: 'Applied the head of player'
|
||||
noHead: 'No player head found for player'
|
||||
invalidName: 'is not a valid minecraft username'
|
||||
wgNoPerm: 'You do not have permission to alter an armor stand in this region'
|
||||
wgNoPerm: 'No permission to alter an armor stand in this region'
|
||||
headFailed: 'Failed to apply the player head. Try again.'
|
||||
noCommandPerm: 'You do not have permission to use this command'
|
||||
#
|
||||
#############################
|
||||
# Tool names & descriptions #
|
||||
#############################
|
||||
tool:
|
||||
summon:
|
||||
name: 'Summon Armor Stand'
|
||||
lore:
|
||||
- 'R-Click to summon an armor stand and pick it up'
|
||||
- 'Any click will drop it'
|
||||
gui:
|
||||
name: 'GUI Multi-Tool'
|
||||
lore:
|
||||
- 'R-Click armor stand to open a GUI to tweak'
|
||||
- 'the attributes of the armor stand or change'
|
||||
- 'its armor and items'
|
||||
rotat:
|
||||
name: 'Rotation'
|
||||
lore:
|
||||
- 'R-Click armor stand to change its Rotation'
|
||||
- 'Value depends on how high up the body you click'
|
||||
headX:
|
||||
name: 'Head X'
|
||||
lore:
|
||||
@ -114,31 +131,6 @@ tool:
|
||||
lore:
|
||||
- 'R-Click armor stand to move +0.1 Z'
|
||||
- 'Crouch R-Click for -0.1 Z'
|
||||
rotat:
|
||||
name: 'Rotation'
|
||||
lore:
|
||||
- 'R-Click armor stand to change its Rotation'
|
||||
- 'Value depends on how high up the body you click'
|
||||
invis:
|
||||
name: 'Toggle Visibility'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle its visibility'
|
||||
summon:
|
||||
name: 'Summon Armor Stand'
|
||||
lore:
|
||||
- 'R-Click to summon an armor stand and pick it up'
|
||||
- 'Any click will drop it'
|
||||
- 'To change summoned armor stand defaults, edit config.yml'
|
||||
clone:
|
||||
name: 'Clone'
|
||||
lore:
|
||||
- 'R-Click armor stand to pick up a clone of it'
|
||||
- 'Any click will drop it'
|
||||
save:
|
||||
name: 'Create Command Block'
|
||||
lore:
|
||||
- 'R-Click armor stand to create command block'
|
||||
- 'with a summon command for this armor stand'
|
||||
lLegX:
|
||||
name: 'Left Leg X'
|
||||
lore:
|
||||
@ -184,45 +176,43 @@ tool:
|
||||
lore:
|
||||
- 'R-Click armor stand to change Body Z'
|
||||
- 'Value depends on how high up the body you click'
|
||||
size:
|
||||
name: 'Toggle Size'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle its size'
|
||||
base:
|
||||
name: 'Toggle Base'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle its base'
|
||||
grav:
|
||||
name: 'Toggle Gravity'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle its gravity'
|
||||
arms:
|
||||
name: 'Toggle Arms'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle its arms'
|
||||
name:
|
||||
name: 'Set Name'
|
||||
lore:
|
||||
- 'R-Click armor stand to set its name'
|
||||
- 'Standard color codes accepted'
|
||||
slots:
|
||||
name: 'Toggle Equipment Lock'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle equipment lock'
|
||||
- 'When equipment is locked, players can not take or add equipment'
|
||||
pHead:
|
||||
name: 'Give a Player Head'
|
||||
lore:
|
||||
- 'R-Click armor stand and specify a player name to'
|
||||
- 'give it that players head'
|
||||
- '(Will not work if used multiple times too fast)'
|
||||
invul:
|
||||
name: 'Toggle Invulnerability'
|
||||
lore:
|
||||
- 'R-Click armor stand to toggle invulnerability'
|
||||
- 'Note: Creative mode players can break invulnerable armor stands'
|
||||
move:
|
||||
gui_move:
|
||||
name: 'Pick Up (Move)'
|
||||
lore:
|
||||
- 'R-Click armor stand to pick it up and move it'
|
||||
- 'Any click will drop it again'
|
||||
- 'Pick up this armor stand to move it'
|
||||
gui_clone:
|
||||
name: 'Clone'
|
||||
lore:
|
||||
- 'Clone this armor stand and pick it up'
|
||||
gui_save:
|
||||
name: 'Create Command Block'
|
||||
lore:
|
||||
- 'Create command block to'
|
||||
- 'summon this armor stand'
|
||||
gui_invis:
|
||||
name: 'Toggle Visibility'
|
||||
lore:
|
||||
gui_size:
|
||||
name: 'Toggle Size'
|
||||
lore:
|
||||
gui_base:
|
||||
name: 'Toggle Base'
|
||||
lore:
|
||||
gui_grav:
|
||||
name: 'Toggle Gravity'
|
||||
lore:
|
||||
gui_arms:
|
||||
name: 'Toggle Arms'
|
||||
lore:
|
||||
gui_name:
|
||||
name: 'Change Name'
|
||||
lore:
|
||||
gui_slots:
|
||||
name: 'Toggle Equipment Lock'
|
||||
lore:
|
||||
gui_pHead:
|
||||
name: 'Give Player Head'
|
||||
lore:
|
||||
gui_invul:
|
||||
name: 'Toggle Invulnerability'
|
||||
lore:
|
@ -1,6 +1,6 @@
|
||||
main: com.gmail.St3venAU.plugins.ArmorStandTools.Main
|
||||
name: ArmorStandTools
|
||||
version: 1.7
|
||||
version: 2.0
|
||||
author: St3venAU
|
||||
description: Armor stand manipulation tools
|
||||
softdepend: [WorldGuard, PlotSquared]
|
||||
|
Laden…
In neuem Issue referenzieren
Einen Benutzer sperren