mirror of
https://github.com/BentoBoxWorld/Level.git
synced 2024-12-25 10:38:20 +01:00
Reworked settings and scanner
Scanner now staggers chunk scanning over time.
This commit is contained in:
parent
71480798bc
commit
01d2bba4c5
@ -14,13 +14,13 @@ island:
|
|||||||
level:
|
level:
|
||||||
parameters: "[player]"
|
parameters: "[player]"
|
||||||
description: "calculate your island level or show the level of [player]"
|
description: "calculate your island level or show the level of [player]"
|
||||||
islandLevelIs: "Island level is"
|
island-level-is: "Island level is [level]"
|
||||||
requiredPointsToNextLevel: "[points] points required until the next level"
|
required-points-to-next-level: "[points] points required until the next level"
|
||||||
deaths: "([number] deaths)"
|
deaths: "([number] deaths)"
|
||||||
|
|
||||||
top:
|
top:
|
||||||
description: "show the Top Ten"
|
description: "show the Top Ten"
|
||||||
guiTitle: "Top Ten"
|
gui-title: "Top Ten"
|
||||||
guiHeading: "[name]:[rank]"
|
gui-heading: "[name]:[rank]"
|
||||||
islandLevel: "Level [level]"
|
island-level: "Level [level]"
|
||||||
|
|
@ -1,344 +0,0 @@
|
|||||||
package bskyblock.addon.level;
|
|
||||||
|
|
||||||
import java.util.ArrayList;
|
|
||||||
import java.util.HashMap;
|
|
||||||
import java.util.HashSet;
|
|
||||||
import java.util.Iterator;
|
|
||||||
import java.util.List;
|
|
||||||
import java.util.Optional;
|
|
||||||
import java.util.Set;
|
|
||||||
|
|
||||||
import org.bukkit.ChunkSnapshot;
|
|
||||||
import org.bukkit.Material;
|
|
||||||
import org.bukkit.World;
|
|
||||||
import org.bukkit.material.MaterialData;
|
|
||||||
|
|
||||||
import com.google.common.collect.HashMultiset;
|
|
||||||
import com.google.common.collect.Multiset;
|
|
||||||
import com.google.common.collect.Multiset.Entry;
|
|
||||||
|
|
||||||
import bskyblock.addon.level.config.Settings;
|
|
||||||
|
|
||||||
import com.google.common.collect.Multisets;
|
|
||||||
|
|
||||||
import us.tastybento.bskyblock.BSkyBlock;
|
|
||||||
import us.tastybento.bskyblock.api.commands.User;
|
|
||||||
import us.tastybento.bskyblock.database.objects.Island;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A class that calculates the level of an island very quickly by copying island
|
|
||||||
* chunks to a list and then processing asynchronously.
|
|
||||||
*
|
|
||||||
* @author tastybento
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
public class ChunkScanner {
|
|
||||||
private static final boolean DEBUG = false;
|
|
||||||
protected static final boolean LEVEL_LOGGING = false;
|
|
||||||
private final Level addon;
|
|
||||||
private final Set<ChunkSnapshot> finalChunk;
|
|
||||||
private final Results result;
|
|
||||||
private final Optional<User> asker;
|
|
||||||
|
|
||||||
|
|
||||||
public ChunkScanner(Level plugin, Island island) {
|
|
||||||
this.addon = plugin;
|
|
||||||
// Get the chunks to scan
|
|
||||||
finalChunk = getIslandChunks(island);
|
|
||||||
this.asker = Optional.empty();
|
|
||||||
// Create new level result
|
|
||||||
result = new Results();
|
|
||||||
runAsyncCount(island);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Calculates the level of an island
|
|
||||||
* @param addon
|
|
||||||
* @param island - island that is being calculated
|
|
||||||
* @param asker - the user who wants the report
|
|
||||||
*/
|
|
||||||
public ChunkScanner(Level addon, Island island, User asker) {
|
|
||||||
this.addon = addon;
|
|
||||||
// Get the chunks to scan
|
|
||||||
finalChunk = getIslandChunks(island);
|
|
||||||
this.asker = Optional.of(asker);
|
|
||||||
// Create new level result
|
|
||||||
result = new Results();
|
|
||||||
runAsyncCount(island);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void runAsyncCount(Island island) {
|
|
||||||
// Run AsyncTask to count blocks in the chunk snapshots
|
|
||||||
addon.getServer().getScheduler().runTaskAsynchronously(addon.getBSkyBlock(), new Runnable() {
|
|
||||||
|
|
||||||
@SuppressWarnings("deprecation")
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
// Copy the limits hashmap
|
|
||||||
HashMap<MaterialData, Integer> limitCount = new HashMap<MaterialData, Integer>(Settings.blockLimits);
|
|
||||||
// Calculate the island score
|
|
||||||
for (ChunkSnapshot chunk: finalChunk) {
|
|
||||||
for (int x = 0; x< 16; x++) {
|
|
||||||
// Check if the block coord is inside the protection zone and if not, don't count it
|
|
||||||
if (chunk.getX() * 16 + x < island.getMinProtectedX() || chunk.getX() * 16 + x >= island.getMinProtectedX() + (island.getProtectionRange() * 2)) {
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("Block is outside protected area - x = " + (chunk.getX() * 16 + x));
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
for (int z = 0; z < 16; z++) {
|
|
||||||
// Check if the block coord is inside the protection zone and if not, don't count it
|
|
||||||
if (chunk.getZ() * 16 + z < island.getMinProtectedZ() || chunk.getZ() * 16 + z >= island.getMinProtectedZ() + (island.getProtectionRange() * 2)) {
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("Block is outside protected area - z = " + (chunk.getZ() * 16 + z));
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
for (int y = 0; y < island.getWorld().getMaxHeight(); y++) {
|
|
||||||
Material type = chunk.getBlockType(x, y, z);
|
|
||||||
// Currently, there is no alternative to using block data (Dec 2017)
|
|
||||||
MaterialData md = new MaterialData(type, (byte) chunk.getBlockData(x, y, z));
|
|
||||||
MaterialData generic = new MaterialData(type);
|
|
||||||
if (!type.equals(Material.AIR)) { // AIR
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("Block is inside protected area " + (chunk.getX() * 16) + "," + (chunk.getZ() * 16 + z));
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("Block is " + md + "[" + generic +"]");
|
|
||||||
if (limitCount.containsKey(md) && Settings.blockValues.containsKey(md)) {
|
|
||||||
int count = limitCount.get(md);
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: Count for non-generic " + md + " is " + count);
|
|
||||||
if (count > 0) {
|
|
||||||
limitCount.put(md, --count);
|
|
||||||
if (Settings.seaHeight > 0 && y<=Settings.seaHeight) {
|
|
||||||
result.underWaterBlockCount += Settings.blockValues.get(md);
|
|
||||||
result.uwCount.add(md);
|
|
||||||
} else {
|
|
||||||
result.rawBlockCount += Settings.blockValues.get(md);
|
|
||||||
result.mdCount.add(md);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
result.ofCount.add(md);
|
|
||||||
}
|
|
||||||
} else if (limitCount.containsKey(generic) && Settings.blockValues.containsKey(generic)) {
|
|
||||||
int count = limitCount.get(generic);
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: Count for generic " + generic + " is " + count);
|
|
||||||
if (count > 0) {
|
|
||||||
limitCount.put(generic, --count);
|
|
||||||
if (Settings.seaHeight > 0 && y<=Settings.seaHeight) {
|
|
||||||
result.underWaterBlockCount += Settings.blockValues.get(generic);
|
|
||||||
result.uwCount.add(md);
|
|
||||||
} else {
|
|
||||||
result.rawBlockCount += Settings.blockValues.get(generic);
|
|
||||||
result.mdCount.add(md);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
result.ofCount.add(md);
|
|
||||||
}
|
|
||||||
} else if (Settings.blockValues.containsKey(md)) {
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: Adding " + md + " = " + Settings.blockValues.get(md));
|
|
||||||
if (Settings.seaHeight > 0 && y<=Settings.seaHeight) {
|
|
||||||
result.underWaterBlockCount += Settings.blockValues.get(md);
|
|
||||||
result.uwCount.add(md);
|
|
||||||
} else {
|
|
||||||
result.rawBlockCount += Settings.blockValues.get(md);
|
|
||||||
result.mdCount.add(md);
|
|
||||||
}
|
|
||||||
} else if (Settings.blockValues.containsKey(generic)) {
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: Adding " + generic + " = " + Settings.blockValues.get(generic));
|
|
||||||
if (Settings.seaHeight > 0 && y<=Settings.seaHeight) {
|
|
||||||
result.underWaterBlockCount += Settings.blockValues.get(generic);
|
|
||||||
result.uwCount.add(md);
|
|
||||||
} else {
|
|
||||||
result.rawBlockCount += Settings.blockValues.get(generic);
|
|
||||||
result.mdCount.add(md);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
result.ncCount.add(md);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
result.rawBlockCount += (long)((double)result.underWaterBlockCount * Settings.underWaterMultiplier);
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: block count = "+result.rawBlockCount);
|
|
||||||
// Set the death penalty
|
|
||||||
result.deathHandicap = BSkyBlock.getInstance().getPlayers().getDeaths(island.getOwner()) * Settings.deathpenalty;
|
|
||||||
// Set final score
|
|
||||||
result.score = (result.rawBlockCount / Settings.levelCost) - result.deathHandicap;
|
|
||||||
|
|
||||||
// Return to main thread
|
|
||||||
addon.getServer().getScheduler().runTask(addon.getBSkyBlock(), new Runnable() {
|
|
||||||
|
|
||||||
@Override
|
|
||||||
public void run() {
|
|
||||||
// Run any modifications
|
|
||||||
// Save the value
|
|
||||||
addon.setIslandLevel(island.getOwner(), result.score);
|
|
||||||
// All done.
|
|
||||||
if (asker.isPresent()) {
|
|
||||||
// Tell the asker the result
|
|
||||||
if (asker.get().isPlayer() && asker.get().isOnline()) {
|
|
||||||
asker.get().sendRawMessage("Your level is " + result.score);
|
|
||||||
} else {
|
|
||||||
// Console
|
|
||||||
sendConsoleReport(asker);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private void sendConsoleReport(Optional<User> asker) {
|
|
||||||
List<String> reportLines = new ArrayList<>();
|
|
||||||
// provide counts
|
|
||||||
reportLines.add("Level Log for island at " + island.getCenter());
|
|
||||||
reportLines.add("Island owner UUID = " + island.getOwner());
|
|
||||||
reportLines.add("Total block value count = " + String.format("%,d",result.rawBlockCount));
|
|
||||||
reportLines.add("Level cost = " + Settings.levelCost);
|
|
||||||
//reportLines.add("Level multiplier = " + levelMultiplier + " (Player must be online to get a permission multiplier)");
|
|
||||||
//reportLines.add("Schematic level handicap = " + levelHandicap + " (level is reduced by this amount)");
|
|
||||||
reportLines.add("Deaths handicap = " + result.deathHandicap);
|
|
||||||
reportLines.add("Level calculated = " + result.score);
|
|
||||||
reportLines.add("==================================");
|
|
||||||
int total = 0;
|
|
||||||
if (!result.uwCount.isEmpty()) {
|
|
||||||
reportLines.add("Underwater block count (Multiplier = x" + Settings.underWaterMultiplier + ") value");
|
|
||||||
reportLines.add("Total number of underwater blocks = " + String.format("%,d",result.uwCount.size()));
|
|
||||||
Iterable<Multiset.Entry<MaterialData>> entriesSortedByCount =
|
|
||||||
Multisets.copyHighestCountFirst(result.uwCount).entrySet();
|
|
||||||
Iterator<Entry<MaterialData>> it = entriesSortedByCount.iterator();
|
|
||||||
while (it.hasNext()) {
|
|
||||||
Entry<MaterialData> en = it.next();
|
|
||||||
MaterialData type = en.getElement();
|
|
||||||
|
|
||||||
int value = 0;
|
|
||||||
if (Settings.blockValues.containsKey(type)) {
|
|
||||||
// Specific
|
|
||||||
value = Settings.blockValues.get(type);
|
|
||||||
} else if (Settings.blockValues.containsKey(new MaterialData(type.getItemType()))) {
|
|
||||||
// Generic
|
|
||||||
value = Settings.blockValues.get(new MaterialData(type.getItemType()));
|
|
||||||
}
|
|
||||||
if (value > 0) {
|
|
||||||
reportLines.add(type.toString() + ":"
|
|
||||||
+ String.format("%,d",en.getCount()) + " blocks x " + value + " = " + (value * en.getCount()));
|
|
||||||
total += (value * en.getCount());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
reportLines.add("Subtotal = " + total);
|
|
||||||
reportLines.add("==================================");
|
|
||||||
}
|
|
||||||
reportLines.add("Regular block count");
|
|
||||||
reportLines.add("Total number of blocks = " + String.format("%,d",result.mdCount.size()));
|
|
||||||
//Iterable<Multiset.Entry<MaterialData>> entriesSortedByCount =
|
|
||||||
// Multisets.copyHighestCountFirst(mdCount).entrySet();
|
|
||||||
Iterable<Multiset.Entry<MaterialData>> entriesSortedByCount =
|
|
||||||
result.mdCount.entrySet();
|
|
||||||
Iterator<Entry<MaterialData>> it = entriesSortedByCount.iterator();
|
|
||||||
while (it.hasNext()) {
|
|
||||||
Entry<MaterialData> en = it.next();
|
|
||||||
MaterialData type = en.getElement();
|
|
||||||
int value = 0;
|
|
||||||
if (Settings.blockValues.containsKey(type)) {
|
|
||||||
// Specific
|
|
||||||
value = Settings.blockValues.get(type);
|
|
||||||
} else if (Settings.blockValues.containsKey(new MaterialData(type.getItemType()))) {
|
|
||||||
// Generic
|
|
||||||
value = Settings.blockValues.get(new MaterialData(type.getItemType()));
|
|
||||||
}
|
|
||||||
if (value > 0) {
|
|
||||||
reportLines.add(type.toString() + ":"
|
|
||||||
+ String.format("%,d",en.getCount()) + " blocks x " + value + " = " + (value * en.getCount()));
|
|
||||||
total += (value * en.getCount());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
reportLines.add("Total = " + total);
|
|
||||||
reportLines.add("==================================");
|
|
||||||
reportLines.add("Blocks not counted because they exceeded limits: " + String.format("%,d",result.ofCount.size()));
|
|
||||||
//entriesSortedByCount = Multisets.copyHighestCountFirst(ofCount).entrySet();
|
|
||||||
entriesSortedByCount = result.ofCount.entrySet();
|
|
||||||
it = entriesSortedByCount.iterator();
|
|
||||||
while (it.hasNext()) {
|
|
||||||
Entry<MaterialData> type = it.next();
|
|
||||||
Integer limit = Settings.blockLimits.get(type.getElement());
|
|
||||||
String explain = ")";
|
|
||||||
if (limit == null) {
|
|
||||||
MaterialData generic = new MaterialData(type.getElement().getItemType());
|
|
||||||
limit = Settings.blockLimits.get(generic);
|
|
||||||
explain = " - All types)";
|
|
||||||
}
|
|
||||||
reportLines.add(type.getElement().toString() + ": " + String.format("%,d",type.getCount()) + " blocks (max " + limit + explain);
|
|
||||||
}
|
|
||||||
reportLines.add("==================================");
|
|
||||||
reportLines.add("Blocks on island that are not in config.yml");
|
|
||||||
reportLines.add("Total number = " + String.format("%,d",result.ncCount.size()));
|
|
||||||
//entriesSortedByCount = Multisets.copyHighestCountFirst(ncCount).entrySet();
|
|
||||||
entriesSortedByCount = result.ncCount.entrySet();
|
|
||||||
it = entriesSortedByCount.iterator();
|
|
||||||
while (it.hasNext()) {
|
|
||||||
Entry<MaterialData> type = it.next();
|
|
||||||
reportLines.add(type.getElement().toString() + ": " + String.format("%,d",type.getCount()) + " blocks");
|
|
||||||
}
|
|
||||||
reportLines.add("=================================");
|
|
||||||
|
|
||||||
for (String line : reportLines) {
|
|
||||||
asker.get().sendRawMessage(line);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
});
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
private Set<ChunkSnapshot> getIslandChunks(Island island) {
|
|
||||||
// Check if player's island world is the nether or overworld and adjust accordingly
|
|
||||||
final World world = island.getWorld();
|
|
||||||
// Get the chunks
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: Getting chunks. Protection range = " + island.getProtectionRange());
|
|
||||||
//long nano = System.nanoTime();
|
|
||||||
Set<ChunkSnapshot> chunkSnapshot = new HashSet<ChunkSnapshot>();
|
|
||||||
for (int x = island.getMinProtectedX(); x < (island.getMinProtectedX() + (island.getProtectionRange() *2) + 16); x += 16) {
|
|
||||||
for (int z = island.getMinProtectedZ(); z < (island.getMinProtectedZ() + (island.getProtectionRange() * 2) + 16); z += 16) {
|
|
||||||
if (!world.isChunkLoaded((int)((double)x/16), (int)((double)z/16))) {
|
|
||||||
// If the chunk isn't already generated, load it but don't try and generate it
|
|
||||||
world.loadChunk((int)((double)x/16), (int)((double)z/16), false);
|
|
||||||
}
|
|
||||||
// chunk is loaded
|
|
||||||
chunkSnapshot.add(world.getBlockAt(x, 0, z).getChunk().getChunkSnapshot());
|
|
||||||
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: getting chunk at " + x + ", " + z);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (DEBUG)
|
|
||||||
addon.getLogger().info("DEBUG: size of chunk snapshot = " + chunkSnapshot.size());
|
|
||||||
return chunkSnapshot;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Results class
|
|
||||||
* @author ben
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
public class Results {
|
|
||||||
Multiset<MaterialData> mdCount = HashMultiset.create();
|
|
||||||
Multiset<MaterialData> uwCount = HashMultiset.create();
|
|
||||||
Multiset<MaterialData> ncCount = HashMultiset.create();
|
|
||||||
Multiset<MaterialData> ofCount = HashMultiset.create();
|
|
||||||
long rawBlockCount;
|
|
||||||
Island island;
|
|
||||||
long underWaterBlockCount = 0;
|
|
||||||
long score;
|
|
||||||
int deathHandicap;
|
|
||||||
}
|
|
||||||
}
|
|
@ -13,7 +13,7 @@ import bskyblock.addon.level.commands.AdminLevel;
|
|||||||
import bskyblock.addon.level.commands.AdminTop;
|
import bskyblock.addon.level.commands.AdminTop;
|
||||||
import bskyblock.addon.level.commands.IslandLevel;
|
import bskyblock.addon.level.commands.IslandLevel;
|
||||||
import bskyblock.addon.level.commands.IslandTop;
|
import bskyblock.addon.level.commands.IslandTop;
|
||||||
import bskyblock.addon.level.config.PluginConfig;
|
import bskyblock.addon.level.config.Settings;
|
||||||
import bskyblock.addon.level.database.object.LevelsData;
|
import bskyblock.addon.level.database.object.LevelsData;
|
||||||
import us.tastybento.bskyblock.BSkyBlock;
|
import us.tastybento.bskyblock.BSkyBlock;
|
||||||
import us.tastybento.bskyblock.Constants;
|
import us.tastybento.bskyblock.Constants;
|
||||||
@ -33,6 +33,9 @@ public class Level extends Addon {
|
|||||||
|
|
||||||
// The BSkyBlock plugin instance.
|
// The BSkyBlock plugin instance.
|
||||||
private BSkyBlock bSkyBlock;
|
private BSkyBlock bSkyBlock;
|
||||||
|
|
||||||
|
// Settings
|
||||||
|
private Settings settings;
|
||||||
|
|
||||||
// Level calc checker
|
// Level calc checker
|
||||||
BukkitTask checker = null;
|
BukkitTask checker = null;
|
||||||
@ -58,7 +61,7 @@ public class Level extends Addon {
|
|||||||
@Override
|
@Override
|
||||||
public void onEnable() {
|
public void onEnable() {
|
||||||
// Load the plugin's config
|
// Load the plugin's config
|
||||||
new PluginConfig(this);
|
settings = new Settings(this);
|
||||||
// Get the BSkyBlock plugin. This will be available because this plugin depends on it in plugin.yml.
|
// Get the BSkyBlock plugin. This will be available because this plugin depends on it in plugin.yml.
|
||||||
bSkyBlock = BSkyBlock.getInstance();
|
bSkyBlock = BSkyBlock.getInstance();
|
||||||
// Check if it is enabled - it might be loaded, but not enabled.
|
// Check if it is enabled - it might be loaded, but not enabled.
|
||||||
@ -100,6 +103,13 @@ public class Level extends Addon {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return the settings
|
||||||
|
*/
|
||||||
|
public final Settings getSettings() {
|
||||||
|
return settings;
|
||||||
|
}
|
||||||
|
|
||||||
public void load() {
|
public void load() {
|
||||||
try {
|
try {
|
||||||
for (LevelsData level : handler.loadObjects()) {
|
for (LevelsData level : handler.loadObjects()) {
|
||||||
|
@ -51,7 +51,7 @@ public class LevelPresenter extends LevelPlugin {
|
|||||||
if (!onLevelWaitTime(sender) || levelWait <= 0 || sender.isOp() || sender.hasPermission(Constants.PERMPREFIX + "mod.info")) {
|
if (!onLevelWaitTime(sender) || levelWait <= 0 || sender.isOp() || sender.hasPermission(Constants.PERMPREFIX + "mod.info")) {
|
||||||
sender.sendRawMessage(ChatColor.GREEN + "Calculating level, please wait...");
|
sender.sendRawMessage(ChatColor.GREEN + "Calculating level, please wait...");
|
||||||
setLevelWaitTime(sender);
|
setLevelWaitTime(sender);
|
||||||
new ChunkScanner(plugin, bSkyBlock.getIslands().getIsland(targetPlayer), sender);
|
new Scanner(plugin, bSkyBlock.getIslands().getIsland(targetPlayer), sender);
|
||||||
} else {
|
} else {
|
||||||
sender.sendRawMessage( ChatColor.YELLOW + String.valueOf(getLevelWaitTime(sender)));
|
sender.sendRawMessage( ChatColor.YELLOW + String.valueOf(getLevelWaitTime(sender)));
|
||||||
}
|
}
|
||||||
|
319
src/main/java/bskyblock/addon/level/Scanner.java
Normal file
319
src/main/java/bskyblock/addon/level/Scanner.java
Normal file
@ -0,0 +1,319 @@
|
|||||||
|
package bskyblock.addon.level;
|
||||||
|
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.HashSet;
|
||||||
|
import java.util.Iterator;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Set;
|
||||||
|
|
||||||
|
import org.bukkit.ChunkSnapshot;
|
||||||
|
import org.bukkit.Material;
|
||||||
|
import org.bukkit.material.MaterialData;
|
||||||
|
import org.bukkit.scheduler.BukkitTask;
|
||||||
|
|
||||||
|
import com.google.common.collect.HashMultiset;
|
||||||
|
import com.google.common.collect.Multiset;
|
||||||
|
import com.google.common.collect.Multiset.Entry;
|
||||||
|
import com.google.common.collect.Multisets;
|
||||||
|
|
||||||
|
import us.tastybento.bskyblock.BSkyBlock;
|
||||||
|
import us.tastybento.bskyblock.api.commands.User;
|
||||||
|
import us.tastybento.bskyblock.database.objects.Island;
|
||||||
|
import us.tastybento.bskyblock.util.Pair;
|
||||||
|
|
||||||
|
public class Scanner {
|
||||||
|
|
||||||
|
private static final int MAX_CHUNKS = 50;
|
||||||
|
private static final long SPEED = 5;
|
||||||
|
private boolean checking = true;
|
||||||
|
private BukkitTask task;
|
||||||
|
|
||||||
|
private Level addon;
|
||||||
|
|
||||||
|
private Set<Pair<Integer, Integer>> chunksToScan;
|
||||||
|
private Island island;
|
||||||
|
private User asker;
|
||||||
|
private Results result;
|
||||||
|
|
||||||
|
// Copy the limits hashmap
|
||||||
|
HashMap<MaterialData, Integer> limitCount;
|
||||||
|
|
||||||
|
|
||||||
|
public Scanner(Level addon, Island island, User asker) {
|
||||||
|
this.addon = addon;
|
||||||
|
this.island = island;
|
||||||
|
this.asker = asker;
|
||||||
|
this.limitCount = new HashMap<>(addon.getSettings().getBlockLimits());
|
||||||
|
// Results go here
|
||||||
|
result = new Results();
|
||||||
|
|
||||||
|
// Get chunks to scan
|
||||||
|
chunksToScan = getChunksToScan(island);
|
||||||
|
|
||||||
|
// Start checking
|
||||||
|
checking = true;
|
||||||
|
|
||||||
|
// Start a recurring task until done or cancelled
|
||||||
|
task = addon.getServer().getScheduler().runTaskTimer(addon.getBSkyBlock(), () -> {
|
||||||
|
Set<ChunkSnapshot> chunkSnapshot = new HashSet<>();
|
||||||
|
if (checking) {
|
||||||
|
Iterator<Pair<Integer, Integer>> it = chunksToScan.iterator();
|
||||||
|
if (!it.hasNext()) {
|
||||||
|
// Nothing left
|
||||||
|
tidyUp();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// Add chunk snapshots to the list
|
||||||
|
while (it.hasNext() && chunkSnapshot.size() < MAX_CHUNKS) {
|
||||||
|
Pair<Integer, Integer> pair = it.next();
|
||||||
|
chunkSnapshot.add(island.getWorld().getChunkAt(pair.x, pair.z).getChunkSnapshot());
|
||||||
|
it.remove();
|
||||||
|
}
|
||||||
|
// Move to next step
|
||||||
|
checking = false;
|
||||||
|
checkChunksAsync(chunkSnapshot);
|
||||||
|
}
|
||||||
|
}, 0L, SPEED);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void checkChunksAsync(Set<ChunkSnapshot> chunkSnapshot) {
|
||||||
|
// Run async task to scan chunks
|
||||||
|
addon.getServer().getScheduler().runTaskAsynchronously(addon.getBSkyBlock(), () -> {
|
||||||
|
|
||||||
|
for (ChunkSnapshot chunk: chunkSnapshot) {
|
||||||
|
scanChunk(chunk);
|
||||||
|
}
|
||||||
|
// Nothing happened, change state
|
||||||
|
checking = true;
|
||||||
|
});
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
private void scanChunk(ChunkSnapshot chunk) {
|
||||||
|
for (int x = 0; x< 16; x++) {
|
||||||
|
// Check if the block coord is inside the protection zone and if not, don't count it
|
||||||
|
if (chunk.getX() * 16 + x < island.getMinProtectedX() || chunk.getX() * 16 + x >= island.getMinProtectedX() + (island.getProtectionRange() * 2)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
for (int z = 0; z < 16; z++) {
|
||||||
|
// Check if the block coord is inside the protection zone and if not, don't count it
|
||||||
|
if (chunk.getZ() * 16 + z < island.getMinProtectedZ() || chunk.getZ() * 16 + z >= island.getMinProtectedZ() + (island.getProtectionRange() * 2)) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int y = 0; y < island.getWorld().getMaxHeight(); y++) {
|
||||||
|
Material blockType = chunk.getBlockType(x, y, z);
|
||||||
|
boolean belowSeaLevel = (addon.getSettings().getSeaHeight() > 0 && y<=addon.getSettings().getSeaHeight()) ? true : false;
|
||||||
|
// Air is free
|
||||||
|
if (!blockType.equals(Material.AIR)) {
|
||||||
|
checkBlock(blockType, chunk.getBlockData(x, y, z), belowSeaLevel);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void checkBlock(Material type, int blockData, boolean belowSeaLevel) {
|
||||||
|
// Currently, there is no alternative to using block data (Feb 2018)
|
||||||
|
@SuppressWarnings("deprecation")
|
||||||
|
MaterialData md = new MaterialData(type, (byte) blockData);
|
||||||
|
int count = limitCount(md);
|
||||||
|
if (count > 0) {
|
||||||
|
if (belowSeaLevel) {
|
||||||
|
result.underWaterBlockCount += count;
|
||||||
|
result.uwCount.add(md);
|
||||||
|
} else {
|
||||||
|
result.rawBlockCount += count;
|
||||||
|
result.mdCount.add(md);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Checks if a block has been limited or not and whether a block has any value or not
|
||||||
|
* @param md
|
||||||
|
* @return value of the block if can be counted
|
||||||
|
*/
|
||||||
|
private int limitCount(MaterialData md) {
|
||||||
|
MaterialData generic = new MaterialData(md.getItemType());
|
||||||
|
if (limitCount.containsKey(md) && addon.getSettings().getBlockValues().containsKey(md)) {
|
||||||
|
int count = limitCount.get(md);
|
||||||
|
if (count > 0) {
|
||||||
|
limitCount.put(md, --count);
|
||||||
|
return addon.getSettings().getBlockValues().get(md);
|
||||||
|
} else {
|
||||||
|
result.ofCount.add(md);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
} else if (limitCount.containsKey(generic) && addon.getSettings().getBlockValues().containsKey(generic)) {
|
||||||
|
int count = limitCount.get(generic);
|
||||||
|
if (count > 0) {
|
||||||
|
limitCount.put(generic, --count);
|
||||||
|
return addon.getSettings().getBlockValues().get(generic);
|
||||||
|
} else {
|
||||||
|
result.ofCount.add(md);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
} else if (addon.getSettings().getBlockValues().containsKey(md)) {
|
||||||
|
return addon.getSettings().getBlockValues().get(md);
|
||||||
|
} else if (addon.getSettings().getBlockValues().containsKey(generic)) {
|
||||||
|
return addon.getSettings().getBlockValues().get(generic);
|
||||||
|
} else {
|
||||||
|
result.ncCount.add(md);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get a set of all the chunks in island
|
||||||
|
* @param island
|
||||||
|
* @return
|
||||||
|
*/
|
||||||
|
private Set<Pair<Integer, Integer>> getChunksToScan(Island island) {
|
||||||
|
// Get the chunks coords
|
||||||
|
Set<Pair<Integer, Integer>> chunkSnapshot = new HashSet<>();
|
||||||
|
for (int x = island.getMinProtectedX(); x < (island.getMinProtectedX() + (island.getProtectionRange() *2) + 16); x += 16) {
|
||||||
|
for (int z = island.getMinProtectedZ(); z < (island.getMinProtectedZ() + (island.getProtectionRange() * 2) + 16); z += 16) {
|
||||||
|
chunkSnapshot.add(new Pair<>(x/16,z/16));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return chunkSnapshot;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void tidyUp() {
|
||||||
|
// Cancel
|
||||||
|
task.cancel();
|
||||||
|
// Finalize calculations
|
||||||
|
result.rawBlockCount += (long)((double)result.underWaterBlockCount * addon.getSettings().getUnderWaterMultiplier());
|
||||||
|
// Set the death penalty
|
||||||
|
result.deathHandicap = BSkyBlock.getInstance().getPlayers().getDeaths(island.getOwner()) * addon.getSettings().getDeathPenalty();
|
||||||
|
// Set final score
|
||||||
|
result.score = (result.rawBlockCount / addon.getSettings().getLevelCost()) - result.deathHandicap;
|
||||||
|
// Run any modifications
|
||||||
|
// Save the value
|
||||||
|
addon.setIslandLevel(island.getOwner(), result.score);
|
||||||
|
// All done.
|
||||||
|
// Tell the asker the result
|
||||||
|
if (asker.isPlayer() && asker.isOnline()) {
|
||||||
|
asker.sendMessage("island.level.island-level-is", "[level]", String.valueOf(result.score));
|
||||||
|
} else {
|
||||||
|
// Console
|
||||||
|
sendConsoleReport(asker, island);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void sendConsoleReport(User asker, Island island) {
|
||||||
|
List<String> reportLines = new ArrayList<>();
|
||||||
|
// provide counts
|
||||||
|
reportLines.add("Level Log for island at " + island.getCenter());
|
||||||
|
reportLines.add("Island owner UUID = " + island.getOwner());
|
||||||
|
reportLines.add("Total block value count = " + String.format("%,d",result.rawBlockCount));
|
||||||
|
reportLines.add("Level cost = " + addon.getSettings().getLevelCost());
|
||||||
|
//reportLines.add("Level multiplier = " + levelMultiplier + " (Player must be online to get a permission multiplier)");
|
||||||
|
//reportLines.add("Schematic level handicap = " + levelHandicap + " (level is reduced by this amount)");
|
||||||
|
reportLines.add("Deaths handicap = " + result.deathHandicap);
|
||||||
|
reportLines.add("Level calculated = " + result.score);
|
||||||
|
reportLines.add("==================================");
|
||||||
|
int total = 0;
|
||||||
|
if (!result.uwCount.isEmpty()) {
|
||||||
|
reportLines.add("Underwater block count (Multiplier = x" + addon.getSettings().getUnderWaterMultiplier() + ") value");
|
||||||
|
reportLines.add("Total number of underwater blocks = " + String.format("%,d",result.uwCount.size()));
|
||||||
|
Iterable<Multiset.Entry<MaterialData>> entriesSortedByCount =
|
||||||
|
Multisets.copyHighestCountFirst(result.uwCount).entrySet();
|
||||||
|
Iterator<Entry<MaterialData>> it = entriesSortedByCount.iterator();
|
||||||
|
while (it.hasNext()) {
|
||||||
|
Entry<MaterialData> en = it.next();
|
||||||
|
MaterialData type = en.getElement();
|
||||||
|
|
||||||
|
int value = 0;
|
||||||
|
if (addon.getSettings().getBlockValues().containsKey(type)) {
|
||||||
|
// Specific
|
||||||
|
value = addon.getSettings().getBlockValues().get(type);
|
||||||
|
} else if (addon.getSettings().getBlockValues().containsKey(new MaterialData(type.getItemType()))) {
|
||||||
|
// Generic
|
||||||
|
value = addon.getSettings().getBlockValues().get(new MaterialData(type.getItemType()));
|
||||||
|
}
|
||||||
|
if (value > 0) {
|
||||||
|
reportLines.add(type.toString() + ":"
|
||||||
|
+ String.format("%,d",en.getCount()) + " blocks x " + value + " = " + (value * en.getCount()));
|
||||||
|
total += (value * en.getCount());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
reportLines.add("Subtotal = " + total);
|
||||||
|
reportLines.add("==================================");
|
||||||
|
}
|
||||||
|
reportLines.add("Regular block count");
|
||||||
|
reportLines.add("Total number of blocks = " + String.format("%,d",result.mdCount.size()));
|
||||||
|
Iterable<Multiset.Entry<MaterialData>> entriesSortedByCount =
|
||||||
|
result.mdCount.entrySet();
|
||||||
|
Iterator<Entry<MaterialData>> it = entriesSortedByCount.iterator();
|
||||||
|
while (it.hasNext()) {
|
||||||
|
Entry<MaterialData> en = it.next();
|
||||||
|
MaterialData type = en.getElement();
|
||||||
|
int value = 0;
|
||||||
|
if (addon.getSettings().getBlockValues().containsKey(type)) {
|
||||||
|
// Specific
|
||||||
|
value = addon.getSettings().getBlockValues().get(type);
|
||||||
|
} else if (addon.getSettings().getBlockValues().containsKey(new MaterialData(type.getItemType()))) {
|
||||||
|
// Generic
|
||||||
|
value = addon.getSettings().getBlockValues().get(new MaterialData(type.getItemType()));
|
||||||
|
}
|
||||||
|
if (value > 0) {
|
||||||
|
reportLines.add(type.toString() + ":"
|
||||||
|
+ String.format("%,d",en.getCount()) + " blocks x " + value + " = " + (value * en.getCount()));
|
||||||
|
total += (value * en.getCount());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
reportLines.add("Total = " + total);
|
||||||
|
reportLines.add("==================================");
|
||||||
|
reportLines.add("Blocks not counted because they exceeded limits: " + String.format("%,d",result.ofCount.size()));
|
||||||
|
//entriesSortedByCount = Multisets.copyHighestCountFirst(ofCount).entrySet();
|
||||||
|
entriesSortedByCount = result.ofCount.entrySet();
|
||||||
|
it = entriesSortedByCount.iterator();
|
||||||
|
while (it.hasNext()) {
|
||||||
|
Entry<MaterialData> type = it.next();
|
||||||
|
Integer limit = addon.getSettings().getBlockLimits().get(type.getElement());
|
||||||
|
String explain = ")";
|
||||||
|
if (limit == null) {
|
||||||
|
MaterialData generic = new MaterialData(type.getElement().getItemType());
|
||||||
|
limit = addon.getSettings().getBlockLimits().get(generic);
|
||||||
|
explain = " - All types)";
|
||||||
|
}
|
||||||
|
reportLines.add(type.getElement().toString() + ": " + String.format("%,d",type.getCount()) + " blocks (max " + limit + explain);
|
||||||
|
}
|
||||||
|
reportLines.add("==================================");
|
||||||
|
reportLines.add("Blocks on island that are not in config.yml");
|
||||||
|
reportLines.add("Total number = " + String.format("%,d",result.ncCount.size()));
|
||||||
|
//entriesSortedByCount = Multisets.copyHighestCountFirst(ncCount).entrySet();
|
||||||
|
entriesSortedByCount = result.ncCount.entrySet();
|
||||||
|
it = entriesSortedByCount.iterator();
|
||||||
|
while (it.hasNext()) {
|
||||||
|
Entry<MaterialData> type = it.next();
|
||||||
|
reportLines.add(type.getElement().toString() + ": " + String.format("%,d",type.getCount()) + " blocks");
|
||||||
|
}
|
||||||
|
reportLines.add("=================================");
|
||||||
|
|
||||||
|
for (String line : reportLines) {
|
||||||
|
asker.sendRawMessage(line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Results class
|
||||||
|
* @author ben
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class Results {
|
||||||
|
Multiset<MaterialData> mdCount = HashMultiset.create();
|
||||||
|
Multiset<MaterialData> uwCount = HashMultiset.create();
|
||||||
|
Multiset<MaterialData> ncCount = HashMultiset.create();
|
||||||
|
Multiset<MaterialData> ofCount = HashMultiset.create();
|
||||||
|
long rawBlockCount = 0;
|
||||||
|
Island island;
|
||||||
|
long underWaterBlockCount = 0;
|
||||||
|
long score = 0;
|
||||||
|
int deathHandicap = 0;
|
||||||
|
}
|
||||||
|
}
|
@ -1,95 +0,0 @@
|
|||||||
package bskyblock.addon.level.config;
|
|
||||||
|
|
||||||
import java.util.HashMap;
|
|
||||||
|
|
||||||
import org.apache.commons.lang.StringUtils;
|
|
||||||
import org.bukkit.Material;
|
|
||||||
import org.bukkit.material.MaterialData;
|
|
||||||
|
|
||||||
import bskyblock.addon.level.Level;
|
|
||||||
|
|
||||||
public class PluginConfig {
|
|
||||||
private static final boolean DEBUG = false;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Loads the various settings from the config.yml file into the plugin
|
|
||||||
*/
|
|
||||||
public PluginConfig(Level plugin) {
|
|
||||||
plugin.saveDefaultConfig();
|
|
||||||
|
|
||||||
// Island level cool down time
|
|
||||||
Settings.levelWait = plugin.getConfig().getInt("levelwait", 60);
|
|
||||||
if (Settings.levelWait < 0) {
|
|
||||||
Settings.levelWait = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Get the under water multiplier
|
|
||||||
Settings.deathpenalty = plugin.getConfig().getInt("deathpenalty", 0);
|
|
||||||
Settings.sumTeamDeaths = plugin.getConfig().getBoolean("sumteamdeaths");
|
|
||||||
Settings.maxDeaths = plugin.getConfig().getInt("maxdeaths", 10);
|
|
||||||
Settings.islandResetDeathReset = plugin.getConfig().getBoolean("islandresetdeathreset", true);
|
|
||||||
Settings.teamJoinDeathReset = plugin.getConfig().getBoolean("teamjoindeathreset", true);
|
|
||||||
Settings.underWaterMultiplier = plugin.getConfig().getDouble("underwater", 1D);
|
|
||||||
Settings.levelCost = plugin.getConfig().getInt("levelcost", 100);
|
|
||||||
if (Settings.levelCost < 1) {
|
|
||||||
Settings.levelCost = 1;
|
|
||||||
plugin.getLogger().warning("levelcost in blockvalues.yml cannot be less than 1. Setting to 1.");
|
|
||||||
}
|
|
||||||
Settings.blockLimits = new HashMap<MaterialData, Integer>();
|
|
||||||
if (plugin.getConfig().isSet("limits")) {
|
|
||||||
for (String material : plugin.getConfig().getConfigurationSection("limits").getKeys(false)) {
|
|
||||||
try {
|
|
||||||
String[] split = material.split(":");
|
|
||||||
byte data = 0;
|
|
||||||
if (split.length>1) {
|
|
||||||
data = Byte.valueOf(split[1]);
|
|
||||||
}
|
|
||||||
Material mat;
|
|
||||||
if (StringUtils.isNumeric(split[0])) {
|
|
||||||
mat = Material.getMaterial(Integer.parseInt(split[0]));
|
|
||||||
} else {
|
|
||||||
mat = Material.valueOf(split[0].toUpperCase());
|
|
||||||
}
|
|
||||||
MaterialData materialData = new MaterialData(mat);
|
|
||||||
materialData.setData(data);
|
|
||||||
Settings.blockLimits.put(materialData, plugin.getConfig().getInt("limits." + material, 0));
|
|
||||||
if (DEBUG) {
|
|
||||||
plugin.getLogger().info("Maximum number of " + materialData + " will be " + Settings.blockLimits.get(materialData));
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
plugin.getLogger().warning("Unknown material (" + material + ") in blockvalues.yml Limits section. Skipping...");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Settings.blockValues = new HashMap<MaterialData, Integer>();
|
|
||||||
if (plugin.getConfig().isSet("blocks")) {
|
|
||||||
for (String material : plugin.getConfig().getConfigurationSection("blocks").getKeys(false)) {
|
|
||||||
try {
|
|
||||||
String[] split = material.split(":");
|
|
||||||
byte data = 0;
|
|
||||||
if (split.length>1) {
|
|
||||||
data = Byte.valueOf(split[1]);
|
|
||||||
}
|
|
||||||
MaterialData materialData = null;
|
|
||||||
if (StringUtils.isNumeric(split[0])) {
|
|
||||||
materialData = new MaterialData(Integer.parseInt(split[0]));
|
|
||||||
} else {
|
|
||||||
materialData = new MaterialData(Material.valueOf(split[0].toUpperCase()));
|
|
||||||
}
|
|
||||||
|
|
||||||
materialData.setData(data);
|
|
||||||
Settings.blockValues.put(materialData, plugin.getConfig().getInt("blocks." + material, 0));
|
|
||||||
if (DEBUG) {
|
|
||||||
plugin.getLogger().info(materialData.toString() + " value = " + Settings.blockValues.get(materialData));
|
|
||||||
}
|
|
||||||
} catch (Exception e) {
|
|
||||||
// e.printStackTrace();
|
|
||||||
plugin.getLogger().warning("Unknown material (" + material + ") in blockvalues.yml blocks section. Skipping...");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
plugin.getLogger().severe("No block values in blockvalues.yml! All island levels will be zero!");
|
|
||||||
}
|
|
||||||
// All done
|
|
||||||
}
|
|
||||||
}
|
|
@ -2,21 +2,250 @@ package bskyblock.addon.level.config;
|
|||||||
|
|
||||||
import java.util.HashMap;
|
import java.util.HashMap;
|
||||||
|
|
||||||
|
import org.apache.commons.lang.StringUtils;
|
||||||
|
import org.bukkit.Material;
|
||||||
import org.bukkit.material.MaterialData;
|
import org.bukkit.material.MaterialData;
|
||||||
|
|
||||||
|
import bskyblock.addon.level.Level;
|
||||||
|
|
||||||
public class Settings {
|
public class Settings {
|
||||||
|
|
||||||
public static boolean sumTeamDeaths;
|
private static final boolean DEBUG = true;
|
||||||
public static int seaHeight;
|
private boolean sumTeamDeaths;
|
||||||
public static HashMap<MaterialData, Integer> blockLimits;
|
private int seaHeight;
|
||||||
public static HashMap<MaterialData, Integer> blockValues;
|
private HashMap<MaterialData, Integer> blockLimits = new HashMap<>();
|
||||||
public static double underWaterMultiplier;
|
private HashMap<MaterialData, Integer> blockValues = new HashMap<>();
|
||||||
public static int deathpenalty;
|
private double underWaterMultiplier;
|
||||||
public static long levelCost;
|
private int deathpenalty;
|
||||||
public static Object defaultLanguage;
|
private long levelCost;
|
||||||
public static int levelWait;
|
private Object defaultLanguage;
|
||||||
public static int maxDeaths;
|
private int levelWait;
|
||||||
public static boolean islandResetDeathReset;
|
private int maxDeaths;
|
||||||
public static boolean teamJoinDeathReset;
|
private boolean islandResetDeathReset;
|
||||||
|
private boolean teamJoinDeathReset;
|
||||||
|
|
||||||
|
public Settings(Level level) {
|
||||||
|
level.saveDefaultConfig();
|
||||||
|
|
||||||
|
setLevelWait(level.getConfig().getInt("levelwait", 60));
|
||||||
|
if (getLevelWait() < 0) {
|
||||||
|
setLevelWait(0);
|
||||||
|
}
|
||||||
|
setDeathpenalty(level.getConfig().getInt("deathpenalty", 0));
|
||||||
|
setSumTeamDeaths(level.getConfig().getBoolean("sumteamdeaths"));
|
||||||
|
setMaxDeaths(level.getConfig().getInt("maxdeaths", 10));
|
||||||
|
setIslandResetDeathReset(level.getConfig().getBoolean("islandresetdeathreset", true));
|
||||||
|
setTeamJoinDeathReset(level.getConfig().getBoolean("teamjoindeathreset", true));
|
||||||
|
setUnderWaterMultiplier(level.getConfig().getDouble("underwater", 1D));
|
||||||
|
setLevelCost(level.getConfig().getInt("levelcost", 100));
|
||||||
|
if (getLevelCost() < 1) {
|
||||||
|
setLevelCost(1);
|
||||||
|
level.getLogger().warning("levelcost in blockvalues.yml cannot be less than 1. Setting to 1.");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (level.getConfig().isSet("limits")) {
|
||||||
|
HashMap<MaterialData, Integer> blockLimits = new HashMap<>();
|
||||||
|
for (String material : level.getConfig().getConfigurationSection("limits").getKeys(false)) {
|
||||||
|
try {
|
||||||
|
String[] split = material.split(":");
|
||||||
|
byte data = 0;
|
||||||
|
if (split.length>1) {
|
||||||
|
data = Byte.valueOf(split[1]);
|
||||||
|
}
|
||||||
|
Material mat;
|
||||||
|
if (StringUtils.isNumeric(split[0])) {
|
||||||
|
mat = Material.getMaterial(Integer.parseInt(split[0]));
|
||||||
|
} else {
|
||||||
|
mat = Material.valueOf(split[0].toUpperCase());
|
||||||
|
}
|
||||||
|
MaterialData materialData = new MaterialData(mat);
|
||||||
|
materialData.setData(data);
|
||||||
|
blockLimits.put(materialData, level.getConfig().getInt("limits." + material, 0));
|
||||||
|
if (DEBUG) {
|
||||||
|
level.getLogger().info("Maximum number of " + materialData + " will be " + blockLimits.get(materialData));
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
level.getLogger().warning("Unknown material (" + material + ") in blockvalues.yml Limits section. Skipping...");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
setBlockLimits(blockLimits);
|
||||||
|
}
|
||||||
|
if (level.getConfig().isSet("blocks")) {
|
||||||
|
HashMap<MaterialData, Integer> blockValues = new HashMap<>();
|
||||||
|
for (String material : level.getConfig().getConfigurationSection("blocks").getKeys(false)) {
|
||||||
|
try {
|
||||||
|
String[] split = material.split(":");
|
||||||
|
byte data = 0;
|
||||||
|
if (split.length>1) {
|
||||||
|
data = Byte.valueOf(split[1]);
|
||||||
|
}
|
||||||
|
MaterialData materialData = null;
|
||||||
|
if (StringUtils.isNumeric(split[0])) {
|
||||||
|
materialData = new MaterialData(Integer.parseInt(split[0]));
|
||||||
|
} else {
|
||||||
|
materialData = new MaterialData(Material.valueOf(split[0].toUpperCase()));
|
||||||
|
}
|
||||||
|
|
||||||
|
materialData.setData(data);
|
||||||
|
blockValues.put(materialData, level.getConfig().getInt("blocks." + material, 0));
|
||||||
|
if (DEBUG) {
|
||||||
|
level.getLogger().info(materialData.toString() + " value = " + blockValues.get(materialData));
|
||||||
|
}
|
||||||
|
} catch (Exception e) {
|
||||||
|
// e.printStackTrace();
|
||||||
|
level.getLogger().warning("Unknown material (" + material + ") in blockvalues.yml blocks section. Skipping...");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
setBlockValues(blockValues);
|
||||||
|
} else {
|
||||||
|
level.getLogger().severe("No block values in blockvalues.yml! All island levels will be zero!");
|
||||||
|
}
|
||||||
|
// All done
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return the sumTeamDeaths
|
||||||
|
*/
|
||||||
|
public final boolean isSumTeamDeaths() {
|
||||||
|
return sumTeamDeaths;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param sumTeamDeaths the sumTeamDeaths to set
|
||||||
|
*/
|
||||||
|
public final void setSumTeamDeaths(boolean sumTeamDeaths) {
|
||||||
|
this.sumTeamDeaths = sumTeamDeaths;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the seaHeight
|
||||||
|
*/
|
||||||
|
public final int getSeaHeight() {
|
||||||
|
return seaHeight;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param seaHeight the seaHeight to set
|
||||||
|
*/
|
||||||
|
public final void setSeaHeight(int seaHeight) {
|
||||||
|
this.seaHeight = seaHeight;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the blockLimits
|
||||||
|
*/
|
||||||
|
public final HashMap<MaterialData, Integer> getBlockLimits() {
|
||||||
|
return blockLimits;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param blockLimits the blockLimits to set
|
||||||
|
*/
|
||||||
|
public final void setBlockLimits(HashMap<MaterialData, Integer> blockLimits) {
|
||||||
|
this.blockLimits = blockLimits;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the blockValues
|
||||||
|
*/
|
||||||
|
public final HashMap<MaterialData, Integer> getBlockValues() {
|
||||||
|
return blockValues;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param blockValues the blockValues to set
|
||||||
|
*/
|
||||||
|
public final void setBlockValues(HashMap<MaterialData, Integer> blockValues) {
|
||||||
|
this.blockValues = blockValues;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the underWaterMultiplier
|
||||||
|
*/
|
||||||
|
public final double getUnderWaterMultiplier() {
|
||||||
|
return underWaterMultiplier;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param underWaterMultiplier the underWaterMultiplier to set
|
||||||
|
*/
|
||||||
|
public final void setUnderWaterMultiplier(double underWaterMultiplier) {
|
||||||
|
this.underWaterMultiplier = underWaterMultiplier;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the deathpenalty
|
||||||
|
*/
|
||||||
|
public final int getDeathPenalty() {
|
||||||
|
return deathpenalty;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param deathpenalty the deathpenalty to set
|
||||||
|
*/
|
||||||
|
public final void setDeathpenalty(int deathpenalty) {
|
||||||
|
this.deathpenalty = deathpenalty;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the levelCost
|
||||||
|
*/
|
||||||
|
public final long getLevelCost() {
|
||||||
|
return levelCost;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param levelCost the levelCost to set
|
||||||
|
*/
|
||||||
|
public final void setLevelCost(long levelCost) {
|
||||||
|
this.levelCost = levelCost;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the defaultLanguage
|
||||||
|
*/
|
||||||
|
public final Object getDefaultLanguage() {
|
||||||
|
return defaultLanguage;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param defaultLanguage the defaultLanguage to set
|
||||||
|
*/
|
||||||
|
public final void setDefaultLanguage(Object defaultLanguage) {
|
||||||
|
this.defaultLanguage = defaultLanguage;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the levelWait
|
||||||
|
*/
|
||||||
|
public final int getLevelWait() {
|
||||||
|
return levelWait;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param levelWait the levelWait to set
|
||||||
|
*/
|
||||||
|
public final void setLevelWait(int levelWait) {
|
||||||
|
this.levelWait = levelWait;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the maxDeaths
|
||||||
|
*/
|
||||||
|
public final int getMaxDeaths() {
|
||||||
|
return maxDeaths;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param maxDeaths the maxDeaths to set
|
||||||
|
*/
|
||||||
|
public final void setMaxDeaths(int maxDeaths) {
|
||||||
|
this.maxDeaths = maxDeaths;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the islandResetDeathReset
|
||||||
|
*/
|
||||||
|
public final boolean isIslandResetDeathReset() {
|
||||||
|
return islandResetDeathReset;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param islandResetDeathReset the islandResetDeathReset to set
|
||||||
|
*/
|
||||||
|
public final void setIslandResetDeathReset(boolean islandResetDeathReset) {
|
||||||
|
this.islandResetDeathReset = islandResetDeathReset;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @return the teamJoinDeathReset
|
||||||
|
*/
|
||||||
|
public final boolean isTeamJoinDeathReset() {
|
||||||
|
return teamJoinDeathReset;
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* @param teamJoinDeathReset the teamJoinDeathReset to set
|
||||||
|
*/
|
||||||
|
public final void setTeamJoinDeathReset(boolean teamJoinDeathReset) {
|
||||||
|
this.teamJoinDeathReset = teamJoinDeathReset;
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user