Fixed Floating Items Remaining

1.17+ introduced a different method to load entities which caused issues.
Paper/Spigot now correctly handle bugged armour stands on chunk load.
This commit is contained in:
James Peters 2021-12-18 19:11:26 +00:00
parent e1532d4116
commit 32757fd506
31 changed files with 204 additions and 113 deletions

View File

@ -8,9 +8,11 @@ import java.lang.reflect.InvocationTargetException;
public class Api { public class Api {
private static Plugin plugin; private static Plugin plugin;
private static NMSProvider nmsProvider;
public static void register(Plugin plugin) { public static void register(Plugin plugin) {
Api.plugin = plugin; Api.plugin = plugin;
Values.init(plugin);
} }
public static Plugin getPlugin() { public static Plugin getPlugin() {
@ -30,4 +32,8 @@ public class Api {
return null; return null;
} }
} }
protected static NMSProvider getNmsProvider() {
return nmsProvider;
}
} }

View File

@ -0,0 +1,56 @@
package com.jamesdpeters.minecraft.chests;
import org.bukkit.Chunk;
import org.bukkit.World;
import org.bukkit.block.Hopper;
import org.bukkit.entity.Entity;
import org.bukkit.entity.ItemFrame;
import org.bukkit.event.Listener;
import org.bukkit.persistence.PersistentDataType;
import java.util.Arrays;
import java.util.stream.Stream;
public abstract class EntityEventListener implements Listener {
protected void fixEntities(Chunk chunk) {
removeEntities(chunk);
setItemFrames(chunk);
}
public void fixEntities(World world) {
removeEntities(world);
setItemFrames(world);
}
private void removeEntities(World world) {
world.getEntities().forEach(this::removeEntity);
}
private void removeEntities(Chunk chunk) {
for (Entity entity : chunk.getEntities()) {
removeEntity(entity);
}
}
protected void removeEntity(Entity entity) {
Integer val = entity.getPersistentDataContainer().get(Values.Instance().PluginKey, PersistentDataType.INTEGER);
if (val != null && val == 1)
entity.remove();
}
private void setItemFrames(World world) {
setItemFrames(world.getEntities().stream());
}
private void setItemFrames(Chunk chunk) {
setItemFrames(Arrays.stream(chunk.getEntities()));
}
private void setItemFrames(Stream<Entity> entityStream) {
entityStream.filter(entity ->
(entity instanceof ItemFrame
&& entity.getLocation().getBlock().getRelative(((ItemFrame) entity).getAttachedFace()).getState() instanceof Hopper))
.forEach(entity -> Api.getNmsProvider().setItemFrameVisible((ItemFrame) entity, !PluginConfig.INVISIBLE_FILTER_ITEM_FRAMES.get()));
}
}

View File

@ -6,6 +6,7 @@ public interface NMSProvider {
ChestOpener getChestOpener(); ChestOpener getChestOpener();
MaterialChecker getMaterialChecker(); MaterialChecker getMaterialChecker();
CraftingProvider getCraftingProvider(); CraftingProvider getCraftingProvider();
EntityEventListener getEntityEventListener();
void setItemFrameVisible(ItemFrame itemFrame, boolean visible); void setItemFrameVisible(ItemFrame itemFrame, boolean visible);
} }

View File

@ -1,4 +1,4 @@
package com.jamesdpeters.minecraft.chests.serialize; package com.jamesdpeters.minecraft.chests;
import org.bukkit.configuration.ConfigurationSection; import org.bukkit.configuration.ConfigurationSection;
import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.configuration.file.FileConfiguration;

View File

@ -0,0 +1,35 @@
package com.jamesdpeters.minecraft.chests;
import org.bukkit.NamespacedKey;
import org.bukkit.plugin.Plugin;
public class Values {
public final static String ChestLinkTag = "[ChestLink]";
public final static String AutoCraftTag = "[AutoCraft]";
public static String identifier(String identifier) {
return "[" + identifier + "]";
}
public final NamespacedKey playerUUID;
public final NamespacedKey PluginKey;
public final NamespacedKey storageID;
public final NamespacedKey hopperTicked;
private static Values Instance;
public Values(Plugin plugin) {
playerUUID = new NamespacedKey(plugin, "playerUUID");
PluginKey = new NamespacedKey(plugin, "ChestsPlusPlus");
storageID = new NamespacedKey(plugin, "storageID");
hopperTicked = new NamespacedKey(plugin, "hopperTicked");
}
public static void init(Plugin plugin) {
Instance = new Values(plugin);
}
public static Values Instance() {
return Instance;
}
}

View File

@ -0,0 +1,14 @@
package com.jamesdpeters.minecraft.chests.v1_14_R1;
import com.jamesdpeters.minecraft.chests.EntityEventListener;
import org.bukkit.event.EventHandler;
import org.bukkit.event.world.ChunkLoadEvent;
public class EntityEventListener_1_14 extends EntityEventListener {
@EventHandler
public void onChunkLoad(ChunkLoadEvent event) {
fixEntities(event.getChunk());
}
}

View File

@ -19,6 +19,11 @@ public class NMSProviderImpl implements NMSProvider {
return new Crafting(); return new Crafting();
} }
@Override
public EntityEventListener getEntityEventListener() {
return new EntityEventListener_1_14();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
//Not support in 1.14 //Not support in 1.14

View File

@ -1,6 +1,7 @@
package com.jamesdpeters.minecraft.chests.v1_15_R1; package com.jamesdpeters.minecraft.chests.v1_15_R1;
import com.jamesdpeters.minecraft.chests.*; import com.jamesdpeters.minecraft.chests.*;
import com.jamesdpeters.minecraft.chests.v1_14_R1.EntityEventListener_1_14;
import org.bukkit.entity.ItemFrame; import org.bukkit.entity.ItemFrame;
public class NMSProviderImpl implements NMSProvider { public class NMSProviderImpl implements NMSProvider {
@ -19,6 +20,11 @@ public class NMSProviderImpl implements NMSProvider {
return new Crafting(); return new Crafting();
} }
@Override
public EntityEventListener getEntityEventListener() {
return new EntityEventListener_1_14();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
//Not supported in 1.15 //Not supported in 1.15

View File

@ -1,6 +1,7 @@
package com.jamesdpeters.minecraft.chests.v1_16_R1; package com.jamesdpeters.minecraft.chests.v1_16_R1;
import com.jamesdpeters.minecraft.chests.*; import com.jamesdpeters.minecraft.chests.*;
import com.jamesdpeters.minecraft.chests.v1_14_R1.EntityEventListener_1_14;
import org.bukkit.block.Lidded; import org.bukkit.block.Lidded;
import org.bukkit.entity.ItemFrame; import org.bukkit.entity.ItemFrame;
@ -32,6 +33,11 @@ public class NMSProviderImpl implements NMSProvider {
return new Crafting(); return new Crafting();
} }
@Override
public EntityEventListener getEntityEventListener() {
return new EntityEventListener_1_14();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
itemFrame.setVisible(visible); itemFrame.setVisible(visible);

View File

@ -1,6 +1,7 @@
package com.jamesdpeters.minecraft.chests.v1_16_R2; package com.jamesdpeters.minecraft.chests.v1_16_R2;
import com.jamesdpeters.minecraft.chests.*; import com.jamesdpeters.minecraft.chests.*;
import com.jamesdpeters.minecraft.chests.v1_14_R1.EntityEventListener_1_14;
import org.bukkit.block.Lidded; import org.bukkit.block.Lidded;
import org.bukkit.entity.ItemFrame; import org.bukkit.entity.ItemFrame;
@ -32,6 +33,11 @@ public class NMSProviderImpl implements NMSProvider {
return new Crafting(); return new Crafting();
} }
@Override
public EntityEventListener getEntityEventListener() {
return new EntityEventListener_1_14();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
itemFrame.setVisible(visible); itemFrame.setVisible(visible);

View File

@ -1,6 +1,7 @@
package com.jamesdpeters.minecraft.chests.v1_16_R3; package com.jamesdpeters.minecraft.chests.v1_16_R3;
import com.jamesdpeters.minecraft.chests.*; import com.jamesdpeters.minecraft.chests.*;
import com.jamesdpeters.minecraft.chests.v1_14_R1.EntityEventListener_1_14;
import org.bukkit.block.Lidded; import org.bukkit.block.Lidded;
import org.bukkit.entity.ItemFrame; import org.bukkit.entity.ItemFrame;
@ -32,6 +33,11 @@ public class NMSProviderImpl implements NMSProvider {
return new Crafting(); return new Crafting();
} }
@Override
public EntityEventListener getEntityEventListener() {
return new EntityEventListener_1_14();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
itemFrame.setVisible(visible); itemFrame.setVisible(visible);

View File

@ -0,0 +1,13 @@
package com.jamesdpeters.minecraft.chests.latest;
import com.jamesdpeters.minecraft.chests.EntityEventListener;
import org.bukkit.event.EventHandler;
import org.bukkit.event.world.EntitiesLoadEvent;
public class EntityEventListener_1_17 extends EntityEventListener {
@EventHandler
public void onEntityLoad(EntitiesLoadEvent event) {
event.getEntities().forEach(this::removeEntity);
}
}

View File

@ -2,6 +2,7 @@ package com.jamesdpeters.minecraft.chests.latest;
import com.jamesdpeters.minecraft.chests.ChestOpener; import com.jamesdpeters.minecraft.chests.ChestOpener;
import com.jamesdpeters.minecraft.chests.CraftingProvider; import com.jamesdpeters.minecraft.chests.CraftingProvider;
import com.jamesdpeters.minecraft.chests.EntityEventListener;
import com.jamesdpeters.minecraft.chests.MaterialChecker; import com.jamesdpeters.minecraft.chests.MaterialChecker;
import com.jamesdpeters.minecraft.chests.NMSProvider; import com.jamesdpeters.minecraft.chests.NMSProvider;
import org.bukkit.block.Lidded; import org.bukkit.block.Lidded;
@ -33,6 +34,11 @@ public class NMSProviderImpl implements NMSProvider {
return new Crafting(); return new Crafting();
} }
@Override
public EntityEventListener getEntityEventListener() {
return new EntityEventListener_1_17();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
itemFrame.setVisible(visible); itemFrame.setVisible(visible);

View File

@ -3,7 +3,7 @@
<modelVersion>4.0.0</modelVersion> <modelVersion>4.0.0</modelVersion>
<groupId>com.jamesdpeters.minecraft.chests</groupId> <groupId>com.jamesdpeters.minecraft.chests</groupId>
<artifactId>ChestsPlusPlus-Master</artifactId> <artifactId>ChestsPlusPlus-Master</artifactId>
<version>2.5-Release</version> <version>2.5.1-Release</version>
<scm> <scm>
<connection>scm:git:git@github.com:JamesPeters98/ChestsPlusPlus.git</connection> <connection>scm:git:git@github.com:JamesPeters98/ChestsPlusPlus.git</connection>
<developerConnection>scm:git:git@github.com:JamesPeters98/ChestsPlusPlus.git</developerConnection> <developerConnection>scm:git:git@github.com:JamesPeters98/ChestsPlusPlus.git</developerConnection>

View File

@ -21,7 +21,6 @@ import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage; import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage;
import com.jamesdpeters.minecraft.chests.serialize.LocationInfo; import com.jamesdpeters.minecraft.chests.serialize.LocationInfo;
import com.jamesdpeters.minecraft.chests.serialize.MaterialSerializer; import com.jamesdpeters.minecraft.chests.serialize.MaterialSerializer;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig;
import com.jamesdpeters.minecraft.chests.serialize.RecipeSerializable; import com.jamesdpeters.minecraft.chests.serialize.RecipeSerializable;
import com.jamesdpeters.minecraft.chests.serialize.SpigotConfig; import com.jamesdpeters.minecraft.chests.serialize.SpigotConfig;
import com.jamesdpeters.minecraft.chests.storage.autocraft.AutoCraftingStorage; import com.jamesdpeters.minecraft.chests.storage.autocraft.AutoCraftingStorage;
@ -83,7 +82,6 @@ public class ChestsPlusPlus extends JavaPlugin {
} }
@SuppressWarnings("ConstantConditions")
@Override @Override
public void onEnable() { public void onEnable() {
int pluginId = 7166; int pluginId = 7166;
@ -128,8 +126,10 @@ public class ChestsPlusPlus extends JavaPlugin {
}), 0, PluginConfig.UPDATE_CHECKER_PERIOD.get() * 20); }), 0, PluginConfig.UPDATE_CHECKER_PERIOD.get() * 20);
} }
// Remove armour stands if disabled getServer().getPluginManager().registerEvents(ApiSpecific.getNmsProvider().getEntityEventListener(), this);
Utils.fixEntities(); Bukkit.getWorlds().forEach(world -> {
ApiSpecific.getNmsProvider().getEntityEventListener().fixEntities(world);
});
//Load storages after load. //Load storages after load.
Bukkit.getScheduler().scheduleSyncDelayedTask(this, () -> { Bukkit.getScheduler().scheduleSyncDelayedTask(this, () -> {

View File

@ -31,6 +31,11 @@ public class NMSProviderDefault implements NMSProvider {
return defaultProvider.getCraftingProvider(); return defaultProvider.getCraftingProvider();
} }
@Override
public EntityEventListener getEntityEventListener() {
return defaultProvider.getEntityEventListener();
}
@Override @Override
public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) { public void setItemFrameVisible(ItemFrame itemFrame, boolean visible) {
//Not supported in Bukkit api 1.14. //Not supported in Bukkit api 1.14.

View File

@ -7,7 +7,7 @@ import com.jamesdpeters.minecraft.chests.lang.Message;
import com.jamesdpeters.minecraft.chests.misc.ServerType; import com.jamesdpeters.minecraft.chests.misc.ServerType;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import com.jamesdpeters.minecraft.chests.serialize.SpigotConfig; import com.jamesdpeters.minecraft.chests.serialize.SpigotConfig;
import com.jamesdpeters.minecraft.chests.storage.chestlink.ChestLinkStorage; import com.jamesdpeters.minecraft.chests.storage.chestlink.ChestLinkStorage;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;

View File

@ -2,7 +2,7 @@ package com.jamesdpeters.minecraft.chests.listeners;
import com.jamesdpeters.minecraft.chests.misc.Messages; import com.jamesdpeters.minecraft.chests.misc.Messages;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.misc.Values; import com.jamesdpeters.minecraft.chests.Values;
import com.jamesdpeters.minecraft.chests.runnables.ChestLinkVerifier; import com.jamesdpeters.minecraft.chests.runnables.ChestLinkVerifier;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage; import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage;
@ -83,7 +83,7 @@ public class StorageListener implements Listener {
setLine(sign, signChangeEvent, 0, ChatColor.RED + ChatColor.stripColor(signChangeEvent.getLine(0))); setLine(sign, signChangeEvent, 0, ChatColor.RED + ChatColor.stripColor(signChangeEvent.getLine(0)));
setLine(sign, signChangeEvent, 1, ChatColor.GREEN + ChatColor.stripColor(signChangeEvent.getLine(1))); setLine(sign, signChangeEvent, 1, ChatColor.GREEN + ChatColor.stripColor(signChangeEvent.getLine(1)));
setLine(sign, signChangeEvent, 2, ChatColor.BOLD + ChatColor.stripColor(addedPlayer.getName())); setLine(sign, signChangeEvent, 2, ChatColor.BOLD + ChatColor.stripColor(addedPlayer.getName()));
sign.getPersistentDataContainer().set(Values.playerUUID, PersistentDataType.STRING, addedPlayer.getUniqueId().toString()); sign.getPersistentDataContainer().set(Values.Instance().playerUUID, PersistentDataType.STRING, addedPlayer.getUniqueId().toString());
sign.update(); sign.update();
} }
@ -116,8 +116,8 @@ public class StorageListener implements Listener {
if (storageType.isValidBlockType(event.getBlockPlaced())) { if (storageType.isValidBlockType(event.getBlockPlaced())) {
ItemMeta itemMeta = event.getItemInHand().getItemMeta(); ItemMeta itemMeta = event.getItemInHand().getItemMeta();
if (itemMeta != null) { if (itemMeta != null) {
String playerUUID = itemMeta.getPersistentDataContainer().get(Values.playerUUID, PersistentDataType.STRING); String playerUUID = itemMeta.getPersistentDataContainer().get(Values.Instance().playerUUID, PersistentDataType.STRING);
String storageID = itemMeta.getPersistentDataContainer().get(Values.storageID, PersistentDataType.STRING); String storageID = itemMeta.getPersistentDataContainer().get(Values.Instance().storageID, PersistentDataType.STRING);
if (playerUUID != null && storageID != null) { if (playerUUID != null && storageID != null) {
OfflinePlayer owner = Bukkit.getOfflinePlayer(UUID.fromString(playerUUID)); OfflinePlayer owner = Bukkit.getOfflinePlayer(UUID.fromString(playerUUID));
@ -178,8 +178,8 @@ public class StorageListener implements Listener {
ItemMeta itemMeta = customChest.getItemMeta(); ItemMeta itemMeta = customChest.getItemMeta();
if (itemMeta != null) { if (itemMeta != null) {
itemMeta.setDisplayName(ChatColor.AQUA + "" + storageType.getSignTag() + " " + storage.getIdentifier()); itemMeta.setDisplayName(ChatColor.AQUA + "" + storageType.getSignTag() + " " + storage.getIdentifier());
itemMeta.getPersistentDataContainer().set(Values.playerUUID, PersistentDataType.STRING, storage.getOwner().getUniqueId().toString()); itemMeta.getPersistentDataContainer().set(Values.Instance().playerUUID, PersistentDataType.STRING, storage.getOwner().getUniqueId().toString());
itemMeta.getPersistentDataContainer().set(Values.storageID, PersistentDataType.STRING, storage.getIdentifier()); itemMeta.getPersistentDataContainer().set(Values.Instance().storageID, PersistentDataType.STRING, storage.getIdentifier());
} }
customChest.setItemMeta(itemMeta); customChest.setItemMeta(itemMeta);
block.getWorld().dropItemNaturally(block.getLocation(), customChest); block.getWorld().dropItemNaturally(block.getLocation(), customChest);

View File

@ -6,7 +6,6 @@ import com.jamesdpeters.minecraft.chests.serialize.Config;
import org.bukkit.event.EventHandler; import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener; import org.bukkit.event.Listener;
import org.bukkit.event.world.ChunkLoadEvent; import org.bukkit.event.world.ChunkLoadEvent;
import org.bukkit.event.world.WorldLoadEvent;
import org.bukkit.event.world.WorldSaveEvent; import org.bukkit.event.world.WorldSaveEvent;
import org.bukkit.scheduler.BukkitRunnable; import org.bukkit.scheduler.BukkitRunnable;
@ -28,15 +27,9 @@ public class WorldListener implements Listener {
} }
} }
@EventHandler
public void onWorldLoad(WorldLoadEvent event) {
Utils.removeEntities(event.getWorld());
}
@EventHandler @EventHandler
public void onChunkLoad(ChunkLoadEvent event) { public void onChunkLoad(ChunkLoadEvent event) {
if (!event.isNewChunk()) { if (!event.isNewChunk()) {
Utils.fixEntities(event.getChunk());
Config.getStorageTypes().forEach(storageType -> { Config.getStorageTypes().forEach(storageType -> {
storageType.getStorageMap().values().forEach(stringHashMap -> { storageType.getStorageMap().values().forEach(stringHashMap -> {
stringHashMap.values().forEach(o -> { stringHashMap.values().forEach(o -> {

View File

@ -1,7 +1,7 @@
package com.jamesdpeters.minecraft.chests.misc; package com.jamesdpeters.minecraft.chests.misc;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import org.bstats.bukkit.Metrics; import org.bstats.bukkit.Metrics;
import org.bstats.charts.SimplePie; import org.bstats.charts.SimplePie;

View File

@ -6,7 +6,7 @@ import com.jamesdpeters.minecraft.chests.filters.Filter;
import com.jamesdpeters.minecraft.chests.filters.HopperFilter; import com.jamesdpeters.minecraft.chests.filters.HopperFilter;
import com.jamesdpeters.minecraft.chests.interfaces.VirtualInventoryHolder; import com.jamesdpeters.minecraft.chests.interfaces.VirtualInventoryHolder;
import com.jamesdpeters.minecraft.chests.serialize.LocationInfo; import com.jamesdpeters.minecraft.chests.serialize.LocationInfo;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import com.jamesdpeters.minecraft.chests.storage.chestlink.ChestLinkStorage; import com.jamesdpeters.minecraft.chests.storage.chestlink.ChestLinkStorage;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;
@ -19,14 +19,11 @@ import org.bukkit.World;
import org.bukkit.block.Block; import org.bukkit.block.Block;
import org.bukkit.block.BlockFace; import org.bukkit.block.BlockFace;
import org.bukkit.block.Container; import org.bukkit.block.Container;
import org.bukkit.block.Hopper;
import org.bukkit.entity.Entity; import org.bukkit.entity.Entity;
import org.bukkit.entity.ItemFrame;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.inventory.InventoryType; import org.bukkit.event.inventory.InventoryType;
import org.bukkit.inventory.Inventory; import org.bukkit.inventory.Inventory;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import org.bukkit.persistence.PersistentDataType;
import org.bukkit.util.Vector; import org.bukkit.util.Vector;
import java.io.File; import java.io.File;
@ -40,7 +37,6 @@ import java.util.List;
import java.util.jar.JarEntry; import java.util.jar.JarEntry;
import java.util.jar.JarFile; import java.util.jar.JarFile;
import java.util.stream.Collectors; import java.util.stream.Collectors;
import java.util.stream.Stream;
public class Utils { public class Utils {
@ -232,52 +228,6 @@ public class Utils {
return itemStacks; return itemStacks;
} }
/**
* Removes all entities that contain a value of 1 under the Values.PluginKey key.
* Updates all Item Frames with invisibility status.
*/
public static void fixEntities() {
Bukkit.getServer().getWorlds().forEach(world -> {
removeEntities(world);
setItemFrames(world);
});
}
public static void fixEntities(Chunk chunk) {
removeEntities(chunk);
setItemFrames(chunk);
}
public static void removeEntities(World world) {
world.getEntities().forEach(Utils::removeEntity);
}
public static void removeEntities(Chunk chunk) {
for (Entity entity : chunk.getEntities()) {
removeEntity(entity);
}
}
private static void removeEntity(Entity entity) {
Integer val = entity.getPersistentDataContainer().get(Values.PluginKey, PersistentDataType.INTEGER);
if (val != null && val == 1) entity.remove();
}
public static void setItemFrames(World world) {
setItemFrames(world.getEntities().stream());
}
public static void setItemFrames(Chunk chunk) {
setItemFrames(Arrays.stream(chunk.getEntities()));
}
private static void setItemFrames(Stream<Entity> entityStream) {
entityStream.filter(entity ->
(entity instanceof ItemFrame
&& entity.getLocation().getBlock().getRelative(((ItemFrame) entity).getAttachedFace()).getState() instanceof Hopper))
.forEach(entity -> ApiSpecific.getNmsProvider().setItemFrameVisible((ItemFrame) entity, !PluginConfig.INVISIBLE_FILTER_ITEM_FRAMES.get()));
}
public static List<String> filterList(List<String> list, String phrase) { public static List<String> filterList(List<String> list, String phrase) {
return list.stream().filter(s -> s.contains(phrase)).collect(Collectors.toList()); return list.stream().filter(s -> s.contains(phrase)).collect(Collectors.toList());
} }

View File

@ -1,18 +0,0 @@
package com.jamesdpeters.minecraft.chests.misc;
import com.jamesdpeters.minecraft.chests.ChestsPlusPlus;
import org.bukkit.NamespacedKey;
public class Values {
public final static String ChestLinkTag = "[ChestLink]";
public final static String AutoCraftTag = "[AutoCraft]";
public static String identifier(String identifier) {
return "[" + identifier + "]";
}
public final static NamespacedKey playerUUID = new NamespacedKey(ChestsPlusPlus.PLUGIN, "playerUUID");
public final static NamespacedKey PluginKey = new NamespacedKey(ChestsPlusPlus.PLUGIN, "ChestsPlusPlus");
public final static NamespacedKey storageID = new NamespacedKey(ChestsPlusPlus.PLUGIN, "storageID");
public final static NamespacedKey hopperTicked = new NamespacedKey(ChestsPlusPlus.PLUGIN, "hopperTicked");
}

View File

@ -4,7 +4,7 @@ import com.jamesdpeters.minecraft.chests.ChestsPlusPlus;
import com.jamesdpeters.minecraft.chests.filters.HopperFilter; import com.jamesdpeters.minecraft.chests.filters.HopperFilter;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.serialize.LocationInfo; import com.jamesdpeters.minecraft.chests.serialize.LocationInfo;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import com.jamesdpeters.minecraft.chests.serialize.SpigotConfig; import com.jamesdpeters.minecraft.chests.serialize.SpigotConfig;
import com.jamesdpeters.minecraft.chests.storage.chestlink.ChestLinkStorage; import com.jamesdpeters.minecraft.chests.storage.chestlink.ChestLinkStorage;
import org.bukkit.Location; import org.bukkit.Location;

View File

@ -1,6 +1,6 @@
package com.jamesdpeters.minecraft.chests.storage; package com.jamesdpeters.minecraft.chests.storage;
import com.jamesdpeters.minecraft.chests.misc.Values; import com.jamesdpeters.minecraft.chests.Values;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage; import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage;
import com.jamesdpeters.minecraft.chests.storage.abstracts.StorageInfo; import com.jamesdpeters.minecraft.chests.storage.abstracts.StorageInfo;
@ -24,7 +24,7 @@ public record StorageUtils<T extends StorageInfo<S>, S extends AbstractStorage>(
public StorageInfo<S> getStorageInfo(Sign sign, String[] lines, UUID uuid) { public StorageInfo<S> getStorageInfo(Sign sign, String[] lines, UUID uuid) {
if (lines != null) { if (lines != null) {
if (lines.length >= 2 && lines[0].contains(storageType.getSignTag())) { if (lines.length >= 2 && lines[0].contains(storageType.getSignTag())) {
String playerUUID = sign.getPersistentDataContainer().get(Values.playerUUID, PersistentDataType.STRING); String playerUUID = sign.getPersistentDataContainer().get(Values.Instance().playerUUID, PersistentDataType.STRING);
String group = ChatColor.stripColor(StringUtils.substringBetween(lines[1], "[", "]")); String group = ChatColor.stripColor(StringUtils.substringBetween(lines[1], "[", "]"));
if (playerUUID == null) { if (playerUUID == null) {
if (uuid == null) return null; if (uuid == null) return null;

View File

@ -4,7 +4,7 @@ import com.jamesdpeters.minecraft.chests.ChestsPlusPlus;
import com.jamesdpeters.minecraft.chests.api.ApiSpecific; import com.jamesdpeters.minecraft.chests.api.ApiSpecific;
import com.jamesdpeters.minecraft.chests.misc.Permissions; import com.jamesdpeters.minecraft.chests.misc.Permissions;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.misc.Values; import com.jamesdpeters.minecraft.chests.Values;
import com.jamesdpeters.minecraft.chests.party.PlayerPartyStorage; import com.jamesdpeters.minecraft.chests.party.PlayerPartyStorage;
import com.jamesdpeters.minecraft.chests.serialize.LocationInfo; import com.jamesdpeters.minecraft.chests.serialize.LocationInfo;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
@ -226,9 +226,14 @@ public abstract class AbstractStorage implements ConfigurationSerializable {
* @param location - location to be added. * @param location - location to be added.
*/ */
public void addLocation(Location location, Location signLocation) { public void addLocation(Location location, Location signLocation) {
LocationInfo locationInfo = new LocationInfo(location); LocationInfo locationInfo = getLocationInfo(location);
locationInfo.setSignLocation(signLocation);
if (locationInfo == null){
locationInfo = new LocationInfo(location);
locationInfoList.add(locationInfo); locationInfoList.add(locationInfo);
}
locationInfo.setSignLocation(signLocation);
if (shouldDisplayArmourStands()) { if (shouldDisplayArmourStands()) {
if (displayItem != null) { if (displayItem != null) {
updateSign(); updateSign();
@ -533,7 +538,7 @@ public abstract class AbstractStorage implements ConfigurationSerializable {
stand.setRightArmPose(angle); stand.setRightArmPose(angle);
//Store value of 1 in armour stand to indicate it belongs to this plugin. //Store value of 1 in armour stand to indicate it belongs to this plugin.
stand.getPersistentDataContainer().set(Values.PluginKey, PersistentDataType.INTEGER, 1); stand.getPersistentDataContainer().set(Values.Instance().PluginKey, PersistentDataType.INTEGER, 1);
return stand; return stand;
} }

View File

@ -4,12 +4,12 @@ package com.jamesdpeters.minecraft.chests.storage.abstracts;
import com.jamesdpeters.minecraft.chests.ChestsPlusPlus; import com.jamesdpeters.minecraft.chests.ChestsPlusPlus;
import com.jamesdpeters.minecraft.chests.misc.Messages; import com.jamesdpeters.minecraft.chests.misc.Messages;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.misc.Values; import com.jamesdpeters.minecraft.chests.Values;
import com.jamesdpeters.minecraft.chests.party.PartyUtils; import com.jamesdpeters.minecraft.chests.party.PartyUtils;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage; import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage;
import com.jamesdpeters.minecraft.chests.serialize.LocationInfo; import com.jamesdpeters.minecraft.chests.serialize.LocationInfo;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import com.jamesdpeters.minecraft.chests.storage.StorageUtils; import com.jamesdpeters.minecraft.chests.storage.StorageUtils;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.Chunk; import org.bukkit.Chunk;
@ -219,11 +219,7 @@ public abstract class StorageType<T extends AbstractStorage> implements Listener
T storage = map.get(identifier); T storage = map.get(identifier);
storage.onStorageAdded(chestLocation.getBlock(), player); storage.onStorageAdded(chestLocation.getBlock(), player);
//If the location isn't already part of the system add it.
if (!storage.containsLocation(chestLocation)) {
storage.addLocation(chestLocation, sign); storage.addLocation(chestLocation, sign);
}
player.playSound(player.getLocation(), Sound.ENTITY_PLAYER_LEVELUP, 1.0f, 1f); player.playSound(player.getLocation(), Sound.ENTITY_PLAYER_LEVELUP, 1.0f, 1f);
Config.saveASync(); Config.saveASync();
@ -370,7 +366,7 @@ public abstract class StorageType<T extends AbstractStorage> implements Listener
WallSign signBlockData = (WallSign) sign.getBlockData(); WallSign signBlockData = (WallSign) sign.getBlockData();
signBlockData.setFacing(facing); signBlockData.setFacing(facing);
sign.setBlockData(signBlockData); sign.setBlockData(signBlockData);
sign.getPersistentDataContainer().set(Values.playerUUID, PersistentDataType.STRING, uuid); sign.getPersistentDataContainer().set(Values.Instance().playerUUID, PersistentDataType.STRING, uuid);
sign.update(); sign.update();
BlockPlaceEvent event = new BlockPlaceEvent(sign.getBlock(), replacedBlockState, placedAgainst, new ItemStack(Material.AIR), player, true, EquipmentSlot.HAND); BlockPlaceEvent event = new BlockPlaceEvent(sign.getBlock(), replacedBlockState, placedAgainst, new ItemStack(Material.AIR), player, true, EquipmentSlot.HAND);

View File

@ -2,7 +2,7 @@ package com.jamesdpeters.minecraft.chests.storage.autocraft;
import com.jamesdpeters.minecraft.chests.interfaces.VirtualCraftingHolder; import com.jamesdpeters.minecraft.chests.interfaces.VirtualCraftingHolder;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import com.jamesdpeters.minecraft.chests.serialize.RecipeSerializable; import com.jamesdpeters.minecraft.chests.serialize.RecipeSerializable;
import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage; import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage;
import org.bukkit.Location; import org.bukkit.Location;

View File

@ -4,7 +4,7 @@ import com.jamesdpeters.minecraft.chests.lang.Message;
import com.jamesdpeters.minecraft.chests.misc.Messages; import com.jamesdpeters.minecraft.chests.misc.Messages;
import com.jamesdpeters.minecraft.chests.misc.Permissions; import com.jamesdpeters.minecraft.chests.misc.Permissions;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.misc.Values; import com.jamesdpeters.minecraft.chests.Values;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage; import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage;
import com.jamesdpeters.minecraft.chests.storage.abstracts.StorageInfo; import com.jamesdpeters.minecraft.chests.storage.abstracts.StorageInfo;
@ -54,7 +54,7 @@ public class AutoCraftingStorageType extends StorageType<AutoCraftingStorage> {
@Override @Override
public String getSignTag() { public String getSignTag() {
return Values.AutoCraftTag; return Values.Instance().AutoCraftTag;
} }
@Override @Override
@ -81,7 +81,7 @@ public class AutoCraftingStorageType extends StorageType<AutoCraftingStorage> {
Messages.ALREADY_PART_OF_GROUP(player, "Crafting Table"); Messages.ALREADY_PART_OF_GROUP(player, "Crafting Table");
return; return;
} }
placeSign(block, toReplace, facing, player, owner, identifier, Values.AutoCraftTag, requireSign); placeSign(block, toReplace, facing, player, owner, identifier, Values.Instance().AutoCraftTag, requireSign);
} }
} }

View File

@ -7,7 +7,7 @@ import com.jamesdpeters.minecraft.chests.misc.Messages;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.runnables.VirtualChestToHopper; import com.jamesdpeters.minecraft.chests.runnables.VirtualChestToHopper;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.PluginConfig; import com.jamesdpeters.minecraft.chests.PluginConfig;
import com.jamesdpeters.minecraft.chests.sort.InventorySorter; import com.jamesdpeters.minecraft.chests.sort.InventorySorter;
import com.jamesdpeters.minecraft.chests.sort.SortMethod; import com.jamesdpeters.minecraft.chests.sort.SortMethod;
import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage; import com.jamesdpeters.minecraft.chests.storage.abstracts.AbstractStorage;

View File

@ -4,7 +4,7 @@ import com.jamesdpeters.minecraft.chests.lang.Message;
import com.jamesdpeters.minecraft.chests.misc.Messages; import com.jamesdpeters.minecraft.chests.misc.Messages;
import com.jamesdpeters.minecraft.chests.misc.Permissions; import com.jamesdpeters.minecraft.chests.misc.Permissions;
import com.jamesdpeters.minecraft.chests.misc.Utils; import com.jamesdpeters.minecraft.chests.misc.Utils;
import com.jamesdpeters.minecraft.chests.misc.Values; import com.jamesdpeters.minecraft.chests.Values;
import com.jamesdpeters.minecraft.chests.runnables.ChestLinkVerifier; import com.jamesdpeters.minecraft.chests.runnables.ChestLinkVerifier;
import com.jamesdpeters.minecraft.chests.serialize.Config; import com.jamesdpeters.minecraft.chests.serialize.Config;
import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage; import com.jamesdpeters.minecraft.chests.serialize.ConfigStorage;
@ -91,7 +91,7 @@ public class ChestLinkStorageType extends StorageType<ChestLinkStorage> {
@Override @Override
public String getSignTag() { public String getSignTag() {
return Values.ChestLinkTag; return Values.Instance().ChestLinkTag;
} }

View File

@ -1,4 +1,4 @@
# Chests++ Language File (Version 2.5-Release) # Chests++ Language File (Version 2.5.1-Release)
# NOTE: This file gets replaced when the plugin launches! If you want to make modifications create a copy first! # NOTE: This file gets replaced when the plugin launches! If you want to make modifications create a copy first!
# To create a new language file simply create a copy of this file and rename it to your desired choice for example 'en_US.properties' # To create a new language file simply create a copy of this file and rename it to your desired choice for example 'en_US.properties'
# It should be located in the 'lang' folder # It should be located in the 'lang' folder