package de.steamwar.fightsystem.winconditions; import de.steamwar.fightsystem.Config; import de.steamwar.fightsystem.FightSystem; import de.steamwar.fightsystem.fight.Fight; import de.steamwar.fightsystem.fight.FightTeam; import de.steamwar.fightsystem.states.FightState; import org.bukkit.Bukkit; import org.bukkit.Material; import org.bukkit.World; import org.bukkit.scheduler.BukkitTask; import java.util.Collections; import java.util.EnumSet; import java.util.HashSet; import java.util.Set; public class WinconditionRelativePercent extends Wincondition{ private static final Set ignoredBlocks; private static TeamPercent blue = null; private static TeamPercent red = null; static{ Set ignored = new HashSet<>(); for(String s : Config.IgnoredBlocks) ignored.add(Material.valueOf(s)); ignoredBlocks = Collections.unmodifiableSet(ignored); } public WinconditionRelativePercent(){ super(Config.RelativePercent || Config.Points, EnumSet.of(FightState.PRE_RUNNING, FightState.RUNNING)); } public static TeamPercent getBlue(){ if(blue == null) blue = new TeamPercent(Fight.getBlueTeam()); return blue; } public static TeamPercent getRed(){ if(red == null) red = new TeamPercent(Fight.getRedTeam()); return red; } @Override public void enable() { getBlue(); getRed(); } @Override public void disable() { blue.task.cancel(); red.task.cancel(); } public static class TeamPercent { private static final World world = Bukkit.getWorlds().get(0); private final FightTeam team; private final int blockCount; private final BukkitTask task; private boolean running = false; private int currentBlocks; private TeamPercent(FightTeam team){ this.team = team; this.blockCount = currentBlocks(); this.currentBlocks = blockCount; task = Bukkit.getScheduler().runTaskTimerAsynchronously(FightSystem.getPlugin(), () -> { if(running) return; running = true; currentBlocks = currentBlocks(); checkPercentDefeat(); running = false; }, 400, 400); } public double getPrintablePercent(){ return Math.round(10000.0 * getPercent()) / 100.0; } final int getBlockCount(){ return blockCount; } double getPercent(){ int blocksDestroyed = blockCount - currentBlocks; return blocksDestroyed > 0 ? blocksDestroyed / (double) blockCount : 0; } private int currentBlocks(){ // Entern active if(!Config.EnterStages.isEmpty() && Config.EnterStages.get(0) <= FightSystem.getFightTime()) return currentBlocks; int blocks = 0; for(int x = team.getCornerX(); x < team.getCornerX() + Config.SchemsizeX; x++){ for(int y = team.getCornerY(); y < team.getCornerY() + Config.SchemsizeY; y++){ for(int z = team.getCornerZ(); z < team.getCornerZ() + Config.SchemsizeZ; z++){ if(!ignoredBlocks.contains(world.getBlockAt(x,y,z).getType())) blocks++; } } } return blocks; } private void checkPercentDefeat(){ if(!Config.RelativePercent) return; if(getPercent() * 100 >= Config.PercentWin){ Bukkit.broadcastMessage(FightSystem.PREFIX + "§cDer Schiff von " + team.getColoredName() + " §cwurde zu stark beschädigt!"); Bukkit.getScheduler().runTask(FightSystem.getPlugin(), () -> FightSystem.setSpectateState(Fight.getOpposite(team), "RelativePercent")); } } } }