package hdvtdev.blockAndSeek.managers; import hdvtdev.blockAndSeek.Keys; import me.libraryaddict.disguise.DisguiseAPI; import me.libraryaddict.disguise.disguisetypes.Disguise; import me.libraryaddict.disguise.disguisetypes.DisguiseType; import me.libraryaddict.disguise.disguisetypes.MiscDisguise; import org.bukkit.Location; import org.bukkit.block.Block; import org.bukkit.block.data.BlockData; import org.bukkit.entity.ArmorStand; import org.bukkit.entity.Player; import org.bukkit.persistence.PersistentDataType; import org.bukkit.util.Vector; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; public class FreezeManager { private static final Map frozenPlayers = new ConcurrentHashMap<>(); private static final Map playerDisguise = new ConcurrentHashMap<>(); private static final Map disguisePlayer = new ConcurrentHashMap<>(); private static final Disguise hideDisguise = new MiscDisguise(DisguiseType.LLAMA_SPIT); private static final Vector zeroVelocity = new Vector(0, 0, 0); public static void addPlayerDisguise(Player player, BlockData blockData) { disguisePlayer.put(blockData, player); playerDisguise.put(player, blockData); } public static void removePlayerDisguise(Player player) { disguisePlayer.remove(playerDisguise.remove(player)); } public static void unfreezeIfFrozen(Player player) { Location location = player.getLocation(); FreezeData data = frozenPlayers.remove(player); if (data != null) { unfreeze(player, location, data); } } public static boolean unfreeze(BlockData blockData) { Player player = disguisePlayer.get(blockData); if (player != null) { freeze(player); return true; } else return false; } private static void unfreeze(Player player, Location location, FreezeData data) { Location blockLocation = location.getBlock().getLocation(); location.getWorld().setBlockData(blockLocation, data.blockData); player.getPersistentDataContainer().remove(Keys.FROZEN_PLAYER); player.setFreezeTicks(0); data.armorStand.remove(); player.setInvulnerable(false); Keys.NO_COLLIDE_TEAM.removeEntry(player.getName()); if (data.disguise != null) DisguiseAPI.disguiseToAll(player, data.disguise); } public static boolean freeze(Player player) { Location location = player.getLocation(); FreezeData data = frozenPlayers.remove(player); if (data != null) { unfreeze(player, location, data); } else { Block block = location.getBlock(); BlockData blockData = block.getBlockData(); Location blockLocation = block.getLocation(); Location centerLocation = blockLocation.toCenterLocation(); Location upperBlockLocation = centerLocation.clone(); upperBlockLocation.setY(upperBlockLocation.getY() + 0.25); if (!upperBlockLocation.getBlock().isSolid() && !blockLocation.getBlock().isSolid()) { location.getWorld().setBlockData(blockLocation, playerDisguise.get(player)); centerLocation.setY(centerLocation.getY() - 0.85); player.setVelocity(zeroVelocity); player.setInvulnerable(true); player.getPersistentDataContainer().set(Keys.FROZEN_PLAYER, PersistentDataType.BOOLEAN, true); Keys.NO_COLLIDE_TEAM.addEntry(player.getName()); ArmorStand armorStand = location.getWorld().spawn(centerLocation, ArmorStand.class, stand -> { stand.setVisible(false); stand.setVisible(false); stand.setCollidable(false); stand.setGravity(true); stand.setSmall(true); stand.setCanMove(false); stand.addPassenger(player); stand.getPersistentDataContainer().set(Keys.FROZEN_PLAYER, PersistentDataType.BOOLEAN, true); stand.setInvulnerable(true); }); Disguise disguise = DisguiseAPI.getDisguise(player); DisguiseAPI.disguiseToAll(player, hideDisguise); player.setFreezeTicks(40); frozenPlayers.put(player, new FreezeData(armorStand, blockData, disguise)); } else return false; } return true; } private record FreezeData(ArmorStand armorStand, BlockData blockData, Disguise disguise) { } }