mirror of
				https://github.com/IntellectualSites/PlotSquared.git
				synced 2025-11-03 10:43:45 +01:00 
			
		
		
		
	And don't add the Core/ code into Bukkit/ code
This commit is contained in:
		@@ -1,224 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.api;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.file.YamlConfiguration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flag;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ChunkManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.SchematicHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.block.GlobalBlockQueue;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.uuid.UUIDWrapper;
 | 
			
		||||
import lombok.NoArgsConstructor;
 | 
			
		||||
 | 
			
		||||
import java.util.Collections;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * PlotSquared API.
 | 
			
		||||
 *
 | 
			
		||||
 * <p>Useful classes:
 | 
			
		||||
 * <ul>
 | 
			
		||||
 * <li>{@link PlotPlayer}</li>
 | 
			
		||||
 * <li>{@link Plot}</li>
 | 
			
		||||
 * <li>{@link com.github.intellectualsites.plotsquared.plot.object.Location}</li>
 | 
			
		||||
 * <li>{@link PlotArea}</li>
 | 
			
		||||
 * <li>{@link PlotSquared}</li>
 | 
			
		||||
 * </ul>
 | 
			
		||||
 *
 | 
			
		||||
 * @version 3.3.3
 | 
			
		||||
 */
 | 
			
		||||
@SuppressWarnings({"unused", "WeakerAccess"}) @NoArgsConstructor public class PlotAPI {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get all plots.
 | 
			
		||||
     *
 | 
			
		||||
     * @return all plots
 | 
			
		||||
     * @see PlotSquared#getPlots()
 | 
			
		||||
     */
 | 
			
		||||
    public Set<Plot> getAllPlots() {
 | 
			
		||||
        return PlotSquared.get().getPlots();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Return all plots for a player.
 | 
			
		||||
     *
 | 
			
		||||
     * @param player Player, whose plots to search for
 | 
			
		||||
     * @return all plots that a player owns
 | 
			
		||||
     */
 | 
			
		||||
    public Set<Plot> getPlayerPlots(PlotPlayer player) {
 | 
			
		||||
        return PlotSquared.get().getPlots(player);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Add a plot world.
 | 
			
		||||
     *
 | 
			
		||||
     * @param plotArea Plot World Object
 | 
			
		||||
     * @see PlotSquared#addPlotArea(PlotArea)
 | 
			
		||||
     */
 | 
			
		||||
    public void addPlotArea(PlotArea plotArea) {
 | 
			
		||||
        PlotSquared.get().addPlotArea(plotArea);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Returns the PlotSquared configurations file.
 | 
			
		||||
     *
 | 
			
		||||
     * @return main configuration
 | 
			
		||||
     * @see PlotSquared#config
 | 
			
		||||
     */
 | 
			
		||||
    public YamlConfiguration getConfig() {
 | 
			
		||||
        return PlotSquared.get().config;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the PlotSquared storage file.
 | 
			
		||||
     *
 | 
			
		||||
     * @return storage configuration
 | 
			
		||||
     * @see PlotSquared#storage
 | 
			
		||||
     */
 | 
			
		||||
    public YamlConfiguration getStorage() {
 | 
			
		||||
        return PlotSquared.get().storage;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the main class for this plugin. Only use this if you really need it.
 | 
			
		||||
     *
 | 
			
		||||
     * @return PlotSquared PlotSquared Main Class
 | 
			
		||||
     * @see PlotSquared
 | 
			
		||||
     */
 | 
			
		||||
    public PlotSquared getMain() {
 | 
			
		||||
        return PlotSquared.get();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * ChunkManager class contains several useful methods.
 | 
			
		||||
     * <ul>
 | 
			
		||||
     * <li>Chunk deletion</li>
 | 
			
		||||
     * <li>Moving or copying regions</li>
 | 
			
		||||
     * <li>Plot swapping</li>
 | 
			
		||||
     * <li>Entity Tracking</li>
 | 
			
		||||
     * <li>Region Regeneration</li>
 | 
			
		||||
     * </ul>
 | 
			
		||||
     *
 | 
			
		||||
     * @return ChunkManager
 | 
			
		||||
     * @see ChunkManager
 | 
			
		||||
     */
 | 
			
		||||
    public ChunkManager getChunkManager() {
 | 
			
		||||
        return ChunkManager.manager;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the block/biome set queue
 | 
			
		||||
     *
 | 
			
		||||
     * @return GlobalBlockQueue.IMP
 | 
			
		||||
     */
 | 
			
		||||
    public GlobalBlockQueue getBlockQueue() {
 | 
			
		||||
        return GlobalBlockQueue.IMP;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * UUIDWrapper class has basic methods for getting UUIDS. It's recommended
 | 
			
		||||
     * to use the UUIDHandler class instead.
 | 
			
		||||
     *
 | 
			
		||||
     * @return UUIDWrapper
 | 
			
		||||
     * @see UUIDWrapper
 | 
			
		||||
     */
 | 
			
		||||
    public UUIDWrapper getUUIDWrapper() {
 | 
			
		||||
        return UUIDHandler.getUUIDWrapper();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * SchematicHandler class contains methods related to pasting, reading
 | 
			
		||||
     * and writing schematics.
 | 
			
		||||
     *
 | 
			
		||||
     * @return SchematicHandler
 | 
			
		||||
     * @see SchematicHandler
 | 
			
		||||
     */
 | 
			
		||||
    public SchematicHandler getSchematicHandler() {
 | 
			
		||||
        return SchematicHandler.manager;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get a list of PlotAreas in the world.
 | 
			
		||||
     *
 | 
			
		||||
     * @param world The world to check for plot areas
 | 
			
		||||
     * @return A set of PlotAreas
 | 
			
		||||
     */
 | 
			
		||||
    public Set<PlotArea> getPlotAreas(String world) {
 | 
			
		||||
        if (world == null) {
 | 
			
		||||
            return Collections.emptySet();
 | 
			
		||||
        }
 | 
			
		||||
        return PlotSquared.get().getPlotAreas(world);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Send a message to the console. The message supports color codes.
 | 
			
		||||
     *
 | 
			
		||||
     * @param message the message
 | 
			
		||||
     * @see MainUtil#sendConsoleMessage(C, String...)
 | 
			
		||||
     */
 | 
			
		||||
    public void sendConsoleMessage(String message) {
 | 
			
		||||
        PlotSquared.log(message);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Send a message to the console.
 | 
			
		||||
     *
 | 
			
		||||
     * @param caption the message
 | 
			
		||||
     * @see #sendConsoleMessage(String)
 | 
			
		||||
     * @see C
 | 
			
		||||
     */
 | 
			
		||||
    public void sendConsoleMessage(C caption) {
 | 
			
		||||
        sendConsoleMessage(caption.s());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Registers a flag for use in plots.
 | 
			
		||||
     *
 | 
			
		||||
     * @param flag the flag to register
 | 
			
		||||
     */
 | 
			
		||||
    public void addFlag(Flag<?> flag) {
 | 
			
		||||
        Flags.registerFlag(flag);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the PlotSquared class.
 | 
			
		||||
     *
 | 
			
		||||
     * @return PlotSquared Class
 | 
			
		||||
     * @see PlotSquared
 | 
			
		||||
     */
 | 
			
		||||
    public PlotSquared getPlotSquared() {
 | 
			
		||||
        return PlotSquared.get();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the PlotPlayer for a UUID.
 | 
			
		||||
     *
 | 
			
		||||
     * <p><i>Please note that PlotSquared can be configured to provide
 | 
			
		||||
     * different UUIDs than bukkit</i>
 | 
			
		||||
     *
 | 
			
		||||
     * @param uuid the uuid of the player to wrap
 | 
			
		||||
     * @return a {@code PlotPlayer}
 | 
			
		||||
     * @see PlotPlayer#wrap(Object)
 | 
			
		||||
     */
 | 
			
		||||
    public PlotPlayer wrapPlayer(UUID uuid) {
 | 
			
		||||
        return PlotPlayer.wrap(uuid);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the PlotPlayer for a username.
 | 
			
		||||
     *
 | 
			
		||||
     * @param player the player to wrap
 | 
			
		||||
     * @return a {@code PlotPlayer}
 | 
			
		||||
     * @see PlotPlayer#wrap(Object)
 | 
			
		||||
     */
 | 
			
		||||
    public PlotPlayer wrapPlayer(String player) {
 | 
			
		||||
        return PlotPlayer.wrap(player);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,36 +1,11 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.bukkit;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.generator.BukkitPlotGenerator;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.ChunkListener;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.EntitySpawnListener;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.PlayerEvents;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.PlotPlusListener;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.SingleWorldListener;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.WorldEvents;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.listeners.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.titles.DefaultTitle_111;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitBlockRegistry;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitChatManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitChunkManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitCommand;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitEconHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitEventUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitHybridUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitInventoryUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitLegacyMappings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitSchematicHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitSetupUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitTaskManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.BukkitUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.SendChunk;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.SetGenCB;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.util.block.BukkitLocalQueue;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.uuid.DefaultUUIDWrapper;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.uuid.FileUUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.uuid.LowerOfflineUUIDWrapper;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.uuid.OfflineUUIDWrapper;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.uuid.SQLUUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.uuid.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.ConfigurationSection;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.IPlotMain;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
@@ -41,57 +16,22 @@ import com.github.intellectualsites.plotsquared.plot.generator.GeneratorWrapper;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridGen;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.IndependentPlotGenerator;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.BlockRegistry;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotId;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.SetupObject;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.chat.PlainChatManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.PlotAreaManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SinglePlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SinglePlotAreaManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SingleWorldGenerator;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.AbstractTitle;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ChatManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ChunkManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ConsoleColors;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EconHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EventUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.InventoryUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.LegacyMappings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.SchematicHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.SetupUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandlerImplementation;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.block.QueueProvider;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.uuid.UUIDWrapper;
 | 
			
		||||
import com.sk89q.worldedit.WorldEdit;
 | 
			
		||||
import com.sk89q.worldedit.bukkit.WorldEditPlugin;
 | 
			
		||||
import com.sk89q.worldedit.extension.platform.Capability;
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.Iterator;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
import javax.annotation.Nullable;
 | 
			
		||||
import lombok.Getter;
 | 
			
		||||
import lombok.NonNull;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.ChatColor;
 | 
			
		||||
import org.bukkit.Chunk;
 | 
			
		||||
import org.bukkit.*;
 | 
			
		||||
import org.bukkit.Location;
 | 
			
		||||
import org.bukkit.Material;
 | 
			
		||||
import org.bukkit.OfflinePlayer;
 | 
			
		||||
import org.bukkit.World;
 | 
			
		||||
import org.bukkit.command.PluginCommand;
 | 
			
		||||
import org.bukkit.entity.Entity;
 | 
			
		||||
import org.bukkit.entity.LivingEntity;
 | 
			
		||||
@@ -104,6 +44,13 @@ import org.bukkit.plugin.Plugin;
 | 
			
		||||
import org.bukkit.plugin.PluginManager;
 | 
			
		||||
import org.bukkit.plugin.java.JavaPlugin;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nullable;
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.util.*;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
public final class BukkitMain extends JavaPlugin implements Listener, IPlotMain {
 | 
			
		||||
 | 
			
		||||
    @Getter private static WorldEdit worldEdit;
 | 
			
		||||
@@ -319,8 +266,7 @@ public final class BukkitMain extends JavaPlugin implements Listener, IPlotMain
 | 
			
		||||
        return getDescription().getVersion();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override
 | 
			
		||||
    public String getPluginName() {
 | 
			
		||||
    @Override public String getPluginName() {
 | 
			
		||||
        return pluginName;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -5,7 +5,10 @@ import com.google.gson.JsonElement;
 | 
			
		||||
import com.google.gson.JsonObject;
 | 
			
		||||
import com.google.gson.JsonParser;
 | 
			
		||||
import com.google.gson.stream.JsonWriter;
 | 
			
		||||
import org.bukkit.*;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.ChatColor;
 | 
			
		||||
import org.bukkit.Material;
 | 
			
		||||
import org.bukkit.Statistic;
 | 
			
		||||
import org.bukkit.Statistic.Type;
 | 
			
		||||
import org.bukkit.command.CommandSender;
 | 
			
		||||
import org.bukkit.configuration.serialization.ConfigurationSerializable;
 | 
			
		||||
 
 | 
			
		||||
@@ -1,7 +1,5 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.bukkit.listeners;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
@@ -11,8 +9,6 @@ import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.RefCla
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.RefField;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.RefMethod;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.util.HashSet;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.Chunk;
 | 
			
		||||
import org.bukkit.Material;
 | 
			
		||||
@@ -31,8 +27,12 @@ import org.bukkit.event.entity.ItemSpawnEvent;
 | 
			
		||||
import org.bukkit.event.world.ChunkLoadEvent;
 | 
			
		||||
import org.bukkit.event.world.ChunkUnloadEvent;
 | 
			
		||||
 | 
			
		||||
@SuppressWarnings("unused")
 | 
			
		||||
public class ChunkListener implements Listener {
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.util.HashSet;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
@SuppressWarnings("unused") public class ChunkListener implements Listener {
 | 
			
		||||
 | 
			
		||||
    private RefMethod methodGetHandleChunk;
 | 
			
		||||
    private RefField mustSave;
 | 
			
		||||
@@ -48,7 +48,7 @@ public class ChunkListener implements Listener {
 | 
			
		||||
                this.methodGetHandleChunk = classCraftChunk.getMethod("getHandle");
 | 
			
		||||
            } catch (Throwable ignored) {
 | 
			
		||||
                PlotSquared.debug(PlotSquared.get().IMP.getPluginName()
 | 
			
		||||
                        + "/Server not compatible for chunk processor trim/gc");
 | 
			
		||||
                    + "/Server not compatible for chunk processor trim/gc");
 | 
			
		||||
 | 
			
		||||
                Settings.Chunk_Processor.AUTO_TRIM = false;
 | 
			
		||||
            }
 | 
			
		||||
@@ -68,10 +68,9 @@ public class ChunkListener implements Listener {
 | 
			
		||||
                        continue;
 | 
			
		||||
                    }
 | 
			
		||||
                    Object w = world.getClass().getDeclaredMethod("getHandle").invoke(world);
 | 
			
		||||
                    Object chunkMap =
 | 
			
		||||
                        w.getClass().getDeclaredMethod("getPlayerChunkMap").invoke(w);
 | 
			
		||||
                    Method methodIsChunkInUse = chunkMap.getClass()
 | 
			
		||||
                        .getDeclaredMethod("isChunkInUse", int.class, int.class);
 | 
			
		||||
                    Object chunkMap = w.getClass().getDeclaredMethod("getPlayerChunkMap").invoke(w);
 | 
			
		||||
                    Method methodIsChunkInUse =
 | 
			
		||||
                        chunkMap.getClass().getDeclaredMethod("isChunkInUse", int.class, int.class);
 | 
			
		||||
                    Chunk[] chunks = world.getLoadedChunks();
 | 
			
		||||
                    for (Chunk chunk : chunks) {
 | 
			
		||||
                        if ((boolean) methodIsChunkInUse
 | 
			
		||||
@@ -145,8 +144,7 @@ public class ChunkListener implements Listener {
 | 
			
		||||
        return plot != null && plot.hasOwner();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onChunkUnload(ChunkUnloadEvent event) {
 | 
			
		||||
    @EventHandler public void onChunkUnload(ChunkUnloadEvent event) {
 | 
			
		||||
        if (ignoreUnload) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
@@ -164,13 +162,11 @@ public class ChunkListener implements Listener {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onChunkLoad(ChunkLoadEvent event) {
 | 
			
		||||
    @EventHandler public void onChunkLoad(ChunkLoadEvent event) {
 | 
			
		||||
        processChunk(event.getChunk(), false);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler(priority = EventPriority.LOWEST)
 | 
			
		||||
    public void onItemSpawn(ItemSpawnEvent event) {
 | 
			
		||||
    @EventHandler(priority = EventPriority.LOWEST) public void onItemSpawn(ItemSpawnEvent event) {
 | 
			
		||||
        Item entity = event.getEntity();
 | 
			
		||||
        Chunk chunk = entity.getLocation().getChunk();
 | 
			
		||||
        if (chunk == this.lastChunk) {
 | 
			
		||||
@@ -227,8 +223,7 @@ public class ChunkListener implements Listener {
 | 
			
		||||
            if (!chunk.isLoaded()) {
 | 
			
		||||
                Bukkit.getScheduler().cancelTask(TaskManager.tasks.get(currentIndex));
 | 
			
		||||
                TaskManager.tasks.remove(currentIndex);
 | 
			
		||||
                PlotSquared
 | 
			
		||||
                        .debug(C.PREFIX.s() + "&aSuccessfully processed and unloaded chunk!");
 | 
			
		||||
                PlotSquared.debug(C.PREFIX.s() + "&aSuccessfully processed and unloaded chunk!");
 | 
			
		||||
                chunk.unload(true, true);
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
@@ -236,8 +231,7 @@ public class ChunkListener implements Listener {
 | 
			
		||||
            if (tiles.length == 0) {
 | 
			
		||||
                Bukkit.getScheduler().cancelTask(TaskManager.tasks.get(currentIndex));
 | 
			
		||||
                TaskManager.tasks.remove(currentIndex);
 | 
			
		||||
                PlotSquared
 | 
			
		||||
                    .debug(C.PREFIX.s() + "&aSuccessfully processed and unloaded chunk!");
 | 
			
		||||
                PlotSquared.debug(C.PREFIX.s() + "&aSuccessfully processed and unloaded chunk!");
 | 
			
		||||
                chunk.unload(true, true);
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
@@ -272,14 +266,14 @@ public class ChunkListener implements Listener {
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            PlotSquared.debug(
 | 
			
		||||
                    C.PREFIX.s() + "&a detected unsafe chunk and processed: " + (chunk.getX() << 4)
 | 
			
		||||
                            + "," + (chunk.getX() << 4));
 | 
			
		||||
                C.PREFIX.s() + "&a detected unsafe chunk and processed: " + (chunk.getX() << 4)
 | 
			
		||||
                    + "," + (chunk.getX() << 4));
 | 
			
		||||
        }
 | 
			
		||||
        if (tiles.length > Settings.Chunk_Processor.MAX_TILES) {
 | 
			
		||||
            if (unload) {
 | 
			
		||||
                PlotSquared.debug(
 | 
			
		||||
                        C.PREFIX.s() + "&c detected unsafe chunk: " + (chunk.getX() << 4) + "," + (
 | 
			
		||||
                                chunk.getX() << 4));
 | 
			
		||||
                    C.PREFIX.s() + "&c detected unsafe chunk: " + (chunk.getX() << 4) + "," + (
 | 
			
		||||
                        chunk.getX() << 4));
 | 
			
		||||
                cleanChunk(chunk);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
 
 | 
			
		||||
@@ -16,90 +16,89 @@ import java.util.HashSet;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@SuppressWarnings("unused")
 | 
			
		||||
public class ForceFieldListener {
 | 
			
		||||
@SuppressWarnings("unused") public class ForceFieldListener {
 | 
			
		||||
 | 
			
		||||
  private static Set<PlotPlayer> getNearbyPlayers(Player player, Plot plot) {
 | 
			
		||||
    Set<PlotPlayer> players = new HashSet<>();
 | 
			
		||||
    for (Player nearPlayer : Iterables
 | 
			
		||||
        .filter(player.getNearbyEntities(5d, 5d, 5d), Player.class)) {
 | 
			
		||||
      PlotPlayer plotPlayer;
 | 
			
		||||
      if ((plotPlayer = BukkitUtil.getPlayer(nearPlayer)) == null || !plot
 | 
			
		||||
          .equals(plotPlayer.getCurrentPlot())) {
 | 
			
		||||
        continue;
 | 
			
		||||
      }
 | 
			
		||||
      if (!plot.isAdded(plotPlayer.getUUID())) {
 | 
			
		||||
        players.add(plotPlayer);
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
    return players;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private static PlotPlayer hasNearbyPermitted(Player player, Plot plot) {
 | 
			
		||||
    for (Player nearPlayer : Iterables
 | 
			
		||||
        .filter(player.getNearbyEntities(5d, 5d, 5d), Player.class)) {
 | 
			
		||||
      PlotPlayer plotPlayer;
 | 
			
		||||
      if ((plotPlayer = BukkitUtil.getPlayer(nearPlayer)) == null || !plot
 | 
			
		||||
          .equals(plotPlayer.getCurrentPlot())) {
 | 
			
		||||
        continue;
 | 
			
		||||
      }
 | 
			
		||||
      if (plot.isAdded(plotPlayer.getUUID())) {
 | 
			
		||||
        return plotPlayer;
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
    return null;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  private static Vector calculateVelocity(PlotPlayer player, PlotPlayer e) {
 | 
			
		||||
    Location playerLocation = player.getLocationFull();
 | 
			
		||||
    Location oPlayerLocation = e.getLocation();
 | 
			
		||||
    double playerX = playerLocation.getX();
 | 
			
		||||
    double playerY = playerLocation.getY();
 | 
			
		||||
    double playerZ = playerLocation.getZ();
 | 
			
		||||
    double oPlayerX = oPlayerLocation.getX();
 | 
			
		||||
    double oPlayerY = oPlayerLocation.getY();
 | 
			
		||||
    double oPlayerZ = oPlayerLocation.getZ();
 | 
			
		||||
    double x = 0d;
 | 
			
		||||
    if (playerX < oPlayerX) {
 | 
			
		||||
      x = 1.0d;
 | 
			
		||||
    } else if (playerX > oPlayerX) {
 | 
			
		||||
      x = -1.0d;
 | 
			
		||||
    }
 | 
			
		||||
    double y = 0d;
 | 
			
		||||
    if (playerY < oPlayerY) {
 | 
			
		||||
      y = 0.5d;
 | 
			
		||||
    } else if (playerY > oPlayerY) {
 | 
			
		||||
      y = -0.5d;
 | 
			
		||||
    }
 | 
			
		||||
    double z = 0d;
 | 
			
		||||
    if (playerZ < oPlayerZ) {
 | 
			
		||||
      z = 1.0d;
 | 
			
		||||
    } else if (playerZ > oPlayerZ) {
 | 
			
		||||
      z = -1.0d;
 | 
			
		||||
    }
 | 
			
		||||
    return new Vector(x, y, z);
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public static void handleForcefield(Player player, PlotPlayer plotPlayer, Plot plot) {
 | 
			
		||||
    if (Flags.FORCEFIELD.isTrue(plot)) {
 | 
			
		||||
      UUID uuid = plotPlayer.getUUID();
 | 
			
		||||
      if (plot.isAdded(uuid)) {
 | 
			
		||||
        Set<PlotPlayer> players = getNearbyPlayers(player, plot);
 | 
			
		||||
        for (PlotPlayer oPlayer : players) {
 | 
			
		||||
          if (!Permissions.hasPermission(oPlayer, C.PERMISSION_ADMIN_ENTRY_FORCEFIELD)) {
 | 
			
		||||
            ((BukkitPlayer) oPlayer).player
 | 
			
		||||
                .setVelocity(calculateVelocity(plotPlayer, oPlayer));
 | 
			
		||||
          }
 | 
			
		||||
    private static Set<PlotPlayer> getNearbyPlayers(Player player, Plot plot) {
 | 
			
		||||
        Set<PlotPlayer> players = new HashSet<>();
 | 
			
		||||
        for (Player nearPlayer : Iterables
 | 
			
		||||
            .filter(player.getNearbyEntities(5d, 5d, 5d), Player.class)) {
 | 
			
		||||
            PlotPlayer plotPlayer;
 | 
			
		||||
            if ((plotPlayer = BukkitUtil.getPlayer(nearPlayer)) == null || !plot
 | 
			
		||||
                .equals(plotPlayer.getCurrentPlot())) {
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            if (!plot.isAdded(plotPlayer.getUUID())) {
 | 
			
		||||
                players.add(plotPlayer);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return players;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private static PlotPlayer hasNearbyPermitted(Player player, Plot plot) {
 | 
			
		||||
        for (Player nearPlayer : Iterables
 | 
			
		||||
            .filter(player.getNearbyEntities(5d, 5d, 5d), Player.class)) {
 | 
			
		||||
            PlotPlayer plotPlayer;
 | 
			
		||||
            if ((plotPlayer = BukkitUtil.getPlayer(nearPlayer)) == null || !plot
 | 
			
		||||
                .equals(plotPlayer.getCurrentPlot())) {
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            if (plot.isAdded(plotPlayer.getUUID())) {
 | 
			
		||||
                return plotPlayer;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private static Vector calculateVelocity(PlotPlayer player, PlotPlayer e) {
 | 
			
		||||
        Location playerLocation = player.getLocationFull();
 | 
			
		||||
        Location oPlayerLocation = e.getLocation();
 | 
			
		||||
        double playerX = playerLocation.getX();
 | 
			
		||||
        double playerY = playerLocation.getY();
 | 
			
		||||
        double playerZ = playerLocation.getZ();
 | 
			
		||||
        double oPlayerX = oPlayerLocation.getX();
 | 
			
		||||
        double oPlayerY = oPlayerLocation.getY();
 | 
			
		||||
        double oPlayerZ = oPlayerLocation.getZ();
 | 
			
		||||
        double x = 0d;
 | 
			
		||||
        if (playerX < oPlayerX) {
 | 
			
		||||
            x = 1.0d;
 | 
			
		||||
        } else if (playerX > oPlayerX) {
 | 
			
		||||
            x = -1.0d;
 | 
			
		||||
        }
 | 
			
		||||
        double y = 0d;
 | 
			
		||||
        if (playerY < oPlayerY) {
 | 
			
		||||
            y = 0.5d;
 | 
			
		||||
        } else if (playerY > oPlayerY) {
 | 
			
		||||
            y = -0.5d;
 | 
			
		||||
        }
 | 
			
		||||
        double z = 0d;
 | 
			
		||||
        if (playerZ < oPlayerZ) {
 | 
			
		||||
            z = 1.0d;
 | 
			
		||||
        } else if (playerZ > oPlayerZ) {
 | 
			
		||||
            z = -1.0d;
 | 
			
		||||
        }
 | 
			
		||||
        return new Vector(x, y, z);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static void handleForcefield(Player player, PlotPlayer plotPlayer, Plot plot) {
 | 
			
		||||
        if (Flags.FORCEFIELD.isTrue(plot)) {
 | 
			
		||||
            UUID uuid = plotPlayer.getUUID();
 | 
			
		||||
            if (plot.isAdded(uuid)) {
 | 
			
		||||
                Set<PlotPlayer> players = getNearbyPlayers(player, plot);
 | 
			
		||||
                for (PlotPlayer oPlayer : players) {
 | 
			
		||||
                    if (!Permissions.hasPermission(oPlayer, C.PERMISSION_ADMIN_ENTRY_FORCEFIELD)) {
 | 
			
		||||
                        ((BukkitPlayer) oPlayer).player
 | 
			
		||||
                            .setVelocity(calculateVelocity(plotPlayer, oPlayer));
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            } else {
 | 
			
		||||
                PlotPlayer oPlayer = hasNearbyPermitted(player, plot);
 | 
			
		||||
                if (oPlayer == null) {
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                if (!Permissions.hasPermission(plotPlayer, C.PERMISSION_ADMIN_ENTRY_FORCEFIELD)) {
 | 
			
		||||
                    player.setVelocity(calculateVelocity(oPlayer, plotPlayer));
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
      } else {
 | 
			
		||||
        PlotPlayer oPlayer = hasNearbyPermitted(player, plot);
 | 
			
		||||
        if (oPlayer == null) {
 | 
			
		||||
          return;
 | 
			
		||||
        }
 | 
			
		||||
        if (!Permissions.hasPermission(plotPlayer, C.PERMISSION_ADMIN_ENTRY_FORCEFIELD)) {
 | 
			
		||||
          player.setVelocity(calculateVelocity(oPlayer, plotPlayer));
 | 
			
		||||
        }
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							@@ -31,8 +31,7 @@ import java.util.Map.Entry;
 | 
			
		||||
import java.util.Optional;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@SuppressWarnings("unused")
 | 
			
		||||
public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
@SuppressWarnings("unused") public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
 | 
			
		||||
    private static final HashMap<UUID, Interval> feedRunnable = new HashMap<>();
 | 
			
		||||
    private static final HashMap<UUID, Interval> healRunnable = new HashMap<>();
 | 
			
		||||
@@ -82,8 +81,7 @@ public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
        }, 0L, 20L);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler(priority = EventPriority.HIGH)
 | 
			
		||||
    public void onInteract(BlockDamageEvent event) {
 | 
			
		||||
    @EventHandler(priority = EventPriority.HIGH) public void onInteract(BlockDamageEvent event) {
 | 
			
		||||
        Player player = event.getPlayer();
 | 
			
		||||
        if (player.getGameMode() != GameMode.SURVIVAL) {
 | 
			
		||||
            return;
 | 
			
		||||
@@ -102,8 +100,7 @@ public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler(priority = EventPriority.HIGH)
 | 
			
		||||
    public void onDamage(EntityDamageEvent event) {
 | 
			
		||||
    @EventHandler(priority = EventPriority.HIGH) public void onDamage(EntityDamageEvent event) {
 | 
			
		||||
        if (event.getEntityType() != EntityType.PLAYER) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
@@ -117,8 +114,7 @@ public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onItemDrop(PlayerDropItemEvent event) {
 | 
			
		||||
    @EventHandler public void onItemDrop(PlayerDropItemEvent event) {
 | 
			
		||||
        Player player = event.getPlayer();
 | 
			
		||||
        PlotPlayer pp = BukkitUtil.getPlayer(player);
 | 
			
		||||
        Plot plot = BukkitUtil.getLocation(player).getOwnedPlot();
 | 
			
		||||
@@ -133,27 +129,24 @@ public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onPlotEnter(PlayerEnterPlotEvent event) {
 | 
			
		||||
    @EventHandler public void onPlotEnter(PlayerEnterPlotEvent event) {
 | 
			
		||||
        Player player = event.getPlayer();
 | 
			
		||||
        Plot plot = event.getPlot();
 | 
			
		||||
        Optional<Integer[]> feed = plot.getFlag(Flags.FEED);
 | 
			
		||||
        feed.ifPresent( value -> feedRunnable.put(player.getUniqueId(), new Interval(value[0], value[1], 20))
 | 
			
		||||
        );
 | 
			
		||||
        feed.ifPresent(
 | 
			
		||||
            value -> feedRunnable.put(player.getUniqueId(), new Interval(value[0], value[1], 20)));
 | 
			
		||||
        Optional<Integer[]> heal = plot.getFlag(Flags.HEAL);
 | 
			
		||||
        heal.ifPresent( value -> healRunnable.put(player.getUniqueId(), new Interval(value[0], value[1], 20))
 | 
			
		||||
        );
 | 
			
		||||
        heal.ifPresent(
 | 
			
		||||
            value -> healRunnable.put(player.getUniqueId(), new Interval(value[0], value[1], 20)));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onPlayerQuit(PlayerQuitEvent event) {
 | 
			
		||||
    @EventHandler public void onPlayerQuit(PlayerQuitEvent event) {
 | 
			
		||||
        Player player = event.getPlayer();
 | 
			
		||||
        feedRunnable.remove(player.getUniqueId());
 | 
			
		||||
        healRunnable.remove(player.getUniqueId());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onPlotLeave(PlayerLeavePlotEvent event) {
 | 
			
		||||
    @EventHandler public void onPlotLeave(PlayerLeavePlotEvent event) {
 | 
			
		||||
        Player leaver = event.getPlayer();
 | 
			
		||||
        Plot plot = event.getPlot();
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
@@ -164,8 +157,7 @@ public class PlotPlusListener extends PlotListener implements Listener {
 | 
			
		||||
        healRunnable.remove(leaver.getUniqueId());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @EventHandler
 | 
			
		||||
    public void onItemPickup(EntityPickupItemEvent event) {
 | 
			
		||||
    @EventHandler public void onItemPickup(EntityPickupItemEvent event) {
 | 
			
		||||
        LivingEntity ent = event.getEntity();
 | 
			
		||||
        if (ent instanceof Player) {
 | 
			
		||||
            Player player = (Player) ent;
 | 
			
		||||
 
 | 
			
		||||
@@ -1,13 +1,9 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.bukkit.listeners;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.PlotAreaManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SinglePlotAreaManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils;
 | 
			
		||||
import java.lang.reflect.Field;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.Chunk;
 | 
			
		||||
import org.bukkit.World;
 | 
			
		||||
@@ -18,6 +14,11 @@ import org.bukkit.event.world.ChunkEvent;
 | 
			
		||||
import org.bukkit.event.world.ChunkLoadEvent;
 | 
			
		||||
import org.bukkit.plugin.Plugin;
 | 
			
		||||
 | 
			
		||||
import java.lang.reflect.Field;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
@SuppressWarnings("unused") public class SingleWorldListener implements Listener {
 | 
			
		||||
 | 
			
		||||
    private Method methodGetHandleChunk;
 | 
			
		||||
 
 | 
			
		||||
@@ -7,7 +7,10 @@ import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotBlock;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
import org.bukkit.*;
 | 
			
		||||
import org.bukkit.GameMode;
 | 
			
		||||
import org.bukkit.Material;
 | 
			
		||||
import org.bukkit.Sound;
 | 
			
		||||
import org.bukkit.WeatherType;
 | 
			
		||||
import org.bukkit.entity.Player;
 | 
			
		||||
import org.bukkit.event.Event;
 | 
			
		||||
import org.bukkit.event.EventException;
 | 
			
		||||
@@ -255,14 +258,15 @@ public class BukkitPlayer extends PlotPlayer {
 | 
			
		||||
    @Override public void playMusic(Location location, PlotBlock id) {
 | 
			
		||||
        if (PlotBlock.isEverything(id) || id.isAir()) {
 | 
			
		||||
            // Let's just stop all the discs because why not?
 | 
			
		||||
            for (final Sound sound : Arrays.stream(Sound.values()).filter(sound -> sound.name().contains("DISC")).collect(
 | 
			
		||||
                Collectors.toList())) {
 | 
			
		||||
            for (final Sound sound : Arrays.stream(Sound.values())
 | 
			
		||||
                .filter(sound -> sound.name().contains("DISC")).collect(Collectors.toList())) {
 | 
			
		||||
                player.stopSound(sound);
 | 
			
		||||
            }
 | 
			
		||||
            // this.player.playEffect(BukkitUtil.getLocation(location), Effect.RECORD_PLAY, Material.AIR);
 | 
			
		||||
        } else {
 | 
			
		||||
            // this.player.playEffect(BukkitUtil.getLocation(location), Effect.RECORD_PLAY, id.to(Material.class));
 | 
			
		||||
            this.player.playSound(BukkitUtil.getLocation(location), Sound.valueOf(id.to(Material.class).name()), Float.MAX_VALUE, 1f);
 | 
			
		||||
            this.player.playSound(BukkitUtil.getLocation(location),
 | 
			
		||||
                Sound.valueOf(id.to(Material.class).name()), Float.MAX_VALUE, 1f);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							@@ -14,13 +14,13 @@ import org.bukkit.enchantments.Enchantment;
 | 
			
		||||
import org.bukkit.inventory.Inventory;
 | 
			
		||||
import org.bukkit.inventory.InventoryHolder;
 | 
			
		||||
import org.bukkit.inventory.ItemStack;
 | 
			
		||||
import org.bukkit.inventory.meta.Damageable;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.HashMap;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
import java.util.Map.Entry;
 | 
			
		||||
import org.bukkit.inventory.meta.Damageable;
 | 
			
		||||
 | 
			
		||||
public class StateWrapper {
 | 
			
		||||
 | 
			
		||||
@@ -242,7 +242,7 @@ public class StateWrapper {
 | 
			
		||||
    public Map<String, Tag> serializeItem(ItemStack item) {
 | 
			
		||||
        Map<String, Tag> data = new HashMap<>();
 | 
			
		||||
        data.put("id", new StringTag(item.getType().name()));
 | 
			
		||||
        data.put("Damage", new ShortTag((short) ((Damageable)item.getItemMeta()).getDamage()));
 | 
			
		||||
        data.put("Damage", new ShortTag((short) ((Damageable) item.getItemMeta()).getDamage()));
 | 
			
		||||
        data.put("Count", new ByteTag((byte) item.getAmount()));
 | 
			
		||||
        if (!item.getEnchantments().isEmpty()) {
 | 
			
		||||
            List<CompoundTag> enchantmentList = new ArrayList<>();
 | 
			
		||||
 
 | 
			
		||||
@@ -61,11 +61,13 @@ public final class BukkitEventUtil extends EventUtil {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean callMerge(Plot plot, int dir, int max) {
 | 
			
		||||
        return callEvent(new PlotMergeEvent(BukkitUtil.getWorld(plot.getWorldName()), plot, dir, max));
 | 
			
		||||
        return callEvent(
 | 
			
		||||
            new PlotMergeEvent(BukkitUtil.getWorld(plot.getWorldName()), plot, dir, max));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean callAutoMerge(Plot plot, List<PlotId> plots) {
 | 
			
		||||
        return callEvent(new PlotAutoMergeEvent(BukkitUtil.getWorld(plot.getWorldName()), plot, plots));
 | 
			
		||||
        return callEvent(
 | 
			
		||||
            new PlotAutoMergeEvent(BukkitUtil.getWorld(plot.getWorldName()), plot, plots));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean callUnlink(PlotArea area, List<PlotId> plots) {
 | 
			
		||||
 
 | 
			
		||||
@@ -110,7 +110,7 @@ public class BukkitHybridUtils extends HybridUtils {
 | 
			
		||||
                    rz[i] = v;
 | 
			
		||||
                }
 | 
			
		||||
                int minY;
 | 
			
		||||
                if ( Settings.Schematics.PASTE_ON_TOP) {
 | 
			
		||||
                if (Settings.Schematics.PASTE_ON_TOP) {
 | 
			
		||||
                    minY = Math.min(hpw.PLOT_HEIGHT, hpw.ROAD_HEIGHT);
 | 
			
		||||
                } else {
 | 
			
		||||
                    minY = 1;
 | 
			
		||||
@@ -162,9 +162,7 @@ public class BukkitHybridUtils extends HybridUtils {
 | 
			
		||||
                                continue;
 | 
			
		||||
                            }
 | 
			
		||||
                            int y = MainUtil.y_loc[i][j];
 | 
			
		||||
                            oldBlocks[y][x][z] = result[i][j] != null ?
 | 
			
		||||
                                result[i][j] :
 | 
			
		||||
                                airBucket;
 | 
			
		||||
                            oldBlocks[y][x][z] = result[i][j] != null ? result[i][j] : airBucket;
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,5 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.bukkit.util;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.LegacyPlotBlock;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotBlock;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.StringPlotBlock;
 | 
			
		||||
 
 | 
			
		||||
@@ -1,7 +1,5 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.bukkit.util;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.bukkit.object.BukkitPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.ChunkLoc;
 | 
			
		||||
@@ -14,15 +12,18 @@ import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.RefFie
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.RefMethod;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.Chunk;
 | 
			
		||||
import org.bukkit.World;
 | 
			
		||||
import org.bukkit.entity.Player;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Collection;
 | 
			
		||||
import java.util.HashMap;
 | 
			
		||||
import java.util.HashSet;
 | 
			
		||||
import java.util.Map.Entry;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.Chunk;
 | 
			
		||||
import org.bukkit.World;
 | 
			
		||||
import org.bukkit.entity.Player;
 | 
			
		||||
 | 
			
		||||
import static com.github.intellectualsites.plotsquared.plot.util.ReflectionUtils.getRefClass;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * An utility that can be used to send chunks, rather than using bukkit code to do so (uses heavy
 | 
			
		||||
@@ -30,33 +31,33 @@ import org.bukkit.entity.Player;
 | 
			
		||||
 */
 | 
			
		||||
public class SendChunk {
 | 
			
		||||
 | 
			
		||||
  private final RefMethod methodGetHandlePlayer;
 | 
			
		||||
  private final RefMethod methodGetHandleChunk;
 | 
			
		||||
  private final RefConstructor mapChunk;
 | 
			
		||||
  private final RefField connection;
 | 
			
		||||
  private final RefMethod send;
 | 
			
		||||
  private final RefMethod methodInitLighting;
 | 
			
		||||
    private final RefMethod methodGetHandlePlayer;
 | 
			
		||||
    private final RefMethod methodGetHandleChunk;
 | 
			
		||||
    private final RefConstructor mapChunk;
 | 
			
		||||
    private final RefField connection;
 | 
			
		||||
    private final RefMethod send;
 | 
			
		||||
    private final RefMethod methodInitLighting;
 | 
			
		||||
 | 
			
		||||
  /**
 | 
			
		||||
   * Constructor.
 | 
			
		||||
   */
 | 
			
		||||
  public SendChunk() throws ClassNotFoundException, NoSuchMethodException, NoSuchFieldException {
 | 
			
		||||
    RefConstructor tempMapChunk;
 | 
			
		||||
    RefClass classCraftPlayer = getRefClass("{cb}.entity.CraftPlayer");
 | 
			
		||||
    this.methodGetHandlePlayer = classCraftPlayer.getMethod("getHandle");
 | 
			
		||||
    RefClass classCraftChunk = getRefClass("{cb}.CraftChunk");
 | 
			
		||||
    this.methodGetHandleChunk = classCraftChunk.getMethod("getHandle");
 | 
			
		||||
    RefClass classChunk = getRefClass("{nms}.Chunk");
 | 
			
		||||
    this.methodInitLighting = classChunk.getMethod("initLighting");
 | 
			
		||||
    RefClass classMapChunk = getRefClass("{nms}.PacketPlayOutMapChunk");
 | 
			
		||||
    tempMapChunk = classMapChunk.getConstructor(classChunk.getRealClass(), int.class);
 | 
			
		||||
    this.mapChunk = tempMapChunk;
 | 
			
		||||
    RefClass classEntityPlayer = getRefClass("{nms}.EntityPlayer");
 | 
			
		||||
    this.connection = classEntityPlayer.getField("playerConnection");
 | 
			
		||||
    RefClass classPacket = getRefClass("{nms}.Packet");
 | 
			
		||||
    RefClass classConnection = getRefClass("{nms}.PlayerConnection");
 | 
			
		||||
    this.send = classConnection.getMethod("sendPacket", classPacket.getRealClass());
 | 
			
		||||
  }
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructor.
 | 
			
		||||
     */
 | 
			
		||||
    public SendChunk() throws ClassNotFoundException, NoSuchMethodException, NoSuchFieldException {
 | 
			
		||||
        RefConstructor tempMapChunk;
 | 
			
		||||
        RefClass classCraftPlayer = getRefClass("{cb}.entity.CraftPlayer");
 | 
			
		||||
        this.methodGetHandlePlayer = classCraftPlayer.getMethod("getHandle");
 | 
			
		||||
        RefClass classCraftChunk = getRefClass("{cb}.CraftChunk");
 | 
			
		||||
        this.methodGetHandleChunk = classCraftChunk.getMethod("getHandle");
 | 
			
		||||
        RefClass classChunk = getRefClass("{nms}.Chunk");
 | 
			
		||||
        this.methodInitLighting = classChunk.getMethod("initLighting");
 | 
			
		||||
        RefClass classMapChunk = getRefClass("{nms}.PacketPlayOutMapChunk");
 | 
			
		||||
        tempMapChunk = classMapChunk.getConstructor(classChunk.getRealClass(), int.class);
 | 
			
		||||
        this.mapChunk = tempMapChunk;
 | 
			
		||||
        RefClass classEntityPlayer = getRefClass("{nms}.EntityPlayer");
 | 
			
		||||
        this.connection = classEntityPlayer.getField("playerConnection");
 | 
			
		||||
        RefClass classPacket = getRefClass("{nms}.Packet");
 | 
			
		||||
        RefClass classConnection = getRefClass("{nms}.PlayerConnection");
 | 
			
		||||
        this.send = classConnection.getMethod("sendPacket", classPacket.getRealClass());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void sendChunk(Collection<Chunk> input) {
 | 
			
		||||
        HashSet<Chunk> chunks = new HashSet<>(input);
 | 
			
		||||
@@ -96,52 +97,51 @@ public class SendChunk {
 | 
			
		||||
            Player player = ((BukkitPlayer) pp).player;
 | 
			
		||||
            Object entity = this.methodGetHandlePlayer.of(player).call();
 | 
			
		||||
 | 
			
		||||
      for (Chunk chunk : list) {
 | 
			
		||||
        int dx = Math.abs(cx - chunk.getX());
 | 
			
		||||
        int dz = Math.abs(cz - chunk.getZ());
 | 
			
		||||
        if ((dx > view) || (dz > view)) {
 | 
			
		||||
          continue;
 | 
			
		||||
            for (Chunk chunk : list) {
 | 
			
		||||
                int dx = Math.abs(cx - chunk.getX());
 | 
			
		||||
                int dz = Math.abs(cz - chunk.getZ());
 | 
			
		||||
                if ((dx > view) || (dz > view)) {
 | 
			
		||||
                    continue;
 | 
			
		||||
                }
 | 
			
		||||
                Object c = this.methodGetHandleChunk.of(chunk).call();
 | 
			
		||||
                chunks.remove(chunk);
 | 
			
		||||
                Object con = this.connection.of(entity).get();
 | 
			
		||||
                Object packet = null;
 | 
			
		||||
                try {
 | 
			
		||||
                    packet = this.mapChunk.create(c, 65535);
 | 
			
		||||
                } catch (Exception ignored) {
 | 
			
		||||
                }
 | 
			
		||||
                if (packet == null) {
 | 
			
		||||
                    PlotSquared.debug("Error with PacketPlayOutMapChunk reflection.");
 | 
			
		||||
                }
 | 
			
		||||
                this.send.of(con).call(packet);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        Object c = this.methodGetHandleChunk.of(chunk).call();
 | 
			
		||||
        chunks.remove(chunk);
 | 
			
		||||
        Object con = this.connection.of(entity).get();
 | 
			
		||||
        Object packet = null;
 | 
			
		||||
        try {
 | 
			
		||||
          packet = this.mapChunk.create(c, 65535);
 | 
			
		||||
        } catch (Exception ignored) {
 | 
			
		||||
        for (final Chunk chunk : chunks) {
 | 
			
		||||
            TaskManager.runTask(() -> {
 | 
			
		||||
                try {
 | 
			
		||||
                    chunk.unload(true, false);
 | 
			
		||||
                } catch (Throwable ignored) {
 | 
			
		||||
                    String worldName = chunk.getWorld().getName();
 | 
			
		||||
                    PlotSquared.debug(
 | 
			
		||||
                        "$4Could not save chunk: " + worldName + ';' + chunk.getX() + ";" + chunk
 | 
			
		||||
                            .getZ());
 | 
			
		||||
                    PlotSquared.debug("$3 - $4File may be open in another process (e.g. MCEdit)");
 | 
			
		||||
                    PlotSquared.debug("$3 - $4" + worldName + "/level.dat or " + worldName
 | 
			
		||||
                        + "/level_old.dat may be corrupt (try repairing or removing these)");
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
        }
 | 
			
		||||
        if (packet == null) {
 | 
			
		||||
          PlotSquared.debug("Error with PacketPlayOutMapChunk reflection.");
 | 
			
		||||
        }
 | 
			
		||||
        this.send.of(con).call(packet);
 | 
			
		||||
      }
 | 
			
		||||
    }
 | 
			
		||||
    for (final Chunk chunk : chunks) {
 | 
			
		||||
      TaskManager.runTask(() -> {
 | 
			
		||||
        try {
 | 
			
		||||
          chunk.unload(true, false);
 | 
			
		||||
        } catch (Throwable ignored) {
 | 
			
		||||
          String worldName = chunk.getWorld().getName();
 | 
			
		||||
          PlotSquared.debug(
 | 
			
		||||
              "$4Could not save chunk: " + worldName + ';' + chunk.getX() + ";"
 | 
			
		||||
                  + chunk.getZ());
 | 
			
		||||
          PlotSquared
 | 
			
		||||
              .debug("$3 - $4File may be open in another process (e.g. MCEdit)");
 | 
			
		||||
          PlotSquared.debug("$3 - $4" + worldName + "/level.dat or " + worldName
 | 
			
		||||
              + "/level_old.dat may be corrupt (try repairing or removing these)");
 | 
			
		||||
        }
 | 
			
		||||
      });
 | 
			
		||||
    }
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  public void sendChunk(String worldName, Collection<ChunkLoc> chunkLocations) {
 | 
			
		||||
    World myWorld = Bukkit.getWorld(worldName);
 | 
			
		||||
    ArrayList<Chunk> chunks = new ArrayList<>();
 | 
			
		||||
    for (ChunkLoc loc : chunkLocations) {
 | 
			
		||||
      if (myWorld.isChunkLoaded(loc.x, loc.z)) {
 | 
			
		||||
        chunks.add(myWorld.getChunkAt(loc.x, loc.z));
 | 
			
		||||
      }
 | 
			
		||||
    public void sendChunk(String worldName, Collection<ChunkLoc> chunkLocations) {
 | 
			
		||||
        World myWorld = Bukkit.getWorld(worldName);
 | 
			
		||||
        ArrayList<Chunk> chunks = new ArrayList<>();
 | 
			
		||||
        for (ChunkLoc loc : chunkLocations) {
 | 
			
		||||
            if (myWorld.isChunkLoaded(loc.x, loc.z)) {
 | 
			
		||||
                chunks.add(myWorld.getChunkAt(loc.x, loc.z));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        sendChunk(chunks);
 | 
			
		||||
    }
 | 
			
		||||
    sendChunk(chunks);
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -5,10 +5,10 @@ import com.github.intellectualsites.plotsquared.bukkit.object.BukkitPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.OfflinePlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.uuid.UUIDWrapper;
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.OfflinePlayer;
 | 
			
		||||
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
public class DefaultUUIDWrapper implements UUIDWrapper {
 | 
			
		||||
@@ -31,8 +31,7 @@ public class DefaultUUIDWrapper implements UUIDWrapper {
 | 
			
		||||
 | 
			
		||||
    @Override public OfflinePlotPlayer[] getOfflinePlayers() {
 | 
			
		||||
        OfflinePlayer[] ops = Bukkit.getOfflinePlayers();
 | 
			
		||||
        return Arrays.stream(ops).map(BukkitOfflinePlayer::new)
 | 
			
		||||
            .toArray(BukkitOfflinePlayer[]::new);
 | 
			
		||||
        return Arrays.stream(ops).map(BukkitOfflinePlayer::new).toArray(BukkitOfflinePlayer[]::new);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public OfflinePlotPlayer getOfflinePlayer(String name) {
 | 
			
		||||
 
 | 
			
		||||
@@ -80,13 +80,11 @@ public class FileUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
                    e.printStackTrace();
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            HashBiMap<StringWrapper, UUID> toAdd =
 | 
			
		||||
                HashBiMap.create(new HashMap<>());
 | 
			
		||||
            HashBiMap<StringWrapper, UUID> toAdd = HashBiMap.create(new HashMap<>());
 | 
			
		||||
            if (Settings.UUID.NATIVE_UUID_PROVIDER) {
 | 
			
		||||
                HashSet<UUID> all = UUIDHandler.getAllUUIDS();
 | 
			
		||||
                PlotSquared.debug("&aFast mode UUID caching enabled!");
 | 
			
		||||
                File playerDataFolder =
 | 
			
		||||
                    new File(container, world + File.separator + "playerdata");
 | 
			
		||||
                File playerDataFolder = new File(container, world + File.separator + "playerdata");
 | 
			
		||||
                String[] dat = playerDataFolder.list(new DatFileFilter());
 | 
			
		||||
                boolean check = all.isEmpty();
 | 
			
		||||
                if (dat != null) {
 | 
			
		||||
@@ -128,8 +126,8 @@ public class FileUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
                    }
 | 
			
		||||
                    return;
 | 
			
		||||
                } else {
 | 
			
		||||
                    PlotSquared.debug("Failed to cache: " + all.size()
 | 
			
		||||
                        + " uuids - slowly processing all files");
 | 
			
		||||
                    PlotSquared.debug(
 | 
			
		||||
                        "Failed to cache: " + all.size() + " uuids - slowly processing all files");
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            HashSet<String> worlds1 = Sets.newHashSet(world, "world");
 | 
			
		||||
@@ -138,8 +136,7 @@ public class FileUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
            File playerDataFolder = null;
 | 
			
		||||
            for (String worldName : worlds1) {
 | 
			
		||||
                // Getting UUIDs
 | 
			
		||||
                playerDataFolder =
 | 
			
		||||
                    new File(container, worldName + File.separator + "playerdata");
 | 
			
		||||
                playerDataFolder = new File(container, worldName + File.separator + "playerdata");
 | 
			
		||||
                String[] dat = playerDataFolder.list(new DatFileFilter());
 | 
			
		||||
                if ((dat != null) && (dat.length != 0)) {
 | 
			
		||||
                    for (String current : dat) {
 | 
			
		||||
@@ -213,8 +210,7 @@ public class FileUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            if (getUUIDMap().isEmpty()) {
 | 
			
		||||
                for (OfflinePlotPlayer op : FileUUIDHandler.this.uuidWrapper
 | 
			
		||||
                    .getOfflinePlayers()) {
 | 
			
		||||
                for (OfflinePlotPlayer op : FileUUIDHandler.this.uuidWrapper.getOfflinePlayers()) {
 | 
			
		||||
                    long last = op.getLastPlayed();
 | 
			
		||||
                    if (last != 0) {
 | 
			
		||||
                        String name = op.getName();
 | 
			
		||||
 
 | 
			
		||||
@@ -9,7 +9,6 @@ import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.uuid.UUIDWrapper;
 | 
			
		||||
import com.google.common.base.Charsets;
 | 
			
		||||
import com.google.common.collect.BiMap;
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import org.bukkit.Bukkit;
 | 
			
		||||
import org.bukkit.OfflinePlayer;
 | 
			
		||||
import org.bukkit.Server;
 | 
			
		||||
@@ -17,6 +16,7 @@ import org.bukkit.entity.Player;
 | 
			
		||||
 | 
			
		||||
import java.lang.reflect.InvocationTargetException;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.Collection;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@@ -93,8 +93,7 @@ public class OfflineUUIDWrapper implements UUIDWrapper {
 | 
			
		||||
 | 
			
		||||
    @Override public OfflinePlotPlayer[] getOfflinePlayers() {
 | 
			
		||||
        OfflinePlayer[] ops = Bukkit.getOfflinePlayers();
 | 
			
		||||
        return Arrays.stream(ops).map(BukkitOfflinePlayer::new)
 | 
			
		||||
            .toArray(BukkitOfflinePlayer[]::new);
 | 
			
		||||
        return Arrays.stream(ops).map(BukkitOfflinePlayer::new).toArray(BukkitOfflinePlayer[]::new);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public OfflinePlotPlayer getOfflinePlayer(String name) {
 | 
			
		||||
 
 | 
			
		||||
@@ -73,14 +73,12 @@ public class SQLUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
        }
 | 
			
		||||
        TaskManager.runTaskAsync(() -> {
 | 
			
		||||
            try {
 | 
			
		||||
                HashBiMap<StringWrapper, UUID> toAdd =
 | 
			
		||||
                    HashBiMap.create(new HashMap<>());
 | 
			
		||||
                HashBiMap<StringWrapper, UUID> toAdd = HashBiMap.create(new HashMap<>());
 | 
			
		||||
                try (PreparedStatement statement = getConnection()
 | 
			
		||||
                    .prepareStatement("SELECT `uuid`, `username` FROM `usercache`");
 | 
			
		||||
                    ResultSet resultSet = statement.executeQuery()) {
 | 
			
		||||
                    while (resultSet.next()) {
 | 
			
		||||
                        StringWrapper username =
 | 
			
		||||
                            new StringWrapper(resultSet.getString("username"));
 | 
			
		||||
                        StringWrapper username = new StringWrapper(resultSet.getString("username"));
 | 
			
		||||
                        UUID uuid = UUID.fromString(resultSet.getString("uuid"));
 | 
			
		||||
                        toAdd.put(new StringWrapper(username.value), uuid);
 | 
			
		||||
                    }
 | 
			
		||||
@@ -99,8 +97,7 @@ public class SQLUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
                    }
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                FileUUIDHandler fileHandler =
 | 
			
		||||
                    new FileUUIDHandler(SQLUUIDHandler.this.uuidWrapper);
 | 
			
		||||
                FileUUIDHandler fileHandler = new FileUUIDHandler(SQLUUIDHandler.this.uuidWrapper);
 | 
			
		||||
                fileHandler.startCaching(() -> {
 | 
			
		||||
                    // If the file based UUID handler didn't cache it, then we can't cache offline mode
 | 
			
		||||
                    // Also, trying to cache based on files again, is useless as that's what the file based uuid cacher does
 | 
			
		||||
@@ -114,18 +111,13 @@ public class SQLUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
                    TaskManager.runTaskAsync(() -> {
 | 
			
		||||
                        while (!toFetch.isEmpty()) {
 | 
			
		||||
                            try {
 | 
			
		||||
                                for (int i = 0;
 | 
			
		||||
                                    i < Math.min(500, toFetch.size()); i++) {
 | 
			
		||||
                                for (int i = 0; i < Math.min(500, toFetch.size()); i++) {
 | 
			
		||||
                                    UUID uuid = toFetch.pop();
 | 
			
		||||
                                    HttpURLConnection connection =
 | 
			
		||||
                                        (HttpURLConnection) new URL(
 | 
			
		||||
                                            SQLUUIDHandler.this.PROFILE_URL + uuid
 | 
			
		||||
                                                .toString().replace("-", ""))
 | 
			
		||||
                                            .openConnection();
 | 
			
		||||
                                    try (InputStream con = connection
 | 
			
		||||
                                        .getInputStream()) {
 | 
			
		||||
                                        InputStreamReader reader =
 | 
			
		||||
                                            new InputStreamReader(con);
 | 
			
		||||
                                    HttpURLConnection connection = (HttpURLConnection) new URL(
 | 
			
		||||
                                        SQLUUIDHandler.this.PROFILE_URL + uuid.toString()
 | 
			
		||||
                                            .replace("-", "")).openConnection();
 | 
			
		||||
                                    try (InputStream con = connection.getInputStream()) {
 | 
			
		||||
                                        InputStreamReader reader = new InputStreamReader(con);
 | 
			
		||||
                                        JSONObject response =
 | 
			
		||||
                                            (JSONObject) SQLUUIDHandler.this.jsonParser
 | 
			
		||||
                                                .parse(reader);
 | 
			
		||||
@@ -208,13 +200,12 @@ public class SQLUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
        // Ignoring duplicates
 | 
			
		||||
        if (super.add(name, uuid)) {
 | 
			
		||||
            TaskManager.runTaskAsync(() -> {
 | 
			
		||||
                try (PreparedStatement statement = getConnection().prepareStatement(
 | 
			
		||||
                    "REPLACE INTO usercache (`uuid`, `username`) VALUES(?, ?)")) {
 | 
			
		||||
                try (PreparedStatement statement = getConnection()
 | 
			
		||||
                    .prepareStatement("REPLACE INTO usercache (`uuid`, `username`) VALUES(?, ?)")) {
 | 
			
		||||
                    statement.setString(1, uuid.toString());
 | 
			
		||||
                    statement.setString(2, name.toString());
 | 
			
		||||
                    statement.execute();
 | 
			
		||||
                    PlotSquared
 | 
			
		||||
                        .debug(C.PREFIX + "&cAdded '&6" + uuid + "&c' - '&6" + name + "&c'");
 | 
			
		||||
                    PlotSquared.debug(C.PREFIX + "&cAdded '&6" + uuid + "&c' - '&6" + name + "&c'");
 | 
			
		||||
                } catch (SQLException e) {
 | 
			
		||||
                    e.printStackTrace();
 | 
			
		||||
                }
 | 
			
		||||
@@ -235,8 +226,8 @@ public class SQLUUIDHandler extends UUIDHandlerImplementation {
 | 
			
		||||
                statement.setString(1, name.value);
 | 
			
		||||
                statement.setString(2, uuid.toString());
 | 
			
		||||
                statement.execute();
 | 
			
		||||
                PlotSquared.debug(
 | 
			
		||||
                    C.PREFIX + "Name change for '" + uuid + "' to '" + name.value + '\'');
 | 
			
		||||
                PlotSquared
 | 
			
		||||
                    .debug(C.PREFIX + "Name change for '" + uuid + "' to '" + name.value + '\'');
 | 
			
		||||
            } catch (SQLException e) {
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
            }
 | 
			
		||||
 
 | 
			
		||||
@@ -1,68 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotId;
 | 
			
		||||
 | 
			
		||||
public abstract class Argument<T> {
 | 
			
		||||
 | 
			
		||||
    public static final Argument<Integer> Integer = new Argument<Integer>("int", 16) {
 | 
			
		||||
        @Override public Integer parse(String in) {
 | 
			
		||||
            Integer value = null;
 | 
			
		||||
            try {
 | 
			
		||||
                value = java.lang.Integer.parseInt(in);
 | 
			
		||||
            } catch (Exception ignored) {
 | 
			
		||||
            }
 | 
			
		||||
            return value;
 | 
			
		||||
        }
 | 
			
		||||
    };
 | 
			
		||||
    public static final Argument<Boolean> Boolean = new Argument<Boolean>("boolean", true) {
 | 
			
		||||
        @Override public Boolean parse(String in) {
 | 
			
		||||
            Boolean value = null;
 | 
			
		||||
            if (in.equalsIgnoreCase("true") || in.equalsIgnoreCase("Yes") || in
 | 
			
		||||
                .equalsIgnoreCase("1")) {
 | 
			
		||||
                value = true;
 | 
			
		||||
            } else if (in.equalsIgnoreCase("false") || in.equalsIgnoreCase("No") || in
 | 
			
		||||
                .equalsIgnoreCase("0")) {
 | 
			
		||||
                value = false;
 | 
			
		||||
            }
 | 
			
		||||
            return value;
 | 
			
		||||
        }
 | 
			
		||||
    };
 | 
			
		||||
    public static final Argument<String> String = new Argument<String>("String", "Example") {
 | 
			
		||||
        @Override public String parse(String in) {
 | 
			
		||||
            return in;
 | 
			
		||||
        }
 | 
			
		||||
    };
 | 
			
		||||
    public static final Argument<String> PlayerName =
 | 
			
		||||
        new Argument<String>("PlayerName", "Dinnerbone") {
 | 
			
		||||
            @Override public String parse(String in) {
 | 
			
		||||
                return in.length() <= 16 ? in : null;
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
    public static final Argument<PlotId> PlotID =
 | 
			
		||||
        new Argument<PlotId>("PlotID", new PlotId(-6, 3)) {
 | 
			
		||||
            @Override public PlotId parse(String in) {
 | 
			
		||||
                return PlotId.fromString(in);
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
    private final String name;
 | 
			
		||||
    private final T example;
 | 
			
		||||
 | 
			
		||||
    public Argument(String name, T example) {
 | 
			
		||||
        this.name = name;
 | 
			
		||||
        this.example = example;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public abstract T parse(String in);
 | 
			
		||||
 | 
			
		||||
    @Override public final String toString() {
 | 
			
		||||
        return this.getName();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public final String getName() {
 | 
			
		||||
        return this.name;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public final T getExample() {
 | 
			
		||||
        return this.example;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,596 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.file.YamlConfiguration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.commands.CommandCategory;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.commands.MainCommand;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.commands.RequiredType;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotMessage;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.lang.annotation.Annotation;
 | 
			
		||||
import java.lang.reflect.InvocationTargetException;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.util.*;
 | 
			
		||||
 | 
			
		||||
public abstract class Command {
 | 
			
		||||
 | 
			
		||||
    // May be none
 | 
			
		||||
    private final ArrayList<Command> allCommands = new ArrayList<>();
 | 
			
		||||
    private final ArrayList<Command> dynamicCommands = new ArrayList<>();
 | 
			
		||||
    private final HashMap<String, Command> staticCommands = new HashMap<>();
 | 
			
		||||
 | 
			
		||||
    // Parent command (may be null)
 | 
			
		||||
    private final Command parent;
 | 
			
		||||
    private final boolean isStatic;
 | 
			
		||||
    // The command ID
 | 
			
		||||
    private String id;
 | 
			
		||||
    private List<String> aliases;
 | 
			
		||||
    private RequiredType required;
 | 
			
		||||
    private String usage;
 | 
			
		||||
    private String description;
 | 
			
		||||
    private String perm;
 | 
			
		||||
    private boolean confirmation;
 | 
			
		||||
    private CommandCategory category;
 | 
			
		||||
    private Argument[] arguments;
 | 
			
		||||
 | 
			
		||||
    public Command(Command parent, boolean isStatic, String id, String perm, RequiredType required,
 | 
			
		||||
        CommandCategory cat) {
 | 
			
		||||
        this.parent = parent;
 | 
			
		||||
        this.isStatic = isStatic;
 | 
			
		||||
        this.id = id;
 | 
			
		||||
        this.perm = perm;
 | 
			
		||||
        this.required = required;
 | 
			
		||||
        this.category = cat;
 | 
			
		||||
        this.aliases = Arrays.asList(id);
 | 
			
		||||
        if (this.parent != null) {
 | 
			
		||||
            this.parent.register(this);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Command(Command parent, boolean isStatic) {
 | 
			
		||||
        this.parent = parent;
 | 
			
		||||
        this.isStatic = isStatic;
 | 
			
		||||
        Annotation cdAnnotation = getClass().getAnnotation(CommandDeclaration.class);
 | 
			
		||||
        if (cdAnnotation != null) {
 | 
			
		||||
            CommandDeclaration declaration = (CommandDeclaration) cdAnnotation;
 | 
			
		||||
            init(declaration);
 | 
			
		||||
        }
 | 
			
		||||
        for (final Method method : getClass().getDeclaredMethods()) {
 | 
			
		||||
            if (method.isAnnotationPresent(CommandDeclaration.class)) {
 | 
			
		||||
                Class<?>[] types = method.getParameterTypes();
 | 
			
		||||
                // final PlotPlayer player, String[] args, RunnableVal3<Command,Runnable,Runnable> confirm, RunnableVal2<Command, CommandResult>
 | 
			
		||||
                // whenDone
 | 
			
		||||
                if (types.length == 5 && types[0] == Command.class && types[1] == PlotPlayer.class
 | 
			
		||||
                    && types[2] == String[].class && types[3] == RunnableVal3.class
 | 
			
		||||
                    && types[4] == RunnableVal2.class) {
 | 
			
		||||
                    Command tmp = new Command(this, true) {
 | 
			
		||||
                        @Override public void execute(PlotPlayer player, String[] args,
 | 
			
		||||
                            RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
                            RunnableVal2<Command, CommandResult> whenDone) {
 | 
			
		||||
                            try {
 | 
			
		||||
                                method.invoke(Command.this, this, player, args, confirm, whenDone);
 | 
			
		||||
                            } catch (IllegalAccessException | InvocationTargetException e) {
 | 
			
		||||
                                e.printStackTrace();
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    };
 | 
			
		||||
                    tmp.init(method.getAnnotation(CommandDeclaration.class));
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Command getParent() {
 | 
			
		||||
        return this.parent;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String getId() {
 | 
			
		||||
        return this.id;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String getFullId() {
 | 
			
		||||
        if (this.parent != null && this.parent.getParent() != null) {
 | 
			
		||||
            return this.parent.getFullId() + "." + this.id;
 | 
			
		||||
        }
 | 
			
		||||
        return this.id;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public List<Command> getCommands(PlotPlayer player) {
 | 
			
		||||
        List<Command> commands = new ArrayList<>();
 | 
			
		||||
        for (Command cmd : this.allCommands) {
 | 
			
		||||
            if (cmd.canExecute(player, false)) {
 | 
			
		||||
                commands.add(cmd);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return commands;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public List<Command> getCommands(CommandCategory cat, PlotPlayer player) {
 | 
			
		||||
        List<Command> commands = getCommands(player);
 | 
			
		||||
        if (cat != null) {
 | 
			
		||||
            Iterator<Command> iterator = commands.iterator();
 | 
			
		||||
            while (iterator.hasNext()) {
 | 
			
		||||
                if (iterator.next().category != cat) {
 | 
			
		||||
                    iterator.remove();
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return commands;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public List<Command> getCommands() {
 | 
			
		||||
        return this.allCommands;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public boolean hasConfirmation(PlotPlayer player) {
 | 
			
		||||
        return this.confirmation && !player.hasPermission(getPermission() + ".confirm.bypass");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public List<String> getAliases() {
 | 
			
		||||
        return this.aliases;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String getDescription() {
 | 
			
		||||
        return this.description;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public RequiredType getRequiredType() {
 | 
			
		||||
        return this.required;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Argument[] getRequiredArguments() {
 | 
			
		||||
        return this.arguments;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void setRequiredArguments(Argument[] arguments) {
 | 
			
		||||
        this.arguments = arguments;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void init(CommandDeclaration declaration) {
 | 
			
		||||
        this.id = declaration.command();
 | 
			
		||||
        this.perm = declaration.permission();
 | 
			
		||||
        this.required = declaration.requiredType();
 | 
			
		||||
        this.category = declaration.category();
 | 
			
		||||
        HashMap<String, Object> options = new HashMap<>();
 | 
			
		||||
        List<String> aliasOptions = new ArrayList<>();
 | 
			
		||||
        aliasOptions.add(this.id);
 | 
			
		||||
        aliasOptions.addAll(Arrays.asList(declaration.aliases()));
 | 
			
		||||
        options.put("aliases", aliasOptions);
 | 
			
		||||
        options.put("description", declaration.description());
 | 
			
		||||
        options.put("usage", declaration.usage());
 | 
			
		||||
        options.put("confirmation", declaration.confirmation());
 | 
			
		||||
        boolean set = false;
 | 
			
		||||
        YamlConfiguration commands =
 | 
			
		||||
            PlotSquared.get() == null ? new YamlConfiguration() : PlotSquared.get().commands;
 | 
			
		||||
        for (Map.Entry<String, Object> entry : options.entrySet()) {
 | 
			
		||||
            String key = this.getFullId() + "." + entry.getKey();
 | 
			
		||||
            if (!commands.contains(key)) {
 | 
			
		||||
                commands.set(key, entry.getValue());
 | 
			
		||||
                set = true;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (set && PlotSquared.get() != null) {
 | 
			
		||||
            try {
 | 
			
		||||
                commands.save(PlotSquared.get().commandsFile);
 | 
			
		||||
            } catch (IOException e) {
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        this.aliases = commands.getStringList(this.getFullId() + ".aliases");
 | 
			
		||||
        this.description = commands.getString(this.getFullId() + ".description");
 | 
			
		||||
        this.usage = commands.getString(this.getFullId() + ".usage");
 | 
			
		||||
        this.confirmation = commands.getBoolean(this.getFullId() + ".confirmation");
 | 
			
		||||
        if (this.parent != null) {
 | 
			
		||||
            this.parent.register(this);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void register(Command command) {
 | 
			
		||||
        if (command.isStatic) {
 | 
			
		||||
            for (String alias : command.aliases) {
 | 
			
		||||
                this.staticCommands.put(alias.toLowerCase(), command);
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            this.dynamicCommands.add(command);
 | 
			
		||||
        }
 | 
			
		||||
        this.allCommands.add(command);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String getPermission() {
 | 
			
		||||
        if (this.perm != null && !this.perm.isEmpty()) {
 | 
			
		||||
            return this.perm;
 | 
			
		||||
        }
 | 
			
		||||
        if (this.parent == null) {
 | 
			
		||||
            return "plots.use";
 | 
			
		||||
        }
 | 
			
		||||
        return "plots." + getFullId();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public <T> void paginate(PlotPlayer player, List<T> c, int size, int page,
 | 
			
		||||
        RunnableVal3<Integer, T, PlotMessage> add, String baseCommand, String header) {
 | 
			
		||||
        // Calculate pages & index
 | 
			
		||||
        if (page < 0) {
 | 
			
		||||
            page = 0;
 | 
			
		||||
        }
 | 
			
		||||
        int totalPages = (int) Math.ceil(c.size() / size);
 | 
			
		||||
        if (page > totalPages) {
 | 
			
		||||
            page = totalPages;
 | 
			
		||||
        }
 | 
			
		||||
        int max = page * size + size;
 | 
			
		||||
        if (max > c.size()) {
 | 
			
		||||
            max = c.size();
 | 
			
		||||
        }
 | 
			
		||||
        // Send the header
 | 
			
		||||
        header = header.replaceAll("%cur", page + 1 + "").replaceAll("%max", totalPages + 1 + "")
 | 
			
		||||
            .replaceAll("%amount%", c.size() + "").replaceAll("%word%", "all");
 | 
			
		||||
        MainUtil.sendMessage(player, header);
 | 
			
		||||
        // Send the page content
 | 
			
		||||
        List<T> subList = c.subList(page * size, max);
 | 
			
		||||
        int i = page * size;
 | 
			
		||||
        for (T obj : subList) {
 | 
			
		||||
            i++;
 | 
			
		||||
            PlotMessage msg = new PlotMessage();
 | 
			
		||||
            add.run(i, obj, msg);
 | 
			
		||||
            msg.send(player);
 | 
			
		||||
        }
 | 
			
		||||
        // Send the footer
 | 
			
		||||
        if (page < totalPages && page > 0) { // Back | Next
 | 
			
		||||
            new PlotMessage().text("<-").color("$1").command(baseCommand + " " + page).text(" | ")
 | 
			
		||||
                .color("$3").text("->").color("$1").command(baseCommand + " " + (page + 2))
 | 
			
		||||
                .text(C.CLICKABLE.s()).color("$2").send(player);
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        if (page == 0 && totalPages != 0) { // Next
 | 
			
		||||
            new PlotMessage().text("<-").color("$3").text(" | ").color("$3").text("->").color("$1")
 | 
			
		||||
                .command(baseCommand + " " + (0 + 2)).text(C.CLICKABLE.s()).color("$2")
 | 
			
		||||
                .send(player);
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        if (page == totalPages && totalPages != 0) { // Back
 | 
			
		||||
            new PlotMessage().text("<-").color("$1").command(baseCommand + " " + page).text(" | ")
 | 
			
		||||
                .color("$3").text("->").color("$3").text(C.CLICKABLE.s()).color("$2").send(player);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * @param player  Caller
 | 
			
		||||
     * @param args    Arguments
 | 
			
		||||
     * @param confirm Instance, Success, Failure
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    public void execute(PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) throws CommandException {
 | 
			
		||||
        if (args.length == 0 || args[0] == null) {
 | 
			
		||||
            if (this.parent == null) {
 | 
			
		||||
                MainCommand.getInstance().help.displayHelp(player, null, 0);
 | 
			
		||||
            } else {
 | 
			
		||||
                C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
            }
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        if (this.allCommands == null || this.allCommands.isEmpty()) {
 | 
			
		||||
            player.sendMessage(
 | 
			
		||||
                "Not Implemented: https://github.com/IntellectualSites/PlotSquared/issues/new");
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        Command cmd = getCommand(args[0]);
 | 
			
		||||
        if (cmd == null) {
 | 
			
		||||
            if (this.parent != null) {
 | 
			
		||||
                C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
            // Help command
 | 
			
		||||
            try {
 | 
			
		||||
                if (args.length == 0 || MathMan.isInteger(args[0])
 | 
			
		||||
                    || CommandCategory.valueOf(args[0].toUpperCase()) != null) {
 | 
			
		||||
                    // This will default certain syntax to the help command
 | 
			
		||||
                    // e.g. /plot, /plot 1, /plot claiming
 | 
			
		||||
                    MainCommand.getInstance().help.execute(player, args, null, null);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
            } catch (IllegalArgumentException ignored) {
 | 
			
		||||
            }
 | 
			
		||||
            // Command recommendation
 | 
			
		||||
            MainUtil.sendMessage(player, C.NOT_VALID_SUBCOMMAND);
 | 
			
		||||
            List<Command> commands = getCommands(player);
 | 
			
		||||
            if (commands.isEmpty()) {
 | 
			
		||||
                MainUtil
 | 
			
		||||
                    .sendMessage(player, C.DID_YOU_MEAN, MainCommand.getInstance().help.getUsage());
 | 
			
		||||
                return;
 | 
			
		||||
            }
 | 
			
		||||
            HashSet<String> setargs = new HashSet<>(args.length);
 | 
			
		||||
            for (String arg : args) {
 | 
			
		||||
                setargs.add(arg.toLowerCase());
 | 
			
		||||
            }
 | 
			
		||||
            String[] allargs = setargs.toArray(new String[setargs.size()]);
 | 
			
		||||
            int best = 0;
 | 
			
		||||
            for (Command current : commands) {
 | 
			
		||||
                int match = getMatch(allargs, current);
 | 
			
		||||
                if (match > best) {
 | 
			
		||||
                    cmd = current;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            if (cmd == null) {
 | 
			
		||||
                cmd = new StringComparison<>(args[0], this.allCommands).getMatchObject();
 | 
			
		||||
            }
 | 
			
		||||
            MainUtil.sendMessage(player, C.DID_YOU_MEAN, cmd.getUsage());
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        String[] newArgs = Arrays.copyOfRange(args, 1, args.length);
 | 
			
		||||
        if (!cmd.checkArgs(player, newArgs) || !cmd.canExecute(player, true)) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        try {
 | 
			
		||||
            cmd.execute(player, newArgs, confirm, whenDone);
 | 
			
		||||
        } catch (CommandException e) {
 | 
			
		||||
            e.perform(player);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public boolean checkArgs(PlotPlayer player, String[] args) {
 | 
			
		||||
        Argument<?>[] reqArgs = getRequiredArguments();
 | 
			
		||||
        if (reqArgs != null && reqArgs.length > 0) {
 | 
			
		||||
            boolean failed = args.length < reqArgs.length;
 | 
			
		||||
            String[] baseSplit = getCommandString().split(" ");
 | 
			
		||||
            String[] fullSplit = getUsage().split(" ");
 | 
			
		||||
            String base = getCommandString();
 | 
			
		||||
            if (fullSplit.length - baseSplit.length < reqArgs.length) {
 | 
			
		||||
                String[] tmp = new String[baseSplit.length + reqArgs.length];
 | 
			
		||||
                System.arraycopy(fullSplit, 0, tmp, 0, fullSplit.length);
 | 
			
		||||
                fullSplit = tmp;
 | 
			
		||||
            }
 | 
			
		||||
            for (int i = 0; i < reqArgs.length; i++) {
 | 
			
		||||
                fullSplit[i + baseSplit.length] = reqArgs[i].getExample().toString();
 | 
			
		||||
                failed = failed || reqArgs[i].parse(args[i]) == null;
 | 
			
		||||
            }
 | 
			
		||||
            if (failed) {
 | 
			
		||||
                C.COMMAND_SYNTAX.send(player, StringMan.join(fullSplit, " "));
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public int getMatch(String[] args, Command cmd) {
 | 
			
		||||
        int count = 0;
 | 
			
		||||
        String perm = cmd.getPermission();
 | 
			
		||||
        HashSet<String> desc = new HashSet<>();
 | 
			
		||||
        for (String alias : cmd.getAliases()) {
 | 
			
		||||
            if (alias.startsWith(args[0])) {
 | 
			
		||||
                count += 5;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        Collections.addAll(desc, cmd.getDescription().split(" "));
 | 
			
		||||
        for (String arg : args) {
 | 
			
		||||
            if (perm.startsWith(arg)) {
 | 
			
		||||
                count++;
 | 
			
		||||
            }
 | 
			
		||||
            if (desc.contains(arg)) {
 | 
			
		||||
                count++;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        String[] usage = cmd.getUsage().split(" ");
 | 
			
		||||
        for (int i = 0; i < Math.min(4, usage.length); i++) {
 | 
			
		||||
            int require;
 | 
			
		||||
            if (usage[i].startsWith("<")) {
 | 
			
		||||
                require = 1;
 | 
			
		||||
            } else {
 | 
			
		||||
                require = 0;
 | 
			
		||||
            }
 | 
			
		||||
            String[] split = usage[i].split("\\|| |\\>|\\<|\\[|\\]|\\{|\\}|\\_|\\/");
 | 
			
		||||
            for (String aSplit : split) {
 | 
			
		||||
                for (String arg : args) {
 | 
			
		||||
                    if (StringMan.isEqualIgnoreCase(arg, aSplit)) {
 | 
			
		||||
                        count += 5 - i + require;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        count += StringMan.intersection(desc, args);
 | 
			
		||||
        return count;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Command getCommand(String arg) {
 | 
			
		||||
        Command cmd = this.staticCommands.get(arg.toLowerCase());
 | 
			
		||||
        if (cmd == null) {
 | 
			
		||||
            for (Command command : this.dynamicCommands) {
 | 
			
		||||
                if (command.matches(arg)) {
 | 
			
		||||
                    return command;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return cmd;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Command getCommand(Class clazz) {
 | 
			
		||||
        for (Command cmd : this.allCommands) {
 | 
			
		||||
            if (cmd.getClass() == clazz) {
 | 
			
		||||
                return cmd;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Command getCommandById(String id) {
 | 
			
		||||
        Command exact = this.staticCommands.get(id);
 | 
			
		||||
        if (exact != null) {
 | 
			
		||||
            return exact;
 | 
			
		||||
        }
 | 
			
		||||
        for (Command cmd : this.allCommands) {
 | 
			
		||||
            if (cmd.getId().equals(id)) {
 | 
			
		||||
                return cmd;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public boolean canExecute(PlotPlayer player, boolean message) {
 | 
			
		||||
        if (player == null) {
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        if (!this.required.allows(player)) {
 | 
			
		||||
            if (message) {
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    this.required == RequiredType.PLAYER ? C.IS_CONSOLE : C.NOT_CONSOLE);
 | 
			
		||||
            }
 | 
			
		||||
        } else if (!Permissions.hasPermission(player, getPermission())) {
 | 
			
		||||
            if (message) {
 | 
			
		||||
                C.NO_PERMISSION.send(player, getPermission());
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public boolean matches(String arg) {
 | 
			
		||||
        arg = arg.toLowerCase();
 | 
			
		||||
        return StringMan.isEqual(arg, this.id) || this.aliases.contains(arg);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String getCommandString() {
 | 
			
		||||
        String base;
 | 
			
		||||
        if (this.parent == null) {
 | 
			
		||||
            return "/" + toString();
 | 
			
		||||
        } else {
 | 
			
		||||
            return this.parent.getCommandString() + " " + toString();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String getUsage() {
 | 
			
		||||
        if (this.usage != null && !this.usage.isEmpty()) {
 | 
			
		||||
            if (this.usage.startsWith("/")) {
 | 
			
		||||
                return this.usage;
 | 
			
		||||
            }
 | 
			
		||||
            return getCommandString() + " " + this.usage;
 | 
			
		||||
        }
 | 
			
		||||
        if (this.allCommands.isEmpty()) {
 | 
			
		||||
            return getCommandString();
 | 
			
		||||
        }
 | 
			
		||||
        StringBuilder args = new StringBuilder("[");
 | 
			
		||||
        String prefix = "";
 | 
			
		||||
        for (Command cmd : this.allCommands) {
 | 
			
		||||
            args.append(prefix).append(cmd.isStatic ? cmd.toString() : "<" + cmd + ">");
 | 
			
		||||
            prefix = "|";
 | 
			
		||||
        }
 | 
			
		||||
        return getCommandString() + " " + args + "]";
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Collection<Command> tabOf(PlotPlayer player, String[] input, boolean space,
 | 
			
		||||
        String... args) {
 | 
			
		||||
        if (!space) {
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
        List<Command> result = new ArrayList<>();
 | 
			
		||||
        int index = input.length - (space ? 0 : 1);
 | 
			
		||||
        for (String arg : args) {
 | 
			
		||||
            arg = arg.replace(getCommandString() + " ", "");
 | 
			
		||||
            String[] split = arg.split(" ");
 | 
			
		||||
            if (split.length <= index) {
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            arg = StringMan.join(Arrays.copyOfRange(split, index, split.length), " ");
 | 
			
		||||
            Command cmd = new Command(null, false, arg, getPermission(), getRequiredType(), null) {
 | 
			
		||||
            };
 | 
			
		||||
            result.add(cmd);
 | 
			
		||||
        }
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Collection<Command> tab(PlotPlayer player, String[] args, boolean space) {
 | 
			
		||||
        switch (args.length) {
 | 
			
		||||
            case 0:
 | 
			
		||||
                return this.allCommands;
 | 
			
		||||
            case 1:
 | 
			
		||||
                String arg = args[0].toLowerCase();
 | 
			
		||||
                if (space) {
 | 
			
		||||
                    Command cmd = getCommand(arg);
 | 
			
		||||
                    if (cmd != null && cmd.canExecute(player, false)) {
 | 
			
		||||
                        return cmd.tab(player, Arrays.copyOfRange(args, 1, args.length), space);
 | 
			
		||||
                    } else {
 | 
			
		||||
                        return null;
 | 
			
		||||
                    }
 | 
			
		||||
                } else {
 | 
			
		||||
                    Set<Command> commands = new HashSet<Command>();
 | 
			
		||||
                    for (Map.Entry<String, Command> entry : this.staticCommands.entrySet()) {
 | 
			
		||||
                        if (entry.getKey().startsWith(arg) && entry.getValue()
 | 
			
		||||
                            .canExecute(player, false)) {
 | 
			
		||||
                            commands.add(entry.getValue());
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    return commands;
 | 
			
		||||
                }
 | 
			
		||||
            default:
 | 
			
		||||
                Command cmd = getCommand(args[0]);
 | 
			
		||||
                if (cmd != null) {
 | 
			
		||||
                    return cmd.tab(player, Arrays.copyOfRange(args, 1, args.length), space);
 | 
			
		||||
                } else {
 | 
			
		||||
                    return null;
 | 
			
		||||
                }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String toString() {
 | 
			
		||||
        return !this.aliases.isEmpty() ? this.aliases.get(0) : this.id;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean equals(Object obj) {
 | 
			
		||||
        if (this == obj) {
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        if (getClass() != obj.getClass()) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Command other = (Command) obj;
 | 
			
		||||
        if (this.hashCode() != other.hashCode()) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        return this.getFullId().equals(other.getFullId());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public int hashCode() {
 | 
			
		||||
        return this.getFullId().hashCode();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void checkTrue(boolean mustBeTrue, C message, Object... args) {
 | 
			
		||||
        if (!mustBeTrue) {
 | 
			
		||||
            throw new CommandException(message, args);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public <T extends Object> T check(T object, C message, Object... args) {
 | 
			
		||||
        if (object == null) {
 | 
			
		||||
            throw new CommandException(message, args);
 | 
			
		||||
        }
 | 
			
		||||
        return object;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public enum CommandResult {
 | 
			
		||||
        FAILURE, SUCCESS
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    public static class CommandException extends RuntimeException {
 | 
			
		||||
        private final Object[] args;
 | 
			
		||||
        private final C message;
 | 
			
		||||
 | 
			
		||||
        public CommandException(C message, Object... args) {
 | 
			
		||||
            this.message = message;
 | 
			
		||||
            this.args = args;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        public void perform(PlotPlayer player) {
 | 
			
		||||
            if (player != null && message != null) {
 | 
			
		||||
                message.send(player, args);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,24 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.commands.RequiredType;
 | 
			
		||||
 | 
			
		||||
public interface CommandCaller {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Send the player a message.
 | 
			
		||||
     *
 | 
			
		||||
     * @param message the message to send
 | 
			
		||||
     */
 | 
			
		||||
    void sendMessage(String message);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Check the player's permissions. <i>Will be cached if permission caching is enabled.</i>
 | 
			
		||||
     *
 | 
			
		||||
     * @param permission the name of the permission
 | 
			
		||||
     */
 | 
			
		||||
    boolean hasPermission(String permission);
 | 
			
		||||
 | 
			
		||||
    boolean isPermissionSet(String permission);
 | 
			
		||||
 | 
			
		||||
    RequiredType getSuperCaller();
 | 
			
		||||
}
 | 
			
		||||
@@ -1,29 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.commands.CommandCategory;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.commands.RequiredType;
 | 
			
		||||
 | 
			
		||||
import java.lang.annotation.ElementType;
 | 
			
		||||
import java.lang.annotation.Retention;
 | 
			
		||||
import java.lang.annotation.RetentionPolicy;
 | 
			
		||||
import java.lang.annotation.Target;
 | 
			
		||||
 | 
			
		||||
@Target({ElementType.TYPE, ElementType.METHOD}) @Retention(RetentionPolicy.RUNTIME)
 | 
			
		||||
public @interface CommandDeclaration {
 | 
			
		||||
 | 
			
		||||
    String command();
 | 
			
		||||
 | 
			
		||||
    String[] aliases() default {};
 | 
			
		||||
 | 
			
		||||
    String permission() default "";
 | 
			
		||||
 | 
			
		||||
    String usage() default "";
 | 
			
		||||
 | 
			
		||||
    String description() default "";
 | 
			
		||||
 | 
			
		||||
    RequiredType requiredType() default RequiredType.NONE;
 | 
			
		||||
 | 
			
		||||
    CommandCategory category() default CommandCategory.INFO;
 | 
			
		||||
 | 
			
		||||
    boolean confirmation() default false;
 | 
			
		||||
}
 | 
			
		||||
@@ -1,87 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nonnull;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Represents a source of configurable options and settings.
 | 
			
		||||
 */
 | 
			
		||||
public interface Configuration extends ConfigurationSection {
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the default value of the given path as provided.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>If no source {@link Configuration} was provided as a default
 | 
			
		||||
     * collection, then a new {@link MemoryConfiguration} will be created to
 | 
			
		||||
     * hold the new default value.</p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>If value is null, the value will be removed from the default
 | 
			
		||||
     * Configuration source.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @param path  Path of the value to set.
 | 
			
		||||
     * @param value Value to set the default to.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown if path is null.
 | 
			
		||||
     */
 | 
			
		||||
    @Override void addDefault(@Nonnull String path, Object value);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the default values of the given paths as provided.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>If no source {@link Configuration} was provided as a default
 | 
			
		||||
     * collection, then a new {@link MemoryConfiguration} will be created to
 | 
			
		||||
     * hold the new default values.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @param defaults A map of Path->Values to add to defaults.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown if defaults is null.
 | 
			
		||||
     */
 | 
			
		||||
    void addDefaults(Map<String, Object> defaults);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the default values of the given paths as provided.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>If no source {@link Configuration} was provided as a default
 | 
			
		||||
     * collection, then a new {@link MemoryConfiguration} will be created to
 | 
			
		||||
     * hold the new default value.</p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>This method will not hold a reference to the specified Configuration,
 | 
			
		||||
     * nor will it automatically update if that Configuration ever changes. If
 | 
			
		||||
     * you check this, you should set the default source with {@link
 | 
			
		||||
     * #setDefaults(Configuration)}.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @param defaults A configuration holding a list of defaults to copy.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown if defaults is null or this.
 | 
			
		||||
     */
 | 
			
		||||
    void addDefaults(Configuration defaults);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the source {@link Configuration} for this configuration.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * If no configuration source was set, but default values were added, then
 | 
			
		||||
     * a {@link MemoryConfiguration} will be returned. If no source was set
 | 
			
		||||
     * and no defaults were set, then this method will return null.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @return Configuration source for default values, or null if none exist.
 | 
			
		||||
     */
 | 
			
		||||
    Configuration getDefaults();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the source of all default values for this {@link Configuration}.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * If a previous source was set, or previous default values were defined,
 | 
			
		||||
     * then they will not be copied to the new source.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @param defaults New source of default values for this configuration.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown if defaults is null or this.
 | 
			
		||||
     */
 | 
			
		||||
    void setDefaults(Configuration defaults);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the {@link ConfigurationOptions} for this {@link Configuration}.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>All setters through this method are chainable.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @return Options for this configuration
 | 
			
		||||
     */
 | 
			
		||||
    ConfigurationOptions options();
 | 
			
		||||
}
 | 
			
		||||
@@ -1,90 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Various settings for controlling the input and output of a {@link
 | 
			
		||||
 * Configuration}.
 | 
			
		||||
 */
 | 
			
		||||
class ConfigurationOptions {
 | 
			
		||||
    private final Configuration configuration;
 | 
			
		||||
    private char pathSeparator = '.';
 | 
			
		||||
    private boolean copyDefaults = false;
 | 
			
		||||
 | 
			
		||||
    protected ConfigurationOptions(Configuration configuration) {
 | 
			
		||||
        this.configuration = configuration;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Returns the {@link Configuration} that this object is responsible for.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Parent configuration
 | 
			
		||||
     */
 | 
			
		||||
    public Configuration configuration() {
 | 
			
		||||
        return configuration;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the char that will be used to separate {@link
 | 
			
		||||
     * ConfigurationSection}s.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This value does not affect how the {@link Configuration} is stored,
 | 
			
		||||
     * only in how you access the data. The default value is '.'.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Path separator
 | 
			
		||||
     */
 | 
			
		||||
    char pathSeparator() {
 | 
			
		||||
        return pathSeparator;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the char that will be used to separate {@link
 | 
			
		||||
     * ConfigurationSection}s.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This value does not affect how the {@link Configuration} is stored,
 | 
			
		||||
     * only in how you access the data. The default value is '.'.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value Path separator
 | 
			
		||||
     * @return This object, for chaining
 | 
			
		||||
     */
 | 
			
		||||
    public ConfigurationOptions pathSeparator(char value) {
 | 
			
		||||
        pathSeparator = value;
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the {@link Configuration} should copy values from its default
 | 
			
		||||
     * {@link Configuration} directly.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If this is true, all values in the default Configuration will be
 | 
			
		||||
     * directly copied, making it impossible to distinguish between values
 | 
			
		||||
     * that were set and values that are provided by default. As a result,
 | 
			
		||||
     * {@link ConfigurationSection#contains(String)} will always
 | 
			
		||||
     * return the same value as {@link
 | 
			
		||||
     * ConfigurationSection#isSet(String)}. The default value is
 | 
			
		||||
     * false.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Whether or not defaults are directly copied
 | 
			
		||||
     */
 | 
			
		||||
    boolean copyDefaults() {
 | 
			
		||||
        return copyDefaults;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets if the {@link Configuration} should copy values from its default
 | 
			
		||||
     * {@link Configuration} directly.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If this is true, all values in the default Configuration will be
 | 
			
		||||
     * directly copied, making it impossible to distinguish between values
 | 
			
		||||
     * that were set and values that are provided by default. As a result,
 | 
			
		||||
     * {@link ConfigurationSection#contains(String)} will always
 | 
			
		||||
     * return the same value as {@link
 | 
			
		||||
     * ConfigurationSection#isSet(String)}. The default value is
 | 
			
		||||
     * false.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value Whether or not defaults are directly copied
 | 
			
		||||
     * @return This object, for chaining
 | 
			
		||||
     */
 | 
			
		||||
    public ConfigurationOptions copyDefaults(boolean value) {
 | 
			
		||||
        copyDefaults = value;
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,649 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nonnull;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Represents a section of a {@link Configuration}.
 | 
			
		||||
 */
 | 
			
		||||
public interface ConfigurationSection {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets a set containing all keys in this section.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If deep is set to true, then this will contain all the keys within any
 | 
			
		||||
     * child {@link ConfigurationSection}s (and their children, etc). These
 | 
			
		||||
     * will be in a valid path notation for you to use.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If deep is set to false, then this will contain only the keys of any
 | 
			
		||||
     * direct children, and not their own children.
 | 
			
		||||
     *
 | 
			
		||||
     * @param deep Whether or not to get a deep list, as opposed to a shallow
 | 
			
		||||
     *             list.
 | 
			
		||||
     * @return Set of keys contained within this ConfigurationSection.
 | 
			
		||||
     */
 | 
			
		||||
    Set<String> getKeys(boolean deep);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets a Map containing all keys and their values for this section.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If deep is set to true, then this will contain all the keys and values
 | 
			
		||||
     * within any child {@link ConfigurationSection}s (and their children,
 | 
			
		||||
     * etc). These keys will be in a valid path notation for you to use.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If deep is set to false, then this will contain only the keys and
 | 
			
		||||
     * values of any direct children, and not their own children.
 | 
			
		||||
     *
 | 
			
		||||
     * @param deep Whether or not to get a deep list, as opposed to a shallow
 | 
			
		||||
     *             list.
 | 
			
		||||
     * @return Map of keys and values of this section.
 | 
			
		||||
     */
 | 
			
		||||
    Map<String, Object> getValues(boolean deep);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if this {@link ConfigurationSection} contains the given path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the value for the requested path does not exist but a default value
 | 
			
		||||
     * has been specified, this will return true.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path to check for existence.
 | 
			
		||||
     * @return True if this section contains the requested path, either via
 | 
			
		||||
     * default or being set.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown when path is {@code null}.
 | 
			
		||||
     */
 | 
			
		||||
    boolean contains(@Nonnull String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if this {@link ConfigurationSection} has a value set for the
 | 
			
		||||
     * given path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the value for the requested path does not exist but a default value
 | 
			
		||||
     * has been specified, this will still return false.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path to check for existence.
 | 
			
		||||
     * @return True if this section contains the requested path, regardless of
 | 
			
		||||
     * having a default.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown when path is {@code null}.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isSet(@Nonnull String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the path of this {@link ConfigurationSection} from its root {@link
 | 
			
		||||
     * Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>For any {@link Configuration} themselves, this will return an empty
 | 
			
		||||
     * string.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the section is no longer contained within its root for any reason,
 | 
			
		||||
     * such as being replaced with a different value,
 | 
			
		||||
     * this may return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>To retrieve the single name of this section, that is, the final part
 | 
			
		||||
     * of the path returned by this method, you may use {@link #getName()}.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Path of this section relative to its root
 | 
			
		||||
     */
 | 
			
		||||
    String getCurrentPath();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the name of this individual {@link ConfigurationSection}, in the
 | 
			
		||||
     * path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This will always be the final part of {@link #getCurrentPath()}, unless
 | 
			
		||||
     * the section is orphaned.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Name of this section
 | 
			
		||||
     */
 | 
			
		||||
    String getName();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the root {@link Configuration} that contains this {@link
 | 
			
		||||
     * ConfigurationSection}
 | 
			
		||||
     *
 | 
			
		||||
     * <p>For any {@link Configuration} themselves, this will return its own
 | 
			
		||||
     * object.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the section is no longer contained within its root for any reason,
 | 
			
		||||
     * such as being replaced with a different value,
 | 
			
		||||
     * this may return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Root configuration containing this section.
 | 
			
		||||
     */
 | 
			
		||||
    Configuration getRoot();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the parent {@link ConfigurationSection} that directly contains
 | 
			
		||||
     * this {@link ConfigurationSection}.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>For any {@link Configuration} themselves, this will return
 | 
			
		||||
     * {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the section is no longer contained within its parent for any
 | 
			
		||||
     * reason, such as being replaced with a different value, this may
 | 
			
		||||
     * return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Parent section containing this section.
 | 
			
		||||
     */
 | 
			
		||||
    ConfigurationSection getParent();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested Object by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the Object does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the Object does not exist and no
 | 
			
		||||
     * default value was specified, this will return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the Object to get.
 | 
			
		||||
     * @return Requested Object.
 | 
			
		||||
     */
 | 
			
		||||
    Object get(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested Object by path, returning a default value if not
 | 
			
		||||
     * found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the Object does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path         Path of the Object to get.
 | 
			
		||||
     * @param defaultValue The default value to return if the path is not found.
 | 
			
		||||
     * @return Requested Object.
 | 
			
		||||
     */
 | 
			
		||||
    Object getOrDefault(@Nonnull String path, Object defaultValue);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the specified path to the given value.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If value is {@code null}, the entry will be removed. Any
 | 
			
		||||
     * existing entry will be replaced, regardless of what the new value is.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Some implementations may have limitations on what you may store. See
 | 
			
		||||
     * their individual javadoc for details. No implementations should allow
 | 
			
		||||
     * you to store {@link Configuration}s or {@link ConfigurationSection}s,
 | 
			
		||||
     * please use {@link #createSection(String)} for that.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path  Path of the object to set.
 | 
			
		||||
     * @param value New value to set the path to.
 | 
			
		||||
     */
 | 
			
		||||
    void set(String path, Object value);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty {@link ConfigurationSection} at the specified path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Any value that was previously set at this path will be overwritten. If
 | 
			
		||||
     * the previous value was itself a {@link ConfigurationSection}, it will
 | 
			
		||||
     * be orphaned.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path to create the section at.
 | 
			
		||||
     * @return Newly created section
 | 
			
		||||
     */
 | 
			
		||||
    ConfigurationSection createSection(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates a {@link ConfigurationSection} at the specified path, with
 | 
			
		||||
     * specified values.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Any value that was previously set at this path will be overwritten. If
 | 
			
		||||
     * the previous value was itself a {@link ConfigurationSection}, it will
 | 
			
		||||
     * be orphaned.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path to create the section at.
 | 
			
		||||
     * @param map  The values to used.
 | 
			
		||||
     * @return Newly created section
 | 
			
		||||
     */
 | 
			
		||||
    ConfigurationSection createSection(String path, Map<?, ?> map);
 | 
			
		||||
 | 
			
		||||
    // Primitives
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested String by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the String does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the String does not exist and no
 | 
			
		||||
     * default value was specified, this will return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the String to get.
 | 
			
		||||
     * @return Requested String.
 | 
			
		||||
     */
 | 
			
		||||
    String getString(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested String by path, returning a default value if not
 | 
			
		||||
     * found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the String does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the String to get.
 | 
			
		||||
     * @param def  The default value to return if the path is not found or is
 | 
			
		||||
     *             not a String.
 | 
			
		||||
     * @return Requested String.
 | 
			
		||||
     */
 | 
			
		||||
    String getString(String path, String def);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is a String.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a String, this will return false. If
 | 
			
		||||
     * the path does not exist, this will return false. If the path does not
 | 
			
		||||
     * exist but a default value has been specified, this will check if that
 | 
			
		||||
     * defaultvalue is a String and return appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the String to check.
 | 
			
		||||
     * @return Whether or not the specified path is a String.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isString(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested int by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the int does not exist but a default value has been specified, this
 | 
			
		||||
     * will return the default value. If the int does not exist and no default
 | 
			
		||||
     * value was specified, this will return 0.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the int to get.
 | 
			
		||||
     * @return Requested int.
 | 
			
		||||
     */
 | 
			
		||||
    int getInt(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested int by path, returning a default value if not found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the int does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the int to get.
 | 
			
		||||
     * @param def  The default value to return if the path is not found or is
 | 
			
		||||
     *             not an int.
 | 
			
		||||
     * @return Requested int.
 | 
			
		||||
     */
 | 
			
		||||
    int getInt(String path, int def);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is an int.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a int, this will return false. If the
 | 
			
		||||
     * path does not exist, this will return false. If the path does not exist
 | 
			
		||||
     * but a default value has been specified, this will check if that default
 | 
			
		||||
     * value is a int and return appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the int to check.
 | 
			
		||||
     * @return Whether or not the specified path is an int.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isInt(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested boolean by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the boolean does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the boolean does not exist and
 | 
			
		||||
     * no default value was specified, this will return false.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the boolean to get.
 | 
			
		||||
     * @return Requested boolean.
 | 
			
		||||
     */
 | 
			
		||||
    boolean getBoolean(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested boolean by path, returning a default value if not
 | 
			
		||||
     * found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the boolean does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path         Path of the boolean to get.
 | 
			
		||||
     * @param defaultValue The default value to return if the path is not found or is
 | 
			
		||||
     *                     not a boolean.
 | 
			
		||||
     * @return Requested boolean.
 | 
			
		||||
     */
 | 
			
		||||
    boolean getBoolean(String path, boolean defaultValue);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is a boolean.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a boolean, this will return false. If the
 | 
			
		||||
     * path does not exist, this will return false. If the path does not exist
 | 
			
		||||
     * but a default value has been specified, this will check if that default
 | 
			
		||||
     * value is a boolean and return appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the boolean to check.
 | 
			
		||||
     * @return Whether or not the specified path is a boolean.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isBoolean(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested double by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the double does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the double does not exist and no
 | 
			
		||||
     * default value was specified, this will return 0.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the double to get.
 | 
			
		||||
     * @return Requested double.
 | 
			
		||||
     */
 | 
			
		||||
    double getDouble(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested double by path, returning a default value if not
 | 
			
		||||
     * found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the double does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path         Path of the double to get.
 | 
			
		||||
     * @param defaultValue The default value to return if the path is not found or is
 | 
			
		||||
     *                     not a double.
 | 
			
		||||
     * @return Requested double.
 | 
			
		||||
     */
 | 
			
		||||
    double getDouble(String path, double defaultValue);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is a double.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a double, this will return false. If the
 | 
			
		||||
     * path does not exist, this will return false. If the path does not exist
 | 
			
		||||
     * but a default value has been specified, this will check if that default
 | 
			
		||||
     * value is a double and return appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the double to check.
 | 
			
		||||
     * @return Whether or not the specified path is a double.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isDouble(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested long by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the long does not exist but a default value has been specified, this
 | 
			
		||||
     * will return the default value. If the long does not exist and no
 | 
			
		||||
     * default value was specified, this will return 0.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the long to get.
 | 
			
		||||
     * @return Requested long.
 | 
			
		||||
     */
 | 
			
		||||
    long getLong(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested long by path, returning a default value if not
 | 
			
		||||
     * found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the long does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the long to get.
 | 
			
		||||
     * @param def  The default value to return if the path is not found or is
 | 
			
		||||
     *             not a long.
 | 
			
		||||
     * @return Requested long.
 | 
			
		||||
     */
 | 
			
		||||
    long getLong(String path, long def);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is a long.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a long, this will return false. If the
 | 
			
		||||
     * path does not exist, this will return false. If the path does not exist
 | 
			
		||||
     * but a default value has been specified, this will check if that default
 | 
			
		||||
     * value is a long and return appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the long to check.
 | 
			
		||||
     * @return Whether or not the specified path is a long.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isLong(String path);
 | 
			
		||||
 | 
			
		||||
    // Java
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified, this
 | 
			
		||||
     * will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return null.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List.
 | 
			
		||||
     */
 | 
			
		||||
    List<?> getList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List by path, returning a default value if not
 | 
			
		||||
     * found.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist then the specified default value will
 | 
			
		||||
     * returned regardless of if a default has been identified in the root
 | 
			
		||||
     * {@link Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @param def  The default value to return if the path is not found or is
 | 
			
		||||
     *             not a List.
 | 
			
		||||
     * @return Requested List.
 | 
			
		||||
     */
 | 
			
		||||
    List<?> getList(String path, List<?> def);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is a List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a List, this will return false. If the
 | 
			
		||||
     * path does not exist, this will return false. If the path does not exist
 | 
			
		||||
     * but a default value has been specified, this will check if that default
 | 
			
		||||
     * value is a List and return appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to check.
 | 
			
		||||
     * @return Whether or not the specified path is a List.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of String by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a String if possible,
 | 
			
		||||
     * but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of String.
 | 
			
		||||
     */
 | 
			
		||||
    List<String> getStringList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Integer by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Integer if
 | 
			
		||||
     * possible, but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Integer.
 | 
			
		||||
     */
 | 
			
		||||
    List<Integer> getIntegerList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Boolean by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Boolean if
 | 
			
		||||
     * possible, but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Boolean.
 | 
			
		||||
     */
 | 
			
		||||
    List<Boolean> getBooleanList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Double by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Double if possible,
 | 
			
		||||
     * but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Double.
 | 
			
		||||
     */
 | 
			
		||||
    List<Double> getDoubleList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Float by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Float if possible,
 | 
			
		||||
     * but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Float.
 | 
			
		||||
     */
 | 
			
		||||
    List<Float> getFloatList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Long by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Long if possible,
 | 
			
		||||
     * but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Long.
 | 
			
		||||
     */
 | 
			
		||||
    List<Long> getLongList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Byte by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Byte if possible,
 | 
			
		||||
     * but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Byte.
 | 
			
		||||
     */
 | 
			
		||||
    List<Byte> getByteList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Character by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Character if
 | 
			
		||||
     * possible, but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Character.
 | 
			
		||||
     */
 | 
			
		||||
    List<Character> getCharacterList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Short by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Short if
 | 
			
		||||
     * possible, but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Short.
 | 
			
		||||
     */
 | 
			
		||||
    List<Short> getShortList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested List of Maps by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the List does not exist but a default value has been specified,
 | 
			
		||||
     * this will return the default value. If the List does not exist and no
 | 
			
		||||
     * default value was specified, this will return an empty List.
 | 
			
		||||
     * <p>This method will attempt to cast any values into a Map if possible,
 | 
			
		||||
     * but may miss any values out if they are not compatible.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the List to get.
 | 
			
		||||
     * @return Requested List of Maps.
 | 
			
		||||
     */
 | 
			
		||||
    List<Map<?, ?>> getMapList(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the requested ConfigurationSection by path.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the ConfigurationSection does not exist but a default value has
 | 
			
		||||
     * been specified, this will return the default value. If the
 | 
			
		||||
     * ConfigurationSection does not exist and no default value was specified,
 | 
			
		||||
     * this will return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the ConfigurationSection to get.
 | 
			
		||||
     * @return Requested ConfigurationSection.
 | 
			
		||||
     */
 | 
			
		||||
    ConfigurationSection getConfigurationSection(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Checks if the specified path is a ConfigurationSection.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the path exists but is not a ConfigurationSection, this will return
 | 
			
		||||
     * false. If the path does not exist, this will return false. If the path
 | 
			
		||||
     * does not exist but a default value has been specified, this will check
 | 
			
		||||
     * if that default value is a ConfigurationSection and return
 | 
			
		||||
     * appropriately.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path Path of the ConfigurationSection to check.
 | 
			
		||||
     * @return Whether or not the specified path is a ConfigurationSection.
 | 
			
		||||
     */
 | 
			
		||||
    boolean isConfigurationSection(String path);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the equivalent {@link ConfigurationSection} from the default
 | 
			
		||||
     * {@link Configuration} defined in {@link #getRoot()}.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the root contains no defaults, or the defaults doesn't contain a
 | 
			
		||||
     * value for this path, or the value at this path is not a {@link
 | 
			
		||||
     * ConfigurationSection} then this will return {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Equivalent section in root configuration
 | 
			
		||||
     */
 | 
			
		||||
    ConfigurationSection getDefaultSection();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the default value in the root at the given path as provided.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If no source {@link Configuration} was provided as a default
 | 
			
		||||
     * collection, then a new {@link MemoryConfiguration} will be created to
 | 
			
		||||
     * hold the new default value.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If value is {@code null}, the value will be removed from the
 | 
			
		||||
     * default Configuration source.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the value as returned by {@link #getDefaultSection()} is
 | 
			
		||||
     * {@code null}, then this will create a new section at the path,
 | 
			
		||||
     * replacing anything that may have existed there previously.
 | 
			
		||||
     *
 | 
			
		||||
     * @param path  Path of the value to set
 | 
			
		||||
     * @param value Value to set the default to
 | 
			
		||||
     * @throws IllegalArgumentException Thrown if path is {@code null}
 | 
			
		||||
     */
 | 
			
		||||
    void addDefault(@Nonnull String path, Object value);
 | 
			
		||||
}
 | 
			
		||||
@@ -1,45 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Exception thrown when attempting to load an invalid {@link Configuration}.
 | 
			
		||||
 */
 | 
			
		||||
@SuppressWarnings("serial") public class InvalidConfigurationException extends Exception {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates a new instance of InvalidConfigurationException without a
 | 
			
		||||
     * message or cause.
 | 
			
		||||
     */
 | 
			
		||||
    public InvalidConfigurationException() {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructs an instance of InvalidConfigurationException with the
 | 
			
		||||
     * specified message.
 | 
			
		||||
     *
 | 
			
		||||
     * @param msg The details of the exception.
 | 
			
		||||
     */
 | 
			
		||||
    public InvalidConfigurationException(String msg) {
 | 
			
		||||
        super(msg);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructs an instance of InvalidConfigurationException with the
 | 
			
		||||
     * specified cause.
 | 
			
		||||
     *
 | 
			
		||||
     * @param cause The cause of the exception.
 | 
			
		||||
     */
 | 
			
		||||
    public InvalidConfigurationException(Throwable cause) {
 | 
			
		||||
        super(cause);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructs an instance of InvalidConfigurationException with the
 | 
			
		||||
     * specified message and cause.
 | 
			
		||||
     *
 | 
			
		||||
     * @param cause The cause of the exception.
 | 
			
		||||
     * @param msg   The details of the exception.
 | 
			
		||||
     */
 | 
			
		||||
    public InvalidConfigurationException(String msg, Throwable cause) {
 | 
			
		||||
        super(msg, cause);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,73 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nonnull;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * This is a {@link Configuration} implementation that does not save or load
 | 
			
		||||
 * from any source, and stores all values in memory only.
 | 
			
		||||
 * This is useful for temporary Configurations for providing defaults.
 | 
			
		||||
 */
 | 
			
		||||
public class MemoryConfiguration extends MemorySection implements Configuration {
 | 
			
		||||
    protected Configuration defaults;
 | 
			
		||||
    protected MemoryConfigurationOptions options;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty {@link MemoryConfiguration} with no default values.
 | 
			
		||||
     */
 | 
			
		||||
    public MemoryConfiguration() {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty {@link MemoryConfiguration} using the specified {@link
 | 
			
		||||
     * Configuration} as a source for all default values.
 | 
			
		||||
     *
 | 
			
		||||
     * @param defaults Default value provider
 | 
			
		||||
     * @throws IllegalArgumentException Thrown if defaults is null
 | 
			
		||||
     */
 | 
			
		||||
    public MemoryConfiguration(Configuration defaults) {
 | 
			
		||||
        this.defaults = defaults;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void addDefault(@Nonnull String path, Object value) {
 | 
			
		||||
        if (this.defaults == null) {
 | 
			
		||||
            this.defaults = new MemoryConfiguration();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        this.defaults.set(path, value);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void addDefaults(Map<String, Object> defaults) {
 | 
			
		||||
        for (Map.Entry<String, Object> entry : defaults.entrySet()) {
 | 
			
		||||
            addDefault(entry.getKey(), entry.getValue());
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void addDefaults(Configuration defaults) {
 | 
			
		||||
        addDefaults(defaults.getValues(true));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public Configuration getDefaults() {
 | 
			
		||||
        return this.defaults;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void setDefaults(Configuration defaults) {
 | 
			
		||||
        if (defaults == null) {
 | 
			
		||||
            throw new NullPointerException("Defaults may not be null");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        this.defaults = defaults;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public ConfigurationSection getParent() {
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public MemoryConfigurationOptions options() {
 | 
			
		||||
        if (this.options == null) {
 | 
			
		||||
            this.options = new MemoryConfigurationOptions(this);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return this.options;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,25 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Various settings for controlling the input and output of a {@link
 | 
			
		||||
 * MemoryConfiguration}.
 | 
			
		||||
 */
 | 
			
		||||
public class MemoryConfigurationOptions extends ConfigurationOptions {
 | 
			
		||||
    protected MemoryConfigurationOptions(MemoryConfiguration configuration) {
 | 
			
		||||
        super(configuration);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public MemoryConfiguration configuration() {
 | 
			
		||||
        return (MemoryConfiguration) super.configuration();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public MemoryConfigurationOptions copyDefaults(boolean value) {
 | 
			
		||||
        super.copyDefaults(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public MemoryConfigurationOptions pathSeparator(char value) {
 | 
			
		||||
        super.pathSeparator(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,771 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nonnull;
 | 
			
		||||
import java.util.*;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * A type of {@link ConfigurationSection} that is stored in memory.
 | 
			
		||||
 */
 | 
			
		||||
public class MemorySection implements ConfigurationSection {
 | 
			
		||||
 | 
			
		||||
    protected final Map<String, Object> map = new LinkedHashMap<>();
 | 
			
		||||
    private final Configuration root;
 | 
			
		||||
    private final ConfigurationSection parent;
 | 
			
		||||
    private final String path;
 | 
			
		||||
    private final String fullPath;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty MemorySection for use as a root {@link Configuration} section.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Note that calling this without being yourself a {@link Configuration}
 | 
			
		||||
     * will throw an exception!
 | 
			
		||||
     *
 | 
			
		||||
     * @throws IllegalStateException Thrown if this is not a {@link Configuration} root.
 | 
			
		||||
     */
 | 
			
		||||
    protected MemorySection() {
 | 
			
		||||
        if (!(this instanceof Configuration)) {
 | 
			
		||||
            throw new IllegalStateException(
 | 
			
		||||
                "Cannot construct a root MemorySection when not a Configuration");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        this.path = "";
 | 
			
		||||
        this.fullPath = "";
 | 
			
		||||
        this.parent = null;
 | 
			
		||||
        this.root = (Configuration) this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty MemorySection with the specified parent and path.
 | 
			
		||||
     *
 | 
			
		||||
     * @param parent Parent section that contains this own section.
 | 
			
		||||
     * @param path   Path that you may access this section from via the root {@link Configuration}.
 | 
			
		||||
     * @throws IllegalArgumentException Thrown is parent or path is null, or if parent contains no
 | 
			
		||||
     *                                  root Configuration.
 | 
			
		||||
     */
 | 
			
		||||
    protected MemorySection(ConfigurationSection parent, String path) {
 | 
			
		||||
        this.path = path;
 | 
			
		||||
        this.parent = parent;
 | 
			
		||||
        this.root = parent.getRoot();
 | 
			
		||||
 | 
			
		||||
        if (this.root == null) {
 | 
			
		||||
            throw new NullPointerException("Path may not be orphaned");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        this.fullPath = createPath(parent, path);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static double toDouble(Object obj, double def) {
 | 
			
		||||
        if (obj instanceof Number) {
 | 
			
		||||
            return ((Number) obj).doubleValue();
 | 
			
		||||
        }
 | 
			
		||||
        if (obj instanceof String) {
 | 
			
		||||
            try {
 | 
			
		||||
                return Double.parseDouble((String) obj);
 | 
			
		||||
            } catch (NumberFormatException ignored) {
 | 
			
		||||
            }
 | 
			
		||||
        } else if (obj instanceof List) {
 | 
			
		||||
            List<?> val = (List<?>) obj;
 | 
			
		||||
            if (!val.isEmpty()) {
 | 
			
		||||
                return toDouble(val.get(0), def);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return def;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static int toInt(Object obj, int def) {
 | 
			
		||||
        if (obj instanceof Number) {
 | 
			
		||||
            return ((Number) obj).intValue();
 | 
			
		||||
        }
 | 
			
		||||
        if (obj instanceof String) {
 | 
			
		||||
            try {
 | 
			
		||||
                return Integer.parseInt((String) obj);
 | 
			
		||||
            } catch (NumberFormatException ignored) {
 | 
			
		||||
            }
 | 
			
		||||
        } else if (obj instanceof List) {
 | 
			
		||||
            List<?> val = (List<?>) obj;
 | 
			
		||||
            if (!val.isEmpty()) {
 | 
			
		||||
                return toInt(val.get(0), def);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return def;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static long toLong(Object obj, long def) {
 | 
			
		||||
        if (obj instanceof Number) {
 | 
			
		||||
            return ((Number) obj).longValue();
 | 
			
		||||
        }
 | 
			
		||||
        if (obj instanceof String) {
 | 
			
		||||
            try {
 | 
			
		||||
                return Long.parseLong((String) obj);
 | 
			
		||||
            } catch (NumberFormatException ignored) {
 | 
			
		||||
            }
 | 
			
		||||
        } else if (obj instanceof List) {
 | 
			
		||||
            List<?> val = (List<?>) obj;
 | 
			
		||||
            if (!val.isEmpty()) {
 | 
			
		||||
                return toLong(val.get(0), def);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return def;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates a full path to the given {@link ConfigurationSection} from its root {@link
 | 
			
		||||
     * Configuration}.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>You may use this method for any given {@link ConfigurationSection}, not
 | 
			
		||||
     * only {@link MemorySection}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param section Section to create a path for.
 | 
			
		||||
     * @param key     Name of the specified section.
 | 
			
		||||
     * @return Full path of the section from its root.
 | 
			
		||||
     */
 | 
			
		||||
    public static String createPath(ConfigurationSection section, String key) {
 | 
			
		||||
        return createPath(section, key, section.getRoot());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates a relative path to the given {@link ConfigurationSection} from the given relative
 | 
			
		||||
     * section.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>You may use this method for any given {@link ConfigurationSection}, not
 | 
			
		||||
     * only {@link MemorySection}.
 | 
			
		||||
     *
 | 
			
		||||
     * @param section    Section to create a path for.
 | 
			
		||||
     * @param key        Name of the specified section.
 | 
			
		||||
     * @param relativeTo Section to create the path relative to.
 | 
			
		||||
     * @return Full path of the section from its root.
 | 
			
		||||
     */
 | 
			
		||||
    public static String createPath(ConfigurationSection section, String key,
 | 
			
		||||
        ConfigurationSection relativeTo) {
 | 
			
		||||
        Configuration root = section.getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            throw new IllegalStateException("Cannot create path without a root");
 | 
			
		||||
        }
 | 
			
		||||
        char separator = root.options().pathSeparator();
 | 
			
		||||
 | 
			
		||||
        StringBuilder builder = new StringBuilder();
 | 
			
		||||
        for (ConfigurationSection parent = section;
 | 
			
		||||
             (parent != null) && (parent != relativeTo); parent = parent.getParent()) {
 | 
			
		||||
            if (builder.length() > 0) {
 | 
			
		||||
                builder.insert(0, separator);
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            builder.insert(0, parent.getName());
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if ((key != null) && !key.isEmpty()) {
 | 
			
		||||
            if (builder.length() > 0) {
 | 
			
		||||
                builder.append(separator);
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            builder.append(key);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return builder.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public Set<String> getKeys(boolean deep) {
 | 
			
		||||
        Set<String> result = new LinkedHashSet<>();
 | 
			
		||||
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if ((root != null) && root.options().copyDefaults()) {
 | 
			
		||||
            ConfigurationSection defaults = getDefaultSection();
 | 
			
		||||
 | 
			
		||||
            if (defaults != null) {
 | 
			
		||||
                result.addAll(defaults.getKeys(deep));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        mapChildrenKeys(result, this, deep);
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public Map<String, Object> getValues(boolean deep) {
 | 
			
		||||
        Map<String, Object> result = new LinkedHashMap<>();
 | 
			
		||||
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if ((root != null) && root.options().copyDefaults()) {
 | 
			
		||||
            ConfigurationSection defaults = getDefaultSection();
 | 
			
		||||
 | 
			
		||||
            if (defaults != null) {
 | 
			
		||||
                result.putAll(defaults.getValues(deep));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        mapChildrenValues(result, this, deep);
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean contains(@Nonnull String path) {
 | 
			
		||||
        return get(path) != null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isSet(@Nonnull String path) {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (root.options().copyDefaults()) {
 | 
			
		||||
            return contains(path);
 | 
			
		||||
        }
 | 
			
		||||
        return getOrDefault(path, null) != null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String getCurrentPath() {
 | 
			
		||||
        return this.fullPath;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String getName() {
 | 
			
		||||
        return this.path;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public Configuration getRoot() {
 | 
			
		||||
        return this.root;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public ConfigurationSection getParent() {
 | 
			
		||||
        return this.parent;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void addDefault(@Nonnull String path, Object value) {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            throw new IllegalStateException("Cannot add default without root");
 | 
			
		||||
        }
 | 
			
		||||
        if (root == this) {
 | 
			
		||||
            throw new UnsupportedOperationException(
 | 
			
		||||
                "Unsupported addDefault(String, Object) implementation");
 | 
			
		||||
        }
 | 
			
		||||
        root.addDefault(createPath(this, path), value);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public ConfigurationSection getDefaultSection() {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        Configuration defaults = root == null ? null : root.getDefaults();
 | 
			
		||||
 | 
			
		||||
        if (defaults != null) {
 | 
			
		||||
            if (defaults.isConfigurationSection(getCurrentPath())) {
 | 
			
		||||
                return defaults.getConfigurationSection(getCurrentPath());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void set(String path, Object value) {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            throw new IllegalStateException("Cannot use section without a root");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        char separator = root.options().pathSeparator();
 | 
			
		||||
        // i1 is the leading (higher) index
 | 
			
		||||
        // i2 is the trailing (lower) index
 | 
			
		||||
        int i1 = -1;
 | 
			
		||||
        int i2;
 | 
			
		||||
        ConfigurationSection section = this;
 | 
			
		||||
        while ((i1 = path.indexOf(separator, i2 = i1 + 1)) != -1) {
 | 
			
		||||
            String node = path.substring(i2, i1);
 | 
			
		||||
            ConfigurationSection subSection = section.getConfigurationSection(node);
 | 
			
		||||
            if (subSection == null) {
 | 
			
		||||
                section = section.createSection(node);
 | 
			
		||||
            } else {
 | 
			
		||||
                section = subSection;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        String key = path.substring(i2);
 | 
			
		||||
        if (section == this) {
 | 
			
		||||
            if (value == null) {
 | 
			
		||||
                this.map.remove(key);
 | 
			
		||||
            } else {
 | 
			
		||||
                this.map.put(key, value);
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            section.set(key, value);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public Object get(String path) {
 | 
			
		||||
        return getOrDefault(path, getDefault(path));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public Object getOrDefault(@Nonnull String path, Object defaultValue) {
 | 
			
		||||
        if (path.isEmpty()) {
 | 
			
		||||
            return this;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            throw new IllegalStateException("Cannot access section without a root");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        char separator = root.options().pathSeparator();
 | 
			
		||||
        // i1 is the leading (higher) index
 | 
			
		||||
        // i2 is the trailing (lower) index
 | 
			
		||||
        int i1 = -1;
 | 
			
		||||
        int i2;
 | 
			
		||||
        ConfigurationSection section = this;
 | 
			
		||||
        while ((i1 = path.indexOf(separator, i2 = i1 + 1)) != -1) {
 | 
			
		||||
            section = section.getConfigurationSection(path.substring(i2, i1));
 | 
			
		||||
            if (section == null) {
 | 
			
		||||
                return defaultValue;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        String key = path.substring(i2);
 | 
			
		||||
        if (section == this) {
 | 
			
		||||
            Object result = this.map.get(key);
 | 
			
		||||
            if (result == null) {
 | 
			
		||||
                return defaultValue;
 | 
			
		||||
            } else {
 | 
			
		||||
                return result;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return section.getOrDefault(key, defaultValue);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public ConfigurationSection createSection(String path) {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            throw new IllegalStateException("Cannot create section without a root");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        char separator = root.options().pathSeparator();
 | 
			
		||||
        // i1 is the leading (higher) index
 | 
			
		||||
        // i2 is the trailing (lower) index
 | 
			
		||||
        int i1 = -1;
 | 
			
		||||
        int i2;
 | 
			
		||||
        ConfigurationSection section = this;
 | 
			
		||||
        while ((i1 = path.indexOf(separator, i2 = i1 + 1)) != -1) {
 | 
			
		||||
            String node = path.substring(i2, i1);
 | 
			
		||||
            ConfigurationSection subSection = section.getConfigurationSection(node);
 | 
			
		||||
            if (subSection == null) {
 | 
			
		||||
                section = section.createSection(node);
 | 
			
		||||
            } else {
 | 
			
		||||
                section = subSection;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        String key = path.substring(i2);
 | 
			
		||||
        if (section == this) {
 | 
			
		||||
            ConfigurationSection result = new MemorySection(this, key);
 | 
			
		||||
            this.map.put(key, result);
 | 
			
		||||
            return result;
 | 
			
		||||
        }
 | 
			
		||||
        return section.createSection(key);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public ConfigurationSection createSection(String path, Map<?, ?> map) {
 | 
			
		||||
        ConfigurationSection section = createSection(path);
 | 
			
		||||
 | 
			
		||||
        for (Map.Entry<?, ?> entry : map.entrySet()) {
 | 
			
		||||
            if (entry.getValue() instanceof Map) {
 | 
			
		||||
                section.createSection(entry.getKey().toString(), (Map<?, ?>) entry.getValue());
 | 
			
		||||
            } else {
 | 
			
		||||
                section.set(entry.getKey().toString(), entry.getValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return section;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Primitives
 | 
			
		||||
    @Override public String getString(String path) {
 | 
			
		||||
        Object def = getDefault(path);
 | 
			
		||||
        return getString(path, def != null ? def.toString() : null);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String getString(String path, String def) {
 | 
			
		||||
        Object val = getOrDefault(path, def);
 | 
			
		||||
        if (val != null) {
 | 
			
		||||
            return val.toString();
 | 
			
		||||
        } else {
 | 
			
		||||
            return def;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isString(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof String;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public int getInt(String path) {
 | 
			
		||||
        Object def = getDefault(path);
 | 
			
		||||
        return getInt(path, toInt(def, 0));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public int getInt(String path, int def) {
 | 
			
		||||
        Object val = getOrDefault(path, def);
 | 
			
		||||
        return toInt(val, def);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isInt(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof Integer;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean getBoolean(String path) {
 | 
			
		||||
        Object def = getDefault(path);
 | 
			
		||||
        if (def instanceof Boolean) {
 | 
			
		||||
            return getBoolean(path, (Boolean) def);
 | 
			
		||||
        } else {
 | 
			
		||||
            return getBoolean(path, false);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean getBoolean(String path, boolean defaultValue) {
 | 
			
		||||
        Object val = getOrDefault(path, defaultValue);
 | 
			
		||||
        if (val instanceof Boolean) {
 | 
			
		||||
            return (Boolean) val;
 | 
			
		||||
        } else {
 | 
			
		||||
            return defaultValue;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isBoolean(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof Boolean;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public double getDouble(String path) {
 | 
			
		||||
        Object def = getDefault(path);
 | 
			
		||||
        return getDouble(path, toDouble(def, 0));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public double getDouble(String path, double defaultValue) {
 | 
			
		||||
        Object val = getOrDefault(path, defaultValue);
 | 
			
		||||
        return toDouble(val, defaultValue);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isDouble(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof Double;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public long getLong(String path) {
 | 
			
		||||
        Object def = getDefault(path);
 | 
			
		||||
        return getLong(path, toLong(def, 0));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public long getLong(String path, long def) {
 | 
			
		||||
        Object val = getOrDefault(path, def);
 | 
			
		||||
        return toLong(val, def);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isLong(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof Long;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Java
 | 
			
		||||
    @Override public List<?> getList(String path) {
 | 
			
		||||
        Object def = getDefault(path);
 | 
			
		||||
        return getList(path, def instanceof List ? (List<?>) def : null);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<?> getList(String path, List<?> def) {
 | 
			
		||||
        Object val = getOrDefault(path, def);
 | 
			
		||||
        return (List<?>) ((val instanceof List) ? val : def);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isList(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof List;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<String> getStringList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        if (list == null) {
 | 
			
		||||
            return new ArrayList<>(0);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        List<String> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if ((object instanceof String) || isPrimitiveWrapper(object)) {
 | 
			
		||||
                result.add(String.valueOf(object));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Integer> getIntegerList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Integer> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Integer) {
 | 
			
		||||
                result.add((Integer) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                try {
 | 
			
		||||
                    result.add(Integer.valueOf((String) object));
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Character) {
 | 
			
		||||
                result.add((int) (Character) object);
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add(((Number) object).intValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Boolean> getBooleanList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Boolean> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Boolean) {
 | 
			
		||||
                result.add((Boolean) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                if (Boolean.TRUE.toString().equals(object)) {
 | 
			
		||||
                    result.add(true);
 | 
			
		||||
                } else if (Boolean.FALSE.toString().equals(object)) {
 | 
			
		||||
                    result.add(false);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Double> getDoubleList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Double> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Double) {
 | 
			
		||||
                result.add((Double) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                try {
 | 
			
		||||
                    result.add(Double.valueOf((String) object));
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Character) {
 | 
			
		||||
                result.add((double) (Character) object);
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add(((Number) object).doubleValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Float> getFloatList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Float> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Float) {
 | 
			
		||||
                result.add((Float) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                try {
 | 
			
		||||
                    result.add(Float.valueOf((String) object));
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Character) {
 | 
			
		||||
                result.add((float) (Character) object);
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add(((Number) object).floatValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Long> getLongList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Long> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Long) {
 | 
			
		||||
                result.add((Long) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                try {
 | 
			
		||||
                    result.add(Long.valueOf((String) object));
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Character) {
 | 
			
		||||
                result.add((long) (Character) object);
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add(((Number) object).longValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Byte> getByteList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Byte> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Byte) {
 | 
			
		||||
                result.add((Byte) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                try {
 | 
			
		||||
                    result.add(Byte.valueOf((String) object));
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Character) {
 | 
			
		||||
                result.add((byte) ((Character) object).charValue());
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add(((Number) object).byteValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Character> getCharacterList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Character> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Character) {
 | 
			
		||||
                result.add((Character) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                String str = (String) object;
 | 
			
		||||
 | 
			
		||||
                if (str.length() == 1) {
 | 
			
		||||
                    result.add(str.charAt(0));
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add((char) ((Number) object).intValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Short> getShortList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
 | 
			
		||||
        List<Short> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Short) {
 | 
			
		||||
                result.add((Short) object);
 | 
			
		||||
            } else if (object instanceof String) {
 | 
			
		||||
                try {
 | 
			
		||||
                    result.add(Short.valueOf((String) object));
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                }
 | 
			
		||||
            } else if (object instanceof Character) {
 | 
			
		||||
                result.add((short) ((Character) object).charValue());
 | 
			
		||||
            } else if (object instanceof Number) {
 | 
			
		||||
                result.add(((Number) object).shortValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public List<Map<?, ?>> getMapList(String path) {
 | 
			
		||||
        List<?> list = getList(path);
 | 
			
		||||
        List<Map<?, ?>> result = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
        for (Object object : list) {
 | 
			
		||||
            if (object instanceof Map) {
 | 
			
		||||
                result.add((Map<?, ?>) object);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public ConfigurationSection getConfigurationSection(String path) {
 | 
			
		||||
        Object val = getOrDefault(path, null);
 | 
			
		||||
        if (val != null) {
 | 
			
		||||
            return (val instanceof ConfigurationSection) ? (ConfigurationSection) val : null;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        val = getOrDefault(path, getDefault(path));
 | 
			
		||||
        return (val instanceof ConfigurationSection) ? createSection(path) : null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean isConfigurationSection(String path) {
 | 
			
		||||
        Object val = get(path);
 | 
			
		||||
        return val instanceof ConfigurationSection;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected boolean isPrimitiveWrapper(Object input) {
 | 
			
		||||
        return (input instanceof Integer) || (input instanceof Boolean)
 | 
			
		||||
            || (input instanceof Character) || (input instanceof Byte) || (input instanceof Short)
 | 
			
		||||
            || (input instanceof Double) || (input instanceof Long) || (input instanceof Float);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected Object getDefault(String path) {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        Configuration defaults = root == null ? null : root.getDefaults();
 | 
			
		||||
        return (defaults == null) ? null : defaults.get(createPath(this, path));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected void mapChildrenKeys(Set<String> output, ConfigurationSection section, boolean deep) {
 | 
			
		||||
        if (section instanceof MemorySection) {
 | 
			
		||||
            MemorySection sec = (MemorySection) section;
 | 
			
		||||
 | 
			
		||||
            for (Map.Entry<String, Object> entry : sec.map.entrySet()) {
 | 
			
		||||
                output.add(createPath(section, entry.getKey(), this));
 | 
			
		||||
 | 
			
		||||
                if (deep && (entry.getValue() instanceof ConfigurationSection)) {
 | 
			
		||||
                    ConfigurationSection subsection = (ConfigurationSection) entry.getValue();
 | 
			
		||||
                    mapChildrenKeys(output, subsection, deep);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            Set<String> keys = section.getKeys(deep);
 | 
			
		||||
 | 
			
		||||
            for (String key : keys) {
 | 
			
		||||
                output.add(createPath(section, key, this));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected void mapChildrenValues(Map<String, Object> output, ConfigurationSection section,
 | 
			
		||||
        boolean deep) {
 | 
			
		||||
        if (section instanceof MemorySection) {
 | 
			
		||||
            MemorySection sec = (MemorySection) section;
 | 
			
		||||
 | 
			
		||||
            for (Map.Entry<String, Object> entry : sec.map.entrySet()) {
 | 
			
		||||
                output.put(createPath(section, entry.getKey(), this), entry.getValue());
 | 
			
		||||
 | 
			
		||||
                if (entry.getValue() instanceof ConfigurationSection) {
 | 
			
		||||
                    if (deep) {
 | 
			
		||||
                        mapChildrenValues(output, (ConfigurationSection) entry.getValue(), deep);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            Map<String, Object> values = section.getValues(deep);
 | 
			
		||||
 | 
			
		||||
            for (Map.Entry<String, Object> entry : values.entrySet()) {
 | 
			
		||||
                output.put(createPath(section, entry.getKey(), this), entry.getValue());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String toString() {
 | 
			
		||||
        Configuration root = getRoot();
 | 
			
		||||
        if (root == null) {
 | 
			
		||||
            return getClass().getSimpleName() + "[path='" + getCurrentPath() + "', root='" + null
 | 
			
		||||
                + "']";
 | 
			
		||||
        } else {
 | 
			
		||||
            return getClass().getSimpleName() + "[path='" + getCurrentPath() + "', root='" + root
 | 
			
		||||
                .getClass().getSimpleName() + "']";
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,158 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.file;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.Configuration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.InvalidConfigurationException;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.MemoryConfiguration;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nonnull;
 | 
			
		||||
import java.io.*;
 | 
			
		||||
import java.nio.charset.StandardCharsets;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * This is a base class for all File based implementations of {@link
 | 
			
		||||
 * Configuration}.
 | 
			
		||||
 */
 | 
			
		||||
public abstract class FileConfiguration extends MemoryConfiguration {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty {@link FileConfiguration} with no default values.
 | 
			
		||||
     */
 | 
			
		||||
    FileConfiguration() {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates an empty {@link FileConfiguration} using the specified {@link
 | 
			
		||||
     * Configuration} as a source for all default values.
 | 
			
		||||
     *
 | 
			
		||||
     * @param defaults Default value provider
 | 
			
		||||
     */
 | 
			
		||||
    public FileConfiguration(Configuration defaults) {
 | 
			
		||||
        super(defaults);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Saves this {@link FileConfiguration} to the specified location.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the file does not exist, it will be created. If already exists, it
 | 
			
		||||
     * will be overwritten. If it cannot be overwritten or created, an
 | 
			
		||||
     * exception will be thrown.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This method will save using the system default encoding, or possibly
 | 
			
		||||
     * using UTF8.
 | 
			
		||||
     *
 | 
			
		||||
     * @param file File to save to.
 | 
			
		||||
     * @throws IOException Thrown when the given file cannot be written to for
 | 
			
		||||
     *                     any reason.
 | 
			
		||||
     */
 | 
			
		||||
    public void save(File file) throws IOException {
 | 
			
		||||
        File parent = file.getParentFile();
 | 
			
		||||
        if (parent != null) {
 | 
			
		||||
            parent.mkdirs();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        String data = saveToString();
 | 
			
		||||
 | 
			
		||||
        try (Writer writer = new OutputStreamWriter(new FileOutputStream(file),
 | 
			
		||||
            StandardCharsets.UTF_8)) {
 | 
			
		||||
            writer.write(data);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Saves this {@link FileConfiguration} to a string, and returns it.
 | 
			
		||||
     *
 | 
			
		||||
     * @return String containing this configuration.
 | 
			
		||||
     */
 | 
			
		||||
    public abstract String saveToString();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Loads this {@link FileConfiguration} from the specified location.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>All the values contained within this configuration will be removed,
 | 
			
		||||
     * leaving only settings and defaults, and the new values will be loaded
 | 
			
		||||
     * from the given file.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the file cannot be loaded for any reason, an exception will be
 | 
			
		||||
     * thrown.
 | 
			
		||||
     *
 | 
			
		||||
     * @param file File to load from.
 | 
			
		||||
     * @throws FileNotFoundException         Thrown when the given file cannot be
 | 
			
		||||
     *                                       opened.
 | 
			
		||||
     * @throws IOException                   Thrown when the given file cannot be read.
 | 
			
		||||
     * @throws InvalidConfigurationException Thrown when the given file is not
 | 
			
		||||
     *                                       a valid Configuration.
 | 
			
		||||
     * @throws IllegalArgumentException      Thrown when file is null.
 | 
			
		||||
     */
 | 
			
		||||
    public void load(@Nonnull File file) throws IOException, InvalidConfigurationException {
 | 
			
		||||
 | 
			
		||||
        FileInputStream stream = new FileInputStream(file);
 | 
			
		||||
 | 
			
		||||
        load(new InputStreamReader(stream, StandardCharsets.UTF_8));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Loads this {@link FileConfiguration} from the specified reader.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>All the values contained within this configuration will be removed,
 | 
			
		||||
     * leaving only settings and defaults, and the new values will be loaded
 | 
			
		||||
     * from the given stream.
 | 
			
		||||
     *
 | 
			
		||||
     * @param reader the reader to load from
 | 
			
		||||
     * @throws IOException                   thrown when underlying reader throws an IOException
 | 
			
		||||
     * @throws InvalidConfigurationException thrown when the reader does not
 | 
			
		||||
     *                                       represent a valid Configuration
 | 
			
		||||
     */
 | 
			
		||||
    public void load(Reader reader) throws IOException, InvalidConfigurationException {
 | 
			
		||||
 | 
			
		||||
        StringBuilder builder = new StringBuilder();
 | 
			
		||||
 | 
			
		||||
        try (BufferedReader input = reader instanceof BufferedReader ?
 | 
			
		||||
            (BufferedReader) reader :
 | 
			
		||||
            new BufferedReader(reader)) {
 | 
			
		||||
            String line;
 | 
			
		||||
 | 
			
		||||
            while ((line = input.readLine()) != null) {
 | 
			
		||||
                builder.append(line);
 | 
			
		||||
                builder.append('\n');
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        loadFromString(builder.toString());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Loads this {@link FileConfiguration} from the specified string, as
 | 
			
		||||
     * opposed to from file.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>All the values contained within this configuration will be removed,
 | 
			
		||||
     * leaving only settings and defaults, and the new values will be loaded
 | 
			
		||||
     * from the given string.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If the string is invalid in any way, an exception will be thrown.
 | 
			
		||||
     *
 | 
			
		||||
     * @param contents Contents of a Configuration to load.
 | 
			
		||||
     * @throws InvalidConfigurationException Thrown if the specified string is
 | 
			
		||||
     *                                       invalid.
 | 
			
		||||
     */
 | 
			
		||||
    public abstract void loadFromString(String contents) throws InvalidConfigurationException;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Compiles the header for this {@link FileConfiguration} and returns the
 | 
			
		||||
     * result.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This will use the header from {@link #options()} -> {@link
 | 
			
		||||
     * FileConfigurationOptions#header()}, respecting the rules of {@link
 | 
			
		||||
     * FileConfigurationOptions#copyHeader()} if set.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Compiled header
 | 
			
		||||
     */
 | 
			
		||||
    protected abstract String buildHeader();
 | 
			
		||||
 | 
			
		||||
    @Override public FileConfigurationOptions options() {
 | 
			
		||||
        if (this.options == null) {
 | 
			
		||||
            this.options = new FileConfigurationOptions(this);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return (FileConfigurationOptions) this.options;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,115 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.file;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.Configuration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.MemoryConfiguration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.MemoryConfigurationOptions;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Various settings for controlling the input and output of a {@link
 | 
			
		||||
 * FileConfiguration}.
 | 
			
		||||
 */
 | 
			
		||||
public class FileConfigurationOptions extends MemoryConfigurationOptions {
 | 
			
		||||
    private String header = null;
 | 
			
		||||
    private boolean copyHeader = true;
 | 
			
		||||
 | 
			
		||||
    protected FileConfigurationOptions(MemoryConfiguration configuration) {
 | 
			
		||||
        super(configuration);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public FileConfiguration configuration() {
 | 
			
		||||
        return (FileConfiguration) super.configuration();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public FileConfigurationOptions copyDefaults(boolean value) {
 | 
			
		||||
        super.copyDefaults(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public FileConfigurationOptions pathSeparator(char value) {
 | 
			
		||||
        super.pathSeparator(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the header that will be applied to the top of the saved output.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This header will be commented out and applied directly at the top of
 | 
			
		||||
     * the generated output of the {@link FileConfiguration}. It is not
 | 
			
		||||
     * required to include a newline at the end of the header as it will
 | 
			
		||||
     * automatically be applied, but you may include one if you wish for extra
 | 
			
		||||
     * spacing.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>{@code null} is a valid value which will indicate that no header]
 | 
			
		||||
     * is to be applied. The default value is {@code null}.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Header
 | 
			
		||||
     */
 | 
			
		||||
    public String header() {
 | 
			
		||||
        return header;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets the header that will be applied to the top of the saved output.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This header will be commented out and applied directly at the top of
 | 
			
		||||
     * the generated output of the {@link FileConfiguration}. It is not
 | 
			
		||||
     * required to include a newline at the end of the header as it will
 | 
			
		||||
     * automatically be applied, but you may include one if you wish for extra
 | 
			
		||||
     * spacing.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>{@code null} is a valid value which will indicate that no header
 | 
			
		||||
     * is to be applied.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value New header
 | 
			
		||||
     * @return This object, for chaining
 | 
			
		||||
     */
 | 
			
		||||
    public FileConfigurationOptions header(String value) {
 | 
			
		||||
        header = value;
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets whether or not the header should be copied from a default source.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If this is true, if a default {@link FileConfiguration} is passed to
 | 
			
		||||
     * {@link FileConfiguration#setDefaults(Configuration)}
 | 
			
		||||
     * then upon saving it will use the header from that config, instead of
 | 
			
		||||
     * the one provided here.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If no default is set on the configuration, or the default is not of
 | 
			
		||||
     * type FileConfiguration, or that config has no header ({@link #header()}
 | 
			
		||||
     * returns null) then the header specified in this configuration will be
 | 
			
		||||
     * used.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Defaults to true.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Whether or not to copy the header
 | 
			
		||||
     */
 | 
			
		||||
    public boolean copyHeader() {
 | 
			
		||||
        return copyHeader;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets whether or not the header should be copied from a default source.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If this is true, if a default {@link FileConfiguration} is passed to
 | 
			
		||||
     * {@link FileConfiguration#setDefaults(Configuration)}
 | 
			
		||||
     * then upon saving it will use the header from that config, instead of
 | 
			
		||||
     * the one provided here.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>If no default is set on the configuration, or the default is not of
 | 
			
		||||
     * type FileConfiguration, or that config has no header ({@link #header()}
 | 
			
		||||
     * returns null) then the header specified in this configuration will be
 | 
			
		||||
     * used.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Defaults to true.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value Whether or not to copy the header
 | 
			
		||||
     * @return This object, for chaining
 | 
			
		||||
     */
 | 
			
		||||
    public FileConfigurationOptions copyHeader(boolean value) {
 | 
			
		||||
        copyHeader = value;
 | 
			
		||||
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,189 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.file;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.Configuration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.ConfigurationSection;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.InvalidConfigurationException;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import org.yaml.snakeyaml.DumperOptions;
 | 
			
		||||
import org.yaml.snakeyaml.Yaml;
 | 
			
		||||
import org.yaml.snakeyaml.error.YAMLException;
 | 
			
		||||
import org.yaml.snakeyaml.representer.Representer;
 | 
			
		||||
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.nio.file.Files;
 | 
			
		||||
import java.nio.file.StandardCopyOption;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * An implementation of {@link Configuration} which saves all files in Yaml.
 | 
			
		||||
 * Note that this implementation is not synchronized.
 | 
			
		||||
 */
 | 
			
		||||
public class YamlConfiguration extends FileConfiguration {
 | 
			
		||||
    private static final String COMMENT_PREFIX = "# ";
 | 
			
		||||
    private static final String BLANK_CONFIG = "{}\n";
 | 
			
		||||
    private final DumperOptions yamlOptions = new DumperOptions();
 | 
			
		||||
    private final Representer yamlRepresenter = new YamlRepresenter();
 | 
			
		||||
    private final Yaml yaml = new Yaml(new YamlConstructor(), yamlRepresenter, yamlOptions);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates a new {@link YamlConfiguration}, loading from the given file.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>Any errors loading the Configuration will be logged and then ignored.
 | 
			
		||||
     * If the specified input is not a valid config, a blank config will be
 | 
			
		||||
     * returned.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>The encoding used may follow the system dependent default.
 | 
			
		||||
     *
 | 
			
		||||
     * @param file Input file
 | 
			
		||||
     * @return Resulting configuration
 | 
			
		||||
     */
 | 
			
		||||
    public static YamlConfiguration loadConfiguration(File file) {
 | 
			
		||||
        YamlConfiguration config = new YamlConfiguration();
 | 
			
		||||
 | 
			
		||||
        try {
 | 
			
		||||
            config.load(file);
 | 
			
		||||
        } catch (InvalidConfigurationException | IOException ex) {
 | 
			
		||||
            try {
 | 
			
		||||
                File dest = new File(file.getAbsolutePath() + "_broken");
 | 
			
		||||
                int i = 0;
 | 
			
		||||
                while (dest.exists()) {
 | 
			
		||||
                    dest = new File(file.getAbsolutePath() + "_broken_" + i++);
 | 
			
		||||
                }
 | 
			
		||||
                Files.copy(file.toPath(), dest.toPath(), StandardCopyOption.REPLACE_EXISTING);
 | 
			
		||||
                PlotSquared.debug("&dCould not read: &7" + file);
 | 
			
		||||
                PlotSquared.debug("&dRenamed to: &7" + dest.getName());
 | 
			
		||||
                PlotSquared.debug("&c============ Full stacktrace ============");
 | 
			
		||||
                ex.printStackTrace();
 | 
			
		||||
                PlotSquared.debug("&c=========================================");
 | 
			
		||||
            } catch (IOException e) {
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return config;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String saveToString() {
 | 
			
		||||
        yamlOptions.setIndent(options().indent());
 | 
			
		||||
        yamlOptions.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK);
 | 
			
		||||
        yamlRepresenter.setDefaultFlowStyle(DumperOptions.FlowStyle.BLOCK);
 | 
			
		||||
 | 
			
		||||
        String header = buildHeader();
 | 
			
		||||
        String dump = yaml.dump(getValues(false));
 | 
			
		||||
 | 
			
		||||
        if (dump.equals(BLANK_CONFIG)) {
 | 
			
		||||
            dump = "";
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return header + dump;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void loadFromString(String contents) throws InvalidConfigurationException {
 | 
			
		||||
 | 
			
		||||
        Map<?, ?> input;
 | 
			
		||||
        try {
 | 
			
		||||
            input = yaml.load(contents);
 | 
			
		||||
        } catch (YAMLException e) {
 | 
			
		||||
            throw new InvalidConfigurationException(e);
 | 
			
		||||
        } catch (ClassCastException ignored) {
 | 
			
		||||
            throw new InvalidConfigurationException("Top level is not a Map.");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        String header = parseHeader(contents);
 | 
			
		||||
        if (!header.isEmpty()) {
 | 
			
		||||
            options().header(header);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (input != null) {
 | 
			
		||||
            convertMapsToSections(input, this);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected void convertMapsToSections(Map<?, ?> input, ConfigurationSection section) {
 | 
			
		||||
        for (Map.Entry<?, ?> entry : input.entrySet()) {
 | 
			
		||||
            String key = entry.getKey().toString();
 | 
			
		||||
            Object value = entry.getValue();
 | 
			
		||||
 | 
			
		||||
            if (value instanceof Map) {
 | 
			
		||||
                convertMapsToSections((Map<?, ?>) value, section.createSection(key));
 | 
			
		||||
            } else {
 | 
			
		||||
                section.set(key, value);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected String parseHeader(String input) {
 | 
			
		||||
        String[] lines = input.split("\r?\n", -1);
 | 
			
		||||
        StringBuilder result = new StringBuilder();
 | 
			
		||||
        boolean readingHeader = true;
 | 
			
		||||
        boolean foundHeader = false;
 | 
			
		||||
 | 
			
		||||
        for (int i = 0; (i < lines.length) && readingHeader; i++) {
 | 
			
		||||
            String line = lines[i];
 | 
			
		||||
 | 
			
		||||
            if (line.startsWith(COMMENT_PREFIX)) {
 | 
			
		||||
                if (i > 0) {
 | 
			
		||||
                    result.append('\n');
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                if (line.length() > COMMENT_PREFIX.length()) {
 | 
			
		||||
                    result.append(line.substring(COMMENT_PREFIX.length()));
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                foundHeader = true;
 | 
			
		||||
            } else if (foundHeader && line.isEmpty()) {
 | 
			
		||||
                result.append('\n');
 | 
			
		||||
            } else if (foundHeader) {
 | 
			
		||||
                readingHeader = false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override protected String buildHeader() {
 | 
			
		||||
        String header = options().header();
 | 
			
		||||
 | 
			
		||||
        if (options().copyHeader()) {
 | 
			
		||||
            Configuration def = getDefaults();
 | 
			
		||||
 | 
			
		||||
            if (def instanceof FileConfiguration) {
 | 
			
		||||
                FileConfiguration fileDefaults = (FileConfiguration) def;
 | 
			
		||||
                String defaultsHeader = fileDefaults.buildHeader();
 | 
			
		||||
 | 
			
		||||
                if ((defaultsHeader != null) && !defaultsHeader.isEmpty()) {
 | 
			
		||||
                    return defaultsHeader;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (header == null) {
 | 
			
		||||
            return "";
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        StringBuilder builder = new StringBuilder();
 | 
			
		||||
        String[] lines = header.split("\r?\n", -1);
 | 
			
		||||
        boolean startedHeader = false;
 | 
			
		||||
 | 
			
		||||
        for (int i = lines.length - 1; i >= 0; i--) {
 | 
			
		||||
            builder.insert(0, '\n');
 | 
			
		||||
 | 
			
		||||
            if (startedHeader || !lines[i].isEmpty()) {
 | 
			
		||||
                builder.insert(0, lines[i]);
 | 
			
		||||
                builder.insert(0, COMMENT_PREFIX);
 | 
			
		||||
                startedHeader = true;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return builder.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public YamlConfigurationOptions options() {
 | 
			
		||||
        if (options == null) {
 | 
			
		||||
            options = new YamlConfigurationOptions(this);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return (YamlConfigurationOptions) options;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,68 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.file;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Various settings for controlling the input and output of a {@link
 | 
			
		||||
 * YamlConfiguration}.
 | 
			
		||||
 */
 | 
			
		||||
public class YamlConfigurationOptions extends FileConfigurationOptions {
 | 
			
		||||
    private int indent = 2;
 | 
			
		||||
 | 
			
		||||
    YamlConfigurationOptions(YamlConfiguration configuration) {
 | 
			
		||||
        super(configuration);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public YamlConfiguration configuration() {
 | 
			
		||||
        return (YamlConfiguration) super.configuration();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public YamlConfigurationOptions copyDefaults(boolean value) {
 | 
			
		||||
        super.copyDefaults(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public YamlConfigurationOptions pathSeparator(char value) {
 | 
			
		||||
        super.pathSeparator(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public YamlConfigurationOptions header(String value) {
 | 
			
		||||
        super.header(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public YamlConfigurationOptions copyHeader(boolean value) {
 | 
			
		||||
        super.copyHeader(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets how much spaces should be used to indent each line.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>The minimum value this may be is 2, and the maximum is 9.
 | 
			
		||||
     *
 | 
			
		||||
     * @return How much to indent by
 | 
			
		||||
     */
 | 
			
		||||
    int indent() {
 | 
			
		||||
        return indent;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Sets how much spaces should be used to indent each line.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>The minimum value this may be is 2, and the maximum is 9.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value New indent
 | 
			
		||||
     * @return This object, for chaining
 | 
			
		||||
     */
 | 
			
		||||
    public YamlConfigurationOptions indent(int value) {
 | 
			
		||||
        if (value < 2) {
 | 
			
		||||
            throw new IllegalArgumentException("Indent must be at least 2 characters");
 | 
			
		||||
        }
 | 
			
		||||
        if (value > 9) {
 | 
			
		||||
            throw new IllegalArgumentException("Indent cannot be greater than 9 characters");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        indent = value;
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,46 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.file;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.serialization.ConfigurationSerialization;
 | 
			
		||||
import org.yaml.snakeyaml.constructor.SafeConstructor;
 | 
			
		||||
import org.yaml.snakeyaml.error.YAMLException;
 | 
			
		||||
import org.yaml.snakeyaml.nodes.Node;
 | 
			
		||||
import org.yaml.snakeyaml.nodes.Tag;
 | 
			
		||||
 | 
			
		||||
import java.util.LinkedHashMap;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
class YamlConstructor extends SafeConstructor {
 | 
			
		||||
 | 
			
		||||
    YamlConstructor() {
 | 
			
		||||
        yamlConstructors.put(Tag.MAP, new ConstructCustomObject());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private class ConstructCustomObject extends ConstructYamlMap {
 | 
			
		||||
        @Override public Object construct(final Node node) {
 | 
			
		||||
            if (node.isTwoStepsConstruction()) {
 | 
			
		||||
                throw new YAMLException("Unexpected referential mapping structure. Node: " + node);
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            final Map<?, ?> raw = (Map<?, ?>) super.construct(node);
 | 
			
		||||
 | 
			
		||||
            if (raw.containsKey(ConfigurationSerialization.SERIALIZED_TYPE_KEY)) {
 | 
			
		||||
                final Map<String, Object> typed = new LinkedHashMap<>(raw.size());
 | 
			
		||||
                for (final Map.Entry<?, ?> entry : raw.entrySet()) {
 | 
			
		||||
                    typed.put(entry.getKey().toString(), entry.getValue());
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                try {
 | 
			
		||||
                    return ConfigurationSerialization.deserializeObject(typed);
 | 
			
		||||
                } catch (final IllegalArgumentException ex) {
 | 
			
		||||
                    throw new YAMLException("Could not deserialize object", ex);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            return raw;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        @Override public void construct2ndStep(final Node node, final Object object) {
 | 
			
		||||
            throw new YAMLException("Unexpected referential mapping structure. Node: " + node);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,40 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.file;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.ConfigurationSection;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.serialization.ConfigurationSerializable;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.serialization.ConfigurationSerialization;
 | 
			
		||||
import org.yaml.snakeyaml.nodes.Node;
 | 
			
		||||
import org.yaml.snakeyaml.representer.Representer;
 | 
			
		||||
 | 
			
		||||
import java.util.LinkedHashMap;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
class YamlRepresenter extends Representer {
 | 
			
		||||
 | 
			
		||||
    YamlRepresenter() {
 | 
			
		||||
        this.multiRepresenters.put(ConfigurationSection.class, new RepresentConfigurationSection());
 | 
			
		||||
        this.multiRepresenters
 | 
			
		||||
            .put(ConfigurationSerializable.class, new RepresentConfigurationSerializable());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private class RepresentConfigurationSection extends RepresentMap {
 | 
			
		||||
 | 
			
		||||
        @Override public Node representData(Object data) {
 | 
			
		||||
            return super.representData(((ConfigurationSection) data).getValues(false));
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    private class RepresentConfigurationSerializable extends RepresentMap {
 | 
			
		||||
 | 
			
		||||
        @Override public Node representData(Object data) {
 | 
			
		||||
            ConfigurationSerializable serializable = (ConfigurationSerializable) data;
 | 
			
		||||
            Map<String, Object> values = new LinkedHashMap<>();
 | 
			
		||||
            values.put(ConfigurationSerialization.SERIALIZED_TYPE_KEY,
 | 
			
		||||
                ConfigurationSerialization.getAlias(serializable.getClass()));
 | 
			
		||||
            values.putAll(serializable.serialize());
 | 
			
		||||
 | 
			
		||||
            return super.representData(values);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,34 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.serialization;
 | 
			
		||||
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Represents an object that may be serialized.
 | 
			
		||||
 * <p>These objects MUST implement one of the following, in addition to
 | 
			
		||||
 * the methods as defined by this interface:
 | 
			
		||||
 * <ul>
 | 
			
		||||
 * <li>A static method "deserialize" that accepts a single {@link Map}<
 | 
			
		||||
 * {@link String}, {@link Object}> and returns the class.</li>
 | 
			
		||||
 * <li>A static method "valueOf" that accepts a single {@link Map}<{@link
 | 
			
		||||
 * String}, {@link Object}> and returns the class.</li>
 | 
			
		||||
 * <li>A constructor that accepts a single {@link Map}<{@link String},
 | 
			
		||||
 * {@link Object}>.</li>
 | 
			
		||||
 * </ul>
 | 
			
		||||
 * In addition to implementing this interface, you must register the class
 | 
			
		||||
 * with {@link ConfigurationSerialization#registerClass(Class)}.
 | 
			
		||||
 *
 | 
			
		||||
 * @see DelegateDeserialization
 | 
			
		||||
 * @see SerializableAs
 | 
			
		||||
 */
 | 
			
		||||
public interface ConfigurationSerializable {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Creates a Map representation of this class.
 | 
			
		||||
     *
 | 
			
		||||
     * <p>This class must provide a method to restore this class, as defined in
 | 
			
		||||
     * the {@link ConfigurationSerializable} interface javadoc.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Map containing the current state of this class
 | 
			
		||||
     */
 | 
			
		||||
    Map<String, Object> serialize();
 | 
			
		||||
}
 | 
			
		||||
@@ -1,262 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.serialization;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.Configuration;
 | 
			
		||||
 | 
			
		||||
import java.lang.reflect.Constructor;
 | 
			
		||||
import java.lang.reflect.InvocationTargetException;
 | 
			
		||||
import java.lang.reflect.Method;
 | 
			
		||||
import java.lang.reflect.Modifier;
 | 
			
		||||
import java.util.HashMap;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
import java.util.logging.Level;
 | 
			
		||||
import java.util.logging.Logger;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Utility class for storing and retrieving classes for {@link Configuration}.
 | 
			
		||||
 */
 | 
			
		||||
public class ConfigurationSerialization {
 | 
			
		||||
 | 
			
		||||
    public static final String SERIALIZED_TYPE_KEY = "==";
 | 
			
		||||
    private static final Map<String, Class<? extends ConfigurationSerializable>> aliases =
 | 
			
		||||
        new HashMap<>();
 | 
			
		||||
    private final Class<? extends ConfigurationSerializable> clazz;
 | 
			
		||||
 | 
			
		||||
    protected ConfigurationSerialization(Class<? extends ConfigurationSerializable> clazz) {
 | 
			
		||||
        this.clazz = clazz;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Attempts to deserialize the given arguments into a new instance of the
 | 
			
		||||
     * given class.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>The class must implement {@link ConfigurationSerializable}, including
 | 
			
		||||
     * the extra methods as specified in the javadoc of
 | 
			
		||||
     * ConfigurationSerializable.</p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>If a new instance could not be made, an example being the class not
 | 
			
		||||
     * fully implementing the interface, null will be returned.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @param args  Arguments for deserialization
 | 
			
		||||
     * @param clazz Class to deserialize into
 | 
			
		||||
     * @return New instance of the specified class
 | 
			
		||||
     */
 | 
			
		||||
    public static ConfigurationSerializable deserializeObject(Map<String, ?> args,
 | 
			
		||||
        Class<? extends ConfigurationSerializable> clazz) {
 | 
			
		||||
        return new ConfigurationSerialization(clazz).deserialize(args);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Attempts to deserialize the given arguments into a new instance of the
 | 
			
		||||
     * <p>
 | 
			
		||||
     * given class.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * The class must implement {@link ConfigurationSerializable}, including
 | 
			
		||||
     * the extra methods as specified in the javadoc of
 | 
			
		||||
     * ConfigurationSerializable.</p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * <p>
 | 
			
		||||
     * If a new instance could not be made, an example being the class not
 | 
			
		||||
     * fully implementing the interface, null will be returned.</p>
 | 
			
		||||
     *
 | 
			
		||||
     * @param args Arguments for deserialization
 | 
			
		||||
     * @return New instance of the specified class
 | 
			
		||||
     */
 | 
			
		||||
    public static ConfigurationSerializable deserializeObject(Map<String, ?> args) {
 | 
			
		||||
        Class<? extends ConfigurationSerializable> clazz = null;
 | 
			
		||||
 | 
			
		||||
        if (args.containsKey(SERIALIZED_TYPE_KEY)) {
 | 
			
		||||
            try {
 | 
			
		||||
                String alias = (String) args.get(SERIALIZED_TYPE_KEY);
 | 
			
		||||
 | 
			
		||||
                if (alias == null) {
 | 
			
		||||
                    throw new IllegalArgumentException("Cannot have null alias");
 | 
			
		||||
                }
 | 
			
		||||
                clazz = getClassByAlias(alias);
 | 
			
		||||
                if (clazz == null) {
 | 
			
		||||
                    throw new IllegalArgumentException(
 | 
			
		||||
                        "Specified class does not exist ('" + alias + "')");
 | 
			
		||||
                }
 | 
			
		||||
            } catch (ClassCastException ex) {
 | 
			
		||||
                ex.fillInStackTrace();
 | 
			
		||||
                throw ex;
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            throw new IllegalArgumentException(
 | 
			
		||||
                "Args doesn't contain type key ('" + SERIALIZED_TYPE_KEY + "')");
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return new ConfigurationSerialization(clazz).deserialize(args);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Registers the given {@link ConfigurationSerializable} class by its
 | 
			
		||||
     * alias.
 | 
			
		||||
     *
 | 
			
		||||
     * @param clazz Class to register
 | 
			
		||||
     */
 | 
			
		||||
    public static void registerClass(Class<? extends ConfigurationSerializable> clazz) {
 | 
			
		||||
        DelegateDeserialization delegate = clazz.getAnnotation(DelegateDeserialization.class);
 | 
			
		||||
 | 
			
		||||
        if (delegate == null) {
 | 
			
		||||
            registerClass(clazz, getAlias(clazz));
 | 
			
		||||
            registerClass(clazz, clazz.getName());
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Registers the given alias to the specified {@link
 | 
			
		||||
     * ConfigurationSerializable} class.
 | 
			
		||||
     *
 | 
			
		||||
     * @param clazz Class to register
 | 
			
		||||
     * @param alias Alias to register as
 | 
			
		||||
     * @see SerializableAs
 | 
			
		||||
     */
 | 
			
		||||
    public static void registerClass(Class<? extends ConfigurationSerializable> clazz,
 | 
			
		||||
        String alias) {
 | 
			
		||||
        aliases.put(alias, clazz);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Unregisters the specified alias to a {@link ConfigurationSerializable}
 | 
			
		||||
     *
 | 
			
		||||
     * @param alias Alias to unregister
 | 
			
		||||
     */
 | 
			
		||||
    public static void unregisterClass(String alias) {
 | 
			
		||||
        aliases.remove(alias);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Unregisters any aliases for the specified {@link
 | 
			
		||||
     * ConfigurationSerializable} class.
 | 
			
		||||
     *
 | 
			
		||||
     * @param clazz Class to unregister
 | 
			
		||||
     */
 | 
			
		||||
    public static void unregisterClass(Class<? extends ConfigurationSerializable> clazz) {
 | 
			
		||||
        while (aliases.values().remove(clazz)) {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Attempts to get a registered {@link ConfigurationSerializable} class by
 | 
			
		||||
     * its alias.
 | 
			
		||||
     *
 | 
			
		||||
     * @param alias Alias of the serializable
 | 
			
		||||
     * @return Registered class, or null if not found
 | 
			
		||||
     */
 | 
			
		||||
    public static Class<? extends ConfigurationSerializable> getClassByAlias(String alias) {
 | 
			
		||||
        return aliases.get(alias);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Gets the correct alias for the given {@link ConfigurationSerializable}
 | 
			
		||||
     * class.
 | 
			
		||||
     *
 | 
			
		||||
     * @param clazz Class to get alias for
 | 
			
		||||
     * @return Alias to use for the class
 | 
			
		||||
     */
 | 
			
		||||
    public static String getAlias(Class<? extends ConfigurationSerializable> clazz) {
 | 
			
		||||
        DelegateDeserialization delegate = clazz.getAnnotation(DelegateDeserialization.class);
 | 
			
		||||
 | 
			
		||||
        if (delegate != null) {
 | 
			
		||||
            if (delegate.value() == clazz) {
 | 
			
		||||
                delegate = null;
 | 
			
		||||
            } else {
 | 
			
		||||
                return getAlias(delegate.value());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        SerializableAs alias = clazz.getAnnotation(SerializableAs.class);
 | 
			
		||||
 | 
			
		||||
        if (alias != null) {
 | 
			
		||||
            return alias.value();
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return clazz.getName();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected Method getMethod(String name, boolean isStatic) {
 | 
			
		||||
        try {
 | 
			
		||||
            Method method = this.clazz.getDeclaredMethod(name, Map.class);
 | 
			
		||||
 | 
			
		||||
            if (!ConfigurationSerializable.class.isAssignableFrom(method.getReturnType())) {
 | 
			
		||||
                return null;
 | 
			
		||||
            }
 | 
			
		||||
            if (Modifier.isStatic(method.getModifiers()) != isStatic) {
 | 
			
		||||
                return null;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            return method;
 | 
			
		||||
        } catch (NoSuchMethodException | SecurityException ignored) {
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected Constructor<? extends ConfigurationSerializable> getConstructor() {
 | 
			
		||||
        try {
 | 
			
		||||
            return this.clazz.getConstructor(Map.class);
 | 
			
		||||
        } catch (NoSuchMethodException | SecurityException ignored) {
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected ConfigurationSerializable deserializeViaMethod(Method method, Map<String, ?> args) {
 | 
			
		||||
        try {
 | 
			
		||||
            ConfigurationSerializable result =
 | 
			
		||||
                (ConfigurationSerializable) method.invoke(null, args);
 | 
			
		||||
 | 
			
		||||
            if (result == null) {
 | 
			
		||||
                Logger.getLogger(ConfigurationSerialization.class.getName()).log(Level.SEVERE,
 | 
			
		||||
                    "Could not call method '" + method.toString() + "' of " + this.clazz
 | 
			
		||||
                        + " for deserialization: method returned null");
 | 
			
		||||
            } else {
 | 
			
		||||
                return result;
 | 
			
		||||
            }
 | 
			
		||||
        } catch (IllegalAccessException | InvocationTargetException | IllegalArgumentException ex) {
 | 
			
		||||
            Logger.getLogger(ConfigurationSerialization.class.getName()).log(Level.SEVERE,
 | 
			
		||||
                "Could not call method '" + method.toString() + "' of " + this.clazz
 | 
			
		||||
                    + " for deserialization",
 | 
			
		||||
                ex instanceof InvocationTargetException ? ex.getCause() : ex);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    protected ConfigurationSerializable deserializeViaCtor(
 | 
			
		||||
        Constructor<? extends ConfigurationSerializable> ctor, Map<String, ?> args) {
 | 
			
		||||
        try {
 | 
			
		||||
            return ctor.newInstance(args);
 | 
			
		||||
        } catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException | InstantiationException ex) {
 | 
			
		||||
            Logger.getLogger(ConfigurationSerialization.class.getName()).log(Level.SEVERE,
 | 
			
		||||
                "Could not call constructor '" + ctor.toString() + "' of " + this.clazz
 | 
			
		||||
                    + " for deserialization",
 | 
			
		||||
                ex instanceof InvocationTargetException ? ex.getCause() : ex);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public ConfigurationSerializable deserialize(Map<String, ?> args) {
 | 
			
		||||
        if (args == null) {
 | 
			
		||||
            throw new NullPointerException("Args must not be null");
 | 
			
		||||
        }
 | 
			
		||||
        ConfigurationSerializable result = null;
 | 
			
		||||
        Method method = getMethod("deserialize", true);
 | 
			
		||||
        if (method != null) {
 | 
			
		||||
            result = deserializeViaMethod(method, args);
 | 
			
		||||
        }
 | 
			
		||||
        if (result == null) {
 | 
			
		||||
            method = getMethod("valueOf", true);
 | 
			
		||||
            if (method != null) {
 | 
			
		||||
                result = deserializeViaMethod(method, args);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (result == null) {
 | 
			
		||||
            Constructor<? extends ConfigurationSerializable> constructor = getConstructor();
 | 
			
		||||
            if (constructor != null) {
 | 
			
		||||
                result = deserializeViaCtor(constructor, args);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,21 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.serialization;
 | 
			
		||||
 | 
			
		||||
import java.lang.annotation.ElementType;
 | 
			
		||||
import java.lang.annotation.Retention;
 | 
			
		||||
import java.lang.annotation.RetentionPolicy;
 | 
			
		||||
import java.lang.annotation.Target;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Applies to a {@link ConfigurationSerializable} that will delegate all
 | 
			
		||||
 * deserialization to another {@link ConfigurationSerializable}.
 | 
			
		||||
 */
 | 
			
		||||
@Retention(RetentionPolicy.RUNTIME) @Target(ElementType.TYPE)
 | 
			
		||||
public @interface DelegateDeserialization {
 | 
			
		||||
    /**
 | 
			
		||||
     * Which class should be used as a delegate for this classes
 | 
			
		||||
     * deserialization
 | 
			
		||||
     *
 | 
			
		||||
     * @return Delegate class
 | 
			
		||||
     */
 | 
			
		||||
    Class<? extends ConfigurationSerializable> value();
 | 
			
		||||
}
 | 
			
		||||
@@ -1,32 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.configuration.serialization;
 | 
			
		||||
 | 
			
		||||
import java.lang.annotation.ElementType;
 | 
			
		||||
import java.lang.annotation.Retention;
 | 
			
		||||
import java.lang.annotation.RetentionPolicy;
 | 
			
		||||
import java.lang.annotation.Target;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Represents an "alias" that a {@link ConfigurationSerializable} may be
 | 
			
		||||
 * stored as.
 | 
			
		||||
 * If this is not present on a {@link ConfigurationSerializable} class, it
 | 
			
		||||
 * will use the fully qualified name of the class.
 | 
			
		||||
 * <p>
 | 
			
		||||
 * This value will be stored in the configuration so that the configuration
 | 
			
		||||
 * deserialization can determine what type it is.
 | 
			
		||||
 * <p>
 | 
			
		||||
 * Using this annotation on any other class than a {@link
 | 
			
		||||
 * ConfigurationSerializable} will have no effect.
 | 
			
		||||
 *
 | 
			
		||||
 * @see ConfigurationSerialization#registerClass(Class, String)
 | 
			
		||||
 */
 | 
			
		||||
@Retention(RetentionPolicy.RUNTIME) @Target(ElementType.TYPE) public @interface SerializableAs {
 | 
			
		||||
    /**
 | 
			
		||||
     * This is the name your class will be stored and retrieved as.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * This name MUST be unique. We recommend using names such as
 | 
			
		||||
     * "MyPluginThing" instead of "Thing".
 | 
			
		||||
     *
 | 
			
		||||
     * @return Name to serialize the class as.
 | 
			
		||||
     */
 | 
			
		||||
    String value();
 | 
			
		||||
}
 | 
			
		||||
@@ -1,815 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.io.StringWriter;
 | 
			
		||||
import java.io.Writer;
 | 
			
		||||
import java.lang.reflect.Array;
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Collection;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * A JSONArray is an ordered sequence of values. Its external text form is a string wrapped in square brackets with
 | 
			
		||||
 * commas separating the values. The internal form is an object having {@code get} and {@code opt} methods for
 | 
			
		||||
 * accessing the values by index, and {@code put} methods for adding or replacing values. The values can be any of
 | 
			
		||||
 * these types: {@code Boolean}, {@code JSONArray}, {@code JSONObject}, {@code Number},
 | 
			
		||||
 * {@code String}, or the {@code JSONObject.NULL object}.
 | 
			
		||||
 *
 | 
			
		||||
 * <p>The constructor can convert a JSON text into a Java object. The {@code toString} method converts to JSON text.
 | 
			
		||||
 *
 | 
			
		||||
 * <p>A {@code get} method returns a value if one can be found, and throws an exception if one cannot be found. An
 | 
			
		||||
 * {@code opt} method returns a default value instead of throwing an exception, and so is useful for obtaining
 | 
			
		||||
 * optional values.
 | 
			
		||||
 *
 | 
			
		||||
 * <p>The generic {@code get()} and {@code opt()} methods return an object which you can cast or query for type.
 | 
			
		||||
 * There are also typed {@code get} and {@code opt} methods that do type checking and type coercion for you.
 | 
			
		||||
 *
 | 
			
		||||
 * <p>The texts produced by the {@code toString} methods strictly conform to JSON syntax rules. The constructors are
 | 
			
		||||
 * more forgiving in the texts they will accept: <ul> <li>An extra {@code ,} <small>(comma)</small> may appear
 | 
			
		||||
 * just before the closing bracket.</li> <li>The {@code null} value will be inserted when there is {@code ,}
 | 
			
		||||
 *  <small>(comma)</small> elision.</li> <li>Strings may be quoted with {@code '} <small>(single
 | 
			
		||||
 * quote)</small>.</li> <li>Strings do not need to be quoted at all if they do not begin with a quote or single quote,
 | 
			
		||||
 * and if they do not contain leading or trailing spaces, and if they do not contain any of these characters: {@code { }
 | 
			
		||||
 * [ ] / \ : , #} and if they do not look like numbers and if they are not the reserved words {@code true},
 | 
			
		||||
 * {@code false}, or {@code null}.</li> </ul>
 | 
			
		||||
 *
 | 
			
		||||
 * @author JSON.org
 | 
			
		||||
 * @version 2014-05-03
 | 
			
		||||
 */
 | 
			
		||||
public class JSONArray {
 | 
			
		||||
    /**
 | 
			
		||||
     * The arrayList where the JSONArray's properties are kept.
 | 
			
		||||
     */
 | 
			
		||||
    private final ArrayList<Object> myArrayList;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct an empty JSONArray.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray() {
 | 
			
		||||
        this.myArrayList = new ArrayList<Object>();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONArray from a JSONTokener.
 | 
			
		||||
     *
 | 
			
		||||
     * @param x A JSONTokener
 | 
			
		||||
     * @throws JSONException If there is a syntax error.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray(JSONTokener x) throws JSONException {
 | 
			
		||||
        this();
 | 
			
		||||
        if (x.nextClean() != '[') {
 | 
			
		||||
            throw x.syntaxError("A JSONArray text must start with '['");
 | 
			
		||||
        }
 | 
			
		||||
        if (x.nextClean() != ']') {
 | 
			
		||||
            x.back();
 | 
			
		||||
            for (; ; ) {
 | 
			
		||||
                if (x.nextClean() == ',') {
 | 
			
		||||
                    x.back();
 | 
			
		||||
                    this.myArrayList.add(JSONObject.NULL);
 | 
			
		||||
                } else {
 | 
			
		||||
                    x.back();
 | 
			
		||||
                    this.myArrayList.add(x.nextValue());
 | 
			
		||||
                }
 | 
			
		||||
                switch (x.nextClean()) {
 | 
			
		||||
                    case ',':
 | 
			
		||||
                        if (x.nextClean() == ']') {
 | 
			
		||||
                            return;
 | 
			
		||||
                        }
 | 
			
		||||
                        x.back();
 | 
			
		||||
                        break;
 | 
			
		||||
                    case ']':
 | 
			
		||||
                        return;
 | 
			
		||||
                    default:
 | 
			
		||||
                        throw x.syntaxError("Expected a ',' or ']'");
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONArray from a source JSON text.
 | 
			
		||||
     *
 | 
			
		||||
     * @param source A string that begins with {@code [} <small>(left bracket)</small> and ends with
 | 
			
		||||
     *               {@code ]}  <small>(right bracket)</small>.
 | 
			
		||||
     * @throws JSONException If there is a syntax error.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray(String source) throws JSONException {
 | 
			
		||||
        this(new JSONTokener(source));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONArray from a Collection.
 | 
			
		||||
     *
 | 
			
		||||
     * @param collection A Collection.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray(Collection<Object> collection) {
 | 
			
		||||
        this.myArrayList = new ArrayList<Object>();
 | 
			
		||||
        if (collection != null) {
 | 
			
		||||
            for (Object aCollection : collection) {
 | 
			
		||||
                this.myArrayList.add(JSONObject.wrap(aCollection));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONArray from an array
 | 
			
		||||
     *
 | 
			
		||||
     * @throws JSONException If not an array.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray(Object array) throws JSONException {
 | 
			
		||||
        this();
 | 
			
		||||
        if (array.getClass().isArray()) {
 | 
			
		||||
            int length = Array.getLength(array);
 | 
			
		||||
            for (int i = 0; i < length; i += 1) {
 | 
			
		||||
                this.put(JSONObject.wrap(Array.get(array, i)));
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            throw new JSONException(
 | 
			
		||||
                "JSONArray initial value should be a string or collection or array.");
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the object value associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return An object value.
 | 
			
		||||
     * @throws JSONException If there is no value for the index.
 | 
			
		||||
     */
 | 
			
		||||
    public Object get(int index) throws JSONException {
 | 
			
		||||
        Object object = opt(index);
 | 
			
		||||
        if (object == null) {
 | 
			
		||||
            throw new JSONException("JSONArray[" + index + "] not found.");
 | 
			
		||||
        }
 | 
			
		||||
        return object;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the boolean value associated with an index. The string values "true" and "false" are converted to boolean.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The truth.
 | 
			
		||||
     * @throws JSONException If there is no value for the index or if the value is not convertible to boolean.
 | 
			
		||||
     */
 | 
			
		||||
    public boolean getBoolean(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        if (object.equals(Boolean.FALSE) || ((object instanceof String) && ((String) object)
 | 
			
		||||
            .equalsIgnoreCase("false"))) {
 | 
			
		||||
            return false;
 | 
			
		||||
        } else if (object.equals(Boolean.TRUE) || ((object instanceof String) && ((String) object)
 | 
			
		||||
            .equalsIgnoreCase("true"))) {
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        throw new JSONException("JSONArray[" + index + "] is not a boolean.");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the double value associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     * @throws JSONException If the key is not found or if the value cannot be converted to a number.
 | 
			
		||||
     */
 | 
			
		||||
    public double getDouble(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        try {
 | 
			
		||||
            return object instanceof Number ?
 | 
			
		||||
                ((Number) object).doubleValue() :
 | 
			
		||||
                Double.parseDouble((String) object);
 | 
			
		||||
        } catch (NumberFormatException ignored) {
 | 
			
		||||
            throw new JSONException("JSONArray[" + index + "] is not a number.");
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the int value associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     * @throws JSONException If the key is not found or if the value is not a number.
 | 
			
		||||
     */
 | 
			
		||||
    public int getInt(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        try {
 | 
			
		||||
            return object instanceof Number ?
 | 
			
		||||
                ((Number) object).intValue() :
 | 
			
		||||
                Integer.parseInt((String) object);
 | 
			
		||||
        } catch (NumberFormatException ignored) {
 | 
			
		||||
            throw new JSONException("JSONArray[" + index + "] is not a number.");
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the JSONArray associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return A JSONArray value.
 | 
			
		||||
     * @throws JSONException If there is no value for the index. or if the value is not a JSONArray
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray getJSONArray(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        if (object instanceof JSONArray) {
 | 
			
		||||
            return (JSONArray) object;
 | 
			
		||||
        }
 | 
			
		||||
        throw new JSONException("JSONArray[" + index + "] is not a JSONArray.");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the JSONObject associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index subscript
 | 
			
		||||
     * @return A JSONObject value.
 | 
			
		||||
     * @throws JSONException If there is no value for the index or if the value is not a JSONObject
 | 
			
		||||
     */
 | 
			
		||||
    public JSONObject getJSONObject(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        if (object instanceof JSONObject) {
 | 
			
		||||
            return (JSONObject) object;
 | 
			
		||||
        }
 | 
			
		||||
        throw new JSONException("JSONArray[" + index + "] is not a JSONObject.");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the long value associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     * @throws JSONException If the key is not found or if the value cannot be converted to a number.
 | 
			
		||||
     */
 | 
			
		||||
    public long getLong(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        try {
 | 
			
		||||
            return object instanceof Number ?
 | 
			
		||||
                ((Number) object).longValue() :
 | 
			
		||||
                Long.parseLong((String) object);
 | 
			
		||||
        } catch (NumberFormatException ignored) {
 | 
			
		||||
            throw new JSONException("JSONArray[" + index + "] is not a number.");
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the string associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return A string value.
 | 
			
		||||
     * @throws JSONException If there is no string value for the index.
 | 
			
		||||
     */
 | 
			
		||||
    public String getString(int index) throws JSONException {
 | 
			
		||||
        Object object = get(index);
 | 
			
		||||
        if (object instanceof String) {
 | 
			
		||||
            return (String) object;
 | 
			
		||||
        }
 | 
			
		||||
        throw new JSONException("JSONArray[" + index + "] not a string.");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Determine if the value is null.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return true if the value at the index is null, or if there is no value.
 | 
			
		||||
     */
 | 
			
		||||
    public boolean isNull(int index) {
 | 
			
		||||
        return JSONObject.NULL.equals(opt(index));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Make a string from the contents of this JSONArray. The {@code separator} string is inserted between each
 | 
			
		||||
     * element. Warning: This method assumes that the data structure is acyclical.
 | 
			
		||||
     *
 | 
			
		||||
     * @param separator A string that will be inserted between the elements.
 | 
			
		||||
     * @return a string.
 | 
			
		||||
     * @throws JSONException If the array contains an invalid number.
 | 
			
		||||
     */
 | 
			
		||||
    public String join(String separator) throws JSONException {
 | 
			
		||||
        int len = length();
 | 
			
		||||
        StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (int i = 0; i < len; i += 1) {
 | 
			
		||||
            if (i > 0) {
 | 
			
		||||
                sb.append(separator);
 | 
			
		||||
            }
 | 
			
		||||
            sb.append(JSONObject.valueToString(this.myArrayList.get(i)));
 | 
			
		||||
        }
 | 
			
		||||
        return sb.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the number of elements in the JSONArray, included nulls.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The length (or size).
 | 
			
		||||
     */
 | 
			
		||||
    public int length() {
 | 
			
		||||
        return this.myArrayList.size();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional object value associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return An object value, or null if there is no object at that index.
 | 
			
		||||
     */
 | 
			
		||||
    public Object opt(int index) {
 | 
			
		||||
        return ((index < 0) || (index >= length())) ? null : this.myArrayList.get(index);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional boolean value associated with an index. It returns false if there is no value at that index, or
 | 
			
		||||
     * if the value is not Boolean.TRUE or the String "true".
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The truth.
 | 
			
		||||
     */
 | 
			
		||||
    public boolean optBoolean(int index) {
 | 
			
		||||
        return this.optBoolean(index, false);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional boolean value associated with an index. It returns the defaultValue if there is no value at that
 | 
			
		||||
     * index or if it is not a Boolean or the String "true" or "false" (case insensitive).
 | 
			
		||||
     *
 | 
			
		||||
     * @param index        The index must be between 0 and length() - 1.
 | 
			
		||||
     * @param defaultValue A boolean default.
 | 
			
		||||
     * @return The truth.
 | 
			
		||||
     */
 | 
			
		||||
    public boolean optBoolean(int index, boolean defaultValue) {
 | 
			
		||||
        try {
 | 
			
		||||
            return getBoolean(index);
 | 
			
		||||
        } catch (JSONException ignored) {
 | 
			
		||||
            return defaultValue;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional double value associated with an index. NaN is returned if there is no value for the index, or if
 | 
			
		||||
     * the value is not a number and cannot be converted to a number.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     */
 | 
			
		||||
    public double optDouble(int index) {
 | 
			
		||||
        return this.optDouble(index, Double.NaN);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional double value associated with an index. The defaultValue is returned if there is no value for the
 | 
			
		||||
     * index, or if the value is not a number and cannot be converted to a number.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index        subscript
 | 
			
		||||
     * @param defaultValue The default value.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     */
 | 
			
		||||
    public double optDouble(int index, double defaultValue) {
 | 
			
		||||
        try {
 | 
			
		||||
            return getDouble(index);
 | 
			
		||||
        } catch (JSONException ignored) {
 | 
			
		||||
            return defaultValue;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional int value associated with an index. Zero is returned if there is no value for the index, or if
 | 
			
		||||
     * the value is not a number and cannot be converted to a number.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     */
 | 
			
		||||
    public int optInt(int index) {
 | 
			
		||||
        return this.optInt(index, 0);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional int value associated with an index. The defaultValue is returned if there is no value for the
 | 
			
		||||
     * index, or if the value is not a number and cannot be converted to a number.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index        The index must be between 0 and length() - 1.
 | 
			
		||||
     * @param defaultValue The default value.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     */
 | 
			
		||||
    public int optInt(int index, int defaultValue) {
 | 
			
		||||
        try {
 | 
			
		||||
            return getInt(index);
 | 
			
		||||
        } catch (JSONException ignored) {
 | 
			
		||||
            return defaultValue;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional JSONArray associated with an index.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index subscript
 | 
			
		||||
     * @return A JSONArray value, or null if the index has no value, or if the value is not a JSONArray.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray optJSONArray(int index) {
 | 
			
		||||
        Object o = opt(index);
 | 
			
		||||
        return o instanceof JSONArray ? (JSONArray) o : null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional JSONObject associated with an index. Null is returned if the key is not found, or null if the
 | 
			
		||||
     * index has no value, or if the value is not a JSONObject.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return A JSONObject value.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONObject optJSONObject(int index) {
 | 
			
		||||
        Object o = opt(index);
 | 
			
		||||
        return o instanceof JSONObject ? (JSONObject) o : null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional long value associated with an index. Zero is returned if there is no value for the index, or if
 | 
			
		||||
     * the value is not a number and cannot be converted to a number.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     */
 | 
			
		||||
    public long optLong(int index) {
 | 
			
		||||
        return this.optLong(index, 0);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional long value associated with an index. The defaultValue
 | 
			
		||||
     * is returned if there is no value for the index, or if the value is not a
 | 
			
		||||
     * number and cannot be converted to a number.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index        The index must be between 0 and length() - 1.
 | 
			
		||||
     * @param defaultValue The default value.
 | 
			
		||||
     * @return The value.
 | 
			
		||||
     */
 | 
			
		||||
    public long optLong(int index, long defaultValue) {
 | 
			
		||||
        try {
 | 
			
		||||
            return getLong(index);
 | 
			
		||||
        } catch (JSONException ignored) {
 | 
			
		||||
            return defaultValue;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional string value associated with an index. It returns an
 | 
			
		||||
     * empty string if there is no value at that index. If the value is not a
 | 
			
		||||
     * string and is not null, then it is converted to a string.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index must be between 0 and length() - 1.
 | 
			
		||||
     * @return A String value.
 | 
			
		||||
     */
 | 
			
		||||
    public String optString(int index) {
 | 
			
		||||
        return this.optString(index, "");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the optional string associated with an index. The defaultValue is
 | 
			
		||||
     * returned if the key is not found.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index        The index must be between 0 and length() - 1.
 | 
			
		||||
     * @param defaultValue The default value.
 | 
			
		||||
     * @return A String value.
 | 
			
		||||
     */
 | 
			
		||||
    public String optString(int index, String defaultValue) {
 | 
			
		||||
        Object object = opt(index);
 | 
			
		||||
        return JSONObject.NULL.equals(object) ? defaultValue : object.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Append a boolean value. This increases the array's length by one.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value A boolean value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(boolean value) {
 | 
			
		||||
        this.put(value ? Boolean.TRUE : Boolean.FALSE);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put a value in the JSONArray, where the value will be a JSONArray which
 | 
			
		||||
     * is produced from a Collection.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value A Collection value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(Collection<Object> value) {
 | 
			
		||||
        this.put(new JSONArray(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Append a double value. This increases the array's length by one.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value A double value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException if the value is not finite.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(double value) throws JSONException {
 | 
			
		||||
        Double d = value;
 | 
			
		||||
        JSONObject.testValidity(d);
 | 
			
		||||
        this.put(d);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Append an int value. This increases the array's length by one.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value An int value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int value) {
 | 
			
		||||
        this.put(Integer.valueOf(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Append an long value. This increases the array's length by one.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value A long value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(long value) {
 | 
			
		||||
        this.put(Long.valueOf(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put a value in the JSONArray, where the value will be a JSONObject which
 | 
			
		||||
     * is produced from a Map.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value A Map value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(Map<String, Object> value) {
 | 
			
		||||
        this.put(new JSONObject(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Append an object value. This increases the array's length by one.
 | 
			
		||||
     *
 | 
			
		||||
     * @param value An object value. The value should be a Boolean, Double,
 | 
			
		||||
     *              Integer, JSONArray, JSONObject, Long, or String, or the JSONObject.NULL object.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(Object value) {
 | 
			
		||||
        this.myArrayList.add(value);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put or replace a boolean value in the JSONArray. If the index is greater than the length of the JSONArray, then
 | 
			
		||||
     * null elements will be added as necessary to pad it out.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value A boolean value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, boolean value) throws JSONException {
 | 
			
		||||
        this.put(index, value ? Boolean.TRUE : Boolean.FALSE);
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put a value in the JSONArray, where the value will be a JSONArray which
 | 
			
		||||
     * is produced from a Collection.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value A Collection value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative or if the value is not
 | 
			
		||||
     *                       finite.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, Collection<Object> value) throws JSONException {
 | 
			
		||||
        this.put(index, new JSONArray(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put or replace a double value. If the index is greater than the length
 | 
			
		||||
     * of the JSONArray, then null elements will be added as necessary to pad
 | 
			
		||||
     * it out.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value A double value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative or if the value is not
 | 
			
		||||
     *                       finite.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, double value) throws JSONException {
 | 
			
		||||
        this.put(index, new Double(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put or replace an int value. If the index is greater than the length of the JSONArray, then null elements will be
 | 
			
		||||
     * added as necessary to pad it out.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value An int value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, int value) throws JSONException {
 | 
			
		||||
        this.put(index, Integer.valueOf(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put or replace a long value. If the index is greater than the length of the JSONArray, then null elements will be
 | 
			
		||||
     * added as necessary to pad it out.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value A long value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, long value) throws JSONException {
 | 
			
		||||
        this.put(index, Long.valueOf(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put a value in the JSONArray, where the value will be a JSONObject that
 | 
			
		||||
     * is produced from a Map.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value The Map value.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative or if the the value is an
 | 
			
		||||
     *                       invalid number.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, Map<String, Object> value) throws JSONException {
 | 
			
		||||
        this.put(index, new JSONObject(value));
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Put or replace an object value in the JSONArray. If the index is greater than the length of the JSONArray, then
 | 
			
		||||
     * null elements will be added as necessary to pad it out.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The subscript.
 | 
			
		||||
     * @param value The value to put into the array. The value should be a Boolean, Double, Integer, JSONArray,
 | 
			
		||||
     *              JSONObject, Long, or String, or the JSONObject.NULL object.
 | 
			
		||||
     * @return this.
 | 
			
		||||
     * @throws JSONException If the index is negative or if the the value is an invalid number.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONArray put(int index, Object value) throws JSONException {
 | 
			
		||||
        JSONObject.testValidity(value);
 | 
			
		||||
        if (index < 0) {
 | 
			
		||||
            throw new JSONException("JSONArray[" + index + "] not found.");
 | 
			
		||||
        }
 | 
			
		||||
        if (index < length()) {
 | 
			
		||||
            this.myArrayList.set(index, value);
 | 
			
		||||
        } else {
 | 
			
		||||
            while (index != length()) {
 | 
			
		||||
                this.put(JSONObject.NULL);
 | 
			
		||||
            }
 | 
			
		||||
            this.put(value);
 | 
			
		||||
        }
 | 
			
		||||
        return this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Remove an index and close the hole.
 | 
			
		||||
     *
 | 
			
		||||
     * @param index The index of the element to be removed.
 | 
			
		||||
     * @return The value that was associated with the index, or null if there was no value.
 | 
			
		||||
     */
 | 
			
		||||
    public Object remove(int index) {
 | 
			
		||||
        return (index >= 0) && (index < length()) ? this.myArrayList.remove(index) : null;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Determine if two JSONArrays are similar. They must contain similar sequences.
 | 
			
		||||
     *
 | 
			
		||||
     * @param other The other JSONArray
 | 
			
		||||
     * @return true if they are equal
 | 
			
		||||
     */
 | 
			
		||||
    public boolean similar(Object other) {
 | 
			
		||||
        if (!(other instanceof JSONArray)) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        int len = length();
 | 
			
		||||
        if (len != ((JSONArray) other).length()) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        for (int i = 0; i < len; i += 1) {
 | 
			
		||||
            Object valueThis = get(i);
 | 
			
		||||
            Object valueOther = ((JSONArray) other).get(i);
 | 
			
		||||
            if (valueThis instanceof JSONObject) {
 | 
			
		||||
                if (!((JSONObject) valueThis).similar(valueOther)) {
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
            } else if (valueThis instanceof JSONArray) {
 | 
			
		||||
                if (!((JSONArray) valueThis).similar(valueOther)) {
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
            } else if (!valueThis.equals(valueOther)) {
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Produce a JSONObject by combining a JSONArray of names with the values of this JSONArray.
 | 
			
		||||
     *
 | 
			
		||||
     * @param names A JSONArray containing a list of key strings. These will be paired with the values.
 | 
			
		||||
     * @return A JSONObject, or null if there are no names or if this JSONArray has no values.
 | 
			
		||||
     * @throws JSONException If any of the names are null.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONObject toJSONObject(JSONArray names) throws JSONException {
 | 
			
		||||
        if ((names == null) || (names.length() == 0) || (length() == 0)) {
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
        JSONObject jo = new JSONObject();
 | 
			
		||||
        for (int i = 0; i < names.length(); i += 1) {
 | 
			
		||||
            jo.put(names.getString(i), opt(i));
 | 
			
		||||
        }
 | 
			
		||||
        return jo;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Make a JSON text of this JSONArray. For compactness, no unnecessary whitespace is added. If it is not possible to
 | 
			
		||||
     * produce a syntactically correct JSON text then null will be returned instead. This could occur if the array
 | 
			
		||||
     * contains an invalid number.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * Warning: This method assumes that the data structure is acyclical.
 | 
			
		||||
     *
 | 
			
		||||
     * @return a printable, displayable, transmittable representation of the array.
 | 
			
		||||
     */
 | 
			
		||||
    @Override public String toString() {
 | 
			
		||||
        try {
 | 
			
		||||
            return this.toString(0);
 | 
			
		||||
        } catch (JSONException ignored) {
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Make a prettyprinted JSON text of this JSONArray. Warning: This method assumes that the data structure is
 | 
			
		||||
     * acyclical.
 | 
			
		||||
     *
 | 
			
		||||
     * @param indentFactor The number of spaces to add to each level of indentation.
 | 
			
		||||
     * @return a printable, displayable, transmittable representation of the object, beginning with
 | 
			
		||||
     * {@code [} <small>(left bracket)</small> and ending with {@code ]}  <small>(right
 | 
			
		||||
     * bracket)</small>.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public String toString(int indentFactor) throws JSONException {
 | 
			
		||||
        StringWriter sw = new StringWriter();
 | 
			
		||||
        synchronized (sw.getBuffer()) {
 | 
			
		||||
            return this.write(sw, indentFactor, 0).toString();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Write the contents of the JSONArray as JSON text to a writer. For compactness, no whitespace is added.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * Warning: This method assumes that the data structure is acyclical.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The writer.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public Writer write(Writer writer) throws JSONException {
 | 
			
		||||
        return this.write(writer, 0, 0);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Write the contents of the JSONArray as JSON text to a writer. For compactness, no whitespace is added.
 | 
			
		||||
     * <p>
 | 
			
		||||
     * Warning: This method assumes that the data structure is acyclical.
 | 
			
		||||
     *
 | 
			
		||||
     * @param indentFactor The number of spaces to add to each level of indentation.
 | 
			
		||||
     * @param indent       The indention of the top level.
 | 
			
		||||
     * @return The writer.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    Writer write(Writer writer, int indentFactor, int indent) throws JSONException {
 | 
			
		||||
        try {
 | 
			
		||||
            boolean commanate = false;
 | 
			
		||||
            int length = length();
 | 
			
		||||
            writer.write('[');
 | 
			
		||||
            if (length == 1) {
 | 
			
		||||
                JSONObject.writeValue(writer, this.myArrayList.get(0), indentFactor, indent);
 | 
			
		||||
            } else if (length != 0) {
 | 
			
		||||
                int newindent = indent + indentFactor;
 | 
			
		||||
                for (int i = 0; i < length; i += 1) {
 | 
			
		||||
                    if (commanate) {
 | 
			
		||||
                        writer.write(',');
 | 
			
		||||
                    }
 | 
			
		||||
                    if (indentFactor > 0) {
 | 
			
		||||
                        writer.write('\n');
 | 
			
		||||
                    }
 | 
			
		||||
                    JSONObject.indent(writer, newindent);
 | 
			
		||||
                    JSONObject.writeValue(writer, this.myArrayList.get(i), indentFactor, newindent);
 | 
			
		||||
                    commanate = true;
 | 
			
		||||
                }
 | 
			
		||||
                if (indentFactor > 0) {
 | 
			
		||||
                    writer.write('\n');
 | 
			
		||||
                }
 | 
			
		||||
                JSONObject.indent(writer, indent);
 | 
			
		||||
            }
 | 
			
		||||
            writer.write(']');
 | 
			
		||||
            return writer;
 | 
			
		||||
        } catch (IOException e) {
 | 
			
		||||
            throw new JSONException(e);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,40 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * The JSONException is thrown by the JSON.org classes when things are amiss.
 | 
			
		||||
 *
 | 
			
		||||
 * @author JSON.org
 | 
			
		||||
 * @version 2014-05-03
 | 
			
		||||
 */
 | 
			
		||||
public class JSONException extends RuntimeException {
 | 
			
		||||
    private static final long serialVersionUID = 0;
 | 
			
		||||
    private Throwable cause;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructs a JSONException with an explanatory message.
 | 
			
		||||
     *
 | 
			
		||||
     * @param message Detail about the reason for the exception.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONException(final String message) {
 | 
			
		||||
        super(message);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructs a new JSONException with the specified cause.
 | 
			
		||||
     *
 | 
			
		||||
     * @param cause The cause.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONException(final Throwable cause) {
 | 
			
		||||
        super(cause.getMessage());
 | 
			
		||||
        this.cause = cause;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Returns the cause of this exception or null if the cause is nonexistent or unknown.
 | 
			
		||||
     *
 | 
			
		||||
     * @return the cause of this exception or null if the cause is nonexistent or unknown.
 | 
			
		||||
     */
 | 
			
		||||
    @Override public Throwable getCause() {
 | 
			
		||||
        return cause;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							@@ -1,16 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * The <code>JSONString</code> interface allows a <code>toJSONString()</code> method so that a class can change the
 | 
			
		||||
 * behavior of <code>JSONObject.toString()</code>, <code>JSONArray.toString()</code>, and
 | 
			
		||||
 * <code>JSONWriter.value(</code>Object<code>)</code>. The <code>toJSONString</code> method will be used instead of the
 | 
			
		||||
 * default behavior of using the Object's <code>toString()</code> method and quoting the result.
 | 
			
		||||
 */
 | 
			
		||||
public interface JSONString {
 | 
			
		||||
    /**
 | 
			
		||||
     * The <code>toJSONString</code> method allows a class to produce its own JSON serialization.
 | 
			
		||||
     *
 | 
			
		||||
     * @return A strictly syntactically correct JSON text.
 | 
			
		||||
     */
 | 
			
		||||
    String toJSONString();
 | 
			
		||||
}
 | 
			
		||||
@@ -1,384 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
import java.io.*;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * A JSONTokener takes a source string and extracts characters and tokens from it. It is used by the JSONObject and
 | 
			
		||||
 * JSONArray constructors to parse JSON source strings.
 | 
			
		||||
 *
 | 
			
		||||
 * @author JSON.org
 | 
			
		||||
 * @version 2014-05-03
 | 
			
		||||
 */
 | 
			
		||||
public class JSONTokener {
 | 
			
		||||
    private final Reader reader;
 | 
			
		||||
    private long character;
 | 
			
		||||
    private boolean eof;
 | 
			
		||||
    private long index;
 | 
			
		||||
    private long line;
 | 
			
		||||
    private char previous;
 | 
			
		||||
    private boolean usePrevious;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONTokener from a Reader.
 | 
			
		||||
     *
 | 
			
		||||
     * @param reader A reader.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONTokener(final Reader reader) {
 | 
			
		||||
        this.reader = reader.markSupported() ? reader : new BufferedReader(reader);
 | 
			
		||||
        eof = false;
 | 
			
		||||
        usePrevious = false;
 | 
			
		||||
        previous = 0;
 | 
			
		||||
        index = 0;
 | 
			
		||||
        character = 1;
 | 
			
		||||
        line = 1;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONTokener from an InputStream.
 | 
			
		||||
     *
 | 
			
		||||
     * @param inputStream The source.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONTokener(final InputStream inputStream) throws JSONException {
 | 
			
		||||
        this(new InputStreamReader(inputStream));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct a JSONTokener from a string.
 | 
			
		||||
     *
 | 
			
		||||
     * @param s A source string.
 | 
			
		||||
     */
 | 
			
		||||
    public JSONTokener(final String s) {
 | 
			
		||||
        this(new StringReader(s));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the hex value of a character (base16).
 | 
			
		||||
     *
 | 
			
		||||
     * @param c A character between '0' and '9' or between 'A' and 'F' or between 'a' and 'f'.
 | 
			
		||||
     * @return An int between 0 and 15, or -1 if c was not a hex digit.
 | 
			
		||||
     */
 | 
			
		||||
    public static int dehexchar(final char c) {
 | 
			
		||||
        if ((c >= '0') && (c <= '9')) {
 | 
			
		||||
            return c - '0';
 | 
			
		||||
        }
 | 
			
		||||
        if ((c >= 'A') && (c <= 'F')) {
 | 
			
		||||
            return c - ('A' - 10);
 | 
			
		||||
        }
 | 
			
		||||
        if ((c >= 'a') && (c <= 'f')) {
 | 
			
		||||
            return c - ('a' - 10);
 | 
			
		||||
        }
 | 
			
		||||
        return -1;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Back up one character. This provides a sort of lookahead capability, so that you can test for a digit or letter
 | 
			
		||||
     * before attempting to parse the next number or identifier.
 | 
			
		||||
     */
 | 
			
		||||
    public void back() throws JSONException {
 | 
			
		||||
        if (usePrevious || (index <= 0)) {
 | 
			
		||||
            throw new JSONException("Stepping back two steps is not supported");
 | 
			
		||||
        }
 | 
			
		||||
        index -= 1;
 | 
			
		||||
        character -= 1;
 | 
			
		||||
        usePrevious = true;
 | 
			
		||||
        eof = false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public boolean end() {
 | 
			
		||||
        return eof && !usePrevious;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Determine if the source string still contains characters that next() can consume.
 | 
			
		||||
     *
 | 
			
		||||
     * @return true if not yet at the end of the source.
 | 
			
		||||
     */
 | 
			
		||||
    public boolean more() throws JSONException {
 | 
			
		||||
        this.next();
 | 
			
		||||
        if (end()) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        back();
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the next character in the source string.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The next character, or 0 if past the end of the source string.
 | 
			
		||||
     */
 | 
			
		||||
    public char next() throws JSONException {
 | 
			
		||||
        int c;
 | 
			
		||||
        if (usePrevious) {
 | 
			
		||||
            usePrevious = false;
 | 
			
		||||
            c = previous;
 | 
			
		||||
        } else {
 | 
			
		||||
            try {
 | 
			
		||||
                c = reader.read();
 | 
			
		||||
            } catch (final IOException exception) {
 | 
			
		||||
                throw new JSONException(exception);
 | 
			
		||||
            }
 | 
			
		||||
            if (c <= 0) { // End of stream
 | 
			
		||||
                eof = true;
 | 
			
		||||
                c = 0;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        index += 1;
 | 
			
		||||
        if (previous == '\r') {
 | 
			
		||||
            line += 1;
 | 
			
		||||
            character = c == '\n' ? 0 : 1;
 | 
			
		||||
        } else if (c == '\n') {
 | 
			
		||||
            line += 1;
 | 
			
		||||
            character = 0;
 | 
			
		||||
        } else {
 | 
			
		||||
            character += 1;
 | 
			
		||||
        }
 | 
			
		||||
        previous = (char) c;
 | 
			
		||||
        return previous;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Consume the next character, and check that it matches a specified character.
 | 
			
		||||
     *
 | 
			
		||||
     * @param c The character to match.
 | 
			
		||||
     * @return The character.
 | 
			
		||||
     * @throws JSONException if the character does not match.
 | 
			
		||||
     */
 | 
			
		||||
    public char next(final char c) throws JSONException {
 | 
			
		||||
        final char n = this.next();
 | 
			
		||||
        if (n != c) {
 | 
			
		||||
            throw syntaxError("Expected '" + c + "' and instead saw '" + n + "'");
 | 
			
		||||
        }
 | 
			
		||||
        return n;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the next n characters.
 | 
			
		||||
     *
 | 
			
		||||
     * @param n The number of characters to take.
 | 
			
		||||
     * @return A string of n characters.
 | 
			
		||||
     * @throws JSONException Substring bounds error if there are not n characters remaining in the source string.
 | 
			
		||||
     */
 | 
			
		||||
    public String next(final int n) throws JSONException {
 | 
			
		||||
        if (n == 0) {
 | 
			
		||||
            return "";
 | 
			
		||||
        }
 | 
			
		||||
        final char[] chars = new char[n];
 | 
			
		||||
        int pos = 0;
 | 
			
		||||
        while (pos < n) {
 | 
			
		||||
            chars[pos] = this.next();
 | 
			
		||||
            if (end()) {
 | 
			
		||||
                throw syntaxError("Substring bounds error");
 | 
			
		||||
            }
 | 
			
		||||
            pos += 1;
 | 
			
		||||
        }
 | 
			
		||||
        return new String(chars);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the next char in the string, skipping whitespace.
 | 
			
		||||
     *
 | 
			
		||||
     * @return A character, or 0 if there are no more characters.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public char nextClean() throws JSONException {
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            final char c = this.next();
 | 
			
		||||
            if ((c == 0) || (c > ' ')) {
 | 
			
		||||
                return c;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Return the characters up to the next close quote character. Backslash processing is done. The formal JSON format
 | 
			
		||||
     * does not allow strings in single quotes, but an implementation is allowed to accept them.
 | 
			
		||||
     *
 | 
			
		||||
     * @param quote The quoting character, either <code>"</code>  <small>(double quote)</small> or <code>'</code>
 | 
			
		||||
     *               <small>(single quote)</small>.
 | 
			
		||||
     * @return A String.
 | 
			
		||||
     * @throws JSONException Unterminated string.
 | 
			
		||||
     */
 | 
			
		||||
    public String nextString(final char quote) throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        final StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            c = this.next();
 | 
			
		||||
            switch (c) {
 | 
			
		||||
                case 0:
 | 
			
		||||
                case '\n':
 | 
			
		||||
                case '\r':
 | 
			
		||||
                    throw syntaxError("Unterminated string");
 | 
			
		||||
                case '\\':
 | 
			
		||||
                    c = this.next();
 | 
			
		||||
                    switch (c) {
 | 
			
		||||
                        case 'b':
 | 
			
		||||
                            sb.append('\b');
 | 
			
		||||
                            break;
 | 
			
		||||
                        case 't':
 | 
			
		||||
                            sb.append('\t');
 | 
			
		||||
                            break;
 | 
			
		||||
                        case 'n':
 | 
			
		||||
                            sb.append('\n');
 | 
			
		||||
                            break;
 | 
			
		||||
                        case 'f':
 | 
			
		||||
                            sb.append('\f');
 | 
			
		||||
                            break;
 | 
			
		||||
                        case 'r':
 | 
			
		||||
                            sb.append('\r');
 | 
			
		||||
                            break;
 | 
			
		||||
                        case 'u':
 | 
			
		||||
                            sb.append((char) Integer.parseInt(this.next(4), 16));
 | 
			
		||||
                            break;
 | 
			
		||||
                        case '"':
 | 
			
		||||
                        case '\'':
 | 
			
		||||
                        case '\\':
 | 
			
		||||
                        case '/':
 | 
			
		||||
                            sb.append(c);
 | 
			
		||||
                            break;
 | 
			
		||||
                        default:
 | 
			
		||||
                            throw syntaxError("Illegal escape.");
 | 
			
		||||
                    }
 | 
			
		||||
                    break;
 | 
			
		||||
                default:
 | 
			
		||||
                    if (c == quote) {
 | 
			
		||||
                        return sb.toString();
 | 
			
		||||
                    }
 | 
			
		||||
                    sb.append(c);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the text up but not including the specified character or the end of line, whichever comes first.
 | 
			
		||||
     *
 | 
			
		||||
     * @param delimiter A delimiter character.
 | 
			
		||||
     * @return A string.
 | 
			
		||||
     */
 | 
			
		||||
    public String nextTo(final char delimiter) throws JSONException {
 | 
			
		||||
        final StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            final char c = this.next();
 | 
			
		||||
            if ((c == delimiter) || (c == 0) || (c == '\n') || (c == '\r')) {
 | 
			
		||||
                if (c != 0) {
 | 
			
		||||
                    back();
 | 
			
		||||
                }
 | 
			
		||||
                return sb.toString().trim();
 | 
			
		||||
            }
 | 
			
		||||
            sb.append(c);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the text up but not including one of the specified delimiter characters or the end of line, whichever comes
 | 
			
		||||
     * first.
 | 
			
		||||
     *
 | 
			
		||||
     * @param delimiters A set of delimiter characters.
 | 
			
		||||
     * @return A string, trimmed.
 | 
			
		||||
     */
 | 
			
		||||
    public String nextTo(final String delimiters) throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        final StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            c = this.next();
 | 
			
		||||
            if ((delimiters.indexOf(c) >= 0) || (c == 0) || (c == '\n') || (c == '\r')) {
 | 
			
		||||
                if (c != 0) {
 | 
			
		||||
                    back();
 | 
			
		||||
                }
 | 
			
		||||
                return sb.toString().trim();
 | 
			
		||||
            }
 | 
			
		||||
            sb.append(c);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the next value. The value can be a Boolean, Double, Integer, JSONArray, JSONObject, Long, or String, or the
 | 
			
		||||
     * JSONObject.NULL object.
 | 
			
		||||
     *
 | 
			
		||||
     * @return An object.
 | 
			
		||||
     * @throws JSONException If syntax error.
 | 
			
		||||
     */
 | 
			
		||||
    public Object nextValue() throws JSONException {
 | 
			
		||||
        char c = nextClean();
 | 
			
		||||
        String string;
 | 
			
		||||
        switch (c) {
 | 
			
		||||
            case '"':
 | 
			
		||||
            case '\'':
 | 
			
		||||
                return nextString(c);
 | 
			
		||||
            case '{':
 | 
			
		||||
                back();
 | 
			
		||||
                return new JSONObject(this);
 | 
			
		||||
            case '[':
 | 
			
		||||
                back();
 | 
			
		||||
                return new JSONArray(this);
 | 
			
		||||
        }
 | 
			
		||||
        /*
 | 
			
		||||
         * Handle unquoted text. This could be the values true, false, or
 | 
			
		||||
         * null, or it can be a number. An implementation (such as this one)
 | 
			
		||||
         * is allowed to also accept non-standard forms.
 | 
			
		||||
         * Accumulate characters until we reach the end of the text or a
 | 
			
		||||
         * formatting character.
 | 
			
		||||
         */
 | 
			
		||||
        final StringBuilder sb = new StringBuilder();
 | 
			
		||||
        while ((c >= ' ') && (",:]}/\\\"[{;=#".indexOf(c) < 0)) {
 | 
			
		||||
            sb.append(c);
 | 
			
		||||
            c = this.next();
 | 
			
		||||
        }
 | 
			
		||||
        back();
 | 
			
		||||
        string = sb.toString().trim();
 | 
			
		||||
        if (string.isEmpty()) {
 | 
			
		||||
            throw syntaxError("Missing value");
 | 
			
		||||
        }
 | 
			
		||||
        return JSONObject.stringToValue(string);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Skip characters until the next character is the requested character. If the requested character is not found, no
 | 
			
		||||
     * characters are skipped.
 | 
			
		||||
     *
 | 
			
		||||
     * @param to A character to skip to.
 | 
			
		||||
     * @return The requested character, or zero if the requested character is not found.
 | 
			
		||||
     */
 | 
			
		||||
    public char skipTo(final char to) throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        try {
 | 
			
		||||
            final long startIndex = index;
 | 
			
		||||
            final long startCharacter = character;
 | 
			
		||||
            final long startLine = line;
 | 
			
		||||
            reader.mark(1000000);
 | 
			
		||||
            do {
 | 
			
		||||
                c = this.next();
 | 
			
		||||
                if (c == 0) {
 | 
			
		||||
                    reader.reset();
 | 
			
		||||
                    index = startIndex;
 | 
			
		||||
                    character = startCharacter;
 | 
			
		||||
                    line = startLine;
 | 
			
		||||
                    return 0;
 | 
			
		||||
                }
 | 
			
		||||
            } while (c != to);
 | 
			
		||||
        } catch (final IOException exception) {
 | 
			
		||||
            throw new JSONException(exception);
 | 
			
		||||
        }
 | 
			
		||||
        back();
 | 
			
		||||
        return c;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Make a JSONException to signal a syntax error.
 | 
			
		||||
     *
 | 
			
		||||
     * @param message The error message.
 | 
			
		||||
     * @return A JSONException object, suitable for throwing
 | 
			
		||||
     */
 | 
			
		||||
    public JSONException syntaxError(final String message) {
 | 
			
		||||
        return new JSONException(message + toString());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Make a printable string of this JSONTokener.
 | 
			
		||||
     *
 | 
			
		||||
     * @return " at {index} [character {character} line {line}]"
 | 
			
		||||
     */
 | 
			
		||||
    @Override public String toString() {
 | 
			
		||||
        return " at " + index + " [character " + character + " line " + line + "]";
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,52 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
import java.util.Enumeration;
 | 
			
		||||
import java.util.Iterator;
 | 
			
		||||
import java.util.Properties;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * Converts a Property file data into JSONObject and back.
 | 
			
		||||
 *
 | 
			
		||||
 * @author JSON.org
 | 
			
		||||
 * @version 2014-05-03
 | 
			
		||||
 */
 | 
			
		||||
public class Property {
 | 
			
		||||
    /**
 | 
			
		||||
     * Converts a property file object into a JSONObject. The property file object is a table of name value pairs.
 | 
			
		||||
     *
 | 
			
		||||
     * @param properties java.util.Properties
 | 
			
		||||
     * @return JSONObject
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public static JSONObject toJSONObject(final java.util.Properties properties)
 | 
			
		||||
        throws JSONException {
 | 
			
		||||
        final JSONObject jo = new JSONObject();
 | 
			
		||||
        if ((properties != null) && !properties.isEmpty()) {
 | 
			
		||||
            final Enumeration enumProperties = properties.propertyNames();
 | 
			
		||||
            while (enumProperties.hasMoreElements()) {
 | 
			
		||||
                final String name = (String) enumProperties.nextElement();
 | 
			
		||||
                jo.put(name, properties.getProperty(name));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return jo;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Converts the JSONObject into a property file object.
 | 
			
		||||
     *
 | 
			
		||||
     * @param jo JSONObject
 | 
			
		||||
     * @return java.util.Properties
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public static Properties toProperties(final JSONObject jo) throws JSONException {
 | 
			
		||||
        final Properties properties = new Properties();
 | 
			
		||||
        if (jo != null) {
 | 
			
		||||
            final Iterator<String> keys = jo.keys();
 | 
			
		||||
            while (keys.hasNext()) {
 | 
			
		||||
                final String name = keys.next();
 | 
			
		||||
                properties.put(name, jo.getString(name));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return properties;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,375 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
import java.util.Iterator;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * This provides static methods to convert an XML text into a JSONObject, and to covert a JSONObject into an XML text.
 | 
			
		||||
 *
 | 
			
		||||
 * @author JSON.org
 | 
			
		||||
 * @version 2014-05-03
 | 
			
		||||
 */
 | 
			
		||||
class XML {
 | 
			
		||||
 | 
			
		||||
    static final Character AMP = '&';
 | 
			
		||||
    static final Character APOS = '\'';
 | 
			
		||||
    static final Character BANG = '!';
 | 
			
		||||
    static final Character EQ = '=';
 | 
			
		||||
    static final Character GT = '>';
 | 
			
		||||
    static final Character LT = '<';
 | 
			
		||||
    static final Character QUEST = '?';
 | 
			
		||||
    static final Character QUOT = '"';
 | 
			
		||||
    static final Character SLASH = '/';
 | 
			
		||||
 | 
			
		||||
    static String escape(String string) {
 | 
			
		||||
        StringBuilder sb = new StringBuilder(string.length());
 | 
			
		||||
        for (int i = 0, length = string.length(); i < length; i++) {
 | 
			
		||||
            char c = string.charAt(i);
 | 
			
		||||
            switch (c) {
 | 
			
		||||
                case '&':
 | 
			
		||||
                    sb.append("&");
 | 
			
		||||
                    break;
 | 
			
		||||
                case '<':
 | 
			
		||||
                    sb.append("<");
 | 
			
		||||
                    break;
 | 
			
		||||
                case '>':
 | 
			
		||||
                    sb.append(">");
 | 
			
		||||
                    break;
 | 
			
		||||
                case '"':
 | 
			
		||||
                    sb.append(""");
 | 
			
		||||
                    break;
 | 
			
		||||
                case '\'':
 | 
			
		||||
                    sb.append("'");
 | 
			
		||||
                    break;
 | 
			
		||||
                default:
 | 
			
		||||
                    sb.append(c);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return sb.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Throw an exception if the string contains whitespace. Whitespace is not allowed in tagNames and attributes.
 | 
			
		||||
     *
 | 
			
		||||
     * @param string A string.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    static void noSpace(String string) throws JSONException {
 | 
			
		||||
        int length = string.length();
 | 
			
		||||
        if (length == 0) {
 | 
			
		||||
            throw new JSONException("Empty string.");
 | 
			
		||||
        }
 | 
			
		||||
        for (char c : string.toCharArray()) {
 | 
			
		||||
            if (Character.isWhitespace(c)) {
 | 
			
		||||
                throw new JSONException('\'' + string + "' contains a space character.");
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Scan the content following the named tag, attaching it to the context.
 | 
			
		||||
     *
 | 
			
		||||
     * @param x       The XMLTokener containing the source string.
 | 
			
		||||
     * @param context The JSONObject that will include the new material.
 | 
			
		||||
     * @param name    The tag name.
 | 
			
		||||
     * @return true if the close tag is processed.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    private static boolean parse(XMLTokener x, JSONObject context, String name)
 | 
			
		||||
        throws JSONException {
 | 
			
		||||
        // Test for and skip past these forms:
 | 
			
		||||
        // <!-- ... -->
 | 
			
		||||
        // <! ... >
 | 
			
		||||
        // <![ ... ]]>
 | 
			
		||||
        // <? ... ?>
 | 
			
		||||
        // Report errors for these forms:
 | 
			
		||||
        // <>
 | 
			
		||||
        // <=
 | 
			
		||||
        // <<
 | 
			
		||||
        Object token = x.nextToken();
 | 
			
		||||
        // <!
 | 
			
		||||
        String string;
 | 
			
		||||
        if (token == BANG) {
 | 
			
		||||
            char c = x.next();
 | 
			
		||||
            if (c == '-') {
 | 
			
		||||
                if (x.next() == '-') {
 | 
			
		||||
                    x.skipPast("-->");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                x.back();
 | 
			
		||||
            } else if (c == '[') {
 | 
			
		||||
                token = x.nextToken();
 | 
			
		||||
                if ("CDATA".equals(token)) {
 | 
			
		||||
                    if (x.next() == '[') {
 | 
			
		||||
                        string = x.nextCDATA();
 | 
			
		||||
                        if (!string.isEmpty()) {
 | 
			
		||||
                            context.accumulate("content", string);
 | 
			
		||||
                        }
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                throw x.syntaxError("Expected 'CDATA['");
 | 
			
		||||
            }
 | 
			
		||||
            int i = 1;
 | 
			
		||||
            do {
 | 
			
		||||
                token = x.nextMeta();
 | 
			
		||||
                if (token == null) {
 | 
			
		||||
                    throw x.syntaxError("Missing '>' after '<!'.");
 | 
			
		||||
                } else if (token == LT) {
 | 
			
		||||
                    i += 1;
 | 
			
		||||
                } else if (token == GT) {
 | 
			
		||||
                    i -= 1;
 | 
			
		||||
                }
 | 
			
		||||
            } while (i > 0);
 | 
			
		||||
            return false;
 | 
			
		||||
        } else if (token == QUEST) {
 | 
			
		||||
            // <?
 | 
			
		||||
            x.skipPast("?>");
 | 
			
		||||
            return false;
 | 
			
		||||
        } else if (token == SLASH) {
 | 
			
		||||
            // Close tag </
 | 
			
		||||
            token = x.nextToken();
 | 
			
		||||
            if (name == null) {
 | 
			
		||||
                throw x.syntaxError("Mismatched close tag " + token);
 | 
			
		||||
            }
 | 
			
		||||
            if (!token.equals(name)) {
 | 
			
		||||
                throw x.syntaxError("Mismatched " + name + " and " + token);
 | 
			
		||||
            }
 | 
			
		||||
            if (x.nextToken() != GT) {
 | 
			
		||||
                throw x.syntaxError("Misshaped close tag");
 | 
			
		||||
            }
 | 
			
		||||
            return true;
 | 
			
		||||
        } else if (token instanceof Character) {
 | 
			
		||||
            throw x.syntaxError("Misshaped tag");
 | 
			
		||||
            // Open tag <
 | 
			
		||||
        } else {
 | 
			
		||||
            String tagName = (String) token;
 | 
			
		||||
            token = null;
 | 
			
		||||
            JSONObject jsonobject = new JSONObject();
 | 
			
		||||
            for (; ; ) {
 | 
			
		||||
                if (token == null) {
 | 
			
		||||
                    token = x.nextToken();
 | 
			
		||||
                }
 | 
			
		||||
                // attribute = value
 | 
			
		||||
                if (token instanceof String) {
 | 
			
		||||
                    string = (String) token;
 | 
			
		||||
                    token = x.nextToken();
 | 
			
		||||
                    if (token == EQ) {
 | 
			
		||||
                        token = x.nextToken();
 | 
			
		||||
                        if (!(token instanceof String)) {
 | 
			
		||||
                            throw x.syntaxError("Missing value");
 | 
			
		||||
                        }
 | 
			
		||||
                        jsonobject.accumulate(string, XML.stringToValue((String) token));
 | 
			
		||||
                        token = null;
 | 
			
		||||
                    } else {
 | 
			
		||||
                        jsonobject.accumulate(string, "");
 | 
			
		||||
                    }
 | 
			
		||||
                    // Empty tag <.../>
 | 
			
		||||
                } else if (token == SLASH) {
 | 
			
		||||
                    if (x.nextToken() != GT) {
 | 
			
		||||
                        throw x.syntaxError("Misshaped tag");
 | 
			
		||||
                    }
 | 
			
		||||
                    if (jsonobject.length() > 0) {
 | 
			
		||||
                        context.accumulate(tagName, jsonobject);
 | 
			
		||||
                    } else {
 | 
			
		||||
                        context.accumulate(tagName, "");
 | 
			
		||||
                    }
 | 
			
		||||
                    return false;
 | 
			
		||||
                    // Content, between <...> and </...>
 | 
			
		||||
                } else if (token == GT) {
 | 
			
		||||
                    for (; ; ) {
 | 
			
		||||
                        token = x.nextContent();
 | 
			
		||||
                        if (token == null) {
 | 
			
		||||
                            if (tagName != null) {
 | 
			
		||||
                                throw x.syntaxError("Unclosed tag " + tagName);
 | 
			
		||||
                            }
 | 
			
		||||
                            return false;
 | 
			
		||||
                        } else if (token instanceof String) {
 | 
			
		||||
                            string = (String) token;
 | 
			
		||||
                            if (!string.isEmpty()) {
 | 
			
		||||
                                jsonobject.accumulate("content", XML.stringToValue(string));
 | 
			
		||||
                            }
 | 
			
		||||
                            // Nested element
 | 
			
		||||
                        } else if (token == LT) {
 | 
			
		||||
                            if (parse(x, jsonobject, tagName)) {
 | 
			
		||||
                                if (jsonobject.length() == 0) {
 | 
			
		||||
                                    context.accumulate(tagName, "");
 | 
			
		||||
                                } else if ((jsonobject.length() == 1) && (jsonobject.opt("content")
 | 
			
		||||
                                    != null)) {
 | 
			
		||||
                                    context.accumulate(tagName, jsonobject.opt("content"));
 | 
			
		||||
                                } else {
 | 
			
		||||
                                    context.accumulate(tagName, jsonobject);
 | 
			
		||||
                                }
 | 
			
		||||
                                return false;
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                } else {
 | 
			
		||||
                    throw x.syntaxError("Misshaped tag");
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Try to convert a string into a number, boolean, or null. If the string can't be converted, return the string.
 | 
			
		||||
     * This is much less ambitious than JSONObject.stringToValue, especially because it does not attempt to convert plus
 | 
			
		||||
     * forms, octal forms, hex forms, or E forms lacking decimal points.
 | 
			
		||||
     *
 | 
			
		||||
     * @param string A String.
 | 
			
		||||
     * @return A simple JSON value.
 | 
			
		||||
     */
 | 
			
		||||
    static Object stringToValue(String string) {
 | 
			
		||||
        if ("true".equalsIgnoreCase(string)) {
 | 
			
		||||
            return Boolean.TRUE;
 | 
			
		||||
        }
 | 
			
		||||
        if ("false".equalsIgnoreCase(string)) {
 | 
			
		||||
            return Boolean.FALSE;
 | 
			
		||||
        }
 | 
			
		||||
        if ("null".equalsIgnoreCase(string)) {
 | 
			
		||||
            return JSONObject.NULL;
 | 
			
		||||
        }
 | 
			
		||||
        //If it might be a number, try converting it, first as a Long, and then as a Double. If that doesn't work, return the string.
 | 
			
		||||
        try {
 | 
			
		||||
            char initial = string.charAt(0);
 | 
			
		||||
            if ((initial == '-') || ((initial >= '0') && (initial <= '9'))) {
 | 
			
		||||
                Long value = Long.valueOf(string);
 | 
			
		||||
                if (value.toString().equals(string)) {
 | 
			
		||||
                    return value;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        } catch (NumberFormatException ignore) {
 | 
			
		||||
            try {
 | 
			
		||||
                Double value = Double.valueOf(string);
 | 
			
		||||
                if (value.toString().equals(string)) {
 | 
			
		||||
                    return value;
 | 
			
		||||
                }
 | 
			
		||||
            } catch (NumberFormatException ignored) {
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return string;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static JSONObject toJSONObject(String string) throws JSONException {
 | 
			
		||||
        JSONObject jo = new JSONObject();
 | 
			
		||||
        XMLTokener x = new XMLTokener(string);
 | 
			
		||||
        while (x.more() && x.skipPast("<")) {
 | 
			
		||||
            parse(x, jo, null);
 | 
			
		||||
        }
 | 
			
		||||
        return jo;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Convert a JSONObject into a well-formed, element-normal XML string.
 | 
			
		||||
     *
 | 
			
		||||
     * @param object A JSONObject.
 | 
			
		||||
     * @return A string.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public static String toString(Object object) throws JSONException {
 | 
			
		||||
        return toString(object, null);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Convert a JSONObject into a well-formed, element-normal XML string.
 | 
			
		||||
     *
 | 
			
		||||
     * @param object  A JSONObject.
 | 
			
		||||
     * @param tagName The optional name of the enclosing tag.
 | 
			
		||||
     * @return A string.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public static String toString(Object object, String tagName) throws JSONException {
 | 
			
		||||
        StringBuilder sb = new StringBuilder();
 | 
			
		||||
        int i;
 | 
			
		||||
        JSONArray ja;
 | 
			
		||||
        int length;
 | 
			
		||||
        String string;
 | 
			
		||||
        if (object instanceof JSONObject) {
 | 
			
		||||
            // Emit <tagName>
 | 
			
		||||
            if (tagName != null) {
 | 
			
		||||
                sb.append('<');
 | 
			
		||||
                sb.append(tagName);
 | 
			
		||||
                sb.append('>');
 | 
			
		||||
            }
 | 
			
		||||
            // Loop thru the keys.
 | 
			
		||||
            JSONObject jo = (JSONObject) object;
 | 
			
		||||
            Iterator<String> keys = jo.keys();
 | 
			
		||||
            while (keys.hasNext()) {
 | 
			
		||||
                String key = keys.next();
 | 
			
		||||
                Object value = jo.opt(key);
 | 
			
		||||
                if (value == null) {
 | 
			
		||||
                    value = "";
 | 
			
		||||
                }
 | 
			
		||||
                string = value instanceof String ? (String) value : null;
 | 
			
		||||
                // Emit content in body
 | 
			
		||||
                if ("content".equals(key)) {
 | 
			
		||||
                    if (value instanceof JSONArray) {
 | 
			
		||||
                        ja = (JSONArray) value;
 | 
			
		||||
                        length = ja.length();
 | 
			
		||||
                        for (i = 0; i < length; i += 1) {
 | 
			
		||||
                            if (i > 0) {
 | 
			
		||||
                                sb.append('\n');
 | 
			
		||||
                            }
 | 
			
		||||
                            sb.append(escape(ja.get(i).toString()));
 | 
			
		||||
                        }
 | 
			
		||||
                    } else {
 | 
			
		||||
                        sb.append(escape(value.toString()));
 | 
			
		||||
                    }
 | 
			
		||||
                    // Emit an array of similar keys
 | 
			
		||||
                } else if (value instanceof JSONArray) {
 | 
			
		||||
                    ja = (JSONArray) value;
 | 
			
		||||
                    length = ja.length();
 | 
			
		||||
                    for (i = 0; i < length; i += 1) {
 | 
			
		||||
                        value = ja.get(i);
 | 
			
		||||
                        if (value instanceof JSONArray) {
 | 
			
		||||
                            sb.append('<');
 | 
			
		||||
                            sb.append(key);
 | 
			
		||||
                            sb.append('>');
 | 
			
		||||
                            sb.append(toString(value));
 | 
			
		||||
                            sb.append("</");
 | 
			
		||||
                            sb.append(key);
 | 
			
		||||
                            sb.append('>');
 | 
			
		||||
                        } else {
 | 
			
		||||
                            sb.append(toString(value, key));
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                } else if ("".equals(value)) {
 | 
			
		||||
                    sb.append('<');
 | 
			
		||||
                    sb.append(key);
 | 
			
		||||
                    sb.append("/>");
 | 
			
		||||
                    // Emit a new tag <k>
 | 
			
		||||
                } else {
 | 
			
		||||
                    sb.append(toString(value, key));
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            if (tagName != null) {
 | 
			
		||||
                // Emit the </tagname> close tag
 | 
			
		||||
                sb.append("</");
 | 
			
		||||
                sb.append(tagName);
 | 
			
		||||
                sb.append('>');
 | 
			
		||||
            }
 | 
			
		||||
            return sb.toString();
 | 
			
		||||
            // XML does not have good support for arrays. If an array appears in
 | 
			
		||||
            // a place
 | 
			
		||||
            // where XML is lacking, synthesize an <array> element.
 | 
			
		||||
        } else {
 | 
			
		||||
            if (object.getClass().isArray()) {
 | 
			
		||||
                object = new JSONArray(object);
 | 
			
		||||
            }
 | 
			
		||||
            if (object instanceof JSONArray) {
 | 
			
		||||
                ja = (JSONArray) object;
 | 
			
		||||
                length = ja.length();
 | 
			
		||||
                for (i = 0; i < length; i += 1) {
 | 
			
		||||
                    sb.append(toString(ja.opt(i), tagName == null ? "array" : tagName));
 | 
			
		||||
                }
 | 
			
		||||
                return sb.toString();
 | 
			
		||||
            } else {
 | 
			
		||||
                string = escape(object.toString());
 | 
			
		||||
                return (tagName == null) ?
 | 
			
		||||
                    '"' + string + '"' :
 | 
			
		||||
                    string.isEmpty() ?
 | 
			
		||||
                        '<' + tagName + "/>" :
 | 
			
		||||
                        '<' + tagName + '>' + string + "</" + tagName + '>';
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,315 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.json;
 | 
			
		||||
 | 
			
		||||
import java.util.HashMap;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * The XMLTokener extends the JSONTokener to provide additional methods for the parsing of XML texts.
 | 
			
		||||
 *
 | 
			
		||||
 * @author JSON.org
 | 
			
		||||
 * @version 2014-05-03
 | 
			
		||||
 */
 | 
			
		||||
public class XMLTokener extends JSONTokener {
 | 
			
		||||
    /**
 | 
			
		||||
     * The table of entity values. It initially contains Character values for amp, apos, gt, lt, quot.
 | 
			
		||||
     */
 | 
			
		||||
    public static final HashMap<String, Character> entity;
 | 
			
		||||
 | 
			
		||||
    static {
 | 
			
		||||
        entity = new HashMap<>(8);
 | 
			
		||||
        entity.put("amp", XML.AMP);
 | 
			
		||||
        entity.put("apos", XML.APOS);
 | 
			
		||||
        entity.put("gt", XML.GT);
 | 
			
		||||
        entity.put("lt", XML.LT);
 | 
			
		||||
        entity.put("quot", XML.QUOT);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Construct an XMLTokener from a string.
 | 
			
		||||
     *
 | 
			
		||||
     * @param s A source string.
 | 
			
		||||
     */
 | 
			
		||||
    public XMLTokener(final String s) {
 | 
			
		||||
        super(s);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the text in the CDATA block.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The string up to the <code>]]></code>.
 | 
			
		||||
     * @throws JSONException If the <code>]]></code> is not found.
 | 
			
		||||
     */
 | 
			
		||||
    public String nextCDATA() throws JSONException {
 | 
			
		||||
        final StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            char c = next();
 | 
			
		||||
            if (end()) {
 | 
			
		||||
                throw syntaxError("Unclosed CDATA");
 | 
			
		||||
            }
 | 
			
		||||
            sb.append(c);
 | 
			
		||||
            int i = sb.length() - 3;
 | 
			
		||||
            if ((i >= 0) && (sb.charAt(i) == ']') && (sb.charAt(i + 1) == ']') && (sb.charAt(i + 2)
 | 
			
		||||
                == '>')) {
 | 
			
		||||
                sb.setLength(i);
 | 
			
		||||
                return sb.toString();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the next XML outer token, trimming whitespace. There are two kinds of tokens: the '<' character which begins
 | 
			
		||||
     * a markup tag, and the content text between markup tags.
 | 
			
		||||
     *
 | 
			
		||||
     * @return A string, or a '<' Character, or null if there is no more source text.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public Object nextContent() throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        do {
 | 
			
		||||
            c = next();
 | 
			
		||||
        } while (Character.isWhitespace(c));
 | 
			
		||||
        if (c == 0) {
 | 
			
		||||
            return null;
 | 
			
		||||
        }
 | 
			
		||||
        if (c == '<') {
 | 
			
		||||
            return XML.LT;
 | 
			
		||||
        }
 | 
			
		||||
        StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            if ((c == '<') || (c == 0)) {
 | 
			
		||||
                back();
 | 
			
		||||
                return sb.toString().trim();
 | 
			
		||||
            }
 | 
			
		||||
            if (c == '&') {
 | 
			
		||||
                sb.append(nextEntity('&'));
 | 
			
		||||
            } else {
 | 
			
		||||
                sb.append(c);
 | 
			
		||||
            }
 | 
			
		||||
            c = next();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Return the next entity. These entities are translated to Characters: <code>& " >  <
 | 
			
		||||
     * "</code>.
 | 
			
		||||
     *
 | 
			
		||||
     * @param ampersand An ampersand character.
 | 
			
		||||
     * @return A Character or an entity String if the entity is not recognized.
 | 
			
		||||
     * @throws JSONException If missing ';' in XML entity.
 | 
			
		||||
     */
 | 
			
		||||
    public Object nextEntity(final char ampersand) throws JSONException {
 | 
			
		||||
        final StringBuilder sb = new StringBuilder();
 | 
			
		||||
        for (; ; ) {
 | 
			
		||||
            final char c = next();
 | 
			
		||||
            if (Character.isLetterOrDigit(c) || (c == '#')) {
 | 
			
		||||
                sb.append(Character.toLowerCase(c));
 | 
			
		||||
            } else if (c == ';') {
 | 
			
		||||
                break;
 | 
			
		||||
            } else {
 | 
			
		||||
                throw syntaxError("Missing ';' in XML entity: &" + sb);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        final String string = sb.toString();
 | 
			
		||||
        final Object object = entity.get(string);
 | 
			
		||||
        return object != null ? object : ampersand + string + ';';
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Returns the next XML meta token. This is used for skipping over <!...> and <?...?> structures.
 | 
			
		||||
     *
 | 
			
		||||
     * @return Syntax characters (<code>< > / = ! ?</code>) are returned as Character, and strings and names are
 | 
			
		||||
     * returned as Boolean. We don't care what the values actually are.
 | 
			
		||||
     * @throws JSONException If a string is not properly closed or if the XML is badly structured.
 | 
			
		||||
     */
 | 
			
		||||
    public Object nextMeta() throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        do {
 | 
			
		||||
            c = next();
 | 
			
		||||
        } while (Character.isWhitespace(c));
 | 
			
		||||
        char q;
 | 
			
		||||
        switch (c) {
 | 
			
		||||
            case 0:
 | 
			
		||||
                throw syntaxError("Misshaped meta tag");
 | 
			
		||||
            case '<':
 | 
			
		||||
                return XML.LT;
 | 
			
		||||
            case '>':
 | 
			
		||||
                return XML.GT;
 | 
			
		||||
            case '/':
 | 
			
		||||
                return XML.SLASH;
 | 
			
		||||
            case '=':
 | 
			
		||||
                return XML.EQ;
 | 
			
		||||
            case '!':
 | 
			
		||||
                return XML.BANG;
 | 
			
		||||
            case '?':
 | 
			
		||||
                return XML.QUEST;
 | 
			
		||||
            case '"':
 | 
			
		||||
            case '\'':
 | 
			
		||||
                q = c;
 | 
			
		||||
                for (; ; ) {
 | 
			
		||||
                    c = next();
 | 
			
		||||
                    if (c == 0) {
 | 
			
		||||
                        throw syntaxError("Unterminated string");
 | 
			
		||||
                    }
 | 
			
		||||
                    if (c == q) {
 | 
			
		||||
                        return Boolean.TRUE;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            default:
 | 
			
		||||
                for (; ; ) {
 | 
			
		||||
                    c = next();
 | 
			
		||||
                    if (Character.isWhitespace(c)) {
 | 
			
		||||
                        return Boolean.TRUE;
 | 
			
		||||
                    }
 | 
			
		||||
                    switch (c) {
 | 
			
		||||
                        case 0:
 | 
			
		||||
                        case '<':
 | 
			
		||||
                        case '>':
 | 
			
		||||
                        case '/':
 | 
			
		||||
                        case '=':
 | 
			
		||||
                        case '!':
 | 
			
		||||
                        case '?':
 | 
			
		||||
                        case '"':
 | 
			
		||||
                        case '\'':
 | 
			
		||||
                            back();
 | 
			
		||||
                            return Boolean.TRUE;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the next XML Token. These tokens are found inside of angle brackets. It may be one of these characters:
 | 
			
		||||
     * <code>/ >= ! ?</code> or it may be a string wrapped in single quotes or double quotes, or it may be a name.
 | 
			
		||||
     *
 | 
			
		||||
     * @return a String or a Character.
 | 
			
		||||
     * @throws JSONException If the XML is not well formed.
 | 
			
		||||
     */
 | 
			
		||||
    public Object nextToken() throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        do {
 | 
			
		||||
            c = next();
 | 
			
		||||
        } while (Character.isWhitespace(c));
 | 
			
		||||
        char q;
 | 
			
		||||
        StringBuilder sb;
 | 
			
		||||
        switch (c) {
 | 
			
		||||
            case 0:
 | 
			
		||||
                throw syntaxError("Misshaped element");
 | 
			
		||||
            case '<':
 | 
			
		||||
                throw syntaxError("Misplaced '<'");
 | 
			
		||||
            case '>':
 | 
			
		||||
                return XML.GT;
 | 
			
		||||
            case '/':
 | 
			
		||||
                return XML.SLASH;
 | 
			
		||||
            case '=':
 | 
			
		||||
                return XML.EQ;
 | 
			
		||||
            case '!':
 | 
			
		||||
                return XML.BANG;
 | 
			
		||||
            case '?':
 | 
			
		||||
                return XML.QUEST;
 | 
			
		||||
            // Quoted string
 | 
			
		||||
            case '"':
 | 
			
		||||
            case '\'':
 | 
			
		||||
                q = c;
 | 
			
		||||
                sb = new StringBuilder();
 | 
			
		||||
                for (; ; ) {
 | 
			
		||||
                    c = next();
 | 
			
		||||
                    if (c == 0) {
 | 
			
		||||
                        throw syntaxError("Unterminated string");
 | 
			
		||||
                    }
 | 
			
		||||
                    if (c == q) {
 | 
			
		||||
                        return sb.toString();
 | 
			
		||||
                    }
 | 
			
		||||
                    if (c == '&') {
 | 
			
		||||
                        sb.append(nextEntity('&'));
 | 
			
		||||
                    } else {
 | 
			
		||||
                        sb.append(c);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            default:
 | 
			
		||||
                // Name
 | 
			
		||||
                sb = new StringBuilder();
 | 
			
		||||
                for (; ; ) {
 | 
			
		||||
                    sb.append(c);
 | 
			
		||||
                    c = next();
 | 
			
		||||
                    if (Character.isWhitespace(c)) {
 | 
			
		||||
                        return sb.toString();
 | 
			
		||||
                    }
 | 
			
		||||
                    switch (c) {
 | 
			
		||||
                        case 0:
 | 
			
		||||
                            return sb.toString();
 | 
			
		||||
                        case '>':
 | 
			
		||||
                        case '/':
 | 
			
		||||
                        case '=':
 | 
			
		||||
                        case '!':
 | 
			
		||||
                        case '?':
 | 
			
		||||
                        case '[':
 | 
			
		||||
                        case ']':
 | 
			
		||||
                            back();
 | 
			
		||||
                            return sb.toString();
 | 
			
		||||
                        case '<':
 | 
			
		||||
                        case '"':
 | 
			
		||||
                        case '\'':
 | 
			
		||||
                            throw syntaxError("Bad character in a name");
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Skip characters until past the requested string. If it is not found, we are left at the end of the source with a
 | 
			
		||||
     * result of false.
 | 
			
		||||
     *
 | 
			
		||||
     * @param to A string to skip past.
 | 
			
		||||
     * @throws JSONException
 | 
			
		||||
     */
 | 
			
		||||
    public boolean skipPast(final String to) throws JSONException {
 | 
			
		||||
        char c;
 | 
			
		||||
        int i;
 | 
			
		||||
        final int length = to.length();
 | 
			
		||||
        final char[] circle = new char[length];
 | 
			
		||||
        /*
 | 
			
		||||
         * First fill the circle buffer with as many characters as are in the
 | 
			
		||||
         * to string. If we reach an early end, bail.
 | 
			
		||||
         */
 | 
			
		||||
        for (i = 0; i < length; i += 1) {
 | 
			
		||||
            c = next();
 | 
			
		||||
            if (c == 0) {
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            circle[i] = c;
 | 
			
		||||
        }
 | 
			
		||||
        /* We will loop, possibly for all of the remaining characters. */
 | 
			
		||||
        for (int offset = 0; ; ) {
 | 
			
		||||
            int j = offset;
 | 
			
		||||
            boolean b = true;
 | 
			
		||||
            /* Compare the circle buffer with the to string. */
 | 
			
		||||
            for (i = 0; i < length; i += 1) {
 | 
			
		||||
                if (circle[j] != to.charAt(i)) {
 | 
			
		||||
                    b = false;
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                j += 1;
 | 
			
		||||
                if (j >= length) {
 | 
			
		||||
                    j -= length;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            /* If we exit the loop with b intact, then victory is ours. */
 | 
			
		||||
            if (b) {
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            /* Get the next character. If there isn't one, then defeat is ours. */
 | 
			
		||||
            c = next();
 | 
			
		||||
            if (c == 0) {
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            /*
 | 
			
		||||
             * Shove the character in the circle buffer and advance the
 | 
			
		||||
             * circle offset. The offset is mod n.
 | 
			
		||||
             */
 | 
			
		||||
            circle[offset] = c;
 | 
			
		||||
            offset += 1;
 | 
			
		||||
            if (offset >= length) {
 | 
			
		||||
                offset -= length;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,285 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.GeneratorWrapper;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.IndependentPlotGenerator;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.logger.ILogger;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.BlockRegistry;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.block.QueueProvider;
 | 
			
		||||
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
 | 
			
		||||
public interface IPlotMain extends ILogger {
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Log a message to console.
 | 
			
		||||
     *
 | 
			
		||||
     * @param message The message to log
 | 
			
		||||
     */
 | 
			
		||||
    void log(String message);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the `PlotSquared` directory.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The plugin directory
 | 
			
		||||
     */
 | 
			
		||||
    File getDirectory();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the directory containing all the worlds.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The directory containing the worlds
 | 
			
		||||
     */
 | 
			
		||||
    File getWorldContainer();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Wrap a player into a PlotPlayer object.
 | 
			
		||||
     *
 | 
			
		||||
     * @param player The player to convert to a PlotPlayer
 | 
			
		||||
     * @return A PlotPlayer
 | 
			
		||||
     */
 | 
			
		||||
    PlotPlayer wrapPlayer(Object player);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Disable the implementation.
 | 
			
		||||
     *
 | 
			
		||||
     * <ul>
 | 
			
		||||
     * <li>If a full disable isn't feasibly, just disable what it can.
 | 
			
		||||
     * </ul>
 | 
			
		||||
     */
 | 
			
		||||
    void disable();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Completely shut down the plugin
 | 
			
		||||
     */
 | 
			
		||||
    void shutdown();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the version of the PlotSquared being used.
 | 
			
		||||
     *
 | 
			
		||||
     * @return the plugin version
 | 
			
		||||
     */
 | 
			
		||||
    int[] getPluginVersion();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the version of the PlotSquared being used as a string.
 | 
			
		||||
     *
 | 
			
		||||
     * @return the plugin version as a string
 | 
			
		||||
     */
 | 
			
		||||
    String getPluginVersionString();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Usually PlotSquared
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    default String getPluginName() {
 | 
			
		||||
        return "PlotSquared";
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the version of Minecraft that is running.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    int[] getServerVersion();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the server implementation name and version
 | 
			
		||||
     */
 | 
			
		||||
    String getServerImplementation();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the NMS package prefix.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The NMS package prefix
 | 
			
		||||
     */
 | 
			
		||||
    String getNMSPackage();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the schematic handler.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The {@link SchematicHandler}
 | 
			
		||||
     */
 | 
			
		||||
    SchematicHandler initSchematicHandler();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the Chat Manager.
 | 
			
		||||
     *
 | 
			
		||||
     * @return The {@link ChatManager}
 | 
			
		||||
     */
 | 
			
		||||
    ChatManager initChatManager();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * The task manager will run and manage Minecraft tasks.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    TaskManager getTaskManager();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Run the task that will kill road mobs.
 | 
			
		||||
     */
 | 
			
		||||
    void runEntityTask();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register the implementation specific commands.
 | 
			
		||||
     */
 | 
			
		||||
    void registerCommands();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register the protection system.
 | 
			
		||||
     */
 | 
			
		||||
    void registerPlayerEvents();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register inventory related events.
 | 
			
		||||
     */
 | 
			
		||||
    void registerInventoryEvents();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register plot plus related events.
 | 
			
		||||
     */
 | 
			
		||||
    void registerPlotPlusEvents();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register force field events.
 | 
			
		||||
     */
 | 
			
		||||
    void registerForceFieldEvents();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register the WorldEdit hook.
 | 
			
		||||
     */
 | 
			
		||||
    boolean initWorldEdit();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the economy provider.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    EconHandler getEconomyHandler();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the {@link QueueProvider} class.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    QueueProvider initBlockQueue();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the {@link WorldUtil} class.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    WorldUtil initWorldUtil();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the EventUtil class.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    EventUtil initEventUtil();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the chunk manager.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    ChunkManager initChunkManager();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the {@link SetupUtils} class.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    SetupUtils initSetupUtils();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get {@link HybridUtils} class.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    HybridUtils initHybridUtils();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Start Metrics.
 | 
			
		||||
     */
 | 
			
		||||
    void startMetrics();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * If a world is already loaded, set the generator (use NMS if required).
 | 
			
		||||
     *
 | 
			
		||||
     * @param world The world to set the generator
 | 
			
		||||
     */
 | 
			
		||||
    void setGenerator(String world);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the {@link UUIDHandlerImplementation} which will cache and
 | 
			
		||||
     * provide UUIDs.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    UUIDHandlerImplementation initUUIDHandler();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the {@link InventoryUtil} class (used for implementation specific
 | 
			
		||||
     * inventory guis).
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    InventoryUtil initInventoryUtil();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Unregister a PlotPlayer from cache e.g. if they have logged off.
 | 
			
		||||
     *
 | 
			
		||||
     * @param player
 | 
			
		||||
     */
 | 
			
		||||
    void unregister(PlotPlayer player);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the generator wrapper for a world (world) and generator (name).
 | 
			
		||||
     *
 | 
			
		||||
     * @param world
 | 
			
		||||
     * @param name
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    GeneratorWrapper<?> getGenerator(String world, String name);
 | 
			
		||||
 | 
			
		||||
    GeneratorWrapper<?> wrapPlotGenerator(String world, IndependentPlotGenerator generator);
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register the chunk processor which will clean out chunks that have too
 | 
			
		||||
     * many blockstates or entities.
 | 
			
		||||
     */
 | 
			
		||||
    void registerChunkProcessor();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Register the world initialization events (used to keep track of worlds
 | 
			
		||||
     * being generated).
 | 
			
		||||
     */
 | 
			
		||||
    void registerWorldEvents();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Usually HybridGen
 | 
			
		||||
     *
 | 
			
		||||
     * @return Default implementation generator
 | 
			
		||||
     */
 | 
			
		||||
    IndependentPlotGenerator getDefaultGenerator();
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Get the class that will manage player titles.
 | 
			
		||||
     *
 | 
			
		||||
     * @return
 | 
			
		||||
     */
 | 
			
		||||
    AbstractTitle initTitleManager();
 | 
			
		||||
 | 
			
		||||
    List<String> getPluginIds();
 | 
			
		||||
 | 
			
		||||
    BlockRegistry<?> getBlockRegistry();
 | 
			
		||||
 | 
			
		||||
    LegacyMappings getLegacyMappings();
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
@@ -1,6 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot;
 | 
			
		||||
 | 
			
		||||
public enum Platform {
 | 
			
		||||
    Bukkit, Sponge, Spigot
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
										
											
												File diff suppressed because it is too large
												Load Diff
											
										
									
								
							@@ -1,45 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot;
 | 
			
		||||
 | 
			
		||||
public class PlotVersion {
 | 
			
		||||
    public final int year, month, day, hash, build;
 | 
			
		||||
 | 
			
		||||
    public PlotVersion(int year, int month, int day, int hash, int build) {
 | 
			
		||||
        this.year = year;
 | 
			
		||||
        this.month = month;
 | 
			
		||||
        this.day = day;
 | 
			
		||||
        this.hash = hash;
 | 
			
		||||
        this.build = build;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public PlotVersion(String version, String commit, String date) {
 | 
			
		||||
        String[] split = version.substring(version.indexOf('=') + 1).split("\\.");
 | 
			
		||||
        this.build = Integer.parseInt(split[1]);
 | 
			
		||||
        this.hash = Integer.parseInt(commit.substring(commit.indexOf('=') + 1), 16);
 | 
			
		||||
        String[] split1 = date.substring(date.indexOf('=') + 1).split("\\.");
 | 
			
		||||
        this.year = Integer.parseInt(split1[0]);
 | 
			
		||||
        this.month = Integer.parseInt(split1[1]);
 | 
			
		||||
        this.day = Integer.parseInt(split1[2]);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static PlotVersion tryParse(String version, String commit, String date) {
 | 
			
		||||
        try {
 | 
			
		||||
            return new PlotVersion(version, commit, date);
 | 
			
		||||
        } catch (Exception ignore) {
 | 
			
		||||
            ignore.printStackTrace();
 | 
			
		||||
            return new PlotVersion(0, 0, 0, 0, 0);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String toString() {
 | 
			
		||||
        if (hash == 0 && build == 0) {
 | 
			
		||||
            return "PlotSquared-" + year + "." + month + "." + day + "-SNAPSHOT";
 | 
			
		||||
        } else {
 | 
			
		||||
            return "PlotSquared-" + year + "." + month + "." + day + "-" + Integer.toHexString(hash)
 | 
			
		||||
                + "-" + build;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public boolean isNewer(PlotVersion other) {
 | 
			
		||||
        return other.build < this.build;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,82 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EventUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
 | 
			
		||||
import java.util.Iterator;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "add",
 | 
			
		||||
    description = "Allow a user to build in a plot while you are online",
 | 
			
		||||
    usage = "/plot add <player>", category = CommandCategory.SETTINGS, permission = "plots.add",
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Add extends Command {
 | 
			
		||||
 | 
			
		||||
    public Add() {
 | 
			
		||||
        super(MainCommand.getInstance(), true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(final PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) throws CommandException {
 | 
			
		||||
        final Plot plot = check(player.getCurrentPlot(), C.NOT_IN_PLOT);
 | 
			
		||||
        checkTrue(plot.hasOwner(), C.PLOT_UNOWNED);
 | 
			
		||||
        checkTrue(plot.isOwner(player.getUUID()) || Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_TRUST), C.NO_PLOT_PERMS);
 | 
			
		||||
        checkTrue(args.length == 1, C.COMMAND_SYNTAX, getUsage());
 | 
			
		||||
        final Set<UUID> uuids = MainUtil.getUUIDsFromString(args[0]);
 | 
			
		||||
        checkTrue(!uuids.isEmpty(), C.INVALID_PLAYER, args[0]);
 | 
			
		||||
        Iterator<UUID> iter = uuids.iterator();
 | 
			
		||||
        int size = plot.getTrusted().size() + plot.getMembers().size();
 | 
			
		||||
        while (iter.hasNext()) {
 | 
			
		||||
            UUID uuid = iter.next();
 | 
			
		||||
            if (uuid == DBFunc.EVERYONE && !(
 | 
			
		||||
                Permissions.hasPermission(player, C.PERMISSION_TRUST_EVERYONE) || Permissions
 | 
			
		||||
                    .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_TRUST))) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.INVALID_PLAYER, MainUtil.getName(uuid));
 | 
			
		||||
                iter.remove();
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            if (plot.isOwner(uuid)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.ALREADY_OWNER, MainUtil.getName(uuid));
 | 
			
		||||
                iter.remove();
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            if (plot.getMembers().contains(uuid)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.ALREADY_ADDED, MainUtil.getName(uuid));
 | 
			
		||||
                iter.remove();
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            size += plot.getTrusted().contains(uuid) ? 0 : 1;
 | 
			
		||||
        }
 | 
			
		||||
        checkTrue(!uuids.isEmpty(), null);
 | 
			
		||||
        checkTrue(size <= plot.getArea().MAX_PLOT_MEMBERS || Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_TRUST), C.PLOT_MAX_MEMBERS);
 | 
			
		||||
        confirm.run(this, new Runnable() {
 | 
			
		||||
            @Override // Success
 | 
			
		||||
            public void run() {
 | 
			
		||||
                for (UUID uuid : uuids) {
 | 
			
		||||
                    if (uuid != DBFunc.EVERYONE) {
 | 
			
		||||
                        if (!plot.removeTrusted(uuid)) {
 | 
			
		||||
                            if (plot.getDenied().contains(uuid)) {
 | 
			
		||||
                                plot.removeDenied(uuid);
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    plot.addMember(uuid);
 | 
			
		||||
                    EventUtil.manager.callMember(player, plot, uuid, true);
 | 
			
		||||
                    MainUtil.sendMessage(player, C.MEMBER_ADDED);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }, null);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,123 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.StringWrapper;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MathMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "setalias", permission = "plots.alias",
 | 
			
		||||
    description = "Set the plot name", usage = "/plot alias <set|remove> <alias>",
 | 
			
		||||
    aliases = {"alias", "sa", "name", "rename", "setname", "seta", "nameplot"},
 | 
			
		||||
    category = CommandCategory.SETTINGS, requiredType = RequiredType.NONE) public class Alias
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
 | 
			
		||||
        if (args.length == 0) {
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, "/plot alias <set|remove> <value>");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            sendMessage(player, C.PLOT_NOT_CLAIMED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (!plot.isOwner(player.getUUID())) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        boolean result = false;
 | 
			
		||||
 | 
			
		||||
        switch (args[0].toLowerCase()) {
 | 
			
		||||
            case "set":
 | 
			
		||||
                if (args.length != 2) {
 | 
			
		||||
                    C.COMMAND_SYNTAX.send(player, "/plot alias <set> <value>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                if (canExecuteCommand(player, C.PERMISSION_ALIAS_SET, false) || canExecuteCommand(
 | 
			
		||||
                    player, C.PERMISSION_ALIAS_SET_OBSOLETE, false)) {
 | 
			
		||||
                    result = setAlias(player, plot, args[1]);
 | 
			
		||||
                } else {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION);
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                break;
 | 
			
		||||
            case "remove":
 | 
			
		||||
                if (canExecuteCommand(player, C.PERMISSION_ALIAS_REMOVE, true)) {
 | 
			
		||||
                    result = removeAlias(player, plot);
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            default:
 | 
			
		||||
                C.COMMAND_SYNTAX.send(player, "/plot alias <set|remove> <alias>");
 | 
			
		||||
                result = false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
    private boolean setAlias(PlotPlayer player, Plot plot, String alias) {
 | 
			
		||||
        if (alias.isEmpty()) {
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, "/plot alias <set> <value>");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (alias.length() >= 50) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.ALIAS_TOO_LONG);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (alias.contains(" ")) {
 | 
			
		||||
            C.NOT_VALID_VALUE.send(player);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (MathMan.isInteger(alias)) {
 | 
			
		||||
            C.NOT_VALID_VALUE.send(player);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        for (Plot p : PlotSquared.get().getPlots(plot.getArea())) {
 | 
			
		||||
            if (p.getAlias().equalsIgnoreCase(alias)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.ALIAS_IS_TAKEN);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (UUIDHandler.nameExists(new StringWrapper(alias)) || PlotSquared.get()
 | 
			
		||||
            .hasPlotArea(alias)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.ALIAS_IS_TAKEN);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        plot.setAlias(alias);
 | 
			
		||||
        MainUtil.sendMessage(player, C.ALIAS_SET_TO.s().replaceAll("%alias%", alias));
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private boolean removeAlias(PlotPlayer player, Plot plot) {
 | 
			
		||||
        plot.setAlias(null);
 | 
			
		||||
        MainUtil.sendMessage(player, C.ALIAS_REMOVED.s());
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private boolean canExecuteCommand(PlotPlayer player, C caption, boolean sendMessage) {
 | 
			
		||||
        if (!Permissions.hasPermission(player, caption)) {
 | 
			
		||||
            if (sendMessage) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.NO_PERMISSION);
 | 
			
		||||
            }
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,469 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.configuration.ConfigurationSection;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Configuration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.AugmentedUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridPlotWorld;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Objects;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "area", permission = "plots.area",
 | 
			
		||||
    category = CommandCategory.ADMINISTRATION, requiredType = RequiredType.NONE,
 | 
			
		||||
    description = "Create a new PlotArea", aliases = "world",
 | 
			
		||||
    usage = "/plot area <create|info|list|tp|regen>", confirmation = true) public class Area
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        if (args.length == 0) {
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        switch (args[0].toLowerCase()) {
 | 
			
		||||
            case "c":
 | 
			
		||||
            case "setup":
 | 
			
		||||
            case "create":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_AREA_CREATE)) {
 | 
			
		||||
                    C.NO_PERMISSION.send(player, C.PERMISSION_AREA_CREATE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                switch (args.length) {
 | 
			
		||||
                    case 1:
 | 
			
		||||
                        C.COMMAND_SYNTAX
 | 
			
		||||
                            .send(player, "/plot area create [world[:id]] [<modifier>=<value>]...");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    case 2:
 | 
			
		||||
                        switch (args[1].toLowerCase()) {
 | 
			
		||||
                            case "pos1": { // Set position 1
 | 
			
		||||
                                HybridPlotWorld area = player.getMeta("area_create_area");
 | 
			
		||||
                                if (area == null) {
 | 
			
		||||
                                    C.COMMAND_SYNTAX.send(player,
 | 
			
		||||
                                        "/plot area create [world[:id]] [<modifier>=<value>]...");
 | 
			
		||||
                                    return false;
 | 
			
		||||
                                }
 | 
			
		||||
                                Location location = player.getLocation();
 | 
			
		||||
                                player.setMeta("area_pos1", location);
 | 
			
		||||
                                C.SET_ATTRIBUTE.send(player, "area_pos1",
 | 
			
		||||
                                    location.getX() + "," + location.getZ());
 | 
			
		||||
                                MainUtil.sendMessage(player,
 | 
			
		||||
                                    "You will now set pos2: /plot area create pos2"
 | 
			
		||||
                                        + "\nNote: The chosen plot size may result in the created area not exactly matching your second position.");
 | 
			
		||||
                                return true;
 | 
			
		||||
                            }
 | 
			
		||||
                            case "pos2":  // Set position 2 and finish creation for type=2 (partial)
 | 
			
		||||
                                final HybridPlotWorld area = player.getMeta("area_create_area");
 | 
			
		||||
                                if (area == null) {
 | 
			
		||||
                                    C.COMMAND_SYNTAX.send(player,
 | 
			
		||||
                                        "/plot area create [world[:id]] [<modifier>=<value>]...");
 | 
			
		||||
                                    return false;
 | 
			
		||||
                                }
 | 
			
		||||
                                Location pos1 = player.getLocation();
 | 
			
		||||
                                Location pos2 = player.getMeta("area_pos1");
 | 
			
		||||
                                int dx = Math.abs(pos1.getX() - pos2.getX());
 | 
			
		||||
                                int dz = Math.abs(pos1.getZ() - pos2.getZ());
 | 
			
		||||
                                int numX = Math.max(1,
 | 
			
		||||
                                    (dx + 1 + area.ROAD_WIDTH + area.SIZE / 2) / area.SIZE);
 | 
			
		||||
                                int numZ = Math.max(1,
 | 
			
		||||
                                    (dz + 1 + area.ROAD_WIDTH + area.SIZE / 2) / area.SIZE);
 | 
			
		||||
                                int ddx = dx - (numX * area.SIZE - area.ROAD_WIDTH);
 | 
			
		||||
                                int ddz = dz - (numZ * area.SIZE - area.ROAD_WIDTH);
 | 
			
		||||
                                int bx = Math.min(pos1.getX(), pos2.getX()) + ddx;
 | 
			
		||||
                                int bz = Math.min(pos1.getZ(), pos2.getZ()) + ddz;
 | 
			
		||||
                                int tx = Math.max(pos1.getX(), pos2.getX()) - ddx;
 | 
			
		||||
                                int tz = Math.max(pos1.getZ(), pos2.getZ()) - ddz;
 | 
			
		||||
                                int lower = (area.ROAD_WIDTH & 1) == 0 ?
 | 
			
		||||
                                    area.ROAD_WIDTH / 2 - 1 :
 | 
			
		||||
                                    area.ROAD_WIDTH / 2;
 | 
			
		||||
                                final int offsetX = bx - (area.ROAD_WIDTH == 0 ? 0 : lower);
 | 
			
		||||
                                final int offsetZ = bz - (area.ROAD_WIDTH == 0 ? 0 : lower);
 | 
			
		||||
                                final RegionWrapper region = new RegionWrapper(bx, tx, bz, tz);
 | 
			
		||||
                                Set<PlotArea> areas =
 | 
			
		||||
                                    PlotSquared.get().getPlotAreas(area.worldname, region);
 | 
			
		||||
                                if (!areas.isEmpty()) {
 | 
			
		||||
                                    C.CLUSTER_INTERSECTION
 | 
			
		||||
                                        .send(player, areas.iterator().next().toString());
 | 
			
		||||
                                    return false;
 | 
			
		||||
                                }
 | 
			
		||||
                                final SetupObject object = new SetupObject();
 | 
			
		||||
                                object.world = area.worldname;
 | 
			
		||||
                                object.id = area.id;
 | 
			
		||||
                                object.terrain = area.TERRAIN;
 | 
			
		||||
                                object.type = area.TYPE;
 | 
			
		||||
                                object.min = new PlotId(1, 1);
 | 
			
		||||
                                object.max = new PlotId(numX, numZ);
 | 
			
		||||
                                object.plotManager = PlotSquared.imp().getPluginName();
 | 
			
		||||
                                object.setupGenerator = PlotSquared.imp().getPluginName();
 | 
			
		||||
                                object.step = area.getSettingNodes();
 | 
			
		||||
                                final String path =
 | 
			
		||||
                                    "worlds." + area.worldname + ".areas." + area.id + '-'
 | 
			
		||||
                                        + object.min + '-' + object.max;
 | 
			
		||||
                                Runnable run = () -> {
 | 
			
		||||
                                    if (offsetX != 0) {
 | 
			
		||||
                                        PlotSquared.get().worlds
 | 
			
		||||
                                            .set(path + ".road.offset.x", offsetX);
 | 
			
		||||
                                    }
 | 
			
		||||
                                    if (offsetZ != 0) {
 | 
			
		||||
                                        PlotSquared.get().worlds
 | 
			
		||||
                                            .set(path + ".road.offset.z", offsetZ);
 | 
			
		||||
                                    }
 | 
			
		||||
                                    final String world = SetupUtils.manager.setupWorld(object);
 | 
			
		||||
                                    if (WorldUtil.IMP.isWorld(world)) {
 | 
			
		||||
                                        PlotSquared.get().loadWorld(world, null);
 | 
			
		||||
                                        C.SETUP_FINISHED.send(player);
 | 
			
		||||
                                        player.teleport(WorldUtil.IMP.getSpawn(world));
 | 
			
		||||
                                        if (area.TERRAIN != 3) {
 | 
			
		||||
                                            ChunkManager.largeRegionTask(world, region,
 | 
			
		||||
                                                new RunnableVal<ChunkLoc>() {
 | 
			
		||||
                                                    @Override public void run(ChunkLoc value) {
 | 
			
		||||
                                                        AugmentedUtils
 | 
			
		||||
                                                            .generate(world, value.x, value.z,
 | 
			
		||||
                                                                null);
 | 
			
		||||
                                                    }
 | 
			
		||||
                                                }, null);
 | 
			
		||||
                                        }
 | 
			
		||||
                                    } else {
 | 
			
		||||
                                        MainUtil.sendMessage(player,
 | 
			
		||||
                                            "An error occurred while creating the world: "
 | 
			
		||||
                                                + area.worldname);
 | 
			
		||||
                                    }
 | 
			
		||||
                                };
 | 
			
		||||
                                if (hasConfirmation(player)) {
 | 
			
		||||
                                    CmdConfirm.addPending(player,
 | 
			
		||||
                                        getCommandString() + " create pos2 (Creates world)", run);
 | 
			
		||||
                                } else {
 | 
			
		||||
                                    run.run();
 | 
			
		||||
                                }
 | 
			
		||||
                                return true;
 | 
			
		||||
                        }
 | 
			
		||||
                    default: // Start creation
 | 
			
		||||
                        final SetupObject object = new SetupObject();
 | 
			
		||||
                        String[] split = args[1].split(":");
 | 
			
		||||
                        String id;
 | 
			
		||||
                        if (split.length == 2) {
 | 
			
		||||
                            id = split[1];
 | 
			
		||||
                        } else {
 | 
			
		||||
                            id = null;
 | 
			
		||||
                        }
 | 
			
		||||
                        object.world = split[0];
 | 
			
		||||
                        final HybridPlotWorld pa = new HybridPlotWorld(object.world, id,
 | 
			
		||||
                            PlotSquared.get().IMP.getDefaultGenerator(), null, null);
 | 
			
		||||
                        PlotArea other = PlotSquared.get().getPlotArea(pa.worldname, id);
 | 
			
		||||
                        if (other != null && Objects.equals(pa.id, other.id)) {
 | 
			
		||||
                            C.SETUP_WORLD_TAKEN.send(player, pa.toString());
 | 
			
		||||
                            return false;
 | 
			
		||||
                        }
 | 
			
		||||
                        Set<PlotArea> areas = PlotSquared.get().getPlotAreas(pa.worldname);
 | 
			
		||||
                        if (!areas.isEmpty()) {
 | 
			
		||||
                            PlotArea area = areas.iterator().next();
 | 
			
		||||
                            pa.TYPE = area.TYPE;
 | 
			
		||||
                        }
 | 
			
		||||
                        pa.SIZE = (short) (pa.PLOT_WIDTH + pa.ROAD_WIDTH);
 | 
			
		||||
                        for (int i = 2; i < args.length; i++) {
 | 
			
		||||
                            String[] pair = args[i].split("=");
 | 
			
		||||
                            if (pair.length != 2) {
 | 
			
		||||
                                C.COMMAND_SYNTAX.send(player, getCommandString()
 | 
			
		||||
                                    + " create [world[:id]] [<modifier>=<value>]...");
 | 
			
		||||
                                return false;
 | 
			
		||||
                            }
 | 
			
		||||
                            switch (pair[0].toLowerCase()) {
 | 
			
		||||
                                case "s":
 | 
			
		||||
                                case "size":
 | 
			
		||||
                                    pa.PLOT_WIDTH = Integer.parseInt(pair[1]);
 | 
			
		||||
                                    pa.SIZE = (short) (pa.PLOT_WIDTH + pa.ROAD_WIDTH);
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "g":
 | 
			
		||||
                                case "gap":
 | 
			
		||||
                                    pa.ROAD_WIDTH = Integer.parseInt(pair[1]);
 | 
			
		||||
                                    pa.SIZE = (short) (pa.PLOT_WIDTH + pa.ROAD_WIDTH);
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "h":
 | 
			
		||||
                                case "height":
 | 
			
		||||
                                    int value = Integer.parseInt(pair[1]);
 | 
			
		||||
                                    pa.PLOT_HEIGHT = value;
 | 
			
		||||
                                    pa.ROAD_HEIGHT = value;
 | 
			
		||||
                                    pa.WALL_HEIGHT = value;
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "f":
 | 
			
		||||
                                case "floor":
 | 
			
		||||
                                    pa.TOP_BLOCK = Configuration.BLOCK_BUCKET.parseString(pair[1]);
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "m":
 | 
			
		||||
                                case "main":
 | 
			
		||||
                                    pa.MAIN_BLOCK = Configuration.BLOCK_BUCKET.parseString(pair[1]);
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "w":
 | 
			
		||||
                                case "wall":
 | 
			
		||||
                                    pa.WALL_FILLING =
 | 
			
		||||
                                        Configuration.BLOCK_BUCKET.parseString(pair[1]);
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "b":
 | 
			
		||||
                                case "border":
 | 
			
		||||
                                    pa.WALL_BLOCK = Configuration.BLOCK_BUCKET.parseString(pair[1]);
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "terrain":
 | 
			
		||||
                                    pa.TERRAIN = Integer.parseInt(pair[1]);
 | 
			
		||||
                                    object.terrain = pa.TERRAIN;
 | 
			
		||||
                                    break;
 | 
			
		||||
                                case "type":
 | 
			
		||||
                                    pa.TYPE = Integer.parseInt(pair[1]);
 | 
			
		||||
                                    object.type = pa.TYPE;
 | 
			
		||||
                                    break;
 | 
			
		||||
                                default:
 | 
			
		||||
                                    C.COMMAND_SYNTAX.send(player, getCommandString()
 | 
			
		||||
                                        + " create [world[:id]] [<modifier>=<value>]...");
 | 
			
		||||
                                    return false;
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                        if (pa.TYPE != 2) {
 | 
			
		||||
                            if (WorldUtil.IMP.isWorld(pa.worldname)) {
 | 
			
		||||
                                C.SETUP_WORLD_TAKEN.send(player, pa.worldname);
 | 
			
		||||
                                return false;
 | 
			
		||||
                            }
 | 
			
		||||
                            Runnable run = () -> {
 | 
			
		||||
                                String path = "worlds." + pa.worldname;
 | 
			
		||||
                                if (!PlotSquared.get().worlds.contains(path)) {
 | 
			
		||||
                                    PlotSquared.get().worlds.createSection(path);
 | 
			
		||||
                                }
 | 
			
		||||
                                ConfigurationSection section =
 | 
			
		||||
                                    PlotSquared.get().worlds.getConfigurationSection(path);
 | 
			
		||||
                                pa.saveConfiguration(section);
 | 
			
		||||
                                pa.loadConfiguration(section);
 | 
			
		||||
                                object.plotManager = PlotSquared.imp().getPluginName();
 | 
			
		||||
                                object.setupGenerator = PlotSquared.imp().getPluginName();
 | 
			
		||||
                                String world = SetupUtils.manager.setupWorld(object);
 | 
			
		||||
                                if (WorldUtil.IMP.isWorld(world)) {
 | 
			
		||||
                                    C.SETUP_FINISHED.send(player);
 | 
			
		||||
                                    player.teleport(WorldUtil.IMP.getSpawn(world));
 | 
			
		||||
                                } else {
 | 
			
		||||
                                    MainUtil.sendMessage(player,
 | 
			
		||||
                                        "An error occurred while creating the world: "
 | 
			
		||||
                                            + pa.worldname);
 | 
			
		||||
                                }
 | 
			
		||||
                                try {
 | 
			
		||||
                                    PlotSquared.get().worlds.save(PlotSquared.get().worldsFile);
 | 
			
		||||
                                } catch (IOException e) {
 | 
			
		||||
                                    e.printStackTrace();
 | 
			
		||||
                                }
 | 
			
		||||
                            };
 | 
			
		||||
                            if (hasConfirmation(player)) {
 | 
			
		||||
                                CmdConfirm.addPending(player,
 | 
			
		||||
                                    getCommandString() + ' ' + StringMan.join(args, " "), run);
 | 
			
		||||
                            } else {
 | 
			
		||||
                                run.run();
 | 
			
		||||
                            }
 | 
			
		||||
                            return true;
 | 
			
		||||
                        }
 | 
			
		||||
                        if (pa.id == null) {
 | 
			
		||||
                            C.COMMAND_SYNTAX.send(player, getCommandString()
 | 
			
		||||
                                + " create [world[:id]] [<modifier>=<value>]...");
 | 
			
		||||
                            return false;
 | 
			
		||||
                        }
 | 
			
		||||
                        if (WorldUtil.IMP.isWorld(pa.worldname)) {
 | 
			
		||||
                            if (!player.getLocation().getWorld().equals(pa.worldname)) {
 | 
			
		||||
                                player.teleport(WorldUtil.IMP.getSpawn(pa.worldname));
 | 
			
		||||
                            }
 | 
			
		||||
                        } else {
 | 
			
		||||
                            object.terrain = 0;
 | 
			
		||||
                            object.type = 0;
 | 
			
		||||
                            SetupUtils.manager.setupWorld(object);
 | 
			
		||||
                            player.teleport(WorldUtil.IMP.getSpawn(pa.worldname));
 | 
			
		||||
                        }
 | 
			
		||||
                        player.setMeta("area_create_area", pa);
 | 
			
		||||
                        MainUtil.sendMessage(player,
 | 
			
		||||
                            "$1Go to the first corner and use: $2 " + getCommandString()
 | 
			
		||||
                                + " create pos1");
 | 
			
		||||
                        break;
 | 
			
		||||
                }
 | 
			
		||||
                return true;
 | 
			
		||||
            case "i":
 | 
			
		||||
            case "info": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_AREA_INFO)) {
 | 
			
		||||
                    C.NO_PERMISSION.send(player, C.PERMISSION_AREA_INFO);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area;
 | 
			
		||||
                switch (args.length) {
 | 
			
		||||
                    case 1:
 | 
			
		||||
                        area = player.getApplicablePlotArea();
 | 
			
		||||
                        break;
 | 
			
		||||
                    case 2:
 | 
			
		||||
                        area = PlotSquared.get().getPlotAreaByString(args[1]);
 | 
			
		||||
                        break;
 | 
			
		||||
                    default:
 | 
			
		||||
                        C.COMMAND_SYNTAX.send(player, getCommandString() + " info [area]");
 | 
			
		||||
                        return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    if (args.length == 2) {
 | 
			
		||||
                        C.NOT_VALID_PLOT_WORLD.send(player, args[1]);
 | 
			
		||||
                    } else {
 | 
			
		||||
                        C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    }
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                String name;
 | 
			
		||||
                double percent;
 | 
			
		||||
                int claimed = area.getPlotCount();
 | 
			
		||||
                int clusters = area.getClusters().size();
 | 
			
		||||
                String region;
 | 
			
		||||
                String generator = String.valueOf(area.getGenerator());
 | 
			
		||||
                if (area.TYPE == 2) {
 | 
			
		||||
                    PlotId min = area.getMin();
 | 
			
		||||
                    PlotId max = area.getMax();
 | 
			
		||||
                    name = area.worldname + ';' + area.id + ';' + min + ';' + max;
 | 
			
		||||
                    int size = (max.x - min.x + 1) * (max.y - min.y + 1);
 | 
			
		||||
                    percent = claimed == 0 ? 0 : size / (double) claimed;
 | 
			
		||||
                    region = area.getRegion().toString();
 | 
			
		||||
                } else {
 | 
			
		||||
                    name = area.worldname;
 | 
			
		||||
                    percent = claimed == 0 ? 0 : 100d * claimed / Integer.MAX_VALUE;
 | 
			
		||||
                    region = "N/A";
 | 
			
		||||
                }
 | 
			
		||||
                String value = "&r$1NAME: " + name + "\n$1Type: $2" + area.TYPE + "\n$1Terrain: $2"
 | 
			
		||||
                    + area.TERRAIN + "\n$1Usage: $2" + String.format("%.2f", percent) + '%'
 | 
			
		||||
                    + "\n$1Claimed: $2" + claimed + "\n$1Clusters: $2" + clusters + "\n$1Region: $2"
 | 
			
		||||
                    + region + "\n$1Generator: $2" + generator;
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    C.PLOT_INFO_HEADER.s() + '\n' + value + '\n' + C.PLOT_INFO_FOOTER.s(), false);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "l":
 | 
			
		||||
            case "list":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_AREA_LIST)) {
 | 
			
		||||
                    C.NO_PERMISSION.send(player, C.PERMISSION_AREA_LIST);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                int page;
 | 
			
		||||
                switch (args.length) {
 | 
			
		||||
                    case 1:
 | 
			
		||||
                        page = 0;
 | 
			
		||||
                        break;
 | 
			
		||||
                    case 2:
 | 
			
		||||
                        if (MathMan.isInteger(args[1])) {
 | 
			
		||||
                            page = Integer.parseInt(args[1]) - 1;
 | 
			
		||||
                            break;
 | 
			
		||||
                        }
 | 
			
		||||
                    default:
 | 
			
		||||
                        C.COMMAND_SYNTAX.send(player, getCommandString() + " list [#]");
 | 
			
		||||
                        return false;
 | 
			
		||||
                }
 | 
			
		||||
                ArrayList<PlotArea> areas = new ArrayList<>(PlotSquared.get().getPlotAreas());
 | 
			
		||||
                paginate(player, areas, 8, page,
 | 
			
		||||
                    new RunnableVal3<Integer, PlotArea, PlotMessage>() {
 | 
			
		||||
                        @Override public void run(Integer i, PlotArea area, PlotMessage message) {
 | 
			
		||||
                            String name;
 | 
			
		||||
                            double percent;
 | 
			
		||||
                            int claimed = area.getPlotCount();
 | 
			
		||||
                            int clusters = area.getClusters().size();
 | 
			
		||||
                            String region;
 | 
			
		||||
                            String generator = String.valueOf(area.getGenerator());
 | 
			
		||||
                            if (area.TYPE == 2) {
 | 
			
		||||
                                PlotId min = area.getMin();
 | 
			
		||||
                                PlotId max = area.getMax();
 | 
			
		||||
                                name = area.worldname + ';' + area.id + ';' + min + ';' + max;
 | 
			
		||||
                                int size = (max.x - min.x + 1) * (max.y - min.y + 1);
 | 
			
		||||
                                percent = claimed == 0 ? 0 : size / (double) claimed;
 | 
			
		||||
                                region = area.getRegion().toString();
 | 
			
		||||
                            } else {
 | 
			
		||||
                                name = area.worldname;
 | 
			
		||||
                                percent = claimed == 0 ?
 | 
			
		||||
                                    0 :
 | 
			
		||||
                                    Short.MAX_VALUE * Short.MAX_VALUE / (double) claimed;
 | 
			
		||||
                                region = "N/A";
 | 
			
		||||
                            }
 | 
			
		||||
                            PlotMessage tooltip = new PlotMessage().text("Claimed=").color("$1")
 | 
			
		||||
                                .text(String.valueOf(claimed)).color("$2").text("\nUsage=")
 | 
			
		||||
                                .color("$1").text(String.format("%.2f", percent) + '%').color("$2")
 | 
			
		||||
                                .text("\nClusters=").color("$1").text(String.valueOf(clusters))
 | 
			
		||||
                                .color("$2").text("\nRegion=").color("$1").text(region).color("$2")
 | 
			
		||||
                                .text("\nGenerator=").color("$1").text(generator).color("$2");
 | 
			
		||||
 | 
			
		||||
                            // type / terrain
 | 
			
		||||
                            String visit = "/plot area tp " + area.toString();
 | 
			
		||||
                            message.text("[").color("$3").text(String.valueOf(i)).command(visit)
 | 
			
		||||
                                .tooltip(visit).color("$1").text("]").color("$3").text(' ' + name)
 | 
			
		||||
                                .tooltip(tooltip).command(getCommandString() + " info " + area)
 | 
			
		||||
                                .color("$1").text(" - ").color("$2")
 | 
			
		||||
                                .text(area.TYPE + ":" + area.TERRAIN).color("$3");
 | 
			
		||||
                        }
 | 
			
		||||
                    }, "/plot area list", C.AREA_LIST_HEADER_PAGED.s());
 | 
			
		||||
                return true;
 | 
			
		||||
            case "regen":
 | 
			
		||||
            case "clear":
 | 
			
		||||
            case "reset":
 | 
			
		||||
            case "regenerate": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_AREA_REGEN)) {
 | 
			
		||||
                    C.NO_PERMISSION.send(player, C.PERMISSION_AREA_REGEN);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                final PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (area.TYPE != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player,
 | 
			
		||||
                        "$4Stop the server and delete: " + area.worldname + "/region");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                ChunkManager
 | 
			
		||||
                    .largeRegionTask(area.worldname, area.getRegion(), new RunnableVal<ChunkLoc>() {
 | 
			
		||||
                        @Override public void run(ChunkLoc value) {
 | 
			
		||||
                            AugmentedUtils.generate(area.worldname, value.x, value.z, null);
 | 
			
		||||
                        }
 | 
			
		||||
                    }, () -> player.sendMessage("Regen complete"));
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "goto":
 | 
			
		||||
            case "v":
 | 
			
		||||
            case "teleport":
 | 
			
		||||
            case "visit":
 | 
			
		||||
            case "tp":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_AREA_TP)) {
 | 
			
		||||
                    C.NO_PERMISSION.send(player, C.PERMISSION_AREA_TP);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 2) {
 | 
			
		||||
                    C.COMMAND_SYNTAX.send(player, "/plot visit [area]");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = PlotSquared.get().getPlotAreaByString(args[1]);
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_VALID_PLOT_WORLD.send(player, args[1]);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Location center;
 | 
			
		||||
                if (area.TYPE != 2) {
 | 
			
		||||
                    center = WorldUtil.IMP.getSpawn(area.worldname);
 | 
			
		||||
                } else {
 | 
			
		||||
                    RegionWrapper region = area.getRegion();
 | 
			
		||||
                    center =
 | 
			
		||||
                        new Location(area.worldname, region.minX + (region.maxX - region.minX) / 2,
 | 
			
		||||
                            0, region.minZ + (region.maxZ - region.minZ) / 2);
 | 
			
		||||
                    center.setY(1 + WorldUtil.IMP
 | 
			
		||||
                        .getHighestBlock(area.worldname, center.getX(), center.getZ()));
 | 
			
		||||
                }
 | 
			
		||||
                player.teleport(center);
 | 
			
		||||
                return true;
 | 
			
		||||
            case "delete":
 | 
			
		||||
            case "remove":
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    "$1World creation settings may be stored in multiple locations:"
 | 
			
		||||
                        + "\n$3 - $2Bukkit bukkit.yml" + "\n$3 - $2" + PlotSquared.imp()
 | 
			
		||||
                        .getPluginName() + " settings.yml"
 | 
			
		||||
                        + "\n$3 - $2Multiverse worlds.yml (or any world management plugin)"
 | 
			
		||||
                        + "\n$1Stop the server and delete it from these locations.");
 | 
			
		||||
                return true;
 | 
			
		||||
        }
 | 
			
		||||
        C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
@@ -1,256 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
import javax.annotation.Nullable;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "auto", permission = "plots.auto",
 | 
			
		||||
    category = CommandCategory.CLAIMING, requiredType = RequiredType.NONE,
 | 
			
		||||
    description = "Claim the nearest plot", aliases = "a", usage = "/plot auto [length,width]")
 | 
			
		||||
public class Auto extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Deprecated public static PlotId getNextPlotId(PlotId id, int step) {
 | 
			
		||||
        return id.getNextId(step);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private static boolean checkAllowedPlots(PlotPlayer player, PlotArea plotarea,
 | 
			
		||||
        @Nullable Integer allowed_plots, int size_x, int size_z) {
 | 
			
		||||
        if (allowed_plots == null)
 | 
			
		||||
            allowed_plots = player.getAllowedPlots();
 | 
			
		||||
        int currentPlots =
 | 
			
		||||
            Settings.Limit.GLOBAL ? player.getPlotCount() : player.getPlotCount(plotarea.worldname);
 | 
			
		||||
        int diff = currentPlots - allowed_plots;
 | 
			
		||||
        if (diff + size_x * size_z > 0) {
 | 
			
		||||
            if (diff < 0) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.CANT_CLAIM_MORE_PLOTS_NUM, -diff + "");
 | 
			
		||||
                return false;
 | 
			
		||||
            } else if (player.hasPersistentMeta("grantedPlots")) {
 | 
			
		||||
                int grantedPlots =
 | 
			
		||||
                    ByteArrayUtilities.bytesToInteger(player.getPersistentMeta("grantedPlots"));
 | 
			
		||||
                if (grantedPlots - diff < size_x * size_z) {
 | 
			
		||||
                    player.removePersistentMeta("grantedPlots");
 | 
			
		||||
                    MainUtil.sendMessage(player, C.CANT_CLAIM_MORE_PLOTS);
 | 
			
		||||
                    return false;
 | 
			
		||||
                } else {
 | 
			
		||||
                    int left = grantedPlots - diff - size_x * size_z;
 | 
			
		||||
                    if (left == 0) {
 | 
			
		||||
                        player.removePersistentMeta("grantedPlots");
 | 
			
		||||
                    } else {
 | 
			
		||||
                        player.setPersistentMeta("grantedPlots",
 | 
			
		||||
                            ByteArrayUtilities.integerToBytes(left));
 | 
			
		||||
                    }
 | 
			
		||||
                    MainUtil.sendMessage(player, C.REMOVED_GRANTED_PLOT, "" + left,
 | 
			
		||||
                        "" + (grantedPlots - left));
 | 
			
		||||
                }
 | 
			
		||||
            } else {
 | 
			
		||||
                MainUtil.sendMessage(player, C.CANT_CLAIM_MORE_PLOTS);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Teleport the player home, or claim a new plot
 | 
			
		||||
     *
 | 
			
		||||
     * @param player
 | 
			
		||||
     * @param area
 | 
			
		||||
     * @param start
 | 
			
		||||
     * @param schem
 | 
			
		||||
     */
 | 
			
		||||
    public static void homeOrAuto(final PlotPlayer player, final PlotArea area, PlotId start,
 | 
			
		||||
        final String schem) {
 | 
			
		||||
        Set<Plot> plots = player.getPlots();
 | 
			
		||||
        if (!plots.isEmpty()) {
 | 
			
		||||
            plots.iterator().next().teleportPlayer(player);
 | 
			
		||||
        } else {
 | 
			
		||||
            autoClaimSafe(player, area, start, schem);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Claim a new plot for a player
 | 
			
		||||
     *
 | 
			
		||||
     * @param player
 | 
			
		||||
     * @param area
 | 
			
		||||
     * @param start
 | 
			
		||||
     * @param schem
 | 
			
		||||
     */
 | 
			
		||||
    public static void autoClaimSafe(final PlotPlayer player, final PlotArea area, PlotId start,
 | 
			
		||||
        final String schem) {
 | 
			
		||||
        autoClaimSafe(player, area, start, schem, null);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Claim a new plot for a player
 | 
			
		||||
     *
 | 
			
		||||
     * @param player
 | 
			
		||||
     * @param area
 | 
			
		||||
     * @param start
 | 
			
		||||
     * @param schem
 | 
			
		||||
     */
 | 
			
		||||
    public static void autoClaimSafe(final PlotPlayer player, final PlotArea area, PlotId start,
 | 
			
		||||
        final String schem, @Nullable final Integer allowed_plots) {
 | 
			
		||||
        player.setMeta(Auto.class.getName(), true);
 | 
			
		||||
        autoClaimFromDatabase(player, area, start, new RunnableVal<Plot>() {
 | 
			
		||||
            @Override public void run(final Plot plot) {
 | 
			
		||||
                TaskManager.IMP.sync(new RunnableVal<Object>() {
 | 
			
		||||
                    @Override public void run(Object ignore) {
 | 
			
		||||
                        player.deleteMeta(Auto.class.getName());
 | 
			
		||||
                        if (plot == null) {
 | 
			
		||||
                            MainUtil.sendMessage(player, C.NO_FREE_PLOTS);
 | 
			
		||||
                        } else if (checkAllowedPlots(player, area, allowed_plots, 1, 1)) {
 | 
			
		||||
                            plot.claim(player, true, schem, false);
 | 
			
		||||
                            if (area.AUTO_MERGE) {
 | 
			
		||||
                                plot.autoMerge(-1, Integer.MAX_VALUE, player.getUUID(), true);
 | 
			
		||||
                            }
 | 
			
		||||
                        } else {
 | 
			
		||||
                            DBFunc.delete(plot);
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                });
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static void autoClaimFromDatabase(final PlotPlayer player, final PlotArea area,
 | 
			
		||||
        PlotId start, final RunnableVal<Plot> whenDone) {
 | 
			
		||||
        final Plot plot = area.getNextFreePlot(player, start);
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            whenDone.run(null);
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        whenDone.value = plot;
 | 
			
		||||
        plot.owner = player.getUUID();
 | 
			
		||||
        DBFunc.createPlotSafe(plot, whenDone, new Runnable() {
 | 
			
		||||
            @Override public void run() {
 | 
			
		||||
                autoClaimFromDatabase(player, area, plot.getId(), whenDone);
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        PlotArea plotarea = player.getApplicablePlotArea();
 | 
			
		||||
        if (plotarea == null) {
 | 
			
		||||
            if (EconHandler.manager != null) {
 | 
			
		||||
                for (PlotArea area : PlotSquared.get().getPlotAreaManager().getAllPlotAreas()) {
 | 
			
		||||
                    if (EconHandler.manager
 | 
			
		||||
                        .hasPermission(area.worldname, player.getName(), "plots.auto")) {
 | 
			
		||||
                        if (plotarea != null) {
 | 
			
		||||
                            plotarea = null;
 | 
			
		||||
                            break;
 | 
			
		||||
                        }
 | 
			
		||||
                        plotarea = area;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            if (plotarea == null) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.NOT_IN_PLOT_WORLD);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        int size_x = 1;
 | 
			
		||||
        int size_z = 1;
 | 
			
		||||
        String schematic = null;
 | 
			
		||||
        if (args.length > 0) {
 | 
			
		||||
            if (Permissions.hasPermission(player, C.PERMISSION_AUTO_MEGA)) {
 | 
			
		||||
                try {
 | 
			
		||||
                    String[] split = args[0].split(",|;");
 | 
			
		||||
                    size_x = Integer.parseInt(split[0]);
 | 
			
		||||
                    size_z = Integer.parseInt(split[1]);
 | 
			
		||||
                    if (size_x < 1 || size_z < 1) {
 | 
			
		||||
                        MainUtil.sendMessage(player, "&cError: size<=0");
 | 
			
		||||
                    }
 | 
			
		||||
                    if (args.length > 1) {
 | 
			
		||||
                        schematic = args[1];
 | 
			
		||||
                    }
 | 
			
		||||
                } catch (NumberFormatException ignored) {
 | 
			
		||||
                    size_x = 1;
 | 
			
		||||
                    size_z = 1;
 | 
			
		||||
                    schematic = args[0];
 | 
			
		||||
                    // PlayerFunctions.sendMessage(plr,
 | 
			
		||||
                    // "&cError: Invalid size (X,Y)");
 | 
			
		||||
                    // return false;
 | 
			
		||||
                }
 | 
			
		||||
            } else {
 | 
			
		||||
                schematic = args[0];
 | 
			
		||||
                // PlayerFunctions.sendMessage(plr, C.NO_PERMISSION);
 | 
			
		||||
                // return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (size_x * size_z > Settings.Claim.MAX_AUTO_AREA) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.CANT_CLAIM_MORE_PLOTS_NUM,
 | 
			
		||||
                Settings.Claim.MAX_AUTO_AREA + "");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        final int allowed_plots = player.getAllowedPlots();
 | 
			
		||||
        if (player.getMeta(Auto.class.getName(), false) || !checkAllowedPlots(player, plotarea,
 | 
			
		||||
            allowed_plots, size_x, size_z))
 | 
			
		||||
            return false;
 | 
			
		||||
 | 
			
		||||
        if (schematic != null && !schematic.isEmpty()) {
 | 
			
		||||
            if (!plotarea.SCHEMATICS.contains(schematic.toLowerCase())) {
 | 
			
		||||
                sendMessage(player, C.SCHEMATIC_INVALID, "non-existent: " + schematic);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            if (!Permissions.hasPermission(player, C.PERMISSION_CLAIM_SCHEMATIC.f(schematic))
 | 
			
		||||
                && !Permissions.hasPermission(player, C.PERMISSION_ADMIN_COMMAND_SCHEMATIC)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                    C.PERMISSION_CLAIM_SCHEMATIC.f(schematic));
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (EconHandler.manager != null && plotarea.USE_ECONOMY) {
 | 
			
		||||
            Expression<Double> costExp = plotarea.PRICES.get("claim");
 | 
			
		||||
            double cost = costExp.evaluate((double) (Settings.Limit.GLOBAL ?
 | 
			
		||||
                player.getPlotCount() :
 | 
			
		||||
                player.getPlotCount(plotarea.worldname)));
 | 
			
		||||
            cost = (size_x * size_z) * cost;
 | 
			
		||||
            if (cost > 0d) {
 | 
			
		||||
                if (EconHandler.manager.getMoney(player) < cost) {
 | 
			
		||||
                    sendMessage(player, C.CANNOT_AFFORD_PLOT, "" + cost);
 | 
			
		||||
                    return true;
 | 
			
		||||
                }
 | 
			
		||||
                EconHandler.manager.withdrawMoney(player, cost);
 | 
			
		||||
                sendMessage(player, C.REMOVED_BALANCE, cost + "");
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        // TODO handle type 2 the same as normal worlds!
 | 
			
		||||
        if (size_x == 1 && size_z == 1) {
 | 
			
		||||
            autoClaimSafe(player, plotarea, null, schematic, allowed_plots);
 | 
			
		||||
            return true;
 | 
			
		||||
        } else {
 | 
			
		||||
            if (plotarea.TYPE == 2) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.NO_FREE_PLOTS);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            while (true) {
 | 
			
		||||
                PlotId start = plotarea.getMeta("lastPlot", new PlotId(0, 0)).getNextId(1);
 | 
			
		||||
                PlotId end = new PlotId(start.x + size_x - 1, start.y + size_z - 1);
 | 
			
		||||
                if (plotarea.canClaim(player, start, end)) {
 | 
			
		||||
                    plotarea.setMeta("lastPlot", start);
 | 
			
		||||
                    for (int i = start.x; i <= end.x; i++) {
 | 
			
		||||
                        for (int j = start.y; j <= end.y; j++) {
 | 
			
		||||
                            Plot plot = plotarea.getPlotAbs(new PlotId(i, j));
 | 
			
		||||
                            boolean teleport = i == end.x && j == end.y;
 | 
			
		||||
                            plot.claim(player, teleport, null);
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    if (!plotarea.mergePlots(MainUtil.getPlotSelectionIds(start, end), true)) {
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                plotarea.setMeta("lastPlot", start);
 | 
			
		||||
            }
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,38 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "setbiome", permission = "plots.set.biome",
 | 
			
		||||
    description = "Set the plot biome", usage = "/plot biome [biome]",
 | 
			
		||||
    aliases = {"biome", "sb", "setb", "b"}, category = CommandCategory.APPEARANCE,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Biome extends SetCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean set(final PlotPlayer player, final Plot plot, final String value) {
 | 
			
		||||
        int biome = WorldUtil.IMP.getBiomeFromString(value);
 | 
			
		||||
        if (biome == -1) {
 | 
			
		||||
            String biomes =
 | 
			
		||||
                StringMan.join(WorldUtil.IMP.getBiomeList(), C.BLOCK_LIST_SEPARATER.s());
 | 
			
		||||
            C.NEED_BIOME.send(player);
 | 
			
		||||
            MainUtil.sendMessage(player, C.SUBCOMMAND_SET_OPTIONS_HEADER.s() + biomes);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.getRunning() > 0) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        plot.addRunning();
 | 
			
		||||
        plot.setBiome(value.toUpperCase(), new Runnable() {
 | 
			
		||||
            @Override public void run() {
 | 
			
		||||
                plot.removeRunning();
 | 
			
		||||
                MainUtil.sendMessage(player, C.BIOME_SET_TO.s() + value.toLowerCase());
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,72 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EconHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
 | 
			
		||||
import java.util.Optional;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "buy", description = "Buy the plot you are standing on",
 | 
			
		||||
    usage = "/plot buy", permission = "plots.buy", category = CommandCategory.CLAIMING,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Buy extends Command {
 | 
			
		||||
 | 
			
		||||
    public Buy() {
 | 
			
		||||
        super(MainCommand.getInstance(), true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(final PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        final RunnableVal2<Command, CommandResult> whenDone) {
 | 
			
		||||
        check(EconHandler.manager, C.ECON_DISABLED);
 | 
			
		||||
        final Plot plot;
 | 
			
		||||
        if (args.length != 0) {
 | 
			
		||||
            checkTrue(args.length == 1, C.COMMAND_SYNTAX, getUsage());
 | 
			
		||||
            plot = check(MainUtil.getPlotFromString(player, args[0], true), null);
 | 
			
		||||
        } else {
 | 
			
		||||
            plot = check(player.getCurrentPlot(), C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        checkTrue(plot.hasOwner(), C.PLOT_UNOWNED);
 | 
			
		||||
        checkTrue(!plot.isOwner(player.getUUID()), C.CANNOT_BUY_OWN);
 | 
			
		||||
        Set<Plot> plots = plot.getConnectedPlots();
 | 
			
		||||
        checkTrue(player.getPlotCount() + plots.size() <= player.getAllowedPlots(),
 | 
			
		||||
            C.CANT_CLAIM_MORE_PLOTS);
 | 
			
		||||
        Optional<Double> flag = plot.getFlag(Flags.PRICE);
 | 
			
		||||
        if (!flag.isPresent()) {
 | 
			
		||||
            throw new CommandException(C.NOT_FOR_SALE);
 | 
			
		||||
        }
 | 
			
		||||
        final double price = flag.get();
 | 
			
		||||
        checkTrue(player.getMoney() >= price, C.CANNOT_AFFORD_PLOT);
 | 
			
		||||
        player.withdraw(price);
 | 
			
		||||
        confirm.run(this, new Runnable() {
 | 
			
		||||
            @Override // Success
 | 
			
		||||
            public void run() {
 | 
			
		||||
                C.REMOVED_BALANCE.send(player, price);
 | 
			
		||||
                EconHandler.manager
 | 
			
		||||
                    .depositMoney(UUIDHandler.getUUIDWrapper().getOfflinePlayer(plot.owner), price);
 | 
			
		||||
                PlotPlayer owner = UUIDHandler.getPlayer(plot.owner);
 | 
			
		||||
                if (owner != null) {
 | 
			
		||||
                    C.PLOT_SOLD.send(owner, plot.getId(), player.getName(), price);
 | 
			
		||||
                }
 | 
			
		||||
                plot.removeFlag(Flags.PRICE);
 | 
			
		||||
                plot.setOwner(player.getUUID());
 | 
			
		||||
                C.CLAIMED.send(player);
 | 
			
		||||
                whenDone.run(Buy.this, CommandResult.SUCCESS);
 | 
			
		||||
            }
 | 
			
		||||
        }, new Runnable() {
 | 
			
		||||
            @Override // Failure
 | 
			
		||||
            public void run() {
 | 
			
		||||
                player.deposit(price);
 | 
			
		||||
                whenDone.run(Buy.this, CommandResult.FAILURE);
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,14 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "chat", description = "Toggle plot chat on or off",
 | 
			
		||||
    usage = "/plot chat [on|off]", permission = "plots.chat", category = CommandCategory.CHAT,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Chat extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        MainCommand.getInstance().toggle.chat(this, player, new String[0], null, null);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,99 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ByteArrayUtilities;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EconHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "claim", aliases = "c",
 | 
			
		||||
    description = "Claim the current plot you're standing on", category = CommandCategory.CLAIMING,
 | 
			
		||||
    requiredType = RequiredType.NONE, permission = "plots.claim", usage = "/plot claim")
 | 
			
		||||
public class Claim extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        String schematic = "";
 | 
			
		||||
        if (args.length >= 1) {
 | 
			
		||||
            schematic = args[0];
 | 
			
		||||
        }
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        final Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        int currentPlots =
 | 
			
		||||
            Settings.Limit.GLOBAL ? player.getPlotCount() : player.getPlotCount(loc.getWorld());
 | 
			
		||||
        int grants = 0;
 | 
			
		||||
        if (currentPlots >= player.getAllowedPlots()) {
 | 
			
		||||
            if (player.hasPersistentMeta("grantedPlots")) {
 | 
			
		||||
                grants =
 | 
			
		||||
                    ByteArrayUtilities.bytesToInteger(player.getPersistentMeta("grantedPlots"));
 | 
			
		||||
                if (grants <= 0) {
 | 
			
		||||
                    player.removePersistentMeta("grantedPlots");
 | 
			
		||||
                    return sendMessage(player, C.CANT_CLAIM_MORE_PLOTS);
 | 
			
		||||
                }
 | 
			
		||||
            } else {
 | 
			
		||||
                return sendMessage(player, C.CANT_CLAIM_MORE_PLOTS);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.canClaim(player)) {
 | 
			
		||||
            return sendMessage(player, C.PLOT_IS_CLAIMED);
 | 
			
		||||
        }
 | 
			
		||||
        final PlotArea area = plot.getArea();
 | 
			
		||||
        if (!schematic.isEmpty()) {
 | 
			
		||||
            if (area.SCHEMATIC_CLAIM_SPECIFY) {
 | 
			
		||||
                if (!area.SCHEMATICS.contains(schematic.toLowerCase())) {
 | 
			
		||||
                    return sendMessage(player, C.SCHEMATIC_INVALID, "non-existent: " + schematic);
 | 
			
		||||
                }
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLAIM_SCHEMATIC.f(schematic))
 | 
			
		||||
                    && !Permissions.hasPermission(player, C.PERMISSION_ADMIN_COMMAND_SCHEMATIC)) {
 | 
			
		||||
                    return sendMessage(player, C.NO_SCHEMATIC_PERMISSION, schematic);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        int border = area.getBorder();
 | 
			
		||||
        if (border != Integer.MAX_VALUE && plot.getDistanceFromOrigin() > border) {
 | 
			
		||||
            return !sendMessage(player, C.BORDER);
 | 
			
		||||
        }
 | 
			
		||||
        if ((EconHandler.manager != null) && area.USE_ECONOMY) {
 | 
			
		||||
            Expression<Double> costExr = area.PRICES.get("claim");
 | 
			
		||||
            double cost = costExr.evaluate((double) currentPlots);
 | 
			
		||||
            if (cost > 0d) {
 | 
			
		||||
                if (EconHandler.manager.getMoney(player) < cost) {
 | 
			
		||||
                    return sendMessage(player, C.CANNOT_AFFORD_PLOT, "" + cost);
 | 
			
		||||
                }
 | 
			
		||||
                EconHandler.manager.withdrawMoney(player, cost);
 | 
			
		||||
                sendMessage(player, C.REMOVED_BALANCE, cost + "");
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (grants > 0) {
 | 
			
		||||
            if (grants == 1) {
 | 
			
		||||
                player.removePersistentMeta("grantedPlots");
 | 
			
		||||
            } else {
 | 
			
		||||
                player.setPersistentMeta("grantedPlots",
 | 
			
		||||
                    ByteArrayUtilities.integerToBytes(grants - 1));
 | 
			
		||||
            }
 | 
			
		||||
            sendMessage(player, C.REMOVED_GRANTED_PLOT, "1", "" + (grants - 1));
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.canClaim(player)) {
 | 
			
		||||
            plot.owner = player.getUUID();
 | 
			
		||||
            final String finalSchematic = schematic;
 | 
			
		||||
            DBFunc.createPlotSafe(plot, () -> TaskManager.IMP.sync(new RunnableVal<Object>() {
 | 
			
		||||
                @Override public void run(Object value) {
 | 
			
		||||
                    plot.claim(player, true, finalSchematic, false);
 | 
			
		||||
                    if (area.AUTO_MERGE) {
 | 
			
		||||
                        plot.autoMerge(-1, Integer.MAX_VALUE, player.getUUID(), true);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }), () -> sendMessage(player, C.PLOT_NOT_CLAIMED));
 | 
			
		||||
            return true;
 | 
			
		||||
        } else {
 | 
			
		||||
            sendMessage(player, C.PLOT_NOT_CLAIMED);
 | 
			
		||||
        }
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,68 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.FlagManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.block.GlobalBlockQueue;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "clear", description = "Clear the plot you stand on",
 | 
			
		||||
    permission = "plots.clear", category = CommandCategory.APPEARANCE, usage = "/plot clear",
 | 
			
		||||
    aliases = "reset", confirmation = true) public class Clear extends Command {
 | 
			
		||||
 | 
			
		||||
    // Note: To clear a specific plot use /plot <plot> clear
 | 
			
		||||
    // The syntax also works with any command: /plot <plot> <command>
 | 
			
		||||
 | 
			
		||||
    public Clear() {
 | 
			
		||||
        super(MainCommand.getInstance(), true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(final PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) throws CommandException {
 | 
			
		||||
        checkTrue(args.length == 0, C.COMMAND_SYNTAX, getUsage());
 | 
			
		||||
        final Plot plot = check(player.getCurrentPlot(), C.NOT_IN_PLOT);
 | 
			
		||||
        checkTrue(plot.isOwner(player.getUUID()) || Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_CLEAR), C.NO_PLOT_PERMS);
 | 
			
		||||
        checkTrue(plot.getRunning() == 0, C.WAIT_FOR_TIMER);
 | 
			
		||||
        checkTrue(!Settings.Done.RESTRICT_BUILDING || !Flags.DONE.isSet(plot) || Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_CONTINUE), C.DONE_ALREADY_DONE);
 | 
			
		||||
        confirm.run(this, new Runnable() {
 | 
			
		||||
            @Override public void run() {
 | 
			
		||||
                final long start = System.currentTimeMillis();
 | 
			
		||||
                boolean result = plot.clear(true, false, new Runnable() {
 | 
			
		||||
                    @Override public void run() {
 | 
			
		||||
                        plot.unlink();
 | 
			
		||||
                        GlobalBlockQueue.IMP.addTask(new Runnable() {
 | 
			
		||||
                            @Override public void run() {
 | 
			
		||||
                                plot.removeRunning();
 | 
			
		||||
                                // If the state changes, then mark it as no longer done
 | 
			
		||||
                                if (plot.getFlag(Flags.DONE).isPresent()) {
 | 
			
		||||
                                    FlagManager.removePlotFlag(plot, Flags.DONE);
 | 
			
		||||
                                }
 | 
			
		||||
                                if (plot.getFlag(Flags.ANALYSIS).isPresent()) {
 | 
			
		||||
                                    FlagManager.removePlotFlag(plot, Flags.ANALYSIS);
 | 
			
		||||
                                }
 | 
			
		||||
                                MainUtil.sendMessage(player, C.CLEARING_DONE,
 | 
			
		||||
                                    "" + (System.currentTimeMillis() - start));
 | 
			
		||||
                            }
 | 
			
		||||
                        });
 | 
			
		||||
                    }
 | 
			
		||||
                });
 | 
			
		||||
                if (!result) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
                } else {
 | 
			
		||||
                    plot.addRunning();
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }, null);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,612 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.HashSet;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "cluster", aliases = "clusters",
 | 
			
		||||
    category = CommandCategory.ADMINISTRATION, requiredType = RequiredType.NONE,
 | 
			
		||||
    permission = "plots.cluster", description = "Manage a plot cluster") public class Cluster
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
 | 
			
		||||
        // list, create, delete, resize, invite, kick, leave, helpers, tp, sethome
 | 
			
		||||
        if (args.length == 0) {
 | 
			
		||||
            // return arguments
 | 
			
		||||
            MainUtil.sendMessage(player, C.CLUSTER_AVAILABLE_ARGS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        String sub = args[0].toLowerCase();
 | 
			
		||||
        switch (sub) {
 | 
			
		||||
            case "l":
 | 
			
		||||
            case "list": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_LIST)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_LIST);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 1) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster list");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Set<PlotCluster> clusters = area.getClusters();
 | 
			
		||||
                MainUtil.sendMessage(player, C.CLUSTER_LIST_HEADING, clusters.size() + "");
 | 
			
		||||
                for (PlotCluster cluster : clusters) {
 | 
			
		||||
                    // Ignore unmanaged clusters
 | 
			
		||||
                    String name = "'" + cluster.getName() + "' : " + cluster.toString();
 | 
			
		||||
                    if (player.getUUID().equals(cluster.owner)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.CLUSTER_LIST_ELEMENT, "&a" + name);
 | 
			
		||||
                    } else if (cluster.helpers.contains(player.getUUID())) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.CLUSTER_LIST_ELEMENT, "&3" + name);
 | 
			
		||||
                    } else if (cluster.invited.contains(player.getUUID())) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.CLUSTER_LIST_ELEMENT, "&9" + name);
 | 
			
		||||
                    } else {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.CLUSTER_LIST_ELEMENT, cluster.toString());
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "c":
 | 
			
		||||
            case "create": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_CREATE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_CREATE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 4) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                        "/plot cluster create <name> <id-bot> <id-top>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                int currentClusters = Settings.Limit.GLOBAL ?
 | 
			
		||||
                    player.getClusterCount() :
 | 
			
		||||
                    player.getPlotCount(player.getLocation().getWorld());
 | 
			
		||||
                if (currentClusters >= player.getAllowedPlots()) {
 | 
			
		||||
                    return sendMessage(player, C.CANT_CLAIM_MORE_CLUSTERS);
 | 
			
		||||
                }
 | 
			
		||||
                // check pos1 / pos2
 | 
			
		||||
                PlotId pos1 = PlotId.fromString(args[2]);
 | 
			
		||||
                PlotId pos2 = PlotId.fromString(args[3]);
 | 
			
		||||
                if (pos1 == null || pos2 == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_VALID_PLOT_ID);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // check if name is taken
 | 
			
		||||
                String name = args[1];
 | 
			
		||||
                if (area.getCluster(name) != null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.ALIAS_IS_TAKEN);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (pos2.x < pos1.x || pos2.y < pos1.y) {
 | 
			
		||||
                    PlotId tmp = new PlotId(Math.min(pos1.x, pos2.x), Math.min(pos1.y, pos2.y));
 | 
			
		||||
                    pos2 = new PlotId(Math.max(pos1.x, pos2.x), Math.max(pos1.y, pos2.y));
 | 
			
		||||
                    pos1 = tmp;
 | 
			
		||||
                }
 | 
			
		||||
                //check if overlap
 | 
			
		||||
                PlotCluster cluster = area.getFirstIntersectingCluster(pos1, pos2);
 | 
			
		||||
                if (cluster != null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.CLUSTER_INTERSECTION, cluster.getName());
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // Check if it occupies existing plots
 | 
			
		||||
                if (!area.contains(pos1) || !area.contains(pos2)) {
 | 
			
		||||
                    C.CLUSTER_OUTSIDE.send(player, area);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Set<Plot> plots = area.getPlotSelectionOwned(pos1, pos2);
 | 
			
		||||
                if (!plots.isEmpty()) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_CREATE_OTHER)) {
 | 
			
		||||
                        UUID uuid = player.getUUID();
 | 
			
		||||
                        for (Plot plot : plots) {
 | 
			
		||||
                            if (!plot.isOwner(uuid)) {
 | 
			
		||||
                                MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                                    C.PERMISSION_CLUSTER_CREATE_OTHER);
 | 
			
		||||
                                return false;
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                // Check allowed cluster size
 | 
			
		||||
                cluster = new PlotCluster(area, pos1, pos2, player.getUUID());
 | 
			
		||||
                int current;
 | 
			
		||||
                if (Settings.Limit.GLOBAL) {
 | 
			
		||||
                    current = player.getPlayerClusterCount();
 | 
			
		||||
                } else {
 | 
			
		||||
                    current = player.getPlayerClusterCount(player.getLocation().getWorld());
 | 
			
		||||
                }
 | 
			
		||||
                int allowed = Permissions.hasPermissionRange(player, C.PERMISSION_CLUSTER_SIZE,
 | 
			
		||||
                    Settings.Limit.MAX_PLOTS);
 | 
			
		||||
                if (current + cluster.getArea() > allowed) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                        C.PERMISSION_CLUSTER_SIZE + "." + (current + cluster.getArea()));
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // create cluster
 | 
			
		||||
                cluster.settings.setAlias(name);
 | 
			
		||||
                area.addCluster(cluster);
 | 
			
		||||
                DBFunc.createCluster(cluster);
 | 
			
		||||
                // Add any existing plots to the current cluster
 | 
			
		||||
                for (Plot plot : plots) {
 | 
			
		||||
                    if (plot.hasOwner()) {
 | 
			
		||||
                        if (!cluster.isAdded(plot.owner)) {
 | 
			
		||||
                            cluster.invited.add(plot.owner);
 | 
			
		||||
                            DBFunc.setInvited(cluster, plot.owner);
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.CLUSTER_ADDED);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "disband":
 | 
			
		||||
            case "del":
 | 
			
		||||
            case "delete": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_DELETE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_DELETE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 1 && args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster delete [name]");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster;
 | 
			
		||||
                if (args.length == 2) {
 | 
			
		||||
                    cluster = area.getCluster(args[1]);
 | 
			
		||||
                    if (cluster == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.INVALID_CLUSTER, args[1]);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                } else {
 | 
			
		||||
                    cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                    if (cluster == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                if (!cluster.owner.equals(player.getUUID())) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_DELETE_OTHER)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_CLUSTER_DELETE_OTHER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                DBFunc.delete(cluster);
 | 
			
		||||
                MainUtil.sendMessage(player, C.CLUSTER_DELETED);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "res":
 | 
			
		||||
            case "resize": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_RESIZE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_RESIZE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 3) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                        "/plot cluster resize <pos1> <pos2>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // check pos1 / pos2
 | 
			
		||||
                PlotId pos1 = PlotId.fromString(args[1]);
 | 
			
		||||
                PlotId pos2 = PlotId.fromString(args[2]);
 | 
			
		||||
                if (pos1 == null || pos2 == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_VALID_PLOT_ID);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (pos2.x < pos1.x || pos2.y < pos1.y) {
 | 
			
		||||
                    pos1 = new PlotId(Math.min(pos1.x, pos2.x), Math.min(pos1.y, pos2.y));
 | 
			
		||||
                    pos2 = new PlotId(Math.max(pos1.x, pos2.x), Math.max(pos1.y, pos2.y));
 | 
			
		||||
                }
 | 
			
		||||
                // check if in cluster
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                if (cluster == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!cluster.hasHelperRights(player.getUUID())) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_RESIZE_OTHER)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_CLUSTER_RESIZE_OTHER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                //check if overlap
 | 
			
		||||
                PlotCluster intersect = area.getFirstIntersectingCluster(pos1, pos2);
 | 
			
		||||
                if (intersect != null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.CLUSTER_INTERSECTION, intersect.getName());
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Set<Plot> existing = area.getPlotSelectionOwned(cluster.getP1(), cluster.getP2());
 | 
			
		||||
                Set<Plot> newPlots = area.getPlotSelectionOwned(pos1, pos2);
 | 
			
		||||
                // Set<Plot> removed = (HashSet<Plot>) existing.clone();
 | 
			
		||||
                Set<Plot> removed = new HashSet<>(existing);
 | 
			
		||||
 | 
			
		||||
                removed.removeAll(newPlots);
 | 
			
		||||
                // Check expand / shrink
 | 
			
		||||
                if (!removed.isEmpty()) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_RESIZE_SHRINK)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_CLUSTER_RESIZE_SHRINK);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                newPlots.removeAll(existing);
 | 
			
		||||
                if (!newPlots.isEmpty()) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_RESIZE_EXPAND)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_CLUSTER_RESIZE_EXPAND);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                // Check allowed cluster size
 | 
			
		||||
                int current;
 | 
			
		||||
                if (Settings.Limit.GLOBAL) {
 | 
			
		||||
                    current = player.getPlayerClusterCount();
 | 
			
		||||
                } else {
 | 
			
		||||
                    current = player.getPlayerClusterCount(player.getLocation().getWorld());
 | 
			
		||||
                }
 | 
			
		||||
                current -= cluster.getArea() + (1 + pos2.x - pos1.x) * (1 + pos2.y - pos1.y);
 | 
			
		||||
                int allowed = Permissions
 | 
			
		||||
                    .hasPermissionRange(player, C.PERMISSION_CLUSTER, Settings.Limit.MAX_PLOTS);
 | 
			
		||||
                if (current + cluster.getArea() > allowed) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                        C.PERMISSION_CLUSTER.s() + "." + (current + cluster.getArea()));
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // resize cluster
 | 
			
		||||
                DBFunc.resizeCluster(cluster, pos1, pos2);
 | 
			
		||||
                MainUtil.sendMessage(player, C.CLUSTER_RESIZED);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "add":
 | 
			
		||||
            case "inv":
 | 
			
		||||
            case "invite": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_INVITE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_INVITE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster invite <player>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // check if in cluster
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                if (cluster == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!cluster.hasHelperRights(player.getUUID())) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_INVITE_OTHER)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_CLUSTER_INVITE_OTHER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                // check uuid
 | 
			
		||||
                UUID uuid = UUIDHandler.getUUID(args[1], null);
 | 
			
		||||
                if (uuid == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.INVALID_PLAYER, args[2]);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!cluster.isAdded(uuid)) {
 | 
			
		||||
                    // add the user if not added
 | 
			
		||||
                    cluster.invited.add(uuid);
 | 
			
		||||
                    DBFunc.setInvited(cluster, uuid);
 | 
			
		||||
                    PlotPlayer player2 = UUIDHandler.getPlayer(uuid);
 | 
			
		||||
                    if (player2 != null) {
 | 
			
		||||
                        MainUtil.sendMessage(player2, C.CLUSTER_INVITED, cluster.getName());
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.CLUSTER_ADDED_USER);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "k":
 | 
			
		||||
            case "remove":
 | 
			
		||||
            case "kick": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_KICK)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_KICK);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster kick <player>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                if (cluster == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!cluster.hasHelperRights(player.getUUID())) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_KICK_OTHER)) {
 | 
			
		||||
                        MainUtil
 | 
			
		||||
                            .sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_KICK_OTHER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                // check uuid
 | 
			
		||||
                UUID uuid = UUIDHandler.getUUID(args[1], null);
 | 
			
		||||
                if (uuid == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.INVALID_PLAYER, args[1]);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // Can't kick if the player is yourself, the owner, or not added to the cluster
 | 
			
		||||
                if (uuid.equals(player.getUUID()) || uuid.equals(cluster.owner) || !cluster
 | 
			
		||||
                    .isAdded(uuid)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.CANNOT_KICK_PLAYER, cluster.getName());
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (cluster.helpers.contains(uuid)) {
 | 
			
		||||
                    cluster.helpers.remove(uuid);
 | 
			
		||||
                    DBFunc.removeHelper(cluster, uuid);
 | 
			
		||||
                }
 | 
			
		||||
                cluster.invited.remove(uuid);
 | 
			
		||||
                DBFunc.removeInvited(cluster, uuid);
 | 
			
		||||
                PlotPlayer player2 = UUIDHandler.getPlayer(uuid);
 | 
			
		||||
                if (player2 != null) {
 | 
			
		||||
                    MainUtil.sendMessage(player2, C.CLUSTER_REMOVED, cluster.getName());
 | 
			
		||||
                }
 | 
			
		||||
                for (Plot plot : new ArrayList<>(
 | 
			
		||||
                    PlotSquared.get().getPlots(player2.getLocation().getWorld(), uuid))) {
 | 
			
		||||
                    PlotCluster current = plot.getCluster();
 | 
			
		||||
                    if (current != null && current.equals(cluster)) {
 | 
			
		||||
                        plot.unclaim();
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player2, C.CLUSTER_KICKED_USER);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "quit":
 | 
			
		||||
            case "leave": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_LEAVE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_LEAVE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 1 && args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster leave [name]");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster;
 | 
			
		||||
                if (args.length == 2) {
 | 
			
		||||
                    cluster = area.getCluster(args[1]);
 | 
			
		||||
                    if (cluster == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.INVALID_CLUSTER, args[1]);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                } else {
 | 
			
		||||
                    cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                    if (cluster == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                UUID uuid = player.getUUID();
 | 
			
		||||
                if (!cluster.isAdded(uuid)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.CLUSTER_NOT_ADDED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (uuid.equals(cluster.owner)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.CLUSTER_CANNOT_LEAVE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (cluster.helpers.contains(uuid)) {
 | 
			
		||||
                    cluster.helpers.remove(uuid);
 | 
			
		||||
                    DBFunc.removeHelper(cluster, uuid);
 | 
			
		||||
                }
 | 
			
		||||
                cluster.invited.remove(uuid);
 | 
			
		||||
                DBFunc.removeInvited(cluster, uuid);
 | 
			
		||||
                MainUtil.sendMessage(player, C.CLUSTER_REMOVED, cluster.getName());
 | 
			
		||||
                for (Plot plot : new ArrayList<>(
 | 
			
		||||
                    PlotSquared.get().getPlots(player.getLocation().getWorld(), uuid))) {
 | 
			
		||||
                    PlotCluster current = plot.getCluster();
 | 
			
		||||
                    if (current != null && current.equals(cluster)) {
 | 
			
		||||
                        plot.unclaim();
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "members":
 | 
			
		||||
            case "admin":
 | 
			
		||||
            case "helper":
 | 
			
		||||
            case "helpers": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_HELPERS)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_HELPERS);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 3) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                        "/plot cluster helpers <add|remove> <player>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                if (cluster == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                UUID uuid = UUIDHandler.getUUID(args[2], null);
 | 
			
		||||
                if (uuid == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.INVALID_PLAYER, args[2]);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args[1].equalsIgnoreCase("add")) {
 | 
			
		||||
                    cluster.helpers.add(uuid);
 | 
			
		||||
                    DBFunc.setHelper(cluster, uuid);
 | 
			
		||||
                    return MainUtil.sendMessage(player, C.CLUSTER_ADDED_HELPER);
 | 
			
		||||
                }
 | 
			
		||||
                if (args[1].equalsIgnoreCase("remove")) {
 | 
			
		||||
                    cluster.helpers.remove(uuid);
 | 
			
		||||
                    DBFunc.removeHelper(cluster, uuid);
 | 
			
		||||
                    return MainUtil.sendMessage(player, C.CLUSTER_REMOVED_HELPER);
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                    "/plot cluster helpers <add|remove> <player>");
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            case "spawn":
 | 
			
		||||
            case "home":
 | 
			
		||||
            case "tp": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_TP)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_TP);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster tp <name>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster = area.getCluster(args[1]);
 | 
			
		||||
                if (cluster == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.INVALID_CLUSTER, args[1]);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                UUID uuid = player.getUUID();
 | 
			
		||||
                if (!cluster.isAdded(uuid)) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_TP_OTHER)) {
 | 
			
		||||
                        MainUtil
 | 
			
		||||
                            .sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_TP_OTHER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                player.teleport(cluster.getHome());
 | 
			
		||||
                return MainUtil.sendMessage(player, C.CLUSTER_TELEPORTING);
 | 
			
		||||
            }
 | 
			
		||||
            case "i":
 | 
			
		||||
            case "info":
 | 
			
		||||
            case "show":
 | 
			
		||||
            case "information": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_INFO)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_INFO);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 1 && args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster info [name]");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster;
 | 
			
		||||
                if (args.length == 2) {
 | 
			
		||||
                    cluster = area.getCluster(args[1]);
 | 
			
		||||
                    if (cluster == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.INVALID_CLUSTER, args[1]);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                } else {
 | 
			
		||||
                    cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                    if (cluster == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                String id = cluster.toString();
 | 
			
		||||
                String owner = UUIDHandler.getName(cluster.owner);
 | 
			
		||||
                if (owner == null) {
 | 
			
		||||
                    owner = "unknown";
 | 
			
		||||
                }
 | 
			
		||||
                String name = cluster.getName();
 | 
			
		||||
                String size = (cluster.getP2().x - cluster.getP1().x + 1) + "x" + (
 | 
			
		||||
                    cluster.getP2().y - cluster.getP1().y + 1);
 | 
			
		||||
                String rights = cluster.isAdded(player.getUUID()) + "";
 | 
			
		||||
                String message = C.CLUSTER_INFO.s();
 | 
			
		||||
                message = message.replaceAll("%id%", id);
 | 
			
		||||
                message = message.replaceAll("%owner%", owner);
 | 
			
		||||
                message = message.replaceAll("%name%", name);
 | 
			
		||||
                message = message.replaceAll("%size%", size);
 | 
			
		||||
                message = message.replaceAll("%rights%", rights);
 | 
			
		||||
                MainUtil.sendMessage(player, message);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "sh":
 | 
			
		||||
            case "setspawn":
 | 
			
		||||
            case "sethome":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_SETHOME)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_CLUSTER_SETHOME);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 1 && args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot cluster sethome");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                if (area == null) {
 | 
			
		||||
                    C.NOT_IN_PLOT_WORLD.send(player);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                PlotCluster cluster = area.getCluster(player.getLocation());
 | 
			
		||||
                if (cluster == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_IN_CLUSTER);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!cluster.hasHelperRights(player.getUUID())) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_CLUSTER_SETHOME_OTHER)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_CLUSTER_SETHOME_OTHER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                Location base = cluster.getClusterBottom();
 | 
			
		||||
                Location relative = player.getLocation().subtract(base.getX(), 0, base.getZ());
 | 
			
		||||
                BlockLoc blockloc = new BlockLoc(relative.getX(), relative.getY(), relative.getZ());
 | 
			
		||||
                cluster.settings.setPosition(blockloc);
 | 
			
		||||
                DBFunc.setPosition(cluster,
 | 
			
		||||
                    relative.getX() + "," + relative.getY() + "," + relative.getZ());
 | 
			
		||||
                return MainUtil.sendMessage(player, C.POSITION_SET);
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, C.CLUSTER_AVAILABLE_ARGS);
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,56 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * CommandCategory.
 | 
			
		||||
 */
 | 
			
		||||
public enum CommandCategory {
 | 
			
		||||
    /**
 | 
			
		||||
     * Claiming CommandConfig.
 | 
			
		||||
     * Such as: /plot claim
 | 
			
		||||
     */
 | 
			
		||||
    CLAIMING("Claiming"), /**
 | 
			
		||||
     * Teleportation CommandConfig.
 | 
			
		||||
     * Such as: /plot visit
 | 
			
		||||
     */
 | 
			
		||||
    TELEPORT("Teleport"), /**
 | 
			
		||||
     * Protection.
 | 
			
		||||
     */
 | 
			
		||||
    SETTINGS("Protection"), /**
 | 
			
		||||
     * Chat.
 | 
			
		||||
     */
 | 
			
		||||
    CHAT("Chat"), /**
 | 
			
		||||
     * Web.
 | 
			
		||||
     */
 | 
			
		||||
    SCHEMATIC("Web"), /**
 | 
			
		||||
     * Cosmetic.
 | 
			
		||||
     */
 | 
			
		||||
    APPEARANCE("Cosmetic"), /**
 | 
			
		||||
     * Information CommandConfig.
 | 
			
		||||
     * Such as: /plot info
 | 
			
		||||
     */
 | 
			
		||||
    INFO("Info"), /**
 | 
			
		||||
     * Debug CommandConfig.
 | 
			
		||||
     * Such as: /plot debug
 | 
			
		||||
     */
 | 
			
		||||
    DEBUG("Debug"), /**
 | 
			
		||||
     * Administration commands.
 | 
			
		||||
     */
 | 
			
		||||
    ADMINISTRATION("Admin");
 | 
			
		||||
    /**
 | 
			
		||||
     * The category name (Readable).
 | 
			
		||||
     */
 | 
			
		||||
    private final String name;
 | 
			
		||||
 | 
			
		||||
    /**
 | 
			
		||||
     * Constructor.
 | 
			
		||||
     *
 | 
			
		||||
     * @param name readable name
 | 
			
		||||
     */
 | 
			
		||||
    CommandCategory(String name) {
 | 
			
		||||
        this.name = name;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public String toString() {
 | 
			
		||||
        return this.name;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,74 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotId;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.comment.CommentInbox;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.comment.PlotComment;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.CommentManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.Map.Entry;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "comment", aliases = {"msg"}, description = "Comment on a plot",
 | 
			
		||||
    category = CommandCategory.CHAT, requiredType = RequiredType.NONE, permission = "plots.comment")
 | 
			
		||||
public class Comment extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        if (args.length < 2) {
 | 
			
		||||
            sendMessage(player, C.COMMENT_SYNTAX,
 | 
			
		||||
                StringMan.join(CommentManager.inboxes.keySet(), "|"));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        CommentInbox inbox = CommentManager.inboxes.get(args[0].toLowerCase());
 | 
			
		||||
        if (inbox == null) {
 | 
			
		||||
            sendMessage(player, C.COMMENT_SYNTAX,
 | 
			
		||||
                StringMan.join(CommentManager.inboxes.keySet(), "|"));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        PlotId id = PlotId.fromString(args[1]);
 | 
			
		||||
        Plot plot = MainUtil.getPlotFromString(player, args[1], false);
 | 
			
		||||
        int index;
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            index = 1;
 | 
			
		||||
            plot = loc.getPlotAbs();
 | 
			
		||||
        } else {
 | 
			
		||||
            if (args.length < 4) {
 | 
			
		||||
                sendMessage(player, C.COMMENT_SYNTAX,
 | 
			
		||||
                    StringMan.join(CommentManager.inboxes.keySet(), "|"));
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            index = 2;
 | 
			
		||||
        }
 | 
			
		||||
        if (!inbox.canWrite(plot, player)) {
 | 
			
		||||
            sendMessage(player, C.NO_PERM_INBOX, "");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        String message = StringMan.join(Arrays.copyOfRange(args, index, args.length), " ");
 | 
			
		||||
        PlotComment comment =
 | 
			
		||||
            new PlotComment(loc.getWorld(), id, message, player.getName(), inbox.toString(),
 | 
			
		||||
                System.currentTimeMillis());
 | 
			
		||||
        boolean result = inbox.addComment(plot, comment);
 | 
			
		||||
        if (!result) {
 | 
			
		||||
            sendMessage(player, C.NO_PLOT_INBOX, "");
 | 
			
		||||
            sendMessage(player, C.COMMENT_SYNTAX,
 | 
			
		||||
                StringMan.join(CommentManager.inboxes.keySet(), "|"));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        for (Entry<String, PlotPlayer> entry : UUIDHandler.getPlayers().entrySet()) {
 | 
			
		||||
            PlotPlayer pp = entry.getValue();
 | 
			
		||||
            if (pp.getAttribute("chatspy")) {
 | 
			
		||||
                MainUtil.sendMessage(pp, "/plot comment " + StringMan.join(args, " "));
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        sendMessage(player, C.COMMENT_ADDED);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,209 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotId;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MathMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
 | 
			
		||||
import java.util.*;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.concurrent.atomic.AtomicBoolean;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "condense", permission = "plots.admin",
 | 
			
		||||
    description = "Condense a plotworld", category = CommandCategory.ADMINISTRATION,
 | 
			
		||||
    requiredType = RequiredType.CONSOLE) public class Condense extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public static boolean TASK = false;
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        if (args.length != 2 && args.length != 3) {
 | 
			
		||||
            MainUtil.sendMessage(player, "/plot condense <area> <start|stop|info> [radius]");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        PlotArea area = PlotSquared.get().getPlotAreaByString(args[0]);
 | 
			
		||||
        if (area == null || !WorldUtil.IMP.isWorld(area.worldname)) {
 | 
			
		||||
            MainUtil.sendMessage(player, "INVALID AREA");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        switch (args[1].toLowerCase()) {
 | 
			
		||||
            case "start": {
 | 
			
		||||
                if (args.length == 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player,
 | 
			
		||||
                        "/plot condense " + area.toString() + " start <radius>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (Condense.TASK) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "TASK ALREADY STARTED");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!MathMan.isInteger(args[2])) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "INVALID RADIUS");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                int radius = Integer.parseInt(args[2]);
 | 
			
		||||
                ArrayList<Plot> plots = new ArrayList<>(PlotSquared.get().getPlots(area));
 | 
			
		||||
                // remove non base plots
 | 
			
		||||
                Iterator<Plot> iterator = plots.iterator();
 | 
			
		||||
                int maxSize = 0;
 | 
			
		||||
                ArrayList<Integer> sizes = new ArrayList<>();
 | 
			
		||||
                while (iterator.hasNext()) {
 | 
			
		||||
                    Plot plot = iterator.next();
 | 
			
		||||
                    if (!plot.isBasePlot()) {
 | 
			
		||||
                        iterator.remove();
 | 
			
		||||
                        continue;
 | 
			
		||||
                    }
 | 
			
		||||
                    int size = plot.getConnectedPlots().size();
 | 
			
		||||
                    if (size > maxSize) {
 | 
			
		||||
                        maxSize = size;
 | 
			
		||||
                    }
 | 
			
		||||
                    sizes.add(size - 1);
 | 
			
		||||
                }
 | 
			
		||||
                // Sort plots by size (buckets?)]
 | 
			
		||||
                //noinspection unchecked
 | 
			
		||||
                ArrayList<Plot>[] buckets = new ArrayList[maxSize];
 | 
			
		||||
                for (int i = 0; i < plots.size(); i++) {
 | 
			
		||||
                    Plot plot = plots.get(i);
 | 
			
		||||
                    int size = sizes.get(i);
 | 
			
		||||
                    ArrayList<Plot> array = buckets[size];
 | 
			
		||||
                    if (array == null) {
 | 
			
		||||
                        array = new ArrayList<>();
 | 
			
		||||
                        buckets[size] = array;
 | 
			
		||||
                    }
 | 
			
		||||
                    array.add(plot);
 | 
			
		||||
                }
 | 
			
		||||
                final ArrayList<Plot> allPlots = new ArrayList<>(plots.size());
 | 
			
		||||
                for (int i = buckets.length - 1; i >= 0; i--) {
 | 
			
		||||
                    ArrayList<Plot> array = buckets[i];
 | 
			
		||||
                    if (array != null) {
 | 
			
		||||
                        allPlots.addAll(array);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                int size = allPlots.size();
 | 
			
		||||
                int minimumRadius = (int) Math.ceil(Math.sqrt(size) / 2 + 1);
 | 
			
		||||
                if (radius < minimumRadius) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "RADIUS TOO SMALL");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                List<PlotId> toMove = new ArrayList<>(getPlots(allPlots, radius));
 | 
			
		||||
                final List<PlotId> free = new ArrayList<>();
 | 
			
		||||
                PlotId start = new PlotId(0, 0);
 | 
			
		||||
                while (start.x <= minimumRadius && start.y <= minimumRadius) {
 | 
			
		||||
                    Plot plot = area.getPlotAbs(start);
 | 
			
		||||
                    if (plot != null && !plot.hasOwner()) {
 | 
			
		||||
                        free.add(plot.getId());
 | 
			
		||||
                    }
 | 
			
		||||
                    start = Auto.getNextPlotId(start, 1);
 | 
			
		||||
                }
 | 
			
		||||
                if (free.isEmpty() || toMove.isEmpty()) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "NO FREE PLOTS FOUND");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, "TASK STARTED...");
 | 
			
		||||
                Runnable run = new Runnable() {
 | 
			
		||||
                    @Override public void run() {
 | 
			
		||||
                        if (!Condense.TASK) {
 | 
			
		||||
                            MainUtil.sendMessage(player, "TASK CANCELLED.");
 | 
			
		||||
                        }
 | 
			
		||||
                        if (allPlots.isEmpty()) {
 | 
			
		||||
                            Condense.TASK = false;
 | 
			
		||||
                            MainUtil.sendMessage(player,
 | 
			
		||||
                                "TASK COMPLETE. PLEASE VERIFY THAT NO NEW PLOTS HAVE BEEN CLAIMED DURING TASK.");
 | 
			
		||||
                            return;
 | 
			
		||||
                        }
 | 
			
		||||
                        final Runnable task = this;
 | 
			
		||||
                        final Plot origin = allPlots.remove(0);
 | 
			
		||||
                        int i = 0;
 | 
			
		||||
                        while (free.size() > i) {
 | 
			
		||||
                            final Plot possible = origin.getArea().getPlotAbs(free.get(i));
 | 
			
		||||
                            if (possible.hasOwner()) {
 | 
			
		||||
                                free.remove(i);
 | 
			
		||||
                                continue;
 | 
			
		||||
                            }
 | 
			
		||||
                            i++;
 | 
			
		||||
                            final AtomicBoolean result = new AtomicBoolean(false);
 | 
			
		||||
                            result.set(origin.move(possible, () -> {
 | 
			
		||||
                                if (result.get()) {
 | 
			
		||||
                                    MainUtil.sendMessage(player,
 | 
			
		||||
                                        "Moving: " + origin + " -> " + possible);
 | 
			
		||||
                                    TaskManager.runTaskLater(task, 1);
 | 
			
		||||
                                }
 | 
			
		||||
                            }, false));
 | 
			
		||||
                            if (result.get()) {
 | 
			
		||||
                                break;
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                        if (free.isEmpty()) {
 | 
			
		||||
                            Condense.TASK = false;
 | 
			
		||||
                            MainUtil.sendMessage(player, "TASK FAILED. NO FREE PLOTS FOUND!");
 | 
			
		||||
                            return;
 | 
			
		||||
                        }
 | 
			
		||||
                        if (i >= free.size()) {
 | 
			
		||||
                            MainUtil.sendMessage(player, "SKIPPING COMPLEX PLOT: " + origin);
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                };
 | 
			
		||||
                Condense.TASK = true;
 | 
			
		||||
                TaskManager.runTaskAsync(run);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "stop":
 | 
			
		||||
                if (!Condense.TASK) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "TASK ALREADY STOPPED");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Condense.TASK = false;
 | 
			
		||||
                MainUtil.sendMessage(player, "TASK STOPPED");
 | 
			
		||||
                return true;
 | 
			
		||||
            case "info":
 | 
			
		||||
                if (args.length == 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player,
 | 
			
		||||
                        "/plot condense " + area.toString() + " info <radius>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!MathMan.isInteger(args[2])) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "INVALID RADIUS");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                int radius = Integer.parseInt(args[2]);
 | 
			
		||||
                Collection<Plot> plots = area.getPlots();
 | 
			
		||||
                int size = plots.size();
 | 
			
		||||
                int minimumRadius = (int) Math.ceil(Math.sqrt(size) / 2 + 1);
 | 
			
		||||
                if (radius < minimumRadius) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "RADIUS TOO SMALL");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                int maxMove = getPlots(plots, minimumRadius).size();
 | 
			
		||||
                int userMove = getPlots(plots, radius).size();
 | 
			
		||||
                MainUtil.sendMessage(player, "=== DEFAULT EVAL ===");
 | 
			
		||||
                MainUtil.sendMessage(player, "MINIMUM RADIUS: " + minimumRadius);
 | 
			
		||||
                MainUtil.sendMessage(player, "MAXIMUM MOVES: " + maxMove);
 | 
			
		||||
                MainUtil.sendMessage(player, "=== INPUT EVAL ===");
 | 
			
		||||
                MainUtil.sendMessage(player, "INPUT RADIUS: " + radius);
 | 
			
		||||
                MainUtil.sendMessage(player, "ESTIMATED MOVES: " + userMove);
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    "ESTIMATED TIME: No idea, times will drastically change based on the system performance and load");
 | 
			
		||||
                MainUtil.sendMessage(player, "&e - Radius is measured in plot width");
 | 
			
		||||
                return true;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player,
 | 
			
		||||
            "/plot condense " + area.worldname + " <start|stop|info> [radius]");
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Set<PlotId> getPlots(Collection<Plot> plots, int radius) {
 | 
			
		||||
        HashSet<PlotId> outside = new HashSet<>();
 | 
			
		||||
        for (Plot plot : plots) {
 | 
			
		||||
            if (plot.getId().x > radius || plot.getId().x < -radius || plot.getId().y > radius
 | 
			
		||||
                || plot.getId().y < -radius) {
 | 
			
		||||
                outside.add(plot.getId());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return outside;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,31 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.CmdInstance;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.CmdConfirm;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "confirm", permission = "plots.use",
 | 
			
		||||
    description = "Confirm an action", category = CommandCategory.INFO) public class Confirm
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        CmdInstance command = CmdConfirm.getPending(player);
 | 
			
		||||
        if (command == null) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.FAILED_CONFIRM);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        CmdConfirm.removePending(player);
 | 
			
		||||
        if ((System.currentTimeMillis() - command.timestamp)
 | 
			
		||||
            > Settings.Confirmation.CONFIRMATION_TIMEOUT_SECONDS * 1000) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.EXPIRED_CONFIRM);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        TaskManager.runTask(command.command);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,45 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "continue",
 | 
			
		||||
    description = "Continue a plot that was previously marked as done",
 | 
			
		||||
    permission = "plots.continue", category = CommandCategory.SETTINGS,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Continue extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        Plot plot = player.getCurrentPlot();
 | 
			
		||||
        if ((plot == null) || !plot.hasOwner()) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_CONTINUE)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasFlag(Flags.DONE)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.DONE_NOT_DONE);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        int size = plot.getConnectedPlots().size();
 | 
			
		||||
        if (Settings.Done.COUNTS_TOWARDS_LIMIT && (player.getAllowedPlots()
 | 
			
		||||
            < player.getPlotCount() + size)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_ADMIN_COMMAND_CONTINUE);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.getRunning() > 0) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        plot.removeFlag(Flags.DONE);
 | 
			
		||||
        MainUtil.sendMessage(player, C.DONE_REMOVED);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,54 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "copy", permission = "plots.copy", aliases = {"copypaste"},
 | 
			
		||||
    category = CommandCategory.CLAIMING, description = "Copy a plot", usage = "/plot copy <X;Z>",
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Copy extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        Plot plot1 = loc.getPlotAbs();
 | 
			
		||||
        if (plot1 == null) {
 | 
			
		||||
            return !MainUtil.sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot1.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN.s())) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (args.length != 1) {
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Plot plot2 = MainUtil.getPlotFromString(player, args[0], true);
 | 
			
		||||
        if (plot2 == null) {
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot1.equals(plot2)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NOT_VALID_PLOT_ID);
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot1.getArea().isCompatible(plot2.getArea())) {
 | 
			
		||||
            C.PLOTWORLD_INCOMPATIBLE.send(player);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot1.copy(plot2, new Runnable() {
 | 
			
		||||
            @Override public void run() {
 | 
			
		||||
                MainUtil.sendMessage(player, C.COPY_SUCCESS);
 | 
			
		||||
            }
 | 
			
		||||
        })) {
 | 
			
		||||
            return true;
 | 
			
		||||
        } else {
 | 
			
		||||
            MainUtil.sendMessage(player, C.REQUIRES_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,32 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridPlotWorld;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "createroadschematic", aliases = {"crs"},
 | 
			
		||||
    category = CommandCategory.ADMINISTRATION, requiredType = RequiredType.NONE,
 | 
			
		||||
    permission = "plots.createroadschematic",
 | 
			
		||||
    description = "Add a road schematic to your world using the roads around your current plot",
 | 
			
		||||
    usage = "/plot createroadschematic") public class CreateRoadSchematic extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!(loc.getPlotArea() instanceof HybridPlotWorld)) {
 | 
			
		||||
            return sendMessage(player, C.NOT_IN_PLOT_WORLD);
 | 
			
		||||
        }
 | 
			
		||||
        HybridUtils.manager.setupRoadSchematic(plot);
 | 
			
		||||
        MainUtil.sendMessage(player,
 | 
			
		||||
            "$1Saved new road schematic. To test the road, fly to a few other plots and use /plot debugroadregen");
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,184 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.MySQL;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.SQLManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.SQLite;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotId;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SinglePlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.sql.SQLException;
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.HashMap;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.Map.Entry;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "database", aliases = {"convert"},
 | 
			
		||||
    category = CommandCategory.ADMINISTRATION, permission = "plots.database",
 | 
			
		||||
    description = "Convert/Backup Storage", requiredType = RequiredType.CONSOLE,
 | 
			
		||||
    usage = "/plot database [area] <sqlite|mysql|import>") public class Database
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public static void insertPlots(final SQLManager manager, final List<Plot> plots,
 | 
			
		||||
        final PlotPlayer player) {
 | 
			
		||||
        TaskManager.runTaskAsync(() -> {
 | 
			
		||||
            try {
 | 
			
		||||
                ArrayList<Plot> ps = new ArrayList<>(plots);
 | 
			
		||||
                MainUtil.sendMessage(player, "&6Starting...");
 | 
			
		||||
                manager.createPlotsAndData(ps, () -> {
 | 
			
		||||
                    MainUtil.sendMessage(player, "&6Database conversion finished!");
 | 
			
		||||
                    manager.close();
 | 
			
		||||
                });
 | 
			
		||||
            } catch (Exception e) {
 | 
			
		||||
                MainUtil
 | 
			
		||||
                    .sendMessage(player, "Failed to insert plot objects, see stacktrace for info");
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        if (args.length < 1) {
 | 
			
		||||
            MainUtil.sendMessage(player, "/plot database [area] <sqlite|mysql|import>");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        List<Plot> plots;
 | 
			
		||||
        PlotArea area = PlotSquared.get().getPlotAreaByString(args[0]);
 | 
			
		||||
        if (area != null) {
 | 
			
		||||
            plots = PlotSquared.get().sortPlotsByTemp(area.getPlots());
 | 
			
		||||
            args = Arrays.copyOfRange(args, 1, args.length);
 | 
			
		||||
        } else {
 | 
			
		||||
            plots = PlotSquared.get().sortPlotsByTemp(PlotSquared.get().getPlots());
 | 
			
		||||
        }
 | 
			
		||||
        if (args.length < 1) {
 | 
			
		||||
            MainUtil.sendMessage(player, "/plot database [world] <sqlite|mysql|import>");
 | 
			
		||||
            MainUtil.sendMessage(player, "[arg] indicates an optional argument");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        try {
 | 
			
		||||
            com.github.intellectualsites.plotsquared.plot.database.Database implementation;
 | 
			
		||||
            String prefix = "";
 | 
			
		||||
            switch (args[0].toLowerCase()) {
 | 
			
		||||
                case "import":
 | 
			
		||||
                    if (args.length < 2) {
 | 
			
		||||
                        MainUtil
 | 
			
		||||
                            .sendMessage(player, "/plot database import <sqlite file> [prefix]");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    File file = MainUtil.getFile(PlotSquared.get().IMP.getDirectory(),
 | 
			
		||||
                        args[1].endsWith(".db") ? args[1] : args[1] + ".db");
 | 
			
		||||
                    if (!file.exists()) {
 | 
			
		||||
                        MainUtil.sendMessage(player, "&6Database does not exist: " + file);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    MainUtil.sendMessage(player, "&6Starting...");
 | 
			
		||||
                    implementation = new SQLite(file);
 | 
			
		||||
                    SQLManager manager =
 | 
			
		||||
                        new SQLManager(implementation, args.length == 3 ? args[2] : "", true);
 | 
			
		||||
                    HashMap<String, HashMap<PlotId, Plot>> map = manager.getPlots();
 | 
			
		||||
                    plots = new ArrayList<>();
 | 
			
		||||
                    for (Entry<String, HashMap<PlotId, Plot>> entry : map.entrySet()) {
 | 
			
		||||
                        String areaname = entry.getKey();
 | 
			
		||||
                        PlotArea pa = PlotSquared.get().getPlotAreaByString(areaname);
 | 
			
		||||
                        if (pa != null) {
 | 
			
		||||
                            for (Entry<PlotId, Plot> entry2 : entry.getValue().entrySet()) {
 | 
			
		||||
                                Plot plot = entry2.getValue();
 | 
			
		||||
                                if (pa.getOwnedPlotAbs(plot.getId()) != null) {
 | 
			
		||||
                                    if (pa instanceof SinglePlotArea) {
 | 
			
		||||
                                        Plot newPlot = pa.getNextFreePlot(null, plot.getId());
 | 
			
		||||
                                        if (newPlot != null) {
 | 
			
		||||
                                            PlotId newId = newPlot.getId();
 | 
			
		||||
                                            PlotId id = plot.getId();
 | 
			
		||||
                                            File worldFile =
 | 
			
		||||
                                                new File(PlotSquared.imp().getWorldContainer(),
 | 
			
		||||
                                                    id.toCommaSeparatedString());
 | 
			
		||||
                                            if (worldFile.exists()) {
 | 
			
		||||
                                                File newFile =
 | 
			
		||||
                                                    new File(PlotSquared.imp().getWorldContainer(),
 | 
			
		||||
                                                        newId.toCommaSeparatedString());
 | 
			
		||||
                                                worldFile.renameTo(newFile);
 | 
			
		||||
                                            }
 | 
			
		||||
                                            id.x = newId.x;
 | 
			
		||||
                                            id.y = newId.y;
 | 
			
		||||
                                            id.recalculateHash();
 | 
			
		||||
                                            plot.setArea(pa);
 | 
			
		||||
                                            plots.add(plot);
 | 
			
		||||
                                            continue;
 | 
			
		||||
                                        }
 | 
			
		||||
                                    }
 | 
			
		||||
                                    MainUtil.sendMessage(player,
 | 
			
		||||
                                        "Skipping duplicate plot: " + plot + " | id=" + plot.temp);
 | 
			
		||||
                                    continue;
 | 
			
		||||
                                }
 | 
			
		||||
                                plot.setArea(pa);
 | 
			
		||||
                                plots.add(plot);
 | 
			
		||||
                            }
 | 
			
		||||
                        } else {
 | 
			
		||||
                            HashMap<PlotId, Plot> plotmap = PlotSquared.get().plots_tmp
 | 
			
		||||
                                .computeIfAbsent(areaname, k -> new HashMap<>());
 | 
			
		||||
                            plotmap.putAll(entry.getValue());
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    DBFunc.createPlotsAndData(plots,
 | 
			
		||||
                        () -> MainUtil.sendMessage(player, "&6Database conversion finished!"));
 | 
			
		||||
                    return true;
 | 
			
		||||
                case "mysql":
 | 
			
		||||
                    if (args.length < 6) {
 | 
			
		||||
                        return MainUtil.sendMessage(player,
 | 
			
		||||
                            "/plot database mysql [host] [port] [username] [password] [database] {prefix}");
 | 
			
		||||
                    }
 | 
			
		||||
                    String host = args[1];
 | 
			
		||||
                    String port = args[2];
 | 
			
		||||
                    String username = args[3];
 | 
			
		||||
                    String password = args[4];
 | 
			
		||||
                    String database = args[5];
 | 
			
		||||
                    if (args.length > 6) {
 | 
			
		||||
                        prefix = args[6];
 | 
			
		||||
                    }
 | 
			
		||||
                    implementation = new MySQL(host, port, database, username, password);
 | 
			
		||||
                    break;
 | 
			
		||||
                case "sqlite":
 | 
			
		||||
                    if (args.length < 2) {
 | 
			
		||||
                        return MainUtil.sendMessage(player, "/plot database sqlite [file]");
 | 
			
		||||
                    }
 | 
			
		||||
                    File sqliteFile =
 | 
			
		||||
                        MainUtil.getFile(PlotSquared.get().IMP.getDirectory(), args[1] + ".db");
 | 
			
		||||
                    implementation = new SQLite(sqliteFile);
 | 
			
		||||
                    break;
 | 
			
		||||
                default:
 | 
			
		||||
                    return MainUtil.sendMessage(player, "/plot database [sqlite/mysql]");
 | 
			
		||||
            }
 | 
			
		||||
            try {
 | 
			
		||||
                SQLManager manager = new SQLManager(implementation, prefix, true);
 | 
			
		||||
                Database.insertPlots(manager, plots, player);
 | 
			
		||||
                return true;
 | 
			
		||||
            } catch (ClassNotFoundException | SQLException e) {
 | 
			
		||||
                MainUtil.sendMessage(player, "$1Failed to save plots, read stacktrace for info");
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    "&d==== Here is an ugly stacktrace, if you are interested in those things ===");
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
                MainUtil.sendMessage(player, "&d==== End of stacktrace ====");
 | 
			
		||||
                MainUtil
 | 
			
		||||
                    .sendMessage(player, "$1Please make sure you are using the correct arguments!");
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        } catch (ClassNotFoundException | SQLException e) {
 | 
			
		||||
            MainUtil.sendMessage(player, "$1Failed to open connection, read stacktrace for info");
 | 
			
		||||
            MainUtil.sendMessage(player,
 | 
			
		||||
                "&d==== Here is an ugly stacktrace, if you are interested in those things ===");
 | 
			
		||||
            e.printStackTrace();
 | 
			
		||||
            MainUtil.sendMessage(player, "&d==== End of stacktrace ====");
 | 
			
		||||
            MainUtil.sendMessage(player, "$1Please make sure you are using the correct arguments!");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,46 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debug", category = CommandCategory.DEBUG,
 | 
			
		||||
    description = "Show debug information", usage = "/plot debug [msg]", permission = "plots.admin")
 | 
			
		||||
public class Debug extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        if ((args.length > 0) && args[0].equalsIgnoreCase("msg")) {
 | 
			
		||||
            StringBuilder msg = new StringBuilder();
 | 
			
		||||
            for (C caption : C.values()) {
 | 
			
		||||
                msg.append(caption.s()).append("\n");
 | 
			
		||||
            }
 | 
			
		||||
            MainUtil.sendMessage(player, msg.toString());
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        StringBuilder information = new StringBuilder();
 | 
			
		||||
        String header = C.DEBUG_HEADER.s();
 | 
			
		||||
        String line = C.DEBUG_LINE.s();
 | 
			
		||||
        String section = C.DEBUG_SECTION.s();
 | 
			
		||||
        information.append(header);
 | 
			
		||||
        information.append(getSection(section, "PlotArea"));
 | 
			
		||||
        information.append(
 | 
			
		||||
            getLine(line, "Plot Worlds", StringMan.join(PlotSquared.get().getPlotAreas(), ", ")));
 | 
			
		||||
        information.append(getLine(line, "Owned Plots", PlotSquared.get().getPlots().size()));
 | 
			
		||||
        information.append(getSection(section, "Messages"));
 | 
			
		||||
        information.append(getLine(line, "Total Messages", C.values().length));
 | 
			
		||||
        information.append(getLine(line, "View all captions", "/plot debug msg"));
 | 
			
		||||
        MainUtil.sendMessage(player, information.toString());
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private String getSection(String line, String val) {
 | 
			
		||||
        return line.replaceAll("%val%", val) + "\n";
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private String getLine(String line, String var, Object val) {
 | 
			
		||||
        return line.replaceAll("%var%", var).replaceAll("%val%", "" + val) + "\n";
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,30 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugallowunsafe",
 | 
			
		||||
    description = "Allow unsafe actions until toggled off", usage = "/plot debugallowunsafe",
 | 
			
		||||
    category = CommandCategory.DEBUG, requiredType = RequiredType.NONE,
 | 
			
		||||
    permission = "plots.debugallowunsafe") public class DebugAllowUnsafe extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public static final List<UUID> unsafeAllowed = new ArrayList<>();
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
 | 
			
		||||
        if (unsafeAllowed.contains(player.getUUID())) {
 | 
			
		||||
            unsafeAllowed.remove(player.getUUID());
 | 
			
		||||
            sendMessage(player, C.DEBUGALLOWUNSAFE_OFF);
 | 
			
		||||
        } else {
 | 
			
		||||
            unsafeAllowed.add(player.getUUID());
 | 
			
		||||
            sendMessage(player, C.DEBUGALLOWUNSAFE_ON);
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
@@ -1,113 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ChunkManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
import com.google.common.collect.BiMap;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Map;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugclaimtest", description =
 | 
			
		||||
    "If you accidentally delete your database, this command will attempt to restore all plots based on the data from plot signs. "
 | 
			
		||||
        + "Execution time may vary", category = CommandCategory.DEBUG,
 | 
			
		||||
    requiredType = RequiredType.CONSOLE, permission = "plots.debugclaimtest")
 | 
			
		||||
public class DebugClaimTest extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        if (args.length < 3) {
 | 
			
		||||
            return !MainUtil.sendMessage(null,
 | 
			
		||||
                "If you accidentally delete your database, this command will attempt to restore all plots based on the data from the "
 | 
			
		||||
                    + "plot signs. \n\n&cMissing world arg /plot debugclaimtest {world} {PlotId min} {PlotId max}");
 | 
			
		||||
        }
 | 
			
		||||
        PlotArea area = PlotSquared.get().getPlotAreaByString(args[0]);
 | 
			
		||||
        if (area == null || !WorldUtil.IMP.isWorld(area.worldname)) {
 | 
			
		||||
            C.NOT_VALID_PLOT_WORLD.send(player, args[0]);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        PlotId min, max;
 | 
			
		||||
        try {
 | 
			
		||||
            args[1].split(";");
 | 
			
		||||
            args[2].split(";");
 | 
			
		||||
            min = PlotId.fromString(args[1]);
 | 
			
		||||
            max = PlotId.fromString(args[2]);
 | 
			
		||||
        } catch (Exception ignored) {
 | 
			
		||||
            return !MainUtil.sendMessage(player,
 | 
			
		||||
                "&cInvalid min/max values. &7The values are to Plot IDs in the format &cX;Y &7where X;Y are the plot coords\nThe conversion "
 | 
			
		||||
                    + "will only check the plots in the selected area.");
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player,
 | 
			
		||||
            "&3Sign Block&8->&3Plot&8: &7Beginning sign to plot conversion. This may take a while...");
 | 
			
		||||
        MainUtil.sendMessage(player,
 | 
			
		||||
            "&3Sign Block&8->&3Plot&8: Found an excess of 250,000 chunks. Limiting search radius... (~3.8 min)");
 | 
			
		||||
        PlotManager manager = area.getPlotManager();
 | 
			
		||||
        ArrayList<Plot> plots = new ArrayList<>();
 | 
			
		||||
        for (PlotId id : MainUtil.getPlotSelectionIds(min, max)) {
 | 
			
		||||
            Plot plot = area.getPlotAbs(id);
 | 
			
		||||
            if (plot.hasOwner()) {
 | 
			
		||||
                MainUtil.sendMessage(player, " - &cDB Already contains: " + plot.getId());
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            Location loc = manager.getSignLoc(area, plot);
 | 
			
		||||
            ChunkLoc chunk = new ChunkLoc(loc.getX() >> 4, loc.getZ() >> 4);
 | 
			
		||||
            boolean result = ChunkManager.manager.loadChunk(area.worldname, chunk, false);
 | 
			
		||||
            if (!result) {
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            String[] lines = WorldUtil.IMP.getSign(loc);
 | 
			
		||||
            if (lines != null) {
 | 
			
		||||
                String line = lines[2];
 | 
			
		||||
                if (line != null && line.length() > 2) {
 | 
			
		||||
                    line = line.substring(2);
 | 
			
		||||
                    BiMap<StringWrapper, UUID> map = UUIDHandler.getUuidMap();
 | 
			
		||||
                    UUID uuid = map.get(new StringWrapper(line));
 | 
			
		||||
                    if (uuid == null) {
 | 
			
		||||
                        for (Map.Entry<StringWrapper, UUID> stringWrapperUUIDEntry : map
 | 
			
		||||
                            .entrySet()) {
 | 
			
		||||
                            if (stringWrapperUUIDEntry.getKey().value.toLowerCase()
 | 
			
		||||
                                .startsWith(line.toLowerCase())) {
 | 
			
		||||
                                uuid = stringWrapperUUIDEntry.getValue();
 | 
			
		||||
                                break;
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    if (uuid == null) {
 | 
			
		||||
                        uuid = UUIDHandler.getUUID(line, null);
 | 
			
		||||
                    }
 | 
			
		||||
                    if (uuid != null) {
 | 
			
		||||
                        MainUtil
 | 
			
		||||
                            .sendMessage(player, " - &aFound plot: " + plot.getId() + " : " + line);
 | 
			
		||||
                        plot.setOwner(uuid);
 | 
			
		||||
                        plots.add(plot);
 | 
			
		||||
                    } else {
 | 
			
		||||
                        MainUtil.sendMessage(player,
 | 
			
		||||
                            " - &cInvalid PlayerName: " + plot.getId() + " : " + line);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (!plots.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player,
 | 
			
		||||
                "&3Sign Block&8->&3Plot&8: &7Updating '" + plots.size() + "' plots!");
 | 
			
		||||
            DBFunc.createPlotsAndData(plots, new Runnable() {
 | 
			
		||||
                @Override public void run() {
 | 
			
		||||
                    MainUtil.sendMessage(player, "&6Database update finished!");
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            for (Plot plot : plots) {
 | 
			
		||||
                plot.create();
 | 
			
		||||
            }
 | 
			
		||||
            MainUtil.sendMessage(player, "&3Sign Block&8->&3Plot&8: &7Complete!");
 | 
			
		||||
        } else {
 | 
			
		||||
            MainUtil.sendMessage(player, "No plots were found for the given search.");
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,429 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flag;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.FlagManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.listener.WEManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.block.GlobalBlockQueue;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.expiry.ExpireManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.expiry.PlotAnalysis;
 | 
			
		||||
import com.google.common.io.Files;
 | 
			
		||||
 | 
			
		||||
import javax.script.*;
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.nio.charset.StandardCharsets;
 | 
			
		||||
import java.sql.Timestamp;
 | 
			
		||||
import java.util.*;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugexec", permission = "plots.admin",
 | 
			
		||||
    description = "Mutli-purpose debug command", aliases = {"exec", "$"},
 | 
			
		||||
    category = CommandCategory.DEBUG) public class DebugExec extends SubCommand {
 | 
			
		||||
    private ScriptEngine engine;
 | 
			
		||||
    private Bindings scope;
 | 
			
		||||
 | 
			
		||||
    public DebugExec() {
 | 
			
		||||
        try {
 | 
			
		||||
            if (PlotSquared.get() != null) {
 | 
			
		||||
                File file = new File(PlotSquared.get().IMP.getDirectory(),
 | 
			
		||||
                    Settings.Paths.SCRIPTS + File.separator + "start.js");
 | 
			
		||||
                if (file.exists()) {
 | 
			
		||||
                    init();
 | 
			
		||||
                    String script = StringMan.join(Files.readLines(new File(new File(
 | 
			
		||||
                            PlotSquared.get().IMP.getDirectory() + File.separator
 | 
			
		||||
                                + Settings.Paths.SCRIPTS), "start.js"), StandardCharsets.UTF_8),
 | 
			
		||||
                        System.getProperty("line.separator"));
 | 
			
		||||
                    this.scope.put("THIS", this);
 | 
			
		||||
                    this.scope.put("PlotPlayer", ConsolePlayer.getConsole());
 | 
			
		||||
                    this.engine.eval(script, this.scope);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        } catch (IOException | ScriptException ignored) {
 | 
			
		||||
            ignored.printStackTrace();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public ScriptEngine getEngine() {
 | 
			
		||||
        if (this.engine == null) {
 | 
			
		||||
            init();
 | 
			
		||||
        }
 | 
			
		||||
        return this.engine;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public Bindings getScope() {
 | 
			
		||||
        return this.scope;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void init() {
 | 
			
		||||
        if (this.engine != null) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        this.engine = new ScriptEngineManager(null).getEngineByName("nashorn");
 | 
			
		||||
        if (this.engine == null) {
 | 
			
		||||
            this.engine = new ScriptEngineManager(null).getEngineByName("JavaScript");
 | 
			
		||||
        }
 | 
			
		||||
        ScriptContext context = new SimpleScriptContext();
 | 
			
		||||
        this.scope = context.getBindings(ScriptContext.ENGINE_SCOPE);
 | 
			
		||||
 | 
			
		||||
        // stuff
 | 
			
		||||
        this.scope.put("MainUtil", new MainUtil());
 | 
			
		||||
        this.scope.put("Settings", new Settings());
 | 
			
		||||
        this.scope.put("StringMan", new StringMan());
 | 
			
		||||
        this.scope.put("MathMan", new MathMan());
 | 
			
		||||
        this.scope.put("FlagManager", new FlagManager());
 | 
			
		||||
 | 
			
		||||
        // Classes
 | 
			
		||||
        this.scope.put("Location", Location.class);
 | 
			
		||||
        this.scope.put("PlotBlock", PlotBlock.class);
 | 
			
		||||
        this.scope.put("Plot", Plot.class);
 | 
			
		||||
        this.scope.put("PlotId", PlotId.class);
 | 
			
		||||
        this.scope.put("Runnable", Runnable.class);
 | 
			
		||||
        this.scope.put("RunnableVal", RunnableVal.class);
 | 
			
		||||
 | 
			
		||||
        // Instances
 | 
			
		||||
        this.scope.put("PS", PlotSquared.get());
 | 
			
		||||
        this.scope.put("GlobalBlockQueue", GlobalBlockQueue.IMP);
 | 
			
		||||
        this.scope.put("ExpireManager", ExpireManager.IMP);
 | 
			
		||||
        if (PlotSquared.get().worldedit != null) {
 | 
			
		||||
            this.scope.put("WEManager", new WEManager());
 | 
			
		||||
        }
 | 
			
		||||
        this.scope.put("TaskManager", TaskManager.IMP);
 | 
			
		||||
        this.scope.put("TitleManager", AbstractTitle.TITLE_CLASS);
 | 
			
		||||
        this.scope.put("ConsolePlayer", ConsolePlayer.getConsole());
 | 
			
		||||
        this.scope.put("SchematicHandler", SchematicHandler.manager);
 | 
			
		||||
        this.scope.put("ChunkManager", ChunkManager.manager);
 | 
			
		||||
        this.scope.put("BlockManager", WorldUtil.IMP);
 | 
			
		||||
        this.scope.put("SetupUtils", SetupUtils.manager);
 | 
			
		||||
        this.scope.put("EventUtil", EventUtil.manager);
 | 
			
		||||
        this.scope.put("EconHandler", EconHandler.manager);
 | 
			
		||||
        this.scope.put("UUIDHandler", UUIDHandler.implementation);
 | 
			
		||||
        this.scope.put("DBFunc", DBFunc.dbManager);
 | 
			
		||||
        this.scope.put("HybridUtils", HybridUtils.manager);
 | 
			
		||||
        this.scope.put("IMP", PlotSquared.get().IMP);
 | 
			
		||||
        this.scope.put("MainCommand", MainCommand.getInstance());
 | 
			
		||||
 | 
			
		||||
        // enums
 | 
			
		||||
        for (Enum<?> value : C.values()) {
 | 
			
		||||
            this.scope.put("C_" + value.name(), value);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        List<String> allowed_params = Arrays
 | 
			
		||||
            .asList("analyze", "calibrate-analysis", "remove-flag", "stop-expire", "start-expire",
 | 
			
		||||
                "seen", "list-scripts", "start-rgar", "stop-rgar", "help", "addcmd", "runasync",
 | 
			
		||||
                "run", "allcmd", "all");
 | 
			
		||||
        if (args.length > 0) {
 | 
			
		||||
            String arg = args[0].toLowerCase();
 | 
			
		||||
            String script;
 | 
			
		||||
            boolean async = false;
 | 
			
		||||
            switch (arg) {
 | 
			
		||||
                case "analyze": {
 | 
			
		||||
                    Plot plot = player.getCurrentPlot();
 | 
			
		||||
                    if (plot == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    PlotAnalysis analysis = plot.getComplexity(null);
 | 
			
		||||
                    if (analysis != null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, "Changes/column: " + analysis.changes / 1.0);
 | 
			
		||||
                        return true;
 | 
			
		||||
                    }
 | 
			
		||||
                    MainUtil.sendMessage(player, "$1Starting task...");
 | 
			
		||||
                    HybridUtils.manager.analyzePlot(plot, new RunnableVal<PlotAnalysis>() {
 | 
			
		||||
                        @Override public void run(PlotAnalysis value) {
 | 
			
		||||
                            MainUtil.sendMessage(player,
 | 
			
		||||
                                "$1Done: $2Use $3/plot debugexec analyze$2 for more information");
 | 
			
		||||
                        }
 | 
			
		||||
                    });
 | 
			
		||||
                    return true;
 | 
			
		||||
                }
 | 
			
		||||
                case "calibrate-analysis":
 | 
			
		||||
                    if (args.length != 2) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                            "/plot debugexec analyze <threshold>");
 | 
			
		||||
                        MainUtil.sendMessage(player,
 | 
			
		||||
                            "$1<threshold> $2= $1The percentage of plots you want to clear (100 clears 100% of plots so no point calibrating "
 | 
			
		||||
                                + "it)");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    double threshold;
 | 
			
		||||
                    try {
 | 
			
		||||
                        threshold = Integer.parseInt(args[1]) / 100d;
 | 
			
		||||
                    } catch (NumberFormatException ignored) {
 | 
			
		||||
                        MainUtil.sendMessage(player, "$2Invalid threshold: " + args[1]);
 | 
			
		||||
                        MainUtil.sendMessage(player,
 | 
			
		||||
                            "$1<threshold> $2= $1The percentage of plots you want to clear as a number between 0 - 100");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    PlotAnalysis.calcOptimalModifiers(() -> MainUtil
 | 
			
		||||
                        .sendMessage(player, "$1Thank you for calibrating plot expiry"), threshold);
 | 
			
		||||
                    return true;
 | 
			
		||||
                case "stop-expire":
 | 
			
		||||
                    if (ExpireManager.IMP == null || !ExpireManager.IMP.cancelTask()) {
 | 
			
		||||
                        return MainUtil.sendMessage(player, "Task already halted");
 | 
			
		||||
                    }
 | 
			
		||||
                    return MainUtil.sendMessage(player, "Cancelled task.");
 | 
			
		||||
                case "remove-flag":
 | 
			
		||||
                    if (args.length != 2) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                            "/plot debugexec remove-flag <flag>");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    String flag = args[1];
 | 
			
		||||
                    for (Plot plot : PlotSquared.get().getBasePlots()) {
 | 
			
		||||
                        Flag<?> flag1 = FlagManager.getFlag(flag);
 | 
			
		||||
                        if (plot.getFlag(flag1).isPresent()) {
 | 
			
		||||
                            plot.removeFlag(flag1);
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    return MainUtil.sendMessage(player, "Cleared flag: " + flag);
 | 
			
		||||
                case "start-rgar": {
 | 
			
		||||
                    if (args.length != 2) {
 | 
			
		||||
                        MainUtil.sendMessage(player,
 | 
			
		||||
                            "&cInvalid syntax: /plot debugexec start-rgar <world>");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    PlotArea area = PlotSquared.get().getPlotAreaByString(args[1]);
 | 
			
		||||
                    if (area == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NOT_VALID_PLOT_WORLD, args[1]);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    boolean result;
 | 
			
		||||
                    if (HybridUtils.regions != null) {
 | 
			
		||||
                        result =
 | 
			
		||||
                            HybridUtils.manager.scheduleRoadUpdate(area, HybridUtils.regions, 0);
 | 
			
		||||
                    } else {
 | 
			
		||||
                        result = HybridUtils.manager.scheduleRoadUpdate(area, 0);
 | 
			
		||||
                    }
 | 
			
		||||
                    if (!result) {
 | 
			
		||||
                        MainUtil.sendMessage(player,
 | 
			
		||||
                            "&cCannot schedule mass schematic update! (Is one already in progress?)");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    return true;
 | 
			
		||||
                }
 | 
			
		||||
                case "stop-rgar":
 | 
			
		||||
                    if (!HybridUtils.UPDATE) {
 | 
			
		||||
                        MainUtil.sendMessage(player, "&cTask not running!");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    HybridUtils.UPDATE = false;
 | 
			
		||||
                    MainUtil.sendMessage(player, "&cCancelling task... (Please wait)");
 | 
			
		||||
                    return true;
 | 
			
		||||
                case "start-expire":
 | 
			
		||||
                    if (ExpireManager.IMP == null) {
 | 
			
		||||
                        ExpireManager.IMP = new ExpireManager();
 | 
			
		||||
                    }
 | 
			
		||||
                    if (ExpireManager.IMP.runAutomatedTask()) {
 | 
			
		||||
                        return MainUtil.sendMessage(player, "Started plot expiry task");
 | 
			
		||||
                    } else {
 | 
			
		||||
                        return MainUtil.sendMessage(player, "Plot expiry task already started");
 | 
			
		||||
                    }
 | 
			
		||||
                case "seen":
 | 
			
		||||
                    if (args.length != 2) {
 | 
			
		||||
                        return MainUtil.sendMessage(player, "Use /plot debugexec seen <player>");
 | 
			
		||||
                    }
 | 
			
		||||
                    UUID uuid = UUIDHandler.getUUID(args[1], null);
 | 
			
		||||
                    if (uuid == null) {
 | 
			
		||||
                        return MainUtil.sendMessage(player, "Player not found: " + args[1]);
 | 
			
		||||
                    }
 | 
			
		||||
                    OfflinePlotPlayer op = UUIDHandler.getUUIDWrapper().getOfflinePlayer(uuid);
 | 
			
		||||
                    if (op == null || op.getLastPlayed() == 0) {
 | 
			
		||||
                        return MainUtil
 | 
			
		||||
                            .sendMessage(player, "Player hasn't connected before: " + args[1]);
 | 
			
		||||
                    }
 | 
			
		||||
                    Timestamp stamp = new Timestamp(op.getLastPlayed());
 | 
			
		||||
                    Date date = new Date(stamp.getTime());
 | 
			
		||||
                    MainUtil.sendMessage(player, "PLAYER: " + args[1]);
 | 
			
		||||
                    MainUtil.sendMessage(player, "UUID: " + uuid);
 | 
			
		||||
                    MainUtil.sendMessage(player, "Object: " + date.toGMTString());
 | 
			
		||||
                    MainUtil.sendMessage(player, "GMT: " + date.toGMTString());
 | 
			
		||||
                    MainUtil.sendMessage(player, "Local: " + date.toLocaleString());
 | 
			
		||||
                    return true;
 | 
			
		||||
                case "h":
 | 
			
		||||
                case "he":
 | 
			
		||||
                case "?":
 | 
			
		||||
                case "help":
 | 
			
		||||
                    MainUtil.sendMessage(player,
 | 
			
		||||
                        "Possible sub commands: /plot debugexec <" + StringMan
 | 
			
		||||
                            .join(allowed_params, "|") + ">");
 | 
			
		||||
                    return false;
 | 
			
		||||
                case "addcmd":
 | 
			
		||||
                    try {
 | 
			
		||||
                        final String cmd = StringMan.join(Files.readLines(MainUtil.getFile(new File(
 | 
			
		||||
                                PlotSquared.get().IMP.getDirectory() + File.separator
 | 
			
		||||
                                    + Settings.Paths.SCRIPTS), args[1]), StandardCharsets.UTF_8),
 | 
			
		||||
                            System.getProperty("line.separator"));
 | 
			
		||||
                        new Command(MainCommand.getInstance(), true, args[1].split("\\.")[0], null,
 | 
			
		||||
                            RequiredType.NONE, CommandCategory.DEBUG) {
 | 
			
		||||
                            @Override public void execute(PlotPlayer player, String[] args,
 | 
			
		||||
                                RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
                                RunnableVal2<Command, CommandResult> whenDone) {
 | 
			
		||||
                                try {
 | 
			
		||||
                                    DebugExec.this.scope.put("PlotPlayer", player);
 | 
			
		||||
                                    DebugExec.this.scope.put("args", args);
 | 
			
		||||
                                    DebugExec.this.engine.eval(cmd, DebugExec.this.scope);
 | 
			
		||||
                                } catch (ScriptException e) {
 | 
			
		||||
                                    e.printStackTrace();
 | 
			
		||||
                                    MainUtil.sendMessage(player, C.COMMAND_WENT_WRONG);
 | 
			
		||||
                                }
 | 
			
		||||
                            }
 | 
			
		||||
                        };
 | 
			
		||||
                        return true;
 | 
			
		||||
                    } catch (IOException e) {
 | 
			
		||||
                        e.printStackTrace();
 | 
			
		||||
                        MainUtil
 | 
			
		||||
                            .sendMessage(player, C.COMMAND_SYNTAX, "/plot debugexec addcmd <file>");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                case "runasync":
 | 
			
		||||
                    async = true;
 | 
			
		||||
                case "run":
 | 
			
		||||
                    try {
 | 
			
		||||
                        script = StringMan.join(Files.readLines(MainUtil.getFile(new File(
 | 
			
		||||
                                PlotSquared.get().IMP.getDirectory() + File.separator
 | 
			
		||||
                                    + Settings.Paths.SCRIPTS), args[1]), StandardCharsets.UTF_8),
 | 
			
		||||
                            System.getProperty("line.separator"));
 | 
			
		||||
                        if (args.length > 2) {
 | 
			
		||||
                            HashMap<String, String> replacements = new HashMap<>();
 | 
			
		||||
                            for (int i = 2; i < args.length; i++) {
 | 
			
		||||
                                replacements.put("%s" + (i - 2), args[i]);
 | 
			
		||||
                            }
 | 
			
		||||
                            script = StringMan.replaceFromMap(script, replacements);
 | 
			
		||||
                        }
 | 
			
		||||
                    } catch (IOException e) {
 | 
			
		||||
                        e.printStackTrace();
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    break;
 | 
			
		||||
                case "list-scripts":
 | 
			
		||||
                    String path = PlotSquared.get().IMP.getDirectory() + File.separator
 | 
			
		||||
                        + Settings.Paths.SCRIPTS;
 | 
			
		||||
                    File folder = new File(path);
 | 
			
		||||
                    File[] filesArray = folder.listFiles();
 | 
			
		||||
 | 
			
		||||
                    int page;
 | 
			
		||||
                    switch (args.length) {
 | 
			
		||||
                        case 1:
 | 
			
		||||
                            page = 0;
 | 
			
		||||
                            break;
 | 
			
		||||
                        case 2:
 | 
			
		||||
                            if (MathMan.isInteger(args[1])) {
 | 
			
		||||
                                page = Integer.parseInt(args[1]) - 1;
 | 
			
		||||
                                break;
 | 
			
		||||
                            }
 | 
			
		||||
                        default:
 | 
			
		||||
                            C.COMMAND_SYNTAX.send(player, "/plot debugexec list-scripts [#]");
 | 
			
		||||
                            return false;
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
                    List<File> allFiles = Arrays.asList(filesArray);
 | 
			
		||||
                    paginate(player, allFiles, 8, page,
 | 
			
		||||
                        new RunnableVal3<Integer, File, PlotMessage>() {
 | 
			
		||||
 | 
			
		||||
                            @Override public void run(Integer i, File file, PlotMessage message) {
 | 
			
		||||
                                String name = file.getName();
 | 
			
		||||
                                message.text("[").color("$3").text(String.valueOf(i)).color("$1")
 | 
			
		||||
                                    .text("]").color("$3").text(' ' + name).color("$1");
 | 
			
		||||
                            }
 | 
			
		||||
                        }, "/plot debugexec list-scripts", "List of scripts");
 | 
			
		||||
                    return true;
 | 
			
		||||
                case "allcmd":
 | 
			
		||||
                    if (args.length < 3) {
 | 
			
		||||
                        C.COMMAND_SYNTAX
 | 
			
		||||
                            .send(player, "/plot debugexec allcmd <condition> <command>");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    long start = System.currentTimeMillis();
 | 
			
		||||
                    Command cmd = MainCommand.getInstance().getCommand(args[3]);
 | 
			
		||||
                    String[] params = Arrays.copyOfRange(args, 4, args.length);
 | 
			
		||||
                    if ("true".equals(args[1])) {
 | 
			
		||||
                        Location loc = player.getMeta(PlotPlayer.META_LOCATION);
 | 
			
		||||
                        Plot plot = player.getMeta(PlotPlayer.META_LAST_PLOT);
 | 
			
		||||
                        for (Plot current : PlotSquared.get().getBasePlots()) {
 | 
			
		||||
                            player.setMeta(PlotPlayer.META_LOCATION, current.getBottomAbs());
 | 
			
		||||
                            player.setMeta(PlotPlayer.META_LAST_PLOT, current);
 | 
			
		||||
                            cmd.execute(player, params, null, null);
 | 
			
		||||
                        }
 | 
			
		||||
                        if (loc == null) {
 | 
			
		||||
                            player.deleteMeta(PlotPlayer.META_LOCATION);
 | 
			
		||||
                        } else {
 | 
			
		||||
                            player.setMeta(PlotPlayer.META_LOCATION, loc);
 | 
			
		||||
                        }
 | 
			
		||||
                        if (plot == null) {
 | 
			
		||||
                            player.deleteMeta(PlotPlayer.META_LAST_PLOT);
 | 
			
		||||
                        } else {
 | 
			
		||||
                            player.setMeta(PlotPlayer.META_LAST_PLOT, plot);
 | 
			
		||||
                        }
 | 
			
		||||
                        player.sendMessage("&c> " + (System.currentTimeMillis() - start));
 | 
			
		||||
                        return true;
 | 
			
		||||
                    }
 | 
			
		||||
                    init();
 | 
			
		||||
                    this.scope.put("_2", params);
 | 
			
		||||
                    this.scope.put("_3", cmd);
 | 
			
		||||
                    script =
 | 
			
		||||
                        "_1=PS.getBasePlots().iterator();while(_1.hasNext()){plot=_1.next();if("
 | 
			
		||||
                            + args[1]
 | 
			
		||||
                            + "){PlotPlayer.setMeta(\"location\",plot.getBottomAbs());PlotPlayer.setMeta(\"lastplot\",plot);_3.onCommand"
 | 
			
		||||
                            + "(PlotPlayer,_2)}}";
 | 
			
		||||
 | 
			
		||||
                    break;
 | 
			
		||||
                case "all":
 | 
			
		||||
                    if (args.length < 3) {
 | 
			
		||||
                        C.COMMAND_SYNTAX.send(player, "/plot debugexec all <condition> <code>");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    script =
 | 
			
		||||
                        "_1=PS.getBasePlots().iterator();while(_1.hasNext()){plot=_1.next();if("
 | 
			
		||||
                            + args[1] + "){" + StringMan
 | 
			
		||||
                            .join(Arrays.copyOfRange(args, 2, args.length), " ") + "}}";
 | 
			
		||||
 | 
			
		||||
                    break;
 | 
			
		||||
                default:
 | 
			
		||||
                    script = StringMan.join(args, " ");
 | 
			
		||||
            }
 | 
			
		||||
            if (!(player instanceof ConsolePlayer)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.NOT_CONSOLE);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            init();
 | 
			
		||||
            this.scope.put("PlotPlayer", player);
 | 
			
		||||
            PlotSquared.debug("> " + script);
 | 
			
		||||
            try {
 | 
			
		||||
                if (async) {
 | 
			
		||||
                    final String toExec = script;
 | 
			
		||||
                    TaskManager.runTaskAsync(() -> {
 | 
			
		||||
                        long start = System.currentTimeMillis();
 | 
			
		||||
                        Object result = null;
 | 
			
		||||
                        try {
 | 
			
		||||
                            result = DebugExec.this.engine.eval(toExec, DebugExec.this.scope);
 | 
			
		||||
                        } catch (ScriptException e) {
 | 
			
		||||
                            e.printStackTrace();
 | 
			
		||||
                        }
 | 
			
		||||
                        PlotSquared
 | 
			
		||||
                            .log("> " + (System.currentTimeMillis() - start) + "ms -> " + result);
 | 
			
		||||
                    });
 | 
			
		||||
                } else {
 | 
			
		||||
                    long start = System.currentTimeMillis();
 | 
			
		||||
                    Object result = this.engine.eval(script, this.scope);
 | 
			
		||||
                    PlotSquared
 | 
			
		||||
                        .log("> " + (System.currentTimeMillis() - start) + "ms -> " + result);
 | 
			
		||||
                }
 | 
			
		||||
                return true;
 | 
			
		||||
            } catch (ScriptException e) {
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,52 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Argument;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flag;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
 | 
			
		||||
import java.util.HashMap;
 | 
			
		||||
import java.util.Iterator;
 | 
			
		||||
import java.util.Map.Entry;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugfixflags", usage = "/plot debugfixflags <world>",
 | 
			
		||||
    permission = "plots.debugfixflags", description = "Attempt to fix all flags for a world",
 | 
			
		||||
    requiredType = RequiredType.CONSOLE, category = CommandCategory.DEBUG)
 | 
			
		||||
public class DebugFixFlags extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public DebugFixFlags() {
 | 
			
		||||
        super(Argument.String);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        PlotArea area = PlotSquared.get().getPlotAreaByString(args[0]);
 | 
			
		||||
        if (area == null || !WorldUtil.IMP.isWorld(area.worldname)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NOT_VALID_PLOT_WORLD, args[0]);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, "&8--- &6Starting task &8 ---");
 | 
			
		||||
        for (Plot plot : area.getPlots()) {
 | 
			
		||||
            HashMap<Flag<?>, Object> flags = plot.getFlags();
 | 
			
		||||
            Iterator<Entry<Flag<?>, Object>> i = flags.entrySet().iterator();
 | 
			
		||||
            boolean changed = false;
 | 
			
		||||
            while (i.hasNext()) {
 | 
			
		||||
                if (i.next().getKey() == null) {
 | 
			
		||||
                    changed = true;
 | 
			
		||||
                    i.remove();
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            if (changed) {
 | 
			
		||||
                DBFunc.setFlags(plot, plot.getFlags());
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, "&aDone!");
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,58 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotId;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.PlotAreaManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SinglePlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.worlds.SinglePlotAreaManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
import com.google.common.base.Charsets;
 | 
			
		||||
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugimportworlds", permission = "plots.admin",
 | 
			
		||||
    description = "Import worlds by player name", requiredType = RequiredType.CONSOLE,
 | 
			
		||||
    category = CommandCategory.TELEPORT) public class DebugImportWorlds extends Command {
 | 
			
		||||
    public DebugImportWorlds() {
 | 
			
		||||
        super(MainCommand.getInstance(), true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) throws CommandException {
 | 
			
		||||
        // UUID.nameUUIDFromBytes(("OfflinePlayer:" + player.getName()).getBytes(Charsets.UTF_8))
 | 
			
		||||
        PlotAreaManager pam = PlotSquared.get().getPlotAreaManager();
 | 
			
		||||
        if (!(pam instanceof SinglePlotAreaManager)) {
 | 
			
		||||
            player.sendMessage("Must be a single plot area!");
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        SinglePlotArea area = ((SinglePlotAreaManager) pam).getArea();
 | 
			
		||||
        PlotId id = new PlotId(0, 0);
 | 
			
		||||
        File container = PlotSquared.imp().getWorldContainer();
 | 
			
		||||
        for (File folder : container.listFiles()) {
 | 
			
		||||
            String name = folder.getName();
 | 
			
		||||
            if (!WorldUtil.IMP.isWorld(name) && PlotId.fromString(name) == null) {
 | 
			
		||||
                UUID uuid = UUIDHandler.getUUID(name, null);
 | 
			
		||||
                if (uuid == null) {
 | 
			
		||||
                    uuid =
 | 
			
		||||
                        UUID.nameUUIDFromBytes(("OfflinePlayer:" + name).getBytes(Charsets.UTF_8));
 | 
			
		||||
                }
 | 
			
		||||
                while (new File(container, id.toCommaSeparatedString()).exists()) {
 | 
			
		||||
                    id = Auto.getNextPlotId(id, 1);
 | 
			
		||||
                }
 | 
			
		||||
                File newDir = new File(container, id.toCommaSeparatedString());
 | 
			
		||||
                if (folder.renameTo(newDir)) {
 | 
			
		||||
                    area.getPlot(id).setOwner(uuid);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        player.sendMessage("Done!");
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,17 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugloadtest", permission = "plots.debugloadtest",
 | 
			
		||||
    description = "This debug command will force the reload of all plots in the DB",
 | 
			
		||||
    usage = "/plot debugloadtest", category = CommandCategory.DEBUG,
 | 
			
		||||
    requiredType = RequiredType.CONSOLE) public class DebugLoadTest extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        PlotSquared.get().plots_tmp = DBFunc.getPlots();
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,146 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.IncendoPaster;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.google.gson.JsonObject;
 | 
			
		||||
import com.google.gson.JsonParser;
 | 
			
		||||
import lombok.NonNull;
 | 
			
		||||
 | 
			
		||||
import java.io.BufferedReader;
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.io.FileReader;
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.nio.file.Files;
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugpaste", aliases = "dp", usage = "/plot debugpaste",
 | 
			
		||||
    description = "Upload settings.yml, worlds.yml, PlotSquared.use_THIS.yml and your latest.log to https://incendo.org",
 | 
			
		||||
    permission = "plots.debugpaste", category = CommandCategory.DEBUG) public class DebugPaste
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    private static String readFile(@NonNull final File file) throws IOException {
 | 
			
		||||
        final StringBuilder content = new StringBuilder();
 | 
			
		||||
        final List<String> lines = new ArrayList<>();
 | 
			
		||||
        try (final BufferedReader reader = new BufferedReader(new FileReader(file))) {
 | 
			
		||||
            String line;
 | 
			
		||||
            while ((line = reader.readLine()) != null) {
 | 
			
		||||
                lines.add(line);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        for (int i = Math.max(0, lines.size() - 1000); i < lines.size(); i++) {
 | 
			
		||||
            content.append(lines.get(i)).append("\n");
 | 
			
		||||
        }
 | 
			
		||||
        return content.toString();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        TaskManager.runTaskAsync(() -> {
 | 
			
		||||
            try {
 | 
			
		||||
                final IncendoPaster incendoPaster = new IncendoPaster("plotsquared");
 | 
			
		||||
 | 
			
		||||
                StringBuilder b = new StringBuilder();
 | 
			
		||||
                b.append(
 | 
			
		||||
                    "# Welcome to this paste\n# It is meant to provide us at IntellectualSites with better information about your "
 | 
			
		||||
                        + "problem\n\n");
 | 
			
		||||
                b.append("# Server Information\n");
 | 
			
		||||
                b.append("server.version: ").append(PlotSquared.get().IMP.getServerImplementation())
 | 
			
		||||
                    .append("\n");
 | 
			
		||||
                b.append("online_mode: ").append(UUIDHandler.getUUIDWrapper()).append(';')
 | 
			
		||||
                    .append(!Settings.UUID.OFFLINE).append('\n');
 | 
			
		||||
                b.append("plugins:");
 | 
			
		||||
                for (String id : PlotSquared.get().IMP.getPluginIds()) {
 | 
			
		||||
                    String[] split = id.split(":");
 | 
			
		||||
                    String[] split2 = split[0].split(";");
 | 
			
		||||
                    String enabled = split.length == 2 ? split[1] : "unknown";
 | 
			
		||||
                    String name = split2[0];
 | 
			
		||||
                    String version = split2.length == 2 ? split2[1] : "unknown";
 | 
			
		||||
                    b.append("\n  ").append(name).append(":\n    ").append("version: '")
 | 
			
		||||
                        .append(version).append('\'').append("\n    enabled: ").append(enabled);
 | 
			
		||||
                }
 | 
			
		||||
                b.append("\n\n# YAY! Now, let's see what we can find in your JVM\n");
 | 
			
		||||
                Runtime runtime = Runtime.getRuntime();
 | 
			
		||||
                b.append("memory.free: ").append(runtime.freeMemory()).append('\n');
 | 
			
		||||
                b.append("memory.max: ").append(runtime.maxMemory()).append('\n');
 | 
			
		||||
                b.append("java.specification.version: '")
 | 
			
		||||
                    .append(System.getProperty("java.specification.version")).append("'\n");
 | 
			
		||||
                b.append("java.vendor: '").append(System.getProperty("java.vendor")).append("'\n");
 | 
			
		||||
                b.append("java.version: '").append(System.getProperty("java.version"))
 | 
			
		||||
                    .append("'\n");
 | 
			
		||||
                b.append("os.arch: '").append(System.getProperty("os.arch")).append("'\n");
 | 
			
		||||
                b.append("os.name: '").append(System.getProperty("os.name")).append("'\n");
 | 
			
		||||
                b.append("os.version: '").append(System.getProperty("os.version")).append("'\n\n");
 | 
			
		||||
                b.append("# Okay :D Great. You are now ready to create your bug report!");
 | 
			
		||||
                b.append(
 | 
			
		||||
                    "\n# You can do so at https://github.com/IntellectualSites/PlotSquared/issues");
 | 
			
		||||
                b.append("\n# or via our Discord at https://discord.gg/ngZCzbU");
 | 
			
		||||
 | 
			
		||||
                incendoPaster.addFile(new IncendoPaster.PasteFile("information", b.toString()));
 | 
			
		||||
 | 
			
		||||
                try {
 | 
			
		||||
                    final File logFile =
 | 
			
		||||
                        new File(PlotSquared.get().IMP.getDirectory(), "../../logs/latest.log");
 | 
			
		||||
                    if (Files.size(logFile.toPath()) > 14_000_000) {
 | 
			
		||||
                        throw new IOException("Too big...");
 | 
			
		||||
                    }
 | 
			
		||||
                    incendoPaster
 | 
			
		||||
                        .addFile(new IncendoPaster.PasteFile("latest.log", readFile(logFile)));
 | 
			
		||||
                } catch (IOException ignored) {
 | 
			
		||||
                    MainUtil
 | 
			
		||||
                        .sendMessage(player, "&clatest.log is too big to be pasted, will ignore");
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                try {
 | 
			
		||||
                    incendoPaster.addFile(new IncendoPaster.PasteFile("settings.yml",
 | 
			
		||||
                        readFile(PlotSquared.get().configFile)));
 | 
			
		||||
                } catch (final IllegalArgumentException ignored) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "&cSkipping settings.yml because it's empty");
 | 
			
		||||
                }
 | 
			
		||||
                try {
 | 
			
		||||
                    incendoPaster.addFile(new IncendoPaster.PasteFile("worlds.yml",
 | 
			
		||||
                        readFile(PlotSquared.get().worldsFile)));
 | 
			
		||||
                } catch (final IllegalArgumentException ignored) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "&cSkipping worlds.yml because it's empty");
 | 
			
		||||
                }
 | 
			
		||||
                try {
 | 
			
		||||
                    incendoPaster.addFile(new IncendoPaster.PasteFile("PlotSquared.use_THIS.yml",
 | 
			
		||||
                        readFile(PlotSquared.get().translationFile)));
 | 
			
		||||
                } catch (final IllegalArgumentException ignored) {
 | 
			
		||||
                    MainUtil.sendMessage(player,
 | 
			
		||||
                        "&cSkipping PlotSquared.use_THIS.yml because it's empty");
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                try {
 | 
			
		||||
                    final String rawResponse = incendoPaster.upload();
 | 
			
		||||
                    final JsonObject jsonObject =
 | 
			
		||||
                        new JsonParser().parse(rawResponse).getAsJsonObject();
 | 
			
		||||
 | 
			
		||||
                    if (jsonObject.has("created")) {
 | 
			
		||||
                        final String pasteId = jsonObject.get("paste_id").getAsString();
 | 
			
		||||
                        final String link =
 | 
			
		||||
                            String.format("https://incendo.org/paste/view/%s", pasteId);
 | 
			
		||||
                        player.sendMessage(C.DEBUG_REPORT_CREATED.s().replace("%url%", link));
 | 
			
		||||
                    } else {
 | 
			
		||||
                        final String responseMessage = jsonObject.get("response").getAsString();
 | 
			
		||||
                        MainUtil.sendMessage(player, String
 | 
			
		||||
                            .format("&cFailed to create the debug paste: %s", responseMessage));
 | 
			
		||||
                    }
 | 
			
		||||
                } catch (final Throwable throwable) {
 | 
			
		||||
                    throwable.printStackTrace();
 | 
			
		||||
                    MainUtil.sendMessage(player,
 | 
			
		||||
                        "&cFailed to create the debug paste: " + throwable.getMessage());
 | 
			
		||||
                }
 | 
			
		||||
            } catch (IOException e) {
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,41 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridPlotManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridPlotWorld;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugroadregen", usage = "/plot debugroadregen",
 | 
			
		||||
    requiredType = RequiredType.NONE,
 | 
			
		||||
    description = "Regenerate all roads based on the road schematic",
 | 
			
		||||
    category = CommandCategory.DEBUG, permission = "plots.debugroadregen")
 | 
			
		||||
public class DebugRoadRegen extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        PlotArea plotArea = loc.getPlotArea();
 | 
			
		||||
        if (!(plotArea instanceof HybridPlotWorld)) {
 | 
			
		||||
            return sendMessage(player, C.NOT_IN_PLOT_WORLD);
 | 
			
		||||
        }
 | 
			
		||||
        Plot plot = player.getCurrentPlot();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            C.NOT_IN_PLOT.send(player);
 | 
			
		||||
        } else if (plot.isMerged()) {
 | 
			
		||||
            C.REQUIRES_UNMERGED.send(player);
 | 
			
		||||
        } else {
 | 
			
		||||
            HybridPlotManager manager = (HybridPlotManager) plotArea.getPlotManager();
 | 
			
		||||
            manager.createRoadEast(plotArea, plot);
 | 
			
		||||
            manager.createRoadSouth(plotArea, plot);
 | 
			
		||||
            manager.createRoadSouthEast(plotArea, plot);
 | 
			
		||||
            MainUtil.sendMessage(player, "&6Regenerating plot south/east roads: " + plot.getId()
 | 
			
		||||
                + "\n&6 - Result: &aSuccess");
 | 
			
		||||
            MainUtil.sendMessage(player, "&cTo regenerate all roads: /plot regenallroads");
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,29 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "debugsavetest", permission = "plots.debugsavetest",
 | 
			
		||||
    category = CommandCategory.DEBUG, requiredType = RequiredType.CONSOLE,
 | 
			
		||||
    usage = "/plot debugsavetest",
 | 
			
		||||
    description = "This command will force the recreation of all plots in the DB")
 | 
			
		||||
public class DebugSaveTest extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        ArrayList<Plot> plots = new ArrayList<Plot>();
 | 
			
		||||
        plots.addAll(PlotSquared.get().getPlots());
 | 
			
		||||
        MainUtil.sendMessage(player, "&6Starting `DEBUGSAVETEST`");
 | 
			
		||||
        DBFunc.createPlotsAndData(plots, new Runnable() {
 | 
			
		||||
            @Override public void run() {
 | 
			
		||||
                MainUtil.sendMessage(player, "&6Database sync finished!");
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,71 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "delete", permission = "plots.delete",
 | 
			
		||||
    description = "Delete the plot you stand on", usage = "/plot delete",
 | 
			
		||||
    aliases = {"dispose", "del"}, category = CommandCategory.CLAIMING,
 | 
			
		||||
    requiredType = RequiredType.NONE, confirmation = true) public class Delete extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    // Note: To delete a specific plot use /plot <plot> delete
 | 
			
		||||
    // The syntax also works with any command: /plot <plot> <command>
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        final Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            return !sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_DELETE)) {
 | 
			
		||||
            return !sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
        }
 | 
			
		||||
        final PlotArea plotArea = plot.getArea();
 | 
			
		||||
        final java.util.Set<Plot> plots = plot.getConnectedPlots();
 | 
			
		||||
        final int currentPlots =
 | 
			
		||||
            Settings.Limit.GLOBAL ? player.getPlotCount() : player.getPlotCount(loc.getWorld());
 | 
			
		||||
        Runnable run = new Runnable() {
 | 
			
		||||
            @Override public void run() {
 | 
			
		||||
                if (plot.getRunning() > 0) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                final long start = System.currentTimeMillis();
 | 
			
		||||
                boolean result = plot.deletePlot(new Runnable() {
 | 
			
		||||
                    @Override public void run() {
 | 
			
		||||
                        plot.removeRunning();
 | 
			
		||||
                        if ((EconHandler.manager != null) && plotArea.USE_ECONOMY) {
 | 
			
		||||
                            Expression<Double> valueExr = plotArea.PRICES.get("sell");
 | 
			
		||||
                            double value = plots.size() * valueExr.evaluate((double) currentPlots);
 | 
			
		||||
                            if (value > 0d) {
 | 
			
		||||
                                EconHandler.manager.depositMoney(player, value);
 | 
			
		||||
                                sendMessage(player, C.ADDED_BALANCE, String.valueOf(value));
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                        MainUtil.sendMessage(player, C.DELETING_DONE,
 | 
			
		||||
                            System.currentTimeMillis() - start);
 | 
			
		||||
                    }
 | 
			
		||||
                });
 | 
			
		||||
                if (result) {
 | 
			
		||||
                    plot.addRunning();
 | 
			
		||||
                } else {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
        if (hasConfirmation(player)) {
 | 
			
		||||
            CmdConfirm.addPending(player, getCommandString() + ' ' + plot.getId(), run);
 | 
			
		||||
        } else {
 | 
			
		||||
            TaskManager.runTask(run);
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,114 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Argument;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
import java.util.Iterator;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "deny", aliases = {"d", "ban"},
 | 
			
		||||
    description = "Deny a user from a plot", usage = "/plot deny <player>",
 | 
			
		||||
    category = CommandCategory.SETTINGS, requiredType = RequiredType.NONE) public class Deny
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public Deny() {
 | 
			
		||||
        super(Argument.PlayerName);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
 | 
			
		||||
        Location location = player.getLocation();
 | 
			
		||||
        Plot plot = location.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_DENY)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        Set<UUID> uuids = MainUtil.getUUIDsFromString(args[0]);
 | 
			
		||||
        if (uuids.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.INVALID_PLAYER, args[0]);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Iterator<UUID> iter = uuids.iterator();
 | 
			
		||||
        while (iter.hasNext()) {
 | 
			
		||||
            UUID uuid = iter.next();
 | 
			
		||||
            if (uuid == DBFunc.EVERYONE && !(
 | 
			
		||||
                Permissions.hasPermission(player, C.PERMISSION_DENY_EVERYONE) || Permissions
 | 
			
		||||
                    .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_DENY))) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.INVALID_PLAYER, MainUtil.getName(uuid));
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            if (plot.isOwner(uuid)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.ALREADY_OWNER, MainUtil.getName(uuid));
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            if (plot.getDenied().contains(uuid)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.ALREADY_ADDED, MainUtil.getName(uuid));
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            if (uuid != DBFunc.EVERYONE) {
 | 
			
		||||
                plot.removeMember(uuid);
 | 
			
		||||
                plot.removeTrusted(uuid);
 | 
			
		||||
            }
 | 
			
		||||
            plot.addDenied(uuid);
 | 
			
		||||
            EventUtil.manager.callDenied(player, plot, uuid, true);
 | 
			
		||||
            if (!uuid.equals(DBFunc.EVERYONE)) {
 | 
			
		||||
                handleKick(UUIDHandler.getPlayer(uuid), plot);
 | 
			
		||||
            } else {
 | 
			
		||||
                for (PlotPlayer plotPlayer : plot.getPlayersInPlot()) {
 | 
			
		||||
                    handleKick(plotPlayer, plot);
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (!uuids.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.DENIED_ADDED);
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private void handleKick(PlotPlayer player, Plot plot) {
 | 
			
		||||
        if (player == null) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.equals(player.getCurrentPlot())) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        if (player.hasPermission("plots.admin.entry.denied")) {
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        if (player.getGameMode() == PlotGameMode.SPECTATOR) {
 | 
			
		||||
            player.stopSpectating();
 | 
			
		||||
        }
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        Location spawn = WorldUtil.IMP.getSpawn(loc.getWorld());
 | 
			
		||||
        MainUtil.sendMessage(player, C.YOU_GOT_DENIED);
 | 
			
		||||
        if (plot.equals(spawn.getPlot())) {
 | 
			
		||||
            Location newSpawn =
 | 
			
		||||
                WorldUtil.IMP.getSpawn(PlotSquared.get().getPlotAreaManager().getAllWorlds()[0]);
 | 
			
		||||
            if (plot.equals(newSpawn.getPlot())) {
 | 
			
		||||
                // Kick from server if you can't be teleported to spawn
 | 
			
		||||
                player.kick(C.YOU_GOT_DENIED.s());
 | 
			
		||||
            } else {
 | 
			
		||||
                player.teleport(newSpawn);
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            player.teleport(spawn);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,30 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.FlagManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "setdescription", permission = "plots.set.desc",
 | 
			
		||||
    description = "Set the plot description", usage = "/plot desc <description>",
 | 
			
		||||
    aliases = {"desc", "setdesc", "setd", "description"}, category = CommandCategory.SETTINGS,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Desc extends SetCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean set(PlotPlayer player, Plot plot, String desc) {
 | 
			
		||||
        if (desc.isEmpty()) {
 | 
			
		||||
            plot.removeFlag(Flags.DESCRIPTION);
 | 
			
		||||
            MainUtil.sendMessage(player, C.DESC_UNSET);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        boolean result = FlagManager.addPlotFlag(plot, Flags.DESCRIPTION, desc);
 | 
			
		||||
        if (!result) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.FLAG_NOT_ADDED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, C.DESC_SET);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,68 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.generator.HybridUtils;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.expiry.ExpireManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.expiry.PlotAnalysis;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "done", aliases = {"submit"}, description = "Mark a plot as done",
 | 
			
		||||
    permission = "plots.done", category = CommandCategory.SETTINGS,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Done extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        final Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if ((plot == null) || !plot.hasOwner()) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_DONE)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.hasFlag(Flags.DONE)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.DONE_ALREADY_DONE);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.getRunning() > 0) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        plot.addRunning();
 | 
			
		||||
        MainUtil.sendMessage(player, C.GENERATING_LINK);
 | 
			
		||||
        final Settings.Auto_Clear doneRequirements = Settings.AUTO_CLEAR.get("done");
 | 
			
		||||
        if (ExpireManager.IMP == null || doneRequirements == null) {
 | 
			
		||||
            finish(plot, player, true);
 | 
			
		||||
            plot.removeRunning();
 | 
			
		||||
        } else {
 | 
			
		||||
            HybridUtils.manager.analyzePlot(plot, new RunnableVal<PlotAnalysis>() {
 | 
			
		||||
                @Override public void run(PlotAnalysis value) {
 | 
			
		||||
                    plot.removeRunning();
 | 
			
		||||
                    boolean result =
 | 
			
		||||
                        value.getComplexity(doneRequirements) <= doneRequirements.THRESHOLD;
 | 
			
		||||
                    finish(plot, player, result);
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private void finish(Plot plot, PlotPlayer pp, boolean success) {
 | 
			
		||||
        if (success) {
 | 
			
		||||
            long flagValue = System.currentTimeMillis() / 1000;
 | 
			
		||||
            plot.setFlag(Flags.DONE, flagValue);
 | 
			
		||||
            MainUtil.sendMessage(pp, C.DONE_SUCCESS);
 | 
			
		||||
        } else {
 | 
			
		||||
            MainUtil.sendMessage(pp, C.DONE_INSUFFICIENT_COMPLEXITY);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,95 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
import com.sk89q.jnbt.CompoundTag;
 | 
			
		||||
 | 
			
		||||
import java.net.URL;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(usage = "/plot download [schematic|world]", command = "download",
 | 
			
		||||
    aliases = {"dl"}, category = CommandCategory.SCHEMATIC, requiredType = RequiredType.NONE,
 | 
			
		||||
    description = "Download your plot", permission = "plots.download") public class Download
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        String world = player.getLocation().getWorld();
 | 
			
		||||
        if (!PlotSquared.get().hasPlotArea(world)) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT_WORLD);
 | 
			
		||||
        }
 | 
			
		||||
        final Plot plot = player.getCurrentPlot();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if ((Settings.Done.REQUIRED_FOR_DOWNLOAD && (!plot.getFlag(Flags.DONE).isPresent()))
 | 
			
		||||
            && !Permissions.hasPermission(player, C.PERMISSION_ADMIN_COMMAND_DOWNLOAD)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.DONE_NOT_DONE);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if ((!plot.isOwner(player.getUUID())) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN.s())) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.getRunning() > 0) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (args.length == 0 || (args.length == 1 && StringMan
 | 
			
		||||
            .isEqualIgnoreCaseToAny(args[0], "sch", "schem", "schematic"))) {
 | 
			
		||||
            if (plot.getVolume() > Integer.MAX_VALUE) {
 | 
			
		||||
                C.SCHEMATIC_TOO_LARGE.send(player);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            plot.addRunning();
 | 
			
		||||
            SchematicHandler.manager.getCompoundTag(plot, new RunnableVal<CompoundTag>() {
 | 
			
		||||
                @Override public void run(CompoundTag value) {
 | 
			
		||||
                    plot.removeRunning();
 | 
			
		||||
                    SchematicHandler.manager.upload(value, null, null, new RunnableVal<URL>() {
 | 
			
		||||
                        @Override public void run(URL url) {
 | 
			
		||||
                            if (url == null) {
 | 
			
		||||
                                MainUtil.sendMessage(player, C.GENERATING_LINK_FAILED);
 | 
			
		||||
                                return;
 | 
			
		||||
                            }
 | 
			
		||||
                            MainUtil.sendMessage(player, url.toString());
 | 
			
		||||
                        }
 | 
			
		||||
                    });
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
        } else if (args.length == 1 && StringMan
 | 
			
		||||
            .isEqualIgnoreCaseToAny(args[0], "mcr", "world", "mca")) {
 | 
			
		||||
            if (!Permissions.hasPermission(player, C.PERMISSION_DOWNLOAD_WORLD)) {
 | 
			
		||||
                C.NO_PERMISSION.send(player, C.PERMISSION_DOWNLOAD_WORLD);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            MainUtil.sendMessage(player, "&cNote: The `.mca` files are 512x512");
 | 
			
		||||
            plot.addRunning();
 | 
			
		||||
            WorldUtil.IMP.saveWorld(world);
 | 
			
		||||
            WorldUtil.IMP.upload(plot, null, null, new RunnableVal<URL>() {
 | 
			
		||||
                @Override public void run(URL url) {
 | 
			
		||||
                    plot.removeRunning();
 | 
			
		||||
                    if (url == null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.GENERATING_LINK_FAILED);
 | 
			
		||||
                        return;
 | 
			
		||||
                    }
 | 
			
		||||
                    MainUtil.sendMessage(player, url.toString());
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
        } else {
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, C.GENERATING_LINK);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,299 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotBlock;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
import java.util.*;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "setflag", aliases = {"f", "flag", "setf", "setflag"},
 | 
			
		||||
    usage = "/plot flag <set|remove|add|list|info> <flag> <value>", description = "Set plot flags",
 | 
			
		||||
    category = CommandCategory.SETTINGS, requiredType = RequiredType.NONE,
 | 
			
		||||
    permission = "plots.flag") public class FlagCmd extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    private boolean checkPermValue(PlotPlayer player, Flag flag, String key, String value) {
 | 
			
		||||
        key = key.toLowerCase();
 | 
			
		||||
        value = value.toLowerCase();
 | 
			
		||||
        String perm = C.PERMISSION_SET_FLAG_KEY_VALUE.f(key.toLowerCase(), value.toLowerCase());
 | 
			
		||||
        if (flag instanceof IntegerFlag && MathMan.isInteger(value)) {
 | 
			
		||||
            try {
 | 
			
		||||
                int numeric = Integer.parseInt(value);
 | 
			
		||||
                perm = perm.substring(0, perm.length() - value.length() - 1);
 | 
			
		||||
                if (numeric > 0) {
 | 
			
		||||
                    int checkRange = PlotSquared.get().getPlatform().equalsIgnoreCase("bukkit") ?
 | 
			
		||||
                        numeric :
 | 
			
		||||
                        Settings.Limit.MAX_PLOTS;
 | 
			
		||||
                    final boolean result = player.hasPermissionRange(perm, checkRange) >= numeric;
 | 
			
		||||
                    if (!result) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_SET_FLAG_KEY_VALUE
 | 
			
		||||
                                .f(key.toLowerCase(), value.toLowerCase()));
 | 
			
		||||
                    }
 | 
			
		||||
                    return result;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
            } catch (NumberFormatException ignore) {
 | 
			
		||||
            }
 | 
			
		||||
        } else if (flag instanceof PlotBlockListFlag) {
 | 
			
		||||
            final PlotBlockListFlag blockListFlag = (PlotBlockListFlag) flag;
 | 
			
		||||
            final HashSet<PlotBlock> parsedBlocks = blockListFlag.parseValue(value);
 | 
			
		||||
            for (final PlotBlock block : parsedBlocks) {
 | 
			
		||||
                final String permission = C.PERMISSION_SET_FLAG_KEY_VALUE
 | 
			
		||||
                    .f(key.toLowerCase(), block.getRawId().toString().toLowerCase());
 | 
			
		||||
                final boolean result = Permissions.hasPermission(player, permission);
 | 
			
		||||
                if (!result) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                        C.PERMISSION_SET_FLAG_KEY_VALUE.f(key.toLowerCase(), value.toLowerCase()));
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        final boolean result = Permissions.hasPermission(player, perm);
 | 
			
		||||
        if (!result) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                C.PERMISSION_SET_FLAG_KEY_VALUE.f(key.toLowerCase(), value.toLowerCase()));
 | 
			
		||||
        }
 | 
			
		||||
        return result;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
 | 
			
		||||
        /*
 | 
			
		||||
         *  plot flag set fly true
 | 
			
		||||
         *  plot flag remove fly
 | 
			
		||||
         *  plot flag remove use 1,3
 | 
			
		||||
         *  plot flag add use 2,4
 | 
			
		||||
         *  plot flag list
 | 
			
		||||
         */
 | 
			
		||||
        if (args.length == 0) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot flag <set|remove|add|list|info>");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            sendMessage(player, C.PLOT_NOT_CLAIMED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_SET_FLAG_OTHER)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_SET_FLAG_OTHER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Flag<?> flag = null;
 | 
			
		||||
        if (args.length > 1) {
 | 
			
		||||
            flag = FlagManager.getFlag(args[1]);
 | 
			
		||||
            if (flag == null || flag.isReserved()) {
 | 
			
		||||
                boolean suggested = false;
 | 
			
		||||
                try {
 | 
			
		||||
                    StringComparison<Flag<?>> stringComparison =
 | 
			
		||||
                        new StringComparison<>(args[1], Flags.getFlags());
 | 
			
		||||
                    String best = stringComparison.getBestMatch();
 | 
			
		||||
                    if (best != null) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NOT_VALID_FLAG_SUGGESTED, best);
 | 
			
		||||
                        suggested = true;
 | 
			
		||||
                    }
 | 
			
		||||
                } catch (final Exception ignored) { /* Happens sometimes because of mean code */ }
 | 
			
		||||
                if (!suggested) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NOT_VALID_FLAG);
 | 
			
		||||
                }
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        switch (args[0].toLowerCase()) {
 | 
			
		||||
            case "info": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_SET_FLAG)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, "plots.flag.info");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 2) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot flag info <flag>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                // flag key
 | 
			
		||||
                MainUtil.sendMessage(player, C.FLAG_KEY, flag.getName());
 | 
			
		||||
                // flag type
 | 
			
		||||
                MainUtil.sendMessage(player, C.FLAG_TYPE, flag.getClass().getSimpleName());
 | 
			
		||||
                // Flag type description
 | 
			
		||||
                MainUtil.sendMessage(player, C.FLAG_DESC, flag.getValueDescription());
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "set": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_SET_FLAG)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_SET_FLAG);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length < 3) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot flag set <flag> <value>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                String value = StringMan.join(Arrays.copyOfRange(args, 2, args.length), " ");
 | 
			
		||||
                if (!checkPermValue(player, flag, args[1], value)) {
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Object parsed = flag.parseValue(value);
 | 
			
		||||
                if (parsed == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "&c" + flag.getValueDescription());
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                boolean result = plot.setFlag(flag, parsed);
 | 
			
		||||
                if (!result) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.FLAG_NOT_ADDED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.FLAG_ADDED);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "remove": {
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_FLAG_REMOVE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_FLAG_REMOVE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length != 2 && args.length != 3) {
 | 
			
		||||
                    MainUtil
 | 
			
		||||
                        .sendMessage(player, C.COMMAND_SYNTAX, "/plot flag remove <flag> [values]");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!Permissions
 | 
			
		||||
                    .hasPermission(player, C.PERMISSION_SET_FLAG_KEY.f(args[1].toLowerCase()))) {
 | 
			
		||||
                    if (args.length != 3) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_SET_FLAG_KEY.f(args[1].toLowerCase()));
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    for (String entry : args[2].split(",")) {
 | 
			
		||||
                        if (!checkPermValue(player, flag, args[1], entry)) {
 | 
			
		||||
                            return false;
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length == 3 && flag instanceof ListFlag) {
 | 
			
		||||
                    String value = StringMan.join(Arrays.copyOfRange(args, 2, args.length), " ");
 | 
			
		||||
                    Optional<? extends Collection> flag1 =
 | 
			
		||||
                        plot.getFlag((Flag<? extends Collection<?>>) flag);
 | 
			
		||||
                    if (flag1.isPresent()) {
 | 
			
		||||
                        boolean o = flag1.get().removeAll((Collection) flag.parseValue(value));
 | 
			
		||||
                        if (o) {
 | 
			
		||||
                            if (flag1.get().isEmpty()) {
 | 
			
		||||
                                final boolean result = plot.removeFlag(flag);
 | 
			
		||||
                                if (result) {
 | 
			
		||||
                                    MainUtil.sendMessage(player, C.FLAG_REMOVED);
 | 
			
		||||
                                } else {
 | 
			
		||||
                                    MainUtil.sendMessage(player, C.FLAG_NOT_REMOVED);
 | 
			
		||||
                                }
 | 
			
		||||
                                return true;
 | 
			
		||||
                            } else {
 | 
			
		||||
                                MainUtil.sendMessage(player, C.FLAG_REMOVED);
 | 
			
		||||
                            }
 | 
			
		||||
                        } else {
 | 
			
		||||
                            MainUtil.sendMessage(player, C.FLAG_NOT_REMOVED);
 | 
			
		||||
                            return false;
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    DBFunc.setFlags(plot, plot.getFlags());
 | 
			
		||||
                    return true;
 | 
			
		||||
                } else {
 | 
			
		||||
                    boolean result = plot.removeFlag(flag);
 | 
			
		||||
                    if (!result) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.FLAG_NOT_REMOVED);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                if (flag == Flags.TIME) {
 | 
			
		||||
                    player.setTime(Long.MAX_VALUE);
 | 
			
		||||
                } else if (flag == Flags.WEATHER) {
 | 
			
		||||
                    player.setWeather(PlotWeather.RESET);
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.FLAG_REMOVED);
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            case "add":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_FLAG_ADD)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_FLAG_ADD);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length < 3) {
 | 
			
		||||
                    MainUtil
 | 
			
		||||
                        .sendMessage(player, C.COMMAND_SYNTAX, "/plot flag add <flag> <values>");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                for (String entry : args[2].split(",")) {
 | 
			
		||||
                    if (!checkPermValue(player, flag, args[1], entry)) {
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                String value = StringMan.join(Arrays.copyOfRange(args, 2, args.length), " ");
 | 
			
		||||
                Object parsed = flag.parseValue(value);
 | 
			
		||||
                if (parsed == null) {
 | 
			
		||||
                    MainUtil.sendMessage(player, "&c" + flag.getValueDescription());
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                Object val = parsed;
 | 
			
		||||
                if (flag instanceof ListFlag) {
 | 
			
		||||
                    Optional<? extends Collection> flag1 =
 | 
			
		||||
                        plot.getFlag((Flag<? extends Collection<?>>) flag);
 | 
			
		||||
                    if (flag1.isPresent()) {
 | 
			
		||||
                        boolean o = flag1.get().addAll((Collection) parsed);
 | 
			
		||||
                        if (o) {
 | 
			
		||||
                            MainUtil.sendMessage(player, C.FLAG_ADDED);
 | 
			
		||||
                            val = flag1.get();
 | 
			
		||||
                        } else {
 | 
			
		||||
                            MainUtil.sendMessage(player, C.FLAG_NOT_ADDED);
 | 
			
		||||
                            return false;
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                boolean result = plot.setFlag(flag, val);
 | 
			
		||||
                if (!result) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.FLAG_NOT_ADDED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.FLAG_ADDED);
 | 
			
		||||
                return true;
 | 
			
		||||
            case "list":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_FLAG_LIST)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_FLAG_LIST);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length > 1) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot flag list");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                HashMap<String, ArrayList<String>> flags = new HashMap<>();
 | 
			
		||||
                for (Flag<?> flag1 : Flags.getFlags()) {
 | 
			
		||||
                    String type = flag1.getClass().getSimpleName();
 | 
			
		||||
                    if (!flags.containsKey(type)) {
 | 
			
		||||
                        flags.put(type, new ArrayList<>());
 | 
			
		||||
                    }
 | 
			
		||||
                    flags.get(type).add(flag1.getName());
 | 
			
		||||
                }
 | 
			
		||||
                StringBuilder message = new StringBuilder();
 | 
			
		||||
                String prefix = "";
 | 
			
		||||
                for (Map.Entry<String, ArrayList<String>> entry : flags.entrySet()) {
 | 
			
		||||
                    String category = entry.getKey();
 | 
			
		||||
                    List<String> flagNames = entry.getValue();
 | 
			
		||||
                    Collections.sort(flagNames);
 | 
			
		||||
                    message.append(prefix).append("&6").append(category).append(": &7")
 | 
			
		||||
                        .append(StringMan.join(flagNames, ", "));
 | 
			
		||||
                    prefix = "\n";
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, message.toString());
 | 
			
		||||
                return true;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot flag <set|remove|add|list|info>");
 | 
			
		||||
        return false;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,221 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
 | 
			
		||||
import java.io.File;
 | 
			
		||||
import java.io.IOException;
 | 
			
		||||
import java.nio.charset.StandardCharsets;
 | 
			
		||||
import java.nio.file.Files;
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.HashSet;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.regex.Matcher;
 | 
			
		||||
import java.util.regex.Pattern;
 | 
			
		||||
 | 
			
		||||
public class GenerateDocs {
 | 
			
		||||
 | 
			
		||||
    public static void main(String[] args) {
 | 
			
		||||
        new WE_Anywhere();
 | 
			
		||||
        List<Command> commands = MainCommand.getInstance().getCommands();
 | 
			
		||||
        GenerateDocs.log("### Want to document some commands?");
 | 
			
		||||
        GenerateDocs.log(" - This page is automatically generated");
 | 
			
		||||
        GenerateDocs
 | 
			
		||||
            .log(" - Fork the project and add a javadoc comment to one of the command classes");
 | 
			
		||||
        GenerateDocs.log(" - Then do a pull request and it will be added to this page");
 | 
			
		||||
        GenerateDocs.log("");
 | 
			
		||||
        GenerateDocs.log("# Contents");
 | 
			
		||||
        for (CommandCategory category : CommandCategory.values()) {
 | 
			
		||||
            GenerateDocs.log("###### " + category.name());
 | 
			
		||||
            for (Command command : MainCommand.getInstance().getCommands(category, null)) {
 | 
			
		||||
                GenerateDocs.log(" - [/plot " + command.getId()
 | 
			
		||||
                    + "](https://github.com/IntellectualSites/PlotSquared/wiki/Commands#" + command
 | 
			
		||||
                    .getId() + ")    ");
 | 
			
		||||
            }
 | 
			
		||||
            GenerateDocs.log("");
 | 
			
		||||
        }
 | 
			
		||||
        GenerateDocs.log("# Commands");
 | 
			
		||||
        for (Command command : commands) {
 | 
			
		||||
            GenerateDocs.printCommand(command);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static void printCommand(Command command) {
 | 
			
		||||
        try {
 | 
			
		||||
            String clazz = command.getClass().getSimpleName();
 | 
			
		||||
            String name = command.getId();
 | 
			
		||||
 | 
			
		||||
            // Header
 | 
			
		||||
            String source =
 | 
			
		||||
                "https://github.com/IntellectualSites/PlotSquared/tree/master/Core/src/main/java/com/intellectualcrafters/plot/commands/"
 | 
			
		||||
                    + clazz + ".java";
 | 
			
		||||
            GenerateDocs.log("## [" + name.toUpperCase() + "](" + source + ")    ");
 | 
			
		||||
 | 
			
		||||
            File file = new File(
 | 
			
		||||
                "Core/src/main/java/com/intellectualcrafters/plot/commands/" + clazz + ".java");
 | 
			
		||||
            List<String> lines = Files.readAllLines(file.toPath(), StandardCharsets.UTF_8);
 | 
			
		||||
            List<String> perms = GenerateDocs.getPerms(name, lines);
 | 
			
		||||
            List<String> usages = GenerateDocs.getUsage(name, lines);
 | 
			
		||||
            String comment = GenerateDocs.getComments(lines);
 | 
			
		||||
 | 
			
		||||
            GenerateDocs.log("#### Description");
 | 
			
		||||
            GenerateDocs.log('`' + command.getDescription() + '`');
 | 
			
		||||
            if (!comment.isEmpty()) {
 | 
			
		||||
                GenerateDocs.log("##### Comments");
 | 
			
		||||
                GenerateDocs.log("``` java");
 | 
			
		||||
                GenerateDocs.log(comment);
 | 
			
		||||
                GenerateDocs.log("```");
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            GenerateDocs.log("#### Usage    ");
 | 
			
		||||
            String mainUsage = command.getUsage().replaceAll("\\{label\\}", "plot");
 | 
			
		||||
            if (!usages.isEmpty() && !usages.get(0).equalsIgnoreCase(mainUsage)) {
 | 
			
		||||
                GenerateDocs.log("##### Primary    ");
 | 
			
		||||
                GenerateDocs.log(" - `" + mainUsage + "`    ");
 | 
			
		||||
                GenerateDocs.log("");
 | 
			
		||||
                GenerateDocs.log("##### Other    ");
 | 
			
		||||
                GenerateDocs.log(" - `" + StringMan.join(usages, "`\n - `") + "`    ");
 | 
			
		||||
                GenerateDocs.log("");
 | 
			
		||||
            } else {
 | 
			
		||||
                GenerateDocs.log('`' + mainUsage + "`    ");
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            if (command.getRequiredType() != RequiredType.NONE) {
 | 
			
		||||
                GenerateDocs.log("#### Required callers");
 | 
			
		||||
                GenerateDocs.log('`' + command.getRequiredType().name() + '`');
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            List<String> aliases = command.getAliases();
 | 
			
		||||
            if (!aliases.isEmpty()) {
 | 
			
		||||
                GenerateDocs.log("#### Aliases");
 | 
			
		||||
                GenerateDocs.log('`' + StringMan.getString(command.getAliases()) + '`');
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            GenerateDocs.log("#### Permissions");
 | 
			
		||||
            if (!perms.isEmpty()) {
 | 
			
		||||
                GenerateDocs.log("##### Primary");
 | 
			
		||||
                GenerateDocs.log(" - `" + command.getPermission() + "`    ");
 | 
			
		||||
                GenerateDocs.log("");
 | 
			
		||||
                GenerateDocs.log("##### Other");
 | 
			
		||||
                GenerateDocs.log(" - `" + StringMan.join(perms, "`\n - `") + '`');
 | 
			
		||||
                GenerateDocs.log("");
 | 
			
		||||
            } else {
 | 
			
		||||
                GenerateDocs.log('`' + command.getPermission() + "`    ");
 | 
			
		||||
            }
 | 
			
		||||
            GenerateDocs.log("***");
 | 
			
		||||
            GenerateDocs.log("");
 | 
			
		||||
        } catch (IOException e) {
 | 
			
		||||
            e.printStackTrace();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static List<String> getUsage(String cmd, List<String> lines) {
 | 
			
		||||
        Pattern p = Pattern.compile("\"([^\"]*)\"");
 | 
			
		||||
        HashSet<String> usages = new HashSet<>();
 | 
			
		||||
        for (String line : lines) {
 | 
			
		||||
            if (line.contains("COMMAND_SYNTAX") && !line.contains("getUsage()")) {
 | 
			
		||||
                Matcher m = p.matcher(line);
 | 
			
		||||
                String prefix = "";
 | 
			
		||||
                StringBuilder usage = new StringBuilder();
 | 
			
		||||
                while (m.find()) {
 | 
			
		||||
                    String match = m.group(1);
 | 
			
		||||
                    usage.append(prefix).append(match);
 | 
			
		||||
                    prefix = " <arg> ";
 | 
			
		||||
                }
 | 
			
		||||
                if (usage.length() != 0) {
 | 
			
		||||
                    usages.add(usage.toString().trim().replaceAll("  ", " ")
 | 
			
		||||
                        .replaceAll("\\{label\\}", "plot"));
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return new ArrayList<>(usages);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static List<String> getPerms(String cmd, List<String> lines) {
 | 
			
		||||
        HashSet<String> perms = new HashSet<>();
 | 
			
		||||
        Pattern p = Pattern.compile("\"([^\"]*)\"");
 | 
			
		||||
        Pattern p2 = Pattern.compile("C.PERMISSION_\\s*(\\w+)");
 | 
			
		||||
        String last = null;
 | 
			
		||||
        for (String line : lines) {
 | 
			
		||||
 | 
			
		||||
            Matcher m2 = p2.matcher(line);
 | 
			
		||||
            while (m2.find()) {
 | 
			
		||||
                perms.add(C.valueOf("PERMISSION_" + m2.group(1)).s());
 | 
			
		||||
            }
 | 
			
		||||
            if (line.contains("Permissions.hasPermission(")) {
 | 
			
		||||
                String[] split = line.split("Permissions.hasPermission");
 | 
			
		||||
                split = Arrays.copyOfRange(split, 1, split.length);
 | 
			
		||||
                for (String method : split) {
 | 
			
		||||
                    String perm = method.split("[,|)]")[1].trim();
 | 
			
		||||
                    if (!perm.equalsIgnoreCase(perm)) {
 | 
			
		||||
                        if (perm.startsWith("C.")) {
 | 
			
		||||
                            perm = C.valueOf(perm.split("\\.")[1]).s();
 | 
			
		||||
                        } else {
 | 
			
		||||
                            continue;
 | 
			
		||||
                        }
 | 
			
		||||
                    } else {
 | 
			
		||||
                        perm = perm.substring(1, perm.length() - 1);
 | 
			
		||||
                    }
 | 
			
		||||
                    perms.add(perm);
 | 
			
		||||
                }
 | 
			
		||||
                Matcher m = p.matcher(line);
 | 
			
		||||
                while (m.find()) {
 | 
			
		||||
                    String perm = m.group(1);
 | 
			
		||||
                    if (perm.endsWith(".")) {
 | 
			
		||||
                        perm += "<arg>";
 | 
			
		||||
                    }
 | 
			
		||||
                    if (perm.startsWith(".")) {
 | 
			
		||||
                        perms.remove(last);
 | 
			
		||||
                        perms.add(last + perm);
 | 
			
		||||
                    } else if (perm.contains(".")) {
 | 
			
		||||
                        last = perm;
 | 
			
		||||
                        perms.add(perm);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            } else if (line.contains("Permissions.hasPermissionRange")) {
 | 
			
		||||
                String[] split = line.split("Permissions.hasPermissionRange");
 | 
			
		||||
                split = Arrays.copyOfRange(split, 1, split.length);
 | 
			
		||||
                for (String method : split) {
 | 
			
		||||
                    String perm = method.split("[,|)]")[1].trim();
 | 
			
		||||
                    if (!perm.equalsIgnoreCase(perm)) {
 | 
			
		||||
                        if (perm.startsWith("C.")) {
 | 
			
		||||
                            perm = C.valueOf(perm.split("\\.")[1]).s();
 | 
			
		||||
                        } else {
 | 
			
		||||
                            continue;
 | 
			
		||||
                        }
 | 
			
		||||
                    } else {
 | 
			
		||||
                        perm = perm.substring(1, perm.length() - 1);
 | 
			
		||||
                    }
 | 
			
		||||
                    perms.add(perm + ".<#>");
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        switch (cmd.toLowerCase()) {
 | 
			
		||||
            case "auto":
 | 
			
		||||
            case "claim":
 | 
			
		||||
                perms.add("plots.plot.<#>");
 | 
			
		||||
                break;
 | 
			
		||||
        }
 | 
			
		||||
        return new ArrayList<>(perms);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static String getComments(List<String> lines) {
 | 
			
		||||
        StringBuilder result = new StringBuilder();
 | 
			
		||||
        for (String line : lines) {
 | 
			
		||||
            line = line.trim();
 | 
			
		||||
            if (line.startsWith("/** ") || line.startsWith("*/ ") || line.startsWith("* ")) {
 | 
			
		||||
                line =
 | 
			
		||||
                    line.replaceAll("/[*][*] ", "").replaceAll("[*]/ ", "").replaceAll("[*] ", "")
 | 
			
		||||
                        .trim();
 | 
			
		||||
                result.append(line + '\n');
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return result.toString().trim();
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static void log(String s) {
 | 
			
		||||
        System.out.println(s);
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,71 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.ByteArrayUtilities;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "grant", category = CommandCategory.CLAIMING,
 | 
			
		||||
    usage = "/plot grant <check|add> [player]", permission = "plots.grant",
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Grant extends Command {
 | 
			
		||||
 | 
			
		||||
    public Grant() {
 | 
			
		||||
        super(MainCommand.getInstance(), true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(final PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) throws CommandException {
 | 
			
		||||
        checkTrue(args.length >= 1 && args.length <= 2, C.COMMAND_SYNTAX, getUsage());
 | 
			
		||||
        final String arg0 = args[0].toLowerCase();
 | 
			
		||||
        switch (arg0) {
 | 
			
		||||
            case "add":
 | 
			
		||||
            case "check":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_GRANT.f(arg0))) {
 | 
			
		||||
                    C.NO_PERMISSION.send(player, C.PERMISSION_GRANT.f(arg0));
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length > 2) {
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                final UUID uuid =
 | 
			
		||||
                    args.length == 2 ? UUIDHandler.getUUIDFromString(args[1]) : player.getUUID();
 | 
			
		||||
                if (uuid == null) {
 | 
			
		||||
                    C.INVALID_PLAYER.send(player, args[1]);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.getPersistentMeta(uuid, "grantedPlots", new RunnableVal<byte[]>() {
 | 
			
		||||
                    @Override public void run(byte[] array) {
 | 
			
		||||
                        if (arg0.equals("check")) { // check
 | 
			
		||||
                            int granted =
 | 
			
		||||
                                array == null ? 0 : ByteArrayUtilities.bytesToInteger(array);
 | 
			
		||||
                            C.GRANTED_PLOTS.send(player, granted);
 | 
			
		||||
                        } else { // add
 | 
			
		||||
                            int amount =
 | 
			
		||||
                                1 + (array == null ? 0 : ByteArrayUtilities.bytesToInteger(array));
 | 
			
		||||
                            boolean replace = array != null;
 | 
			
		||||
                            String key = "grantedPlots";
 | 
			
		||||
                            byte[] rawData = ByteArrayUtilities.integerToBytes(amount);
 | 
			
		||||
                            PlotPlayer online = UUIDHandler.getPlayer(uuid);
 | 
			
		||||
                            if (online != null) {
 | 
			
		||||
                                online.setPersistentMeta(key, rawData);
 | 
			
		||||
                            } else {
 | 
			
		||||
                                DBFunc.addPersistentMeta(uuid, key, rawData, replace);
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                });
 | 
			
		||||
        }
 | 
			
		||||
        C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,91 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MathMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.helpmenu.HelpMenu;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "help", description = "Get this help menu", aliases = {"he", "?"},
 | 
			
		||||
    category = CommandCategory.INFO, usage = "help [category|#]", permission = "plots.use")
 | 
			
		||||
public class Help extends Command {
 | 
			
		||||
    public Help(Command parent) {
 | 
			
		||||
        super(parent, true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean canExecute(PlotPlayer player, boolean message) {
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) {
 | 
			
		||||
        switch (args.length) {
 | 
			
		||||
            case 0:
 | 
			
		||||
                displayHelp(player, null, 0);
 | 
			
		||||
                return;
 | 
			
		||||
            case 1:
 | 
			
		||||
                if (MathMan.isInteger(args[0])) {
 | 
			
		||||
                    try {
 | 
			
		||||
                        displayHelp(player, null, Integer.parseInt(args[0]));
 | 
			
		||||
                    } catch (NumberFormatException ignored) {
 | 
			
		||||
                        displayHelp(player, null, 1);
 | 
			
		||||
                    }
 | 
			
		||||
                } else {
 | 
			
		||||
                    displayHelp(player, args[0], 1);
 | 
			
		||||
                }
 | 
			
		||||
                return;
 | 
			
		||||
            case 2:
 | 
			
		||||
                if (MathMan.isInteger(args[1])) {
 | 
			
		||||
                    try {
 | 
			
		||||
                        displayHelp(player, args[0], Integer.parseInt(args[1]));
 | 
			
		||||
                    } catch (NumberFormatException ignored) {
 | 
			
		||||
                        displayHelp(player, args[0], 1);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                return;
 | 
			
		||||
            default:
 | 
			
		||||
                C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void displayHelp(PlotPlayer player, String cat, int page) {
 | 
			
		||||
        CommandCategory catEnum = null;
 | 
			
		||||
        if (cat != null) {
 | 
			
		||||
            if (!StringMan.isEqualIgnoreCase(cat, "all")) {
 | 
			
		||||
                for (CommandCategory c : CommandCategory.values()) {
 | 
			
		||||
                    if (StringMan.isEqualIgnoreCaseToAny(cat, c.name(), c.toString())) {
 | 
			
		||||
                        catEnum = c;
 | 
			
		||||
                        cat = c.name();
 | 
			
		||||
                        break;
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                if (catEnum == null) {
 | 
			
		||||
                    cat = null;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (cat == null && page == 0) {
 | 
			
		||||
            StringBuilder builder = new StringBuilder();
 | 
			
		||||
            builder.append(C.HELP_HEADER.s());
 | 
			
		||||
            for (CommandCategory c : CommandCategory.values()) {
 | 
			
		||||
                builder.append("\n" + StringMan
 | 
			
		||||
                    .replaceAll(C.HELP_INFO_ITEM.s(), "%category%", c.toString().toLowerCase(),
 | 
			
		||||
                        "%category_desc%", c.toString()));
 | 
			
		||||
            }
 | 
			
		||||
            builder.append("\n").append(C.HELP_INFO_ITEM.s().replaceAll("%category%", "all")
 | 
			
		||||
                .replaceAll("%category_desc%", "Display all commands"));
 | 
			
		||||
            builder.append("\n" + C.HELP_FOOTER.s());
 | 
			
		||||
            MainUtil.sendMessage(player, builder.toString(), false);
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        page--;
 | 
			
		||||
        new HelpMenu(player).setCategory(catEnum).getCommands().generateMaxPages()
 | 
			
		||||
            .generatePage(page, getParent().toString()).render();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,198 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.comment.CommentInbox;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.comment.PlotComment;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.CommentManager;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.StringMan;
 | 
			
		||||
 | 
			
		||||
import java.util.ArrayList;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
import java.util.Optional;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "inbox", description = "Review the comments for a plot",
 | 
			
		||||
    usage = "/plot inbox [inbox] [delete <index>|clear|page]", permission = "plots.inbox",
 | 
			
		||||
    category = CommandCategory.CHAT, requiredType = RequiredType.NONE) public class Inbox
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public void displayComments(PlotPlayer player, List<PlotComment> oldComments, int page) {
 | 
			
		||||
        if (oldComments == null || oldComments.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.INBOX_EMPTY);
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
        PlotComment[] comments = oldComments.toArray(new PlotComment[oldComments.size()]);
 | 
			
		||||
        if (page < 0) {
 | 
			
		||||
            page = 0;
 | 
			
		||||
        }
 | 
			
		||||
        // Get the total pages
 | 
			
		||||
        // int totalPages = ((int) Math.ceil(12 *
 | 
			
		||||
        int totalPages = (int) Math.ceil(comments.length / 12);
 | 
			
		||||
        if (page > totalPages) {
 | 
			
		||||
            page = totalPages;
 | 
			
		||||
        }
 | 
			
		||||
        // Only display 12 per page
 | 
			
		||||
        int max = page * 12 + 12;
 | 
			
		||||
        if (max > comments.length) {
 | 
			
		||||
            max = comments.length;
 | 
			
		||||
        }
 | 
			
		||||
        StringBuilder string = new StringBuilder();
 | 
			
		||||
        string.append(StringMan
 | 
			
		||||
            .replaceAll(C.COMMENT_LIST_HEADER_PAGED.s(), "%amount%", comments.length, "%cur",
 | 
			
		||||
                page + 1, "%max", totalPages + 1, "%word", "all") + '\n');
 | 
			
		||||
 | 
			
		||||
        // This might work xD
 | 
			
		||||
        for (int x = page * 12; x < max; x++) {
 | 
			
		||||
            PlotComment comment = comments[x];
 | 
			
		||||
            String color;
 | 
			
		||||
            if (player.getName().equals(comment.senderName)) {
 | 
			
		||||
                color = "&a";
 | 
			
		||||
            } else {
 | 
			
		||||
                color = "&7";
 | 
			
		||||
            }
 | 
			
		||||
            string.append("&8[&7#").append(x + 1).append("&8][&7").append(comment.world).append(';')
 | 
			
		||||
                .append(comment.id).append("&8][&6").append(comment.senderName).append("&8]")
 | 
			
		||||
                .append(color).append(comment.comment).append('\n');
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, string.toString());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        final Plot plot = player.getCurrentPlot();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (args.length == 0) {
 | 
			
		||||
            sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                "/plot inbox [inbox] [delete <index>|clear|page]");
 | 
			
		||||
            for (final CommentInbox inbox : CommentManager.inboxes.values()) {
 | 
			
		||||
                if (inbox.canRead(plot, player)) {
 | 
			
		||||
                    if (!inbox.getComments(plot, new RunnableVal<List<PlotComment>>() {
 | 
			
		||||
                        @Override public void run(List<PlotComment> value) {
 | 
			
		||||
                            if (value != null) {
 | 
			
		||||
                                int total = 0;
 | 
			
		||||
                                int unread = 0;
 | 
			
		||||
                                for (PlotComment comment : value) {
 | 
			
		||||
                                    total++;
 | 
			
		||||
                                    if (comment.timestamp > CommentManager
 | 
			
		||||
                                        .getTimestamp(player, inbox.toString())) {
 | 
			
		||||
                                        unread++;
 | 
			
		||||
                                    }
 | 
			
		||||
                                }
 | 
			
		||||
                                if (total != 0) {
 | 
			
		||||
                                    String color;
 | 
			
		||||
                                    if (unread > 0) {
 | 
			
		||||
                                        color = "&c";
 | 
			
		||||
                                    } else {
 | 
			
		||||
                                        color = "";
 | 
			
		||||
                                    }
 | 
			
		||||
                                    sendMessage(player, C.INBOX_ITEM,
 | 
			
		||||
                                        color + inbox.toString() + " (" + total + '/' + unread
 | 
			
		||||
                                            + ')');
 | 
			
		||||
                                    return;
 | 
			
		||||
                                }
 | 
			
		||||
                            }
 | 
			
		||||
                            sendMessage(player, C.INBOX_ITEM, inbox.toString());
 | 
			
		||||
                        }
 | 
			
		||||
                    })) {
 | 
			
		||||
                        sendMessage(player, C.INBOX_ITEM, inbox.toString());
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        final CommentInbox inbox = CommentManager.inboxes.get(args[0].toLowerCase());
 | 
			
		||||
        if (inbox == null) {
 | 
			
		||||
            sendMessage(player, C.INVALID_INBOX,
 | 
			
		||||
                StringMan.join(CommentManager.inboxes.keySet(), ", "));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        player.setMeta("inbox:" + inbox.toString(), System.currentTimeMillis());
 | 
			
		||||
        final int page;
 | 
			
		||||
        if (args.length > 1) {
 | 
			
		||||
            switch (args[1].toLowerCase()) {
 | 
			
		||||
                case "delete":
 | 
			
		||||
                    if (!inbox.canModify(plot, player)) {
 | 
			
		||||
                        sendMessage(player, C.NO_PERM_INBOX_MODIFY);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    if (args.length != 3) {
 | 
			
		||||
                        sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                            "/plot inbox " + inbox.toString() + " delete <index>");
 | 
			
		||||
                    }
 | 
			
		||||
                    final int index;
 | 
			
		||||
                    try {
 | 
			
		||||
                        index = Integer.parseInt(args[2]);
 | 
			
		||||
                        if (index < 1) {
 | 
			
		||||
                            sendMessage(player, C.NOT_VALID_INBOX_INDEX, index + "");
 | 
			
		||||
                            return false;
 | 
			
		||||
                        }
 | 
			
		||||
                    } catch (NumberFormatException ignored) {
 | 
			
		||||
                        sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                            "/plot inbox " + inbox.toString() + " delete <index>");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
 | 
			
		||||
                    if (!inbox.getComments(plot, new RunnableVal<List<PlotComment>>() {
 | 
			
		||||
                        @Override public void run(List<PlotComment> value) {
 | 
			
		||||
                            if (index > value.size()) {
 | 
			
		||||
                                sendMessage(player, C.NOT_VALID_INBOX_INDEX, index + "");
 | 
			
		||||
                                return;
 | 
			
		||||
                            }
 | 
			
		||||
                            PlotComment comment = value.get(index - 1);
 | 
			
		||||
                            inbox.removeComment(plot, comment);
 | 
			
		||||
                            plot.getSettings().removeComment(comment);
 | 
			
		||||
                            MainUtil.sendMessage(player, C.COMMENT_REMOVED, comment.comment);
 | 
			
		||||
                        }
 | 
			
		||||
                    })) {
 | 
			
		||||
                        sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    return true;
 | 
			
		||||
                case "clear":
 | 
			
		||||
                    if (!inbox.canModify(plot, player)) {
 | 
			
		||||
                        sendMessage(player, C.NO_PERM_INBOX_MODIFY);
 | 
			
		||||
                    }
 | 
			
		||||
                    inbox.clearInbox(plot);
 | 
			
		||||
                    Optional<ArrayList<PlotComment>> comments =
 | 
			
		||||
                        plot.getSettings().getComments(inbox.toString());
 | 
			
		||||
                    comments
 | 
			
		||||
                        .ifPresent(plotComments -> plot.getSettings().removeComments(plotComments));
 | 
			
		||||
                    MainUtil.sendMessage(player, C.COMMENT_REMOVED, "*");
 | 
			
		||||
                    return true;
 | 
			
		||||
                default:
 | 
			
		||||
                    try {
 | 
			
		||||
                        page = Integer.parseInt(args[1]);
 | 
			
		||||
                    } catch (NumberFormatException ignored) {
 | 
			
		||||
                        sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                            "/plot inbox [inbox] [delete <index>|clear|page]");
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            page = 1;
 | 
			
		||||
        }
 | 
			
		||||
        if (!inbox.canRead(plot, player)) {
 | 
			
		||||
            sendMessage(player, C.NO_PERM_INBOX);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!inbox.getComments(plot, new RunnableVal<List<PlotComment>>() {
 | 
			
		||||
            @Override public void run(List<PlotComment> value) {
 | 
			
		||||
                displayComments(player, value, page);
 | 
			
		||||
            }
 | 
			
		||||
        })) {
 | 
			
		||||
            sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,155 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.expiry.ExpireManager;
 | 
			
		||||
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "info", aliases = "i", description = "Display plot info",
 | 
			
		||||
    usage = "/plot info <id>", category = CommandCategory.INFO) public class Info
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        Plot plot;
 | 
			
		||||
        String arg;
 | 
			
		||||
        if (args.length > 0) {
 | 
			
		||||
            arg = args[0];
 | 
			
		||||
            switch (arg) {
 | 
			
		||||
                case "trusted":
 | 
			
		||||
                case "alias":
 | 
			
		||||
                case "inv":
 | 
			
		||||
                case "biome":
 | 
			
		||||
                case "denied":
 | 
			
		||||
                case "flags":
 | 
			
		||||
                case "id":
 | 
			
		||||
                case "size":
 | 
			
		||||
                case "members":
 | 
			
		||||
                case "seen":
 | 
			
		||||
                case "owner":
 | 
			
		||||
                case "rating":
 | 
			
		||||
                    plot = MainUtil.getPlotFromString(player, null, false);
 | 
			
		||||
                    break;
 | 
			
		||||
                default:
 | 
			
		||||
                    plot = MainUtil.getPlotFromString(player, arg, false);
 | 
			
		||||
                    if (args.length == 2) {
 | 
			
		||||
                        arg = args[1];
 | 
			
		||||
                    } else {
 | 
			
		||||
                        arg = null;
 | 
			
		||||
                    }
 | 
			
		||||
                    break;
 | 
			
		||||
            }
 | 
			
		||||
            if (plot == null) {
 | 
			
		||||
                plot = player.getCurrentPlot();
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            arg = null;
 | 
			
		||||
            plot = player.getCurrentPlot();
 | 
			
		||||
        }
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NOT_IN_PLOT.s());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (arg != null) {
 | 
			
		||||
            if (args.length == 1) {
 | 
			
		||||
                args = new String[0];
 | 
			
		||||
            } else {
 | 
			
		||||
                args = new String[] {args[1]};
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (args.length == 1 && args[0].equalsIgnoreCase("inv")) {
 | 
			
		||||
            PlotInventory inv = new PlotInventory(player) {
 | 
			
		||||
                @Override public boolean onClick(int index) {
 | 
			
		||||
                    // TODO InfoInventory not implemented yet!!!!!!!!
 | 
			
		||||
                    // See plot rating or musicsubcommand on examples
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
            };
 | 
			
		||||
            UUID uuid = player.getUUID();
 | 
			
		||||
            String name = MainUtil.getName(plot.owner);
 | 
			
		||||
            inv.setItem(1, new PlotItemStack(388, (short) 0, 1, "&cPlot Info",
 | 
			
		||||
                "&cID: &6" + plot.getId().toString(), "&cOwner: &6" + name,
 | 
			
		||||
                "&cAlias: &6" + plot.getAlias(),
 | 
			
		||||
                "&cBiome: &6" + plot.getBiome().replaceAll("_", "").toLowerCase(),
 | 
			
		||||
                "&cCan Build: &6" + plot.isAdded(uuid),
 | 
			
		||||
                "&cSeen: &6" + MainUtil.secToTime((int) (ExpireManager.IMP.getAge(plot) / 1000)),
 | 
			
		||||
                "&cIs Denied: &6" + plot.isDenied(uuid)));
 | 
			
		||||
            inv.setItem(1, new PlotItemStack(388, (short) 0, 1, "&cTrusted",
 | 
			
		||||
                "&cAmount: &6" + plot.getTrusted().size(),
 | 
			
		||||
                "&8Click to view a list of the trusted users"));
 | 
			
		||||
            inv.setItem(1, new PlotItemStack(388, (short) 0, 1, "&cMembers",
 | 
			
		||||
                "&cAmount: &6" + plot.getMembers().size(),
 | 
			
		||||
                "&8Click to view a list of plot members"));
 | 
			
		||||
            inv.setItem(1, new PlotItemStack(388, (short) 0, 1, "&cDenied", "&cDenied",
 | 
			
		||||
                "&cAmount: &6" + plot.getDenied().size(),
 | 
			
		||||
                "&8Click to view a list of denied players"));
 | 
			
		||||
            inv.setItem(1, new PlotItemStack(388, (short) 0, 1, "&cFlags", "&cFlags",
 | 
			
		||||
                "&cAmount: &6" + plot.getFlags().size(), "&8Click to view a list of plot flags"));
 | 
			
		||||
            inv.openInventory();
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        boolean hasOwner = plot.hasOwner();
 | 
			
		||||
        // Wildcard player {added}
 | 
			
		||||
        boolean containsEveryone = plot.getTrusted().contains(DBFunc.EVERYONE);
 | 
			
		||||
        boolean trustedEveryone = plot.getMembers().contains(DBFunc.EVERYONE);
 | 
			
		||||
        // Unclaimed?
 | 
			
		||||
        if (!hasOwner && !containsEveryone && !trustedEveryone) {
 | 
			
		||||
            MainUtil
 | 
			
		||||
                .sendMessage(player, C.PLOT_INFO_UNCLAIMED, plot.getId().x + ";" + plot.getId().y);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        String info = C.PLOT_INFO.s();
 | 
			
		||||
        boolean full;
 | 
			
		||||
        if (arg != null) {
 | 
			
		||||
            info = getCaption(arg);
 | 
			
		||||
            if (info == null) {
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    "&6Categories&7: &amembers&7, &aalias&7, &abiome&7, &aseen&7, &adenied&7, &aflags&7, &aid&7, &asize&7, &atrusted&7, "
 | 
			
		||||
                        + "&aowner&7, &arating");
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            full = true;
 | 
			
		||||
        } else {
 | 
			
		||||
            full = false;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.format(info, plot, player, full, new RunnableVal<String>() {
 | 
			
		||||
            @Override public void run(String value) {
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    C.PLOT_INFO_HEADER.s() + '\n' + value + '\n' + C.PLOT_INFO_FOOTER.s(), false);
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    private String getCaption(String string) {
 | 
			
		||||
        switch (string) {
 | 
			
		||||
            case "trusted":
 | 
			
		||||
                return C.PLOT_INFO_TRUSTED.s();
 | 
			
		||||
            case "alias":
 | 
			
		||||
                return C.PLOT_INFO_ALIAS.s();
 | 
			
		||||
            case "biome":
 | 
			
		||||
                return C.PLOT_INFO_BIOME.s();
 | 
			
		||||
            case "denied":
 | 
			
		||||
                return C.PLOT_INFO_DENIED.s();
 | 
			
		||||
            case "flags":
 | 
			
		||||
                return C.PLOT_INFO_FLAGS.s();
 | 
			
		||||
            case "id":
 | 
			
		||||
                return C.PLOT_INFO_ID.s();
 | 
			
		||||
            case "size":
 | 
			
		||||
                return C.PLOT_INFO_SIZE.s();
 | 
			
		||||
            case "members":
 | 
			
		||||
                return C.PLOT_INFO_MEMBERS.s();
 | 
			
		||||
            case "owner":
 | 
			
		||||
                return C.PLOT_INFO_OWNER.s();
 | 
			
		||||
            case "rating":
 | 
			
		||||
                return C.PLOT_INFO_RATING.s();
 | 
			
		||||
            case "seen":
 | 
			
		||||
                return C.PLOT_INFO_SEEN.s();
 | 
			
		||||
            default:
 | 
			
		||||
                return null;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,92 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Argument;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.database.DBFunc;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.UUIDHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.WorldUtil;
 | 
			
		||||
 | 
			
		||||
import java.util.HashSet;
 | 
			
		||||
import java.util.Set;
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "kick", aliases = {"k"}, description = "Kick a player from your plot",
 | 
			
		||||
    permission = "plots.kick", usage = "/plot kick <player>", category = CommandCategory.TELEPORT,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Kick extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public Kick() {
 | 
			
		||||
        super(Argument.PlayerName);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        Location location = player.getLocation();
 | 
			
		||||
        Plot plot = location.getPlot();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if ((!plot.hasOwner() || !plot.isOwner(player.getUUID())) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_KICK)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Set<UUID> uuids = MainUtil.getUUIDsFromString(args[0]);
 | 
			
		||||
        if (uuids.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.INVALID_PLAYER, args[0]);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        Set<PlotPlayer> players = new HashSet<>();
 | 
			
		||||
        for (UUID uuid : uuids) {
 | 
			
		||||
            if (uuid == DBFunc.EVERYONE) {
 | 
			
		||||
                for (PlotPlayer pp : plot.getPlayersInPlot()) {
 | 
			
		||||
                    if (pp == player || Permissions
 | 
			
		||||
                        .hasPermission(pp, C.PERMISSION_ADMIN_ENTRY_DENIED)) {
 | 
			
		||||
                        continue;
 | 
			
		||||
                    }
 | 
			
		||||
                    players.add(pp);
 | 
			
		||||
                }
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            PlotPlayer pp = UUIDHandler.getPlayer(uuid);
 | 
			
		||||
            if (pp != null) {
 | 
			
		||||
                players.add(pp);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        players.remove(player); // Don't ever kick the calling player
 | 
			
		||||
        if (players.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.INVALID_PLAYER, args[0]);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        for (PlotPlayer player2 : players) {
 | 
			
		||||
            if (!plot.equals(player2.getCurrentPlot())) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.INVALID_PLAYER, args[0]);
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            if (Permissions.hasPermission(player2, C.PERMISSION_ADMIN_ENTRY_DENIED)) {
 | 
			
		||||
                C.CANNOT_KICK_PLAYER.send(player, player2.getName());
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
            Location spawn = WorldUtil.IMP.getSpawn(location.getWorld());
 | 
			
		||||
            C.YOU_GOT_KICKED.send(player2);
 | 
			
		||||
            if (plot.equals(spawn.getPlot())) {
 | 
			
		||||
                Location newSpawn = WorldUtil.IMP
 | 
			
		||||
                    .getSpawn(PlotSquared.get().getPlotAreaManager().getAllWorlds()[0]);
 | 
			
		||||
                if (plot.equals(newSpawn.getPlot())) {
 | 
			
		||||
                    // Kick from server if you can't be teleported to spawn
 | 
			
		||||
                    player2.kick(C.YOU_GOT_KICKED.s());
 | 
			
		||||
                } else {
 | 
			
		||||
                    player2.plotkick(newSpawn);
 | 
			
		||||
                }
 | 
			
		||||
            } else {
 | 
			
		||||
                player2.plotkick(spawn);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,48 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal2;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.RunnableVal3;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EventUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "leave",
 | 
			
		||||
    description = "Removes self from being trusted or a member of the plot",
 | 
			
		||||
    permission = "plots.leave", category = CommandCategory.CLAIMING,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Leave extends Command {
 | 
			
		||||
    public Leave() {
 | 
			
		||||
        super(MainCommand.getInstance(), true);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) throws CommandException {
 | 
			
		||||
        final Plot plot = check(player.getCurrentPlot(), C.NOT_IN_PLOT);
 | 
			
		||||
        checkTrue(plot.hasOwner(), C.PLOT_UNOWNED);
 | 
			
		||||
        checkTrue(plot.isAdded(player.getUUID()), C.NO_PLOT_PERMS);
 | 
			
		||||
        checkTrue(args.length == 0, C.COMMAND_SYNTAX, getUsage());
 | 
			
		||||
        if (plot.isOwner(player.getUUID())) {
 | 
			
		||||
            checkTrue(plot.hasOwner(), C.ALREADY_OWNER);
 | 
			
		||||
            // TODO setowner, other
 | 
			
		||||
        } else {
 | 
			
		||||
            UUID uuid = player.getUUID();
 | 
			
		||||
            if (plot.isAdded(uuid)) {
 | 
			
		||||
                if (plot.removeTrusted(uuid)) {
 | 
			
		||||
                    EventUtil.manager.callTrusted(player, plot, uuid, false);
 | 
			
		||||
                }
 | 
			
		||||
                if (plot.removeMember(uuid)) {
 | 
			
		||||
                    EventUtil.manager.callMember(player, plot, uuid, false);
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.INVALID_PLAYER, args[0]);
 | 
			
		||||
            } else {
 | 
			
		||||
                MainUtil.sendMessage(player, C.REMOVED_PLAYERS, 1);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,397 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared.SortType;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.expiry.ExpireManager;
 | 
			
		||||
 | 
			
		||||
import java.util.*;
 | 
			
		||||
import java.util.Map.Entry;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "list", aliases = {"l", "find", "search"}, description = "List plots",
 | 
			
		||||
    permission = "plots.list", category = CommandCategory.INFO,
 | 
			
		||||
    usage = "/plot list <forsale|mine|shared|world|top|all|unowned|unknown|player|world|done|fuzzy <search...>> [#]")
 | 
			
		||||
public class ListCmd extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    private String[] getArgumentList(PlotPlayer player) {
 | 
			
		||||
        List<String> args = new ArrayList<>();
 | 
			
		||||
        if (EconHandler.manager != null && Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_LIST_FORSALE)) {
 | 
			
		||||
            args.add("forsale");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_MINE)) {
 | 
			
		||||
            args.add("mine");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_SHARED)) {
 | 
			
		||||
            args.add("shared");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_WORLD)) {
 | 
			
		||||
            args.add("world");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_TOP)) {
 | 
			
		||||
            args.add("top");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_ALL)) {
 | 
			
		||||
            args.add("all");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_UNOWNED)) {
 | 
			
		||||
            args.add("unowned");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_UNKNOWN)) {
 | 
			
		||||
            args.add("unknown");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_PLAYER)) {
 | 
			
		||||
            args.add("<player>");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_WORLD)) {
 | 
			
		||||
            args.add("<world>");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_DONE)) {
 | 
			
		||||
            args.add("done");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_EXPIRED)) {
 | 
			
		||||
            args.add("expired");
 | 
			
		||||
        }
 | 
			
		||||
        if (Permissions.hasPermission(player, C.PERMISSION_LIST_FUZZY)) {
 | 
			
		||||
            args.add("fuzzy <search...>");
 | 
			
		||||
        }
 | 
			
		||||
        return args.toArray(new String[args.size()]);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void noArgs(PlotPlayer player) {
 | 
			
		||||
        MainUtil.sendMessage(player,
 | 
			
		||||
            C.SUBCOMMAND_SET_OPTIONS_HEADER.s() + Arrays.toString(getArgumentList(player)));
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        if (args.length < 1) {
 | 
			
		||||
            noArgs(player);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        int page = 0;
 | 
			
		||||
        if (args.length > 1) {
 | 
			
		||||
            try {
 | 
			
		||||
                page = Integer.parseInt(args[args.length - 1]);
 | 
			
		||||
                --page;
 | 
			
		||||
                if (page < 0) {
 | 
			
		||||
                    page = 0;
 | 
			
		||||
                }
 | 
			
		||||
            } catch (NumberFormatException ignored) {
 | 
			
		||||
                page = -1;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        List<Plot> plots = null;
 | 
			
		||||
 | 
			
		||||
        String world = player.getLocation().getWorld();
 | 
			
		||||
        PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
        String arg = args[0].toLowerCase();
 | 
			
		||||
        boolean sort = true;
 | 
			
		||||
        switch (arg) {
 | 
			
		||||
            case "mine":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_MINE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_MINE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                sort = false;
 | 
			
		||||
                plots = PlotSquared.get().sortPlotsByTemp(PlotSquared.get().getBasePlots(player));
 | 
			
		||||
                break;
 | 
			
		||||
            case "shared":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_SHARED)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_SHARED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>();
 | 
			
		||||
                for (Plot plot : PlotSquared.get().getPlots()) {
 | 
			
		||||
                    if (plot.getTrusted().contains(player.getUUID()) || plot.getMembers()
 | 
			
		||||
                        .contains(player.getUUID())) {
 | 
			
		||||
                        plots.add(plot);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "world":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_WORLD)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_WORLD);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_WORLD_NAME.f(world))) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                        C.PERMISSION_LIST_WORLD_NAME.f(world));
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>(PlotSquared.get().getPlots(world));
 | 
			
		||||
                break;
 | 
			
		||||
            case "expired":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_EXPIRED)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_EXPIRED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = ExpireManager.IMP == null ?
 | 
			
		||||
                    new ArrayList<Plot>() :
 | 
			
		||||
                    new ArrayList<>(ExpireManager.IMP.getPendingExpired());
 | 
			
		||||
                break;
 | 
			
		||||
            case "area":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_AREA)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_AREA);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_WORLD_NAME.f(world))) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                        C.PERMISSION_LIST_WORLD_NAME.f(world));
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = area == null ? new ArrayList<Plot>() : new ArrayList<>(area.getPlots());
 | 
			
		||||
                break;
 | 
			
		||||
            case "all":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_ALL)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_ALL);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>(PlotSquared.get().getPlots());
 | 
			
		||||
                break;
 | 
			
		||||
            case "done":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_DONE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_DONE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>();
 | 
			
		||||
                for (Plot plot : PlotSquared.get().getPlots()) {
 | 
			
		||||
                    Optional<String> flag = plot.getFlag(Flags.DONE);
 | 
			
		||||
                    if (flag.isPresent()) {
 | 
			
		||||
                        plots.add(plot);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                Collections.sort(plots, new Comparator<Plot>() {
 | 
			
		||||
                    @Override public int compare(Plot a, Plot b) {
 | 
			
		||||
                        String va = "" + a.getFlags().get(Flags.DONE);
 | 
			
		||||
                        String vb = "" + b.getFlags().get(Flags.DONE);
 | 
			
		||||
                        if (MathMan.isInteger(va)) {
 | 
			
		||||
                            if (MathMan.isInteger(vb)) {
 | 
			
		||||
                                return Integer.parseInt(vb) - Integer.parseInt(va);
 | 
			
		||||
                            }
 | 
			
		||||
                            return -1;
 | 
			
		||||
                        }
 | 
			
		||||
                        return 1;
 | 
			
		||||
                    }
 | 
			
		||||
                });
 | 
			
		||||
                sort = false;
 | 
			
		||||
                break;
 | 
			
		||||
            case "top":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_TOP)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_TOP);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>(PlotSquared.get().getPlots());
 | 
			
		||||
                Collections.sort(plots, new Comparator<Plot>() {
 | 
			
		||||
                    @Override public int compare(Plot p1, Plot p2) {
 | 
			
		||||
                        double v1 = 0;
 | 
			
		||||
                        int p1s = p1.getSettings().getRatings().size();
 | 
			
		||||
                        int p2s = p2.getRatings().size();
 | 
			
		||||
                        if (!p1.getSettings().getRatings().isEmpty()) {
 | 
			
		||||
                            for (Entry<UUID, Rating> entry : p1.getRatings().entrySet()) {
 | 
			
		||||
                                double av = entry.getValue().getAverageRating();
 | 
			
		||||
                                v1 += av * av;
 | 
			
		||||
                            }
 | 
			
		||||
                            v1 /= p1s;
 | 
			
		||||
                            v1 += p1s;
 | 
			
		||||
                        }
 | 
			
		||||
                        double v2 = 0;
 | 
			
		||||
                        if (!p2.getSettings().getRatings().isEmpty()) {
 | 
			
		||||
                            for (Entry<UUID, Rating> entry : p2.getRatings().entrySet()) {
 | 
			
		||||
                                double av = entry.getValue().getAverageRating();
 | 
			
		||||
                                v2 += av * av;
 | 
			
		||||
                            }
 | 
			
		||||
                            v2 /= p2s;
 | 
			
		||||
                            v2 += p2s;
 | 
			
		||||
                        }
 | 
			
		||||
                        if (v2 == v1 && v2 != 0) {
 | 
			
		||||
                            return p2s - p1s;
 | 
			
		||||
                        }
 | 
			
		||||
                        return (int) Math.signum(v2 - v1);
 | 
			
		||||
                    }
 | 
			
		||||
                });
 | 
			
		||||
                sort = false;
 | 
			
		||||
                break;
 | 
			
		||||
            case "forsale":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_FORSALE)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_FORSALE);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (EconHandler.manager == null) {
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>();
 | 
			
		||||
                for (Plot plot : PlotSquared.get().getPlots()) {
 | 
			
		||||
                    Optional<Double> price = plot.getFlag(Flags.PRICE);
 | 
			
		||||
                    if (price.isPresent()) {
 | 
			
		||||
                        plots.add(plot);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "unowned":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_UNOWNED)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_UNOWNED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>();
 | 
			
		||||
                for (Plot plot : PlotSquared.get().getPlots()) {
 | 
			
		||||
                    if (plot.owner == null) {
 | 
			
		||||
                        plots.add(plot);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "unknown":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_UNKNOWN)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_UNKNOWN);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plots = new ArrayList<>();
 | 
			
		||||
                for (Plot plot : PlotSquared.get().getPlots()) {
 | 
			
		||||
                    if (plot.owner == null) {
 | 
			
		||||
                        continue;
 | 
			
		||||
                    }
 | 
			
		||||
                    if (UUIDHandler.getName(plot.owner) == null) {
 | 
			
		||||
                        plots.add(plot);
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            case "fuzzy":
 | 
			
		||||
                if (!Permissions.hasPermission(player, C.PERMISSION_LIST_FUZZY)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_FUZZY);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                if (args.length < (page == -1 ? 2 : 3)) {
 | 
			
		||||
                    C.COMMAND_SYNTAX.send(player, "/plot list fuzzy <search...> [#]");
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                String term;
 | 
			
		||||
                if (MathMan.isInteger(args[args.length - 1])) {
 | 
			
		||||
                    term = StringMan.join(Arrays.copyOfRange(args, 1, args.length - 1), " ");
 | 
			
		||||
                } else {
 | 
			
		||||
                    term = StringMan.join(Arrays.copyOfRange(args, 1, args.length), " ");
 | 
			
		||||
                }
 | 
			
		||||
                plots = MainUtil.getPlotsBySearch(term);
 | 
			
		||||
                sort = false;
 | 
			
		||||
                break;
 | 
			
		||||
            default:
 | 
			
		||||
                if (PlotSquared.get().hasPlotArea(args[0])) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_LIST_WORLD)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_WORLD);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    if (!Permissions
 | 
			
		||||
                        .hasPermission(player, C.PERMISSION_LIST_WORLD_NAME.f(args[0]))) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION,
 | 
			
		||||
                            C.PERMISSION_LIST_WORLD_NAME.f(args[0]));
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    plots = new ArrayList<>(PlotSquared.get().getPlots(args[0]));
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
                UUID uuid = UUIDHandler.getUUID(args[0], null);
 | 
			
		||||
                if (uuid == null) {
 | 
			
		||||
                    try {
 | 
			
		||||
                        uuid = UUID.fromString(args[0]);
 | 
			
		||||
                    } catch (Exception ignored) {
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
                if (uuid != null) {
 | 
			
		||||
                    if (!Permissions.hasPermission(player, C.PERMISSION_LIST_PLAYER)) {
 | 
			
		||||
                        MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_LIST_PLAYER);
 | 
			
		||||
                        return false;
 | 
			
		||||
                    }
 | 
			
		||||
                    sort = false;
 | 
			
		||||
                    plots = PlotSquared.get().sortPlotsByTemp(PlotSquared.get().getPlots(uuid));
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (plots == null) {
 | 
			
		||||
            sendMessage(player, C.DID_YOU_MEAN,
 | 
			
		||||
                new StringComparison<>(args[0], new String[] {"mine", "shared", "world", "all"})
 | 
			
		||||
                    .getBestMatch());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (plots.isEmpty()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.FOUND_NO_PLOTS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        displayPlots(player, plots, 12, page, area, args, sort);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void displayPlots(final PlotPlayer player, List<Plot> plots, int pageSize, int page,
 | 
			
		||||
        PlotArea area, String[] args, boolean sort) {
 | 
			
		||||
        // Header
 | 
			
		||||
        Iterator<Plot> iterator = plots.iterator();
 | 
			
		||||
        while (iterator.hasNext()) {
 | 
			
		||||
            if (!iterator.next().isBasePlot()) {
 | 
			
		||||
                iterator.remove();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (sort) {
 | 
			
		||||
            plots = PlotSquared.get().sortPlots(plots, SortType.CREATION_DATE, area);
 | 
			
		||||
        }
 | 
			
		||||
        this.paginate(player, plots, pageSize, page,
 | 
			
		||||
            new RunnableVal3<Integer, Plot, PlotMessage>() {
 | 
			
		||||
                @Override public void run(Integer i, Plot plot, PlotMessage message) {
 | 
			
		||||
                    String color;
 | 
			
		||||
                    if (plot.owner == null) {
 | 
			
		||||
                        color = "$3";
 | 
			
		||||
                    } else if (plot.isOwner(player.getUUID())) {
 | 
			
		||||
                        color = "$1";
 | 
			
		||||
                    } else if (plot.isAdded(player.getUUID())) {
 | 
			
		||||
                        color = "$4";
 | 
			
		||||
                    } else if (plot.isDenied(player.getUUID())) {
 | 
			
		||||
                        color = "$2";
 | 
			
		||||
                    } else {
 | 
			
		||||
                        color = "$1";
 | 
			
		||||
                    }
 | 
			
		||||
                    PlotMessage trusted = new PlotMessage().text(C.color(C.PLOT_INFO_TRUSTED.s()
 | 
			
		||||
                        .replaceAll("%trusted%", MainUtil.getPlayerList(plot.getTrusted()))))
 | 
			
		||||
                        .color("$1");
 | 
			
		||||
                    PlotMessage members = new PlotMessage().text(C.color(C.PLOT_INFO_MEMBERS.s()
 | 
			
		||||
                        .replaceAll("%members%", MainUtil.getPlayerList(plot.getMembers()))))
 | 
			
		||||
                        .color("$1");
 | 
			
		||||
                    String strFlags = StringMan.join(plot.getFlags().values(), ",");
 | 
			
		||||
                    if (strFlags.isEmpty()) {
 | 
			
		||||
                        strFlags = C.NONE.s();
 | 
			
		||||
                    }
 | 
			
		||||
                    PlotMessage flags = new PlotMessage()
 | 
			
		||||
                        .text(C.color(C.PLOT_INFO_FLAGS.s().replaceAll("%flags%", strFlags)))
 | 
			
		||||
                        .color("$1");
 | 
			
		||||
                    message.text("[").color("$3").text(i + "")
 | 
			
		||||
                        .command("/plot visit " + plot.getArea() + ";" + plot.getId())
 | 
			
		||||
                        .tooltip("/plot visit " + plot.getArea() + ";" + plot.getId()).color("$1")
 | 
			
		||||
                        .text("]").color("$3").text(" " + plot.toString())
 | 
			
		||||
                        .tooltip(trusted, members, flags)
 | 
			
		||||
                        .command("/plot info " + plot.getArea() + ";" + plot.getId()).color(color)
 | 
			
		||||
                        .text(" - ").color("$2");
 | 
			
		||||
                    String prefix = "";
 | 
			
		||||
                    for (UUID uuid : plot.getOwners()) {
 | 
			
		||||
                        String name = UUIDHandler.getName(uuid);
 | 
			
		||||
                        if (name == null) {
 | 
			
		||||
                            message = message.text(prefix).color("$4").text("unknown").color("$2")
 | 
			
		||||
                                .tooltip(uuid.toString()).suggest(uuid.toString());
 | 
			
		||||
                        } else {
 | 
			
		||||
                            PlotPlayer pp = UUIDHandler.getPlayer(uuid);
 | 
			
		||||
                            if (pp != null) {
 | 
			
		||||
                                message = message.text(prefix).color("$4").text(name).color("$1")
 | 
			
		||||
                                    .tooltip(new PlotMessage("Online").color("$4"));
 | 
			
		||||
                            } else {
 | 
			
		||||
                                message = message.text(prefix).color("$4").text(name).color("$1")
 | 
			
		||||
                                    .tooltip(new PlotMessage("Offline").color("$3"));
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                        prefix = ", ";
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }, "/plot list " + args[0], C.PLOT_LIST_HEADER_PAGED.s());
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
@@ -1,179 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.schematic.Schematic;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.SchematicHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.TaskManager;
 | 
			
		||||
 | 
			
		||||
import java.net.MalformedURLException;
 | 
			
		||||
import java.net.URL;
 | 
			
		||||
import java.util.List;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "load", aliases = {"restore"}, category = CommandCategory.SCHEMATIC,
 | 
			
		||||
    requiredType = RequiredType.NONE, description = "Load your plot", permission = "plots.load",
 | 
			
		||||
    usage = "/plot load") public class Load extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        String world = player.getLocation().getWorld();
 | 
			
		||||
        if (!PlotSquared.get().hasPlotArea(world)) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT_WORLD);
 | 
			
		||||
        }
 | 
			
		||||
        final Plot plot = player.getCurrentPlot();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN_COMMAND_LOAD)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.getRunning() > 0) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.WAIT_FOR_TIMER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        if (args.length != 0) {
 | 
			
		||||
            if (args.length == 1) {
 | 
			
		||||
                List<String> schematics = player.getMeta("plot_schematics");
 | 
			
		||||
                if (schematics == null) {
 | 
			
		||||
                    // No schematics found:
 | 
			
		||||
                    MainUtil.sendMessage(player, C.LOAD_NULL);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                String schem;
 | 
			
		||||
                try {
 | 
			
		||||
                    schem = schematics.get(Integer.parseInt(args[0]) - 1);
 | 
			
		||||
                } catch (Exception ignored) {
 | 
			
		||||
                    // use /plot load <index>
 | 
			
		||||
                    MainUtil
 | 
			
		||||
                        .sendMessage(player, C.NOT_VALID_NUMBER, "(1, " + schematics.size() + ')');
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                final URL url;
 | 
			
		||||
                try {
 | 
			
		||||
                    url = new URL(Settings.Web.URL + "saves/" + player.getUUID() + '/' + schem);
 | 
			
		||||
                } catch (MalformedURLException e) {
 | 
			
		||||
                    e.printStackTrace();
 | 
			
		||||
                    MainUtil.sendMessage(player, C.LOAD_FAILED);
 | 
			
		||||
                    return false;
 | 
			
		||||
                }
 | 
			
		||||
                plot.addRunning();
 | 
			
		||||
                MainUtil.sendMessage(player, C.GENERATING_COMPONENT);
 | 
			
		||||
                TaskManager.runTaskAsync(() -> {
 | 
			
		||||
                    Schematic schematic = SchematicHandler.manager.getSchematic(url);
 | 
			
		||||
                    if (schematic == null) {
 | 
			
		||||
                        plot.removeRunning();
 | 
			
		||||
                        sendMessage(player, C.SCHEMATIC_INVALID,
 | 
			
		||||
                            "non-existent or not in gzip format");
 | 
			
		||||
                        return;
 | 
			
		||||
                    }
 | 
			
		||||
                    PlotArea area = plot.getArea();
 | 
			
		||||
                    SchematicHandler.manager
 | 
			
		||||
                        .paste(schematic, plot, 0, area.MIN_BUILD_HEIGHT, 0, false,
 | 
			
		||||
                            new RunnableVal<Boolean>() {
 | 
			
		||||
                                @Override public void run(Boolean value) {
 | 
			
		||||
                                    plot.removeRunning();
 | 
			
		||||
                                    if (value) {
 | 
			
		||||
                                        sendMessage(player, C.SCHEMATIC_PASTE_SUCCESS);
 | 
			
		||||
                                    } else {
 | 
			
		||||
                                        sendMessage(player, C.SCHEMATIC_PASTE_FAILED);
 | 
			
		||||
                                    }
 | 
			
		||||
                                }
 | 
			
		||||
                            });
 | 
			
		||||
                });
 | 
			
		||||
                return true;
 | 
			
		||||
            }
 | 
			
		||||
            plot.removeRunning();
 | 
			
		||||
            MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot load <index>");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        // list schematics
 | 
			
		||||
 | 
			
		||||
        List<String> schematics = player.getMeta("plot_schematics");
 | 
			
		||||
        if (schematics == null) {
 | 
			
		||||
            plot.addRunning();
 | 
			
		||||
            TaskManager.runTaskAsync(() -> {
 | 
			
		||||
                List<String> schematics1 = SchematicHandler.manager.getSaves(player.getUUID());
 | 
			
		||||
                plot.removeRunning();
 | 
			
		||||
                if ((schematics1 == null) || schematics1.isEmpty()) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.LOAD_FAILED);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                player.setMeta("plot_schematics", schematics1);
 | 
			
		||||
                displaySaves(player);
 | 
			
		||||
            });
 | 
			
		||||
        } else {
 | 
			
		||||
            displaySaves(player);
 | 
			
		||||
        }
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public void displaySaves(PlotPlayer player) {
 | 
			
		||||
        List<String> schematics = player.getMeta("plot_schematics");
 | 
			
		||||
        for (int i = 0; i < Math.min(schematics.size(), 32); i++) {
 | 
			
		||||
            try {
 | 
			
		||||
                String schematic = schematics.get(i).split("\\.")[0];
 | 
			
		||||
                String[] split = schematic.split("_");
 | 
			
		||||
                if (split.length < 5) {
 | 
			
		||||
                    continue;
 | 
			
		||||
                }
 | 
			
		||||
                String time =
 | 
			
		||||
                    secToTime((System.currentTimeMillis() / 1000) - Long.parseLong(split[0]));
 | 
			
		||||
                String world = split[1];
 | 
			
		||||
                PlotId id = PlotId.fromString(split[2] + ';' + split[3]);
 | 
			
		||||
                String size = split[4];
 | 
			
		||||
                String color = "$4";
 | 
			
		||||
                MainUtil.sendMessage(player,
 | 
			
		||||
                    "$3[$2" + (i + 1) + "$3] " + color + time + "$3 | " + color + world + ';' + id
 | 
			
		||||
                        + "$3 | " + color + size + 'x' + size);
 | 
			
		||||
            } catch (Exception e) {
 | 
			
		||||
                e.printStackTrace();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, C.LOAD_LIST);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public String secToTime(long time) {
 | 
			
		||||
        StringBuilder toreturn = new StringBuilder();
 | 
			
		||||
        if (time >= 33868800) {
 | 
			
		||||
            int years = (int) (time / 33868800);
 | 
			
		||||
            time -= years * 33868800;
 | 
			
		||||
            toreturn.append(years).append("y ");
 | 
			
		||||
        }
 | 
			
		||||
        if (time >= 604800) {
 | 
			
		||||
            int weeks = (int) (time / 604800);
 | 
			
		||||
            time -= weeks * 604800;
 | 
			
		||||
            toreturn.append(weeks).append("w ");
 | 
			
		||||
        }
 | 
			
		||||
        if (time >= 86400) {
 | 
			
		||||
            int days = (int) (time / 86400);
 | 
			
		||||
            time -= days * 86400;
 | 
			
		||||
            toreturn.append(days).append("d ");
 | 
			
		||||
        }
 | 
			
		||||
        if (time >= 3600) {
 | 
			
		||||
            int hours = (int) (time / 3600);
 | 
			
		||||
            time -= hours * 3600;
 | 
			
		||||
            toreturn.append(hours).append("h ");
 | 
			
		||||
        }
 | 
			
		||||
        if (time >= 60) {
 | 
			
		||||
            int minutes = (int) (time / 60);
 | 
			
		||||
            time -= minutes * 60;
 | 
			
		||||
            toreturn.append(minutes).append("m ");
 | 
			
		||||
        }
 | 
			
		||||
        if (toreturn.length() == 0 || (time > 0)) {
 | 
			
		||||
            toreturn.append(time).append("s ");
 | 
			
		||||
        }
 | 
			
		||||
        return toreturn.toString().trim();
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,286 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.Command;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.CmdConfirm;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.EconHandler;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * PlotSquared command class.
 | 
			
		||||
 */
 | 
			
		||||
@CommandDeclaration(command = "plot",
 | 
			
		||||
    aliases = {"plots", "p", "plotsquared", "plot2", "p2", "ps", "2", "plotme", "plotz", "ap"})
 | 
			
		||||
public class MainCommand extends Command {
 | 
			
		||||
 | 
			
		||||
    private static MainCommand instance;
 | 
			
		||||
    public Help help;
 | 
			
		||||
    public Toggle toggle;
 | 
			
		||||
 | 
			
		||||
    private MainCommand() {
 | 
			
		||||
        super(null, true);
 | 
			
		||||
        instance = this;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static MainCommand getInstance() {
 | 
			
		||||
        if (instance == null) {
 | 
			
		||||
            instance = new MainCommand();
 | 
			
		||||
            new Buy();
 | 
			
		||||
            new Save();
 | 
			
		||||
            new Load();
 | 
			
		||||
            new Confirm();
 | 
			
		||||
            new Template();
 | 
			
		||||
            new Download();
 | 
			
		||||
            new Template();
 | 
			
		||||
            new Setup();
 | 
			
		||||
            new Area();
 | 
			
		||||
            new DebugSaveTest();
 | 
			
		||||
            new DebugLoadTest();
 | 
			
		||||
            new CreateRoadSchematic();
 | 
			
		||||
            new DebugAllowUnsafe();
 | 
			
		||||
            new RegenAllRoads();
 | 
			
		||||
            new Claim();
 | 
			
		||||
            new Auto();
 | 
			
		||||
            new Visit();
 | 
			
		||||
            new Set();
 | 
			
		||||
            new Clear();
 | 
			
		||||
            new Delete();
 | 
			
		||||
            new Trust();
 | 
			
		||||
            new Add();
 | 
			
		||||
            new Leave();
 | 
			
		||||
            new Deny();
 | 
			
		||||
            new Remove();
 | 
			
		||||
            new Info();
 | 
			
		||||
            new Near();
 | 
			
		||||
            new ListCmd();
 | 
			
		||||
            new Debug();
 | 
			
		||||
            new SchematicCmd();
 | 
			
		||||
            new PluginCmd();
 | 
			
		||||
            new Purge();
 | 
			
		||||
            new Reload();
 | 
			
		||||
            new Relight();
 | 
			
		||||
            new Merge();
 | 
			
		||||
            new DebugPaste();
 | 
			
		||||
            new Unlink();
 | 
			
		||||
            new Kick();
 | 
			
		||||
            new Rate();
 | 
			
		||||
            new DebugClaimTest();
 | 
			
		||||
            new Inbox();
 | 
			
		||||
            new Comment();
 | 
			
		||||
            new Database();
 | 
			
		||||
            new Swap();
 | 
			
		||||
            new Music();
 | 
			
		||||
            new DebugRoadRegen();
 | 
			
		||||
            new Trust();
 | 
			
		||||
            new DebugExec();
 | 
			
		||||
            new FlagCmd();
 | 
			
		||||
            new Target();
 | 
			
		||||
            new DebugFixFlags();
 | 
			
		||||
            new Move();
 | 
			
		||||
            new Condense();
 | 
			
		||||
            new Copy();
 | 
			
		||||
            new Chat();
 | 
			
		||||
            new Trim();
 | 
			
		||||
            new Done();
 | 
			
		||||
            new Continue();
 | 
			
		||||
            new Middle();
 | 
			
		||||
            new Grant();
 | 
			
		||||
            // Set commands
 | 
			
		||||
            new Owner();
 | 
			
		||||
            new Desc();
 | 
			
		||||
            new Biome();
 | 
			
		||||
            new Alias();
 | 
			
		||||
            new SetHome();
 | 
			
		||||
            new Cluster();
 | 
			
		||||
            new DebugImportWorlds();
 | 
			
		||||
            // Referenced commands
 | 
			
		||||
            instance.toggle = new Toggle();
 | 
			
		||||
            instance.help = new Help(instance);
 | 
			
		||||
        }
 | 
			
		||||
        return instance;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    public static boolean onCommand(final PlotPlayer player, String... args) {
 | 
			
		||||
        if (args.length >= 1 && args[0].contains(":")) {
 | 
			
		||||
            String[] split2 = args[0].split(":");
 | 
			
		||||
            if (split2.length == 2) {
 | 
			
		||||
                // Ref: c:v, this will push value to the last spot in the array
 | 
			
		||||
                // ex. /p h:2 SomeUsername
 | 
			
		||||
                // > /p h SomeUsername 2
 | 
			
		||||
                String[] tmp = new String[args.length + 1];
 | 
			
		||||
                tmp[0] = split2[0];
 | 
			
		||||
                tmp[args.length] = split2[1];
 | 
			
		||||
                if (args.length >= 2) {
 | 
			
		||||
                    System.arraycopy(args, 1, tmp, 1, args.length - 1);
 | 
			
		||||
                }
 | 
			
		||||
                args = tmp;
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        try {
 | 
			
		||||
            getInstance().execute(player, args, new RunnableVal3<Command, Runnable, Runnable>() {
 | 
			
		||||
                @Override
 | 
			
		||||
                public void run(final Command cmd, final Runnable success, final Runnable failure) {
 | 
			
		||||
                    if (cmd.hasConfirmation(player)) {
 | 
			
		||||
                        CmdConfirm.addPending(player, cmd.getUsage(), new Runnable() {
 | 
			
		||||
                            @Override public void run() {
 | 
			
		||||
                                if (EconHandler.manager != null) {
 | 
			
		||||
                                    PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                                    if (area != null) {
 | 
			
		||||
                                        Expression<Double> priceEval =
 | 
			
		||||
                                            area.PRICES.get(cmd.getFullId());
 | 
			
		||||
                                        Double price =
 | 
			
		||||
                                            priceEval != null ? priceEval.evaluate(0d) : 0d;
 | 
			
		||||
                                        if (price != null
 | 
			
		||||
                                            && EconHandler.manager.getMoney(player) < price) {
 | 
			
		||||
                                            if (failure != null) {
 | 
			
		||||
                                                failure.run();
 | 
			
		||||
                                            }
 | 
			
		||||
                                            return;
 | 
			
		||||
                                        }
 | 
			
		||||
                                    }
 | 
			
		||||
                                }
 | 
			
		||||
                                if (success != null) {
 | 
			
		||||
                                    success.run();
 | 
			
		||||
                                }
 | 
			
		||||
                            }
 | 
			
		||||
                        });
 | 
			
		||||
                        return;
 | 
			
		||||
                    }
 | 
			
		||||
                    if (EconHandler.manager != null) {
 | 
			
		||||
                        PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                        if (area != null) {
 | 
			
		||||
                            Expression<Double> priceEval = area.PRICES.get(cmd.getFullId());
 | 
			
		||||
                            Double price = priceEval != null ? priceEval.evaluate(0d) : 0d;
 | 
			
		||||
                            if (price != 0d && EconHandler.manager.getMoney(player) < price) {
 | 
			
		||||
                                if (failure != null) {
 | 
			
		||||
                                    failure.run();
 | 
			
		||||
                                }
 | 
			
		||||
                                return;
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    }
 | 
			
		||||
                    if (success != null) {
 | 
			
		||||
                        success.run();
 | 
			
		||||
                    }
 | 
			
		||||
                }
 | 
			
		||||
            }, new RunnableVal2<Command, CommandResult>() {
 | 
			
		||||
                @Override public void run(Command cmd, CommandResult result) {
 | 
			
		||||
                    // Post command stuff!?
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
        } catch (CommandException e) {
 | 
			
		||||
            e.perform(player);
 | 
			
		||||
        }
 | 
			
		||||
        // Always true
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Deprecated
 | 
			
		||||
    /**
 | 
			
		||||
     * @Deprecated legacy
 | 
			
		||||
     */ public void addCommand(SubCommand command) {
 | 
			
		||||
        PlotSquared.debug("Command registration is now done during instantiation");
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public void execute(final PlotPlayer player, String[] args,
 | 
			
		||||
        RunnableVal3<Command, Runnable, Runnable> confirm,
 | 
			
		||||
        RunnableVal2<Command, CommandResult> whenDone) {
 | 
			
		||||
        // Clear perm caching //
 | 
			
		||||
        player.deleteMeta("perm");
 | 
			
		||||
        // Optional command scope //
 | 
			
		||||
        Location loc = null;
 | 
			
		||||
        Plot plot = null;
 | 
			
		||||
        boolean tp = false;
 | 
			
		||||
        if (args.length >= 2) {
 | 
			
		||||
            PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
            Plot newPlot = Plot.fromString(area, args[0]);
 | 
			
		||||
            if (newPlot != null && (player instanceof ConsolePlayer || newPlot.getArea()
 | 
			
		||||
                .equals(area) || Permissions.hasPermission(player, C.PERMISSION_ADMIN)) && !newPlot
 | 
			
		||||
                .isDenied(player.getUUID())) {
 | 
			
		||||
                Location newLoc = newPlot.getCenter();
 | 
			
		||||
                if (player.canTeleport(newLoc)) {
 | 
			
		||||
                    // Save meta
 | 
			
		||||
                    loc = player.getMeta(PlotPlayer.META_LOCATION);
 | 
			
		||||
                    plot = player.getMeta(PlotPlayer.META_LAST_PLOT);
 | 
			
		||||
                    tp = true;
 | 
			
		||||
                    // Set loc
 | 
			
		||||
                    player.setMeta(PlotPlayer.META_LOCATION, newLoc);
 | 
			
		||||
                    player.setMeta(PlotPlayer.META_LAST_PLOT, newPlot);
 | 
			
		||||
                } else {
 | 
			
		||||
                    C.BORDER.send(player);
 | 
			
		||||
                }
 | 
			
		||||
                // Trim command
 | 
			
		||||
                args = Arrays.copyOfRange(args, 1, args.length);
 | 
			
		||||
            }
 | 
			
		||||
            if (args.length >= 2 && !args[0].isEmpty() && args[0].charAt(0) == '-') {
 | 
			
		||||
                switch (args[0].substring(1)) {
 | 
			
		||||
                    case "f":
 | 
			
		||||
                        confirm = new RunnableVal3<Command, Runnable, Runnable>() {
 | 
			
		||||
                            @Override
 | 
			
		||||
                            public void run(Command cmd, Runnable success, Runnable failure) {
 | 
			
		||||
                                if (EconHandler.manager != null) {
 | 
			
		||||
                                    PlotArea area = player.getApplicablePlotArea();
 | 
			
		||||
                                    if (area != null) {
 | 
			
		||||
                                        Expression<Double> priceEval =
 | 
			
		||||
                                            area.PRICES.get(cmd.getFullId());
 | 
			
		||||
                                        Double price =
 | 
			
		||||
                                            priceEval != null ? priceEval.evaluate(0d) : 0d;
 | 
			
		||||
                                        if (price != 0d
 | 
			
		||||
                                            && EconHandler.manager.getMoney(player) < price) {
 | 
			
		||||
                                            if (failure != null) {
 | 
			
		||||
                                                failure.run();
 | 
			
		||||
                                            }
 | 
			
		||||
                                            return;
 | 
			
		||||
                                        }
 | 
			
		||||
                                    }
 | 
			
		||||
                                }
 | 
			
		||||
                                if (success != null) {
 | 
			
		||||
                                    success.run();
 | 
			
		||||
                                }
 | 
			
		||||
                            }
 | 
			
		||||
                        };
 | 
			
		||||
                        args = Arrays.copyOfRange(args, 1, args.length);
 | 
			
		||||
                        break;
 | 
			
		||||
                    default:
 | 
			
		||||
                        C.INVALID_COMMAND_FLAG.send(player);
 | 
			
		||||
                        return;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        try {
 | 
			
		||||
            super.execute(player, args, confirm, whenDone);
 | 
			
		||||
        } catch (CommandException e) {
 | 
			
		||||
            throw e;
 | 
			
		||||
        } catch (Throwable e) {
 | 
			
		||||
            e.printStackTrace();
 | 
			
		||||
            String message = e.getLocalizedMessage();
 | 
			
		||||
            if (message != null) {
 | 
			
		||||
                C.ERROR.send(player, message);
 | 
			
		||||
            } else {
 | 
			
		||||
                C.ERROR.send(player);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        // Reset command scope //
 | 
			
		||||
        if (tp && !(player instanceof ConsolePlayer)) {
 | 
			
		||||
            if (loc == null) {
 | 
			
		||||
                player.deleteMeta(PlotPlayer.META_LOCATION);
 | 
			
		||||
            } else {
 | 
			
		||||
                player.setMeta(PlotPlayer.META_LOCATION, loc);
 | 
			
		||||
            }
 | 
			
		||||
            if (plot == null) {
 | 
			
		||||
                player.deleteMeta(PlotPlayer.META_LAST_PLOT);
 | 
			
		||||
            } else {
 | 
			
		||||
                player.setMeta(PlotPlayer.META_LAST_PLOT, plot);
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean canExecute(PlotPlayer player, boolean message) {
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,198 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.Settings;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.*;
 | 
			
		||||
 | 
			
		||||
import java.util.UUID;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "merge", aliases = "m",
 | 
			
		||||
    description = "Merge the plot you are standing on, with another plot",
 | 
			
		||||
    permission = "plots.merge", usage = "/plot merge <all|n|e|s|w> [removeroads]",
 | 
			
		||||
    category = CommandCategory.SETTINGS, requiredType = RequiredType.NONE, confirmation = true)
 | 
			
		||||
public class Merge extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    public static final String[] values = new String[] {"north", "east", "south", "west", "auto"};
 | 
			
		||||
    public static final String[] aliases = new String[] {"n", "e", "s", "w", "all"};
 | 
			
		||||
 | 
			
		||||
    public static String direction(float yaw) {
 | 
			
		||||
        yaw = yaw / 90;
 | 
			
		||||
        int i = Math.round(yaw);
 | 
			
		||||
        switch (i) {
 | 
			
		||||
            case -4:
 | 
			
		||||
            case 0:
 | 
			
		||||
            case 4:
 | 
			
		||||
                return "SOUTH";
 | 
			
		||||
            case -1:
 | 
			
		||||
            case 3:
 | 
			
		||||
                return "EAST";
 | 
			
		||||
            case -2:
 | 
			
		||||
            case 2:
 | 
			
		||||
                return "NORTH";
 | 
			
		||||
            case -3:
 | 
			
		||||
            case 1:
 | 
			
		||||
                return "WEST";
 | 
			
		||||
            default:
 | 
			
		||||
                return "";
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocationFull();
 | 
			
		||||
        final Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        UUID uuid = player.getUUID();
 | 
			
		||||
        if (!plot.isOwner(uuid)) {
 | 
			
		||||
            if (!Permissions.hasPermission(player, C.PERMISSION_ADMIN_COMMAND_MERGE)) {
 | 
			
		||||
                MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
                return false;
 | 
			
		||||
            } else {
 | 
			
		||||
                uuid = plot.guessOwner();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        final PlotArea plotArea = plot.getArea();
 | 
			
		||||
        Expression<Double> priceExr =
 | 
			
		||||
            plotArea.PRICES.getOrDefault("merge", Expression.constant(0d));
 | 
			
		||||
        final int size = plot.getConnectedPlots().size();
 | 
			
		||||
        final double price = priceExr.evaluate((double) size);
 | 
			
		||||
        if (EconHandler.manager != null && plotArea.USE_ECONOMY && price > 0d
 | 
			
		||||
            && EconHandler.manager.getMoney(player) < price) {
 | 
			
		||||
            sendMessage(player, C.CANNOT_AFFORD_MERGE, String.valueOf(price));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        final int maxSize =
 | 
			
		||||
            Permissions.hasPermissionRange(player, "plots.merge", Settings.Limit.MAX_PLOTS);
 | 
			
		||||
        if (size - 1 > maxSize) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PERMISSION, "plots.merge." + (size + 1));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        int direction = -1;
 | 
			
		||||
        if (args.length == 0) {
 | 
			
		||||
            switch (direction(player.getLocationFull().getYaw())) {
 | 
			
		||||
                case "NORTH":
 | 
			
		||||
                    direction = 0;
 | 
			
		||||
                    break;
 | 
			
		||||
                case "EAST":
 | 
			
		||||
                    direction = 1;
 | 
			
		||||
                    break;
 | 
			
		||||
                case "SOUTH":
 | 
			
		||||
                    direction = 2;
 | 
			
		||||
                    break;
 | 
			
		||||
                case "WEST":
 | 
			
		||||
                    direction = 3;
 | 
			
		||||
                    break;
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            if ("all".equalsIgnoreCase(args[0]) || "auto".equalsIgnoreCase(args[0])) {
 | 
			
		||||
                boolean terrain = true;
 | 
			
		||||
                if (args.length == 2) {
 | 
			
		||||
                    terrain = "true".equalsIgnoreCase(args[1]);
 | 
			
		||||
                }
 | 
			
		||||
                if (!terrain && !Permissions.hasPermission(player, C.PERMISSION_MERGE_KEEPROAD)) {
 | 
			
		||||
                    MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_MERGE_KEEPROAD.s());
 | 
			
		||||
                    return true;
 | 
			
		||||
                }
 | 
			
		||||
                if (plot.autoMerge(-1, maxSize, uuid, terrain)) {
 | 
			
		||||
                    if (EconHandler.manager != null && plotArea.USE_ECONOMY && price > 0d) {
 | 
			
		||||
                        EconHandler.manager.withdrawMoney(player, price);
 | 
			
		||||
                        sendMessage(player, C.REMOVED_BALANCE, String.valueOf(price));
 | 
			
		||||
                    }
 | 
			
		||||
                    MainUtil.sendMessage(player, C.SUCCESS_MERGE);
 | 
			
		||||
                    return true;
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.NO_AVAILABLE_AUTOMERGE);
 | 
			
		||||
                return false;
 | 
			
		||||
 | 
			
		||||
            }
 | 
			
		||||
            for (int i = 0; i < values.length; i++) {
 | 
			
		||||
                if (args[0].equalsIgnoreCase(values[i]) || args[0].equalsIgnoreCase(aliases[i])) {
 | 
			
		||||
                    direction = i;
 | 
			
		||||
                    break;
 | 
			
		||||
                }
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (direction == -1) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.COMMAND_SYNTAX,
 | 
			
		||||
                "/plot merge <" + StringMan.join(values, "|") + "> [removeroads]");
 | 
			
		||||
            MainUtil
 | 
			
		||||
                .sendMessage(player, C.DIRECTION.s().replaceAll("%dir%", direction(loc.getYaw())));
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        final boolean terrain;
 | 
			
		||||
        if (args.length == 2) {
 | 
			
		||||
            terrain = "true".equalsIgnoreCase(args[1]);
 | 
			
		||||
        } else {
 | 
			
		||||
            terrain = true;
 | 
			
		||||
        }
 | 
			
		||||
        if (!terrain && !Permissions.hasPermission(player, C.PERMISSION_MERGE_KEEPROAD)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_MERGE_KEEPROAD.s());
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot.autoMerge(direction, maxSize - size, uuid, terrain)) {
 | 
			
		||||
            if (EconHandler.manager != null && plotArea.USE_ECONOMY && price > 0d) {
 | 
			
		||||
                EconHandler.manager.withdrawMoney(player, price);
 | 
			
		||||
                sendMessage(player, C.REMOVED_BALANCE, String.valueOf(price));
 | 
			
		||||
            }
 | 
			
		||||
            MainUtil.sendMessage(player, C.SUCCESS_MERGE);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        Plot adjacent = plot.getRelative(direction);
 | 
			
		||||
        if (adjacent == null || !adjacent.hasOwner() || adjacent.getMerged((direction + 2) % 4)
 | 
			
		||||
            || adjacent.isOwner(uuid)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_AVAILABLE_AUTOMERGE);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!Permissions.hasPermission(player, C.PERMISSION_MERGE_OTHER)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PERMISSION, C.PERMISSION_MERGE_OTHER);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        java.util.Set<UUID> uuids = adjacent.getOwners();
 | 
			
		||||
        boolean isOnline = false;
 | 
			
		||||
        for (final UUID owner : uuids) {
 | 
			
		||||
            final PlotPlayer accepter = UUIDHandler.getPlayer(owner);
 | 
			
		||||
            if (accepter == null) {
 | 
			
		||||
                continue;
 | 
			
		||||
            }
 | 
			
		||||
            isOnline = true;
 | 
			
		||||
            final int dir = direction;
 | 
			
		||||
            Runnable run = () -> {
 | 
			
		||||
                MainUtil.sendMessage(accepter, C.MERGE_ACCEPTED);
 | 
			
		||||
                plot.autoMerge(dir, maxSize - size, owner, terrain);
 | 
			
		||||
                PlotPlayer plotPlayer = UUIDHandler.getPlayer(player.getUUID());
 | 
			
		||||
                if (plotPlayer == null) {
 | 
			
		||||
                    sendMessage(accepter, C.MERGE_NOT_VALID);
 | 
			
		||||
                    return;
 | 
			
		||||
                }
 | 
			
		||||
                if (EconHandler.manager != null && plotArea.USE_ECONOMY && price > 0d) {
 | 
			
		||||
                    if (EconHandler.manager.getMoney(player) < price) {
 | 
			
		||||
                        sendMessage(player, C.CANNOT_AFFORD_MERGE, String.valueOf(price));
 | 
			
		||||
                        return;
 | 
			
		||||
                    }
 | 
			
		||||
                    EconHandler.manager.withdrawMoney(player, price);
 | 
			
		||||
                    sendMessage(player, C.REMOVED_BALANCE, String.valueOf(price));
 | 
			
		||||
                }
 | 
			
		||||
                MainUtil.sendMessage(player, C.SUCCESS_MERGE);
 | 
			
		||||
            };
 | 
			
		||||
            if (hasConfirmation(player)) {
 | 
			
		||||
                CmdConfirm.addPending(accepter,
 | 
			
		||||
                    C.MERGE_REQUEST_CONFIRM.s().replaceAll("%s", player.getName()), run);
 | 
			
		||||
            } else {
 | 
			
		||||
                run.run();
 | 
			
		||||
            }
 | 
			
		||||
        }
 | 
			
		||||
        if (!isOnline) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_AVAILABLE_AUTOMERGE);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        MainUtil.sendMessage(player, C.MERGE_REQUESTED);
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,29 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
 | 
			
		||||
/**
 | 
			
		||||
 * @author manuelgu, altered by Citymonstret
 | 
			
		||||
 */
 | 
			
		||||
@CommandDeclaration(command = "middle", aliases = {"center", "centre"},
 | 
			
		||||
    description = "Teleports you to the center of the plot", usage = "/plot middle",
 | 
			
		||||
    category = CommandCategory.TELEPORT, requiredType = RequiredType.NONE) public class Middle
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] arguments) {
 | 
			
		||||
        Location location = player.getLocation();
 | 
			
		||||
        Plot plot = location.getPlot();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.hasOwner()) {
 | 
			
		||||
            return sendMessage(player, C.PLOT_UNOWNED);
 | 
			
		||||
        }
 | 
			
		||||
        player.teleport(plot.getCenter());
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
@@ -1,65 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.PlotSquared;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Location;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.Plot;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotArea;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.PlotPlayer;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.MainUtil;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.util.Permissions;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(usage = "/plot move <X;Z>", command = "move", description = "Move a plot",
 | 
			
		||||
    aliases = {"debugmove"}, permission = "plots.move", category = CommandCategory.CLAIMING,
 | 
			
		||||
    requiredType = RequiredType.NONE) public class Move extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(final PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        Plot plot1 = loc.getPlotAbs();
 | 
			
		||||
        if (plot1 == null) {
 | 
			
		||||
            return !MainUtil.sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot1.isOwner(player.getUUID()) && !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN.s())) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        boolean override = false;
 | 
			
		||||
        if (args.length == 2 && args[1].equalsIgnoreCase("-f")) {
 | 
			
		||||
            args = new String[] {args[0]};
 | 
			
		||||
            override = true;
 | 
			
		||||
        }
 | 
			
		||||
        if (args.length != 1) {
 | 
			
		||||
            C.COMMAND_SYNTAX.send(player, getUsage());
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        PlotArea area = PlotSquared.get().getPlotAreaByString(args[0]);
 | 
			
		||||
        Plot plot2;
 | 
			
		||||
        if (area == null) {
 | 
			
		||||
            plot2 = MainUtil.getPlotFromString(player, args[0], true);
 | 
			
		||||
            if (plot2 == null) {
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        } else {
 | 
			
		||||
            plot2 = area.getPlotAbs(plot1.getId());
 | 
			
		||||
        }
 | 
			
		||||
        if (plot1.equals(plot2)) {
 | 
			
		||||
            MainUtil.sendMessage(player, C.NOT_VALID_PLOT_ID);
 | 
			
		||||
            MainUtil.sendMessage(player, C.COMMAND_SYNTAX, "/plot copy <X;Z>");
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot1.getArea().isCompatible(plot2.getArea()) && (!override || !Permissions
 | 
			
		||||
            .hasPermission(player, C.PERMISSION_ADMIN.s()))) {
 | 
			
		||||
            C.PLOTWORLD_INCOMPATIBLE.send(player);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
        if (plot1.move(plot2, () -> MainUtil.sendMessage(player, C.MOVE_SUCCESS), false)) {
 | 
			
		||||
            return true;
 | 
			
		||||
        } else {
 | 
			
		||||
            MainUtil.sendMessage(player, C.REQUIRES_UNOWNED);
 | 
			
		||||
            return false;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
@@ -1,69 +0,0 @@
 | 
			
		||||
package com.github.intellectualsites.plotsquared.plot.commands;
 | 
			
		||||
 | 
			
		||||
import com.github.intellectualsites.plotsquared.commands.CommandDeclaration;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.config.C;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.flag.Flags;
 | 
			
		||||
import com.github.intellectualsites.plotsquared.plot.object.*;
 | 
			
		||||
 | 
			
		||||
import java.util.Arrays;
 | 
			
		||||
import java.util.Collection;
 | 
			
		||||
import java.util.Locale;
 | 
			
		||||
 | 
			
		||||
@CommandDeclaration(command = "music", permission = "plots.music",
 | 
			
		||||
    description = "Play music in your plot", usage = "/plot music",
 | 
			
		||||
    category = CommandCategory.APPEARANCE, requiredType = RequiredType.PLAYER) public class Music
 | 
			
		||||
    extends SubCommand {
 | 
			
		||||
 | 
			
		||||
    private static final Collection<String> DISCS = Arrays
 | 
			
		||||
        .asList("music_disc_13", "music_disc_cat", "music_disc_blocks", "music_disc_chirp",
 | 
			
		||||
            "music_disc_far", "music_disc_mall", "music_disc_mellohi", "music_disc_stal",
 | 
			
		||||
            "music_disc_strad", "music_disc_ward", "music_disc_11", "music_disc_wait");
 | 
			
		||||
 | 
			
		||||
    @Override public boolean onCommand(PlotPlayer player, String[] args) {
 | 
			
		||||
        Location loc = player.getLocation();
 | 
			
		||||
        final Plot plot = loc.getPlotAbs();
 | 
			
		||||
        if (plot == null) {
 | 
			
		||||
            return !sendMessage(player, C.NOT_IN_PLOT);
 | 
			
		||||
        }
 | 
			
		||||
        if (!plot.isAdded(player.getUUID())) {
 | 
			
		||||
            sendMessage(player, C.NO_PLOT_PERMS);
 | 
			
		||||
            return true;
 | 
			
		||||
        }
 | 
			
		||||
        PlotInventory inv = new PlotInventory(player, 2, "Plot Jukebox") {
 | 
			
		||||
            @Override public boolean onClick(int index) {
 | 
			
		||||
                PlotItemStack item = getItem(index);
 | 
			
		||||
                if (item == null) {
 | 
			
		||||
                    return true;
 | 
			
		||||
                }
 | 
			
		||||
                if (item.getPlotBlock().equalsAny(7, "bedrock")) {
 | 
			
		||||
                    plot.removeFlag(Flags.MUSIC);
 | 
			
		||||
                    C.FLAG_REMOVED.send(player);
 | 
			
		||||
                } else if (item.name.toLowerCase(Locale.ENGLISH).contains("disc")) {
 | 
			
		||||
                    plot.setFlag(Flags.MUSIC, item.getPlotBlock().getRawId());
 | 
			
		||||
                    C.FLAG_ADDED.send(player);
 | 
			
		||||
                } else {
 | 
			
		||||
                    C.FLAG_NOT_ADDED.send(player);
 | 
			
		||||
                }
 | 
			
		||||
                return false;
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
        int index = 0;
 | 
			
		||||
 | 
			
		||||
        for (final String disc : DISCS) {
 | 
			
		||||
            final String name = String.format("&r&6%s", disc);
 | 
			
		||||
            final String[] lore = {"&r&aClick to play!"};
 | 
			
		||||
            final PlotItemStack item = new PlotItemStack(disc, 1, name, lore);
 | 
			
		||||
            inv.setItem(index++, item);
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        // Always add the cancel button
 | 
			
		||||
        // if (player.getMeta("music") != null) {
 | 
			
		||||
        String name = "&r&6Cancel music";
 | 
			
		||||
        String[] lore = {"&r&cClick to cancel!"};
 | 
			
		||||
        inv.setItem(index, new PlotItemStack("bedrock", 1, name, lore));
 | 
			
		||||
        // }
 | 
			
		||||
 | 
			
		||||
        inv.openInventory();
 | 
			
		||||
        return true;
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
Some files were not shown because too many files have changed in this diff Show More
		Reference in New Issue
	
	Block a user