diff --git a/BauSystem_12/src/de/steamwar/bausystem/world/TNTSimulator_12.java b/BauSystem_12/src/de/steamwar/bausystem/world/TNTSimulator_12.java
new file mode 100644
index 0000000..099c96f
--- /dev/null
+++ b/BauSystem_12/src/de/steamwar/bausystem/world/TNTSimulator_12.java
@@ -0,0 +1,34 @@
+/*
+ * This file is a part of the SteamWar software.
+ *
+ * Copyright (C) 2020 SteamWar.de-Serverteam
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+
+package de.steamwar.bausystem.world;
+
+import org.bukkit.Material;
+
+public class TNTSimulator_12 {
+
+ public static Material active() {
+ return Material.CONCRETE;
+ }
+
+ public static Material notActive() {
+ return Material.CONCRETE;
+ }
+
+}
diff --git a/BauSystem_15/src/de/steamwar/bausystem/world/TNTSimulator_15.java b/BauSystem_15/src/de/steamwar/bausystem/world/TNTSimulator_15.java
new file mode 100644
index 0000000..8fea70d
--- /dev/null
+++ b/BauSystem_15/src/de/steamwar/bausystem/world/TNTSimulator_15.java
@@ -0,0 +1,35 @@
+/*
+ *
+ * This file is a part of the SteamWar software.
+ *
+ * Copyright (C) 2020 SteamWar.de-Serverteam
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+
+package de.steamwar.bausystem.world;
+
+import org.bukkit.Material;
+
+public class TNTSimulator_15 {
+
+ public static Material active() {
+ return Material.LIME_CONCRETE;
+ }
+
+ public static Material notActive() {
+ return Material.RED_CONCRETE;
+ }
+
+}
diff --git a/BauSystem_Main/src/de/steamwar/bausystem/BauSystem.java b/BauSystem_Main/src/de/steamwar/bausystem/BauSystem.java
index cef05e9..dd1817f 100644
--- a/BauSystem_Main/src/de/steamwar/bausystem/BauSystem.java
+++ b/BauSystem_Main/src/de/steamwar/bausystem/BauSystem.java
@@ -97,6 +97,8 @@ public class BauSystem extends JavaPlugin implements Listener {
getCommand("detonator").setExecutor(new CommandDetonator());
getCommand("detonator").setTabCompleter(new CommandDetonatorTabCompleter());
getCommand("script").setExecutor(new CommandScript());
+ getCommand("simulator").setExecutor(new CommandSimulator());
+ getCommand("simulator").setTabCompleter(new CommandSimulatorTabCompleter());
getCommand("gui").setExecutor(new CommandGUI());
Bukkit.getPluginManager().registerEvents(this, this);
@@ -104,6 +106,7 @@ public class BauSystem extends JavaPlugin implements Listener {
Bukkit.getPluginManager().registerEvents(new ScriptListener(), this);
Bukkit.getPluginManager().registerEvents(new BauScoreboard(), this);
Bukkit.getPluginManager().registerEvents(new ClipboardListener(), this);
+ Bukkit.getPluginManager().registerEvents(new TNTSimulatorListener(), this);
Bukkit.getPluginManager().registerEvents(new CommandGUI(), this);
Bukkit.getPluginManager().registerEvents(new DetonatorListener(), this);
new AFKStopper();
diff --git a/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandGUI.java b/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandGUI.java
index be01a34..5576d67 100644
--- a/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandGUI.java
+++ b/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandGUI.java
@@ -55,8 +55,6 @@ public class CommandGUI implements CommandExecutor, Listener {
inv.setItem(37, getMaterial("GLASS_PANE", "THIN_GLASS"), "§7Platzhalter", clickType -> {
});
- inv.setItem(38, getMaterial("GLASS_PANE", "THIN_GLASS"), "§7Platzhalter", clickType -> {
- });
inv.setItem(43, getMaterial("GLASS_PANE", "THIN_GLASS"), "§7Platzhalter", clickType -> {
});
inv.setItem(42, Material.NETHER_STAR, "§7Bau GUI Item", Arrays.asList("§7Du kannst dieses Item zum Öffnen der BauGUI nutzen", "§7oder Doppel F (Swap hands) drücken."), false, clickType -> {
@@ -64,14 +62,7 @@ public class CommandGUI implements CommandExecutor, Listener {
player.performCommand("gui item");
});
- ItemStack dtWand = Detonator.WAND.clone();
- ItemMeta meta = dtWand.getItemMeta();
- List lore = meta.getLore();
- lore.add("§8/§7dt wand");
- if (Welt.noPermission(player, Permission.world))
- lore.add("§cDu hast keine Worldrechte");
- meta.setLore(lore);
- dtWand.setItemMeta(meta);
+ ItemStack dtWand = wand(player, Detonator.WAND, "§8/§7dt wand", Permission.world, "§cDu hast keine Worldrechte");
inv.setItem(39, dtWand, clickType -> {
if (Welt.noPermission(player, Permission.world))
return;
@@ -79,6 +70,14 @@ public class CommandGUI implements CommandExecutor, Listener {
player.performCommand("dt wand");
});
+ ItemStack simWand = wand(player, TNTSimulator.WAND, "§8/§7sim wand", Permission.world, "§cDu hast keine Worldrechte");
+ inv.setItem(38, simWand, clickType -> {
+ if (Welt.noPermission(player, Permission.world))
+ return;
+ player.closeInventory();
+ player.performCommand("sim wand");
+ });
+
inv.setItem(40, getMaterial("WOODEN_AXE", "WOOD_AXE"), "§eWorldedit Axt", getNoPermsLore(Arrays.asList("§8//§7wand"), player, "§cDu hast keine Worldeditrechte", Permission.worldedit), false, clickType -> {
if (Welt.noPermission(player, Permission.world))
return;
@@ -567,6 +566,18 @@ public class CommandGUI implements CommandExecutor, Listener {
return null;
}
+ private static ItemStack wand(Player player, ItemStack base, String command, Permission permission, String noPermissionMessage) {
+ base = base.clone();
+ ItemMeta meta = base.getItemMeta();
+ List lore = meta.getLore();
+ lore.add(command);
+ if (Welt.noPermission(player, permission))
+ lore.add(noPermissionMessage);
+ meta.setLore(lore);
+ base.setItemMeta(meta);
+ return base;
+ }
+
@Override
public boolean onCommand(CommandSender commandSender, Command command, String s, String[] strings) {
if (!(commandSender instanceof Player))
diff --git a/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandSimulator.java b/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandSimulator.java
new file mode 100644
index 0000000..325f1a3
--- /dev/null
+++ b/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandSimulator.java
@@ -0,0 +1,79 @@
+/*
+ *
+ * This file is a part of the SteamWar software.
+ *
+ * Copyright (C) 2020 SteamWar.de-Serverteam
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+
+package de.steamwar.bausystem.commands;
+
+import de.steamwar.bausystem.BauSystem;
+import de.steamwar.bausystem.Permission;
+import de.steamwar.bausystem.PlayerUtils;
+import de.steamwar.bausystem.world.TNTSimulator;
+import de.steamwar.bausystem.world.Welt;
+import org.bukkit.command.Command;
+import org.bukkit.command.CommandExecutor;
+import org.bukkit.command.CommandSender;
+import org.bukkit.entity.Player;
+
+public class CommandSimulator implements CommandExecutor {
+
+ private void help(Player player) {
+ player.sendMessage("§8/§esimulator §8- §7Öffnet die Simulations GUI");
+ player.sendMessage("§8/§esimulator start §8- §7Startet die Simulation");
+ player.sendMessage("§8/§esimulator wand §8- §7Legt dir den Simulatorstab ins Inventar");
+ player.sendMessage("§8/§esimulator delete §8- §7Löscht alle TNT");
+ }
+
+ private boolean permissionCheck(Player player) {
+ if (Welt.noPermission(player, Permission.world)) {
+ player.sendMessage(BauSystem.PREFIX + "§cDu darfst hier nicht den Simulator nutzen");
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public boolean onCommand(CommandSender commandSender, Command command, String s, String[] args) {
+ if (!(commandSender instanceof Player))
+ return false;
+ Player player = (Player) commandSender;
+ if (!permissionCheck(player)) {
+ return false;
+ }
+
+ if (args.length == 1) {
+ switch (args[0].toLowerCase()) {
+ case "wand":
+ PlayerUtils.giveItemToPlayer(player, TNTSimulator.WAND);
+ break;
+ case "start":
+ TNTSimulator.get(player).start();
+ break;
+ case "delete":
+ TNTSimulator.get(player).delete();
+ default:
+ help(player);
+ break;
+ }
+ return false;
+ }
+ TNTSimulator.openSimulator(player);
+ return false;
+ }
+
+}
diff --git a/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandSimulatorTabCompleter.java b/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandSimulatorTabCompleter.java
new file mode 100644
index 0000000..0103d30
--- /dev/null
+++ b/BauSystem_Main/src/de/steamwar/bausystem/commands/CommandSimulatorTabCompleter.java
@@ -0,0 +1,60 @@
+/*
+ *
+ * This file is a part of the SteamWar software.
+ *
+ * Copyright (C) 2020 SteamWar.de-Serverteam
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ */
+
+package de.steamwar.bausystem.commands;
+
+import org.bukkit.command.Command;
+import org.bukkit.command.CommandSender;
+import org.bukkit.command.TabCompleter;
+import org.bukkit.entity.Player;
+
+import java.util.ArrayList;
+import java.util.List;
+
+public class CommandSimulatorTabCompleter implements TabCompleter {
+
+ @Override
+ public List onTabComplete(CommandSender sender, Command command, String label, String[] args) {
+ if(!(sender instanceof Player)) return new ArrayList<>();
+ return simulatorTabComplete((Player) sender, args);
+ }
+
+ private List simulatorTabComplete(Player player, String[] args) {
+ List tabComplete = new ArrayList<>();
+ tabComplete.add("wand");
+ tabComplete.add("start");
+ tabComplete.add("delete");
+
+ if (args.length >= 2) {
+ return new ArrayList<>();
+ }
+ return manageList(tabComplete, args, 0);
+ }
+
+ private List manageList(List strings, String[] args, int index) {
+ for (int i = strings.size() - 1; i >= 0; i--) {
+ if (!strings.get(i).startsWith(args[index])) {
+ strings.remove(i);
+ }
+ }
+ return strings;
+ }
+
+}
diff --git a/BauSystem_Main/src/de/steamwar/bausystem/world/TNTSimulator.java b/BauSystem_Main/src/de/steamwar/bausystem/world/TNTSimulator.java
new file mode 100644
index 0000000..7a9fb2d
--- /dev/null
+++ b/BauSystem_Main/src/de/steamwar/bausystem/world/TNTSimulator.java
@@ -0,0 +1,441 @@
+/*
+ *
+ * This file is a part of the SteamWar software.
+ *
+ * Copyright (C) 2020 SteamWar.de-Serverteam
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ * /
+ */
+
+package de.steamwar.bausystem.world;
+
+import de.steamwar.bausystem.BauSystem;
+import de.steamwar.core.VersionedCallable;
+import de.steamwar.inventory.SWAnvilInv;
+import de.steamwar.inventory.SWInventory;
+import de.steamwar.inventory.SWItem;
+import de.steamwar.inventory.SWListInv;
+import org.bukkit.Bukkit;
+import org.bukkit.Material;
+import org.bukkit.World;
+import org.bukkit.entity.Player;
+import org.bukkit.entity.TNTPrimed;
+import org.bukkit.inventory.ItemStack;
+import org.bukkit.util.Consumer;
+import org.bukkit.util.Vector;
+
+import java.util.*;
+import java.util.concurrent.atomic.AtomicInteger;
+
+public class TNTSimulator {
+
+ private static final Vector X_VECTOR = new Vector(0.0625, 0, 0);
+ private static final Vector NX_VECTOR = new Vector(-0.0625, 0, 0);
+ private static final Vector Y_VECTOR = new Vector(0, 0.0625, 0);
+ private static final Vector NY_VECTOR = new Vector(0, -0.0625, 0);
+ private static final Vector Z_VECTOR = new Vector(0, 0, 0.0625);
+ private static final Vector NZ_VECTOR = new Vector(0, 0, -0.0625);
+ private static final List LORE = Collections.singletonList("§eZum ändern klicken");
+ private static final List EMPTY = new ArrayList<>();
+
+ static final Map TNT_SIMULATOR_MAP = new HashMap<>();
+ private final Set TNT_SPAWNS = new HashSet<>();
+
+ public static final ItemStack WAND = new SWItem(Material.BLAZE_ROD, "§eKanonensimulator", Arrays.asList("§eRechtsklick Block §8- §7Füge einen TNT hinzu", "§eRechtsklick Luft §8- §7Öffne den Simulator", "§eLinksklick §8- §7Starte die Simulation"), false, null).getItemStack();
+
+ public static TNTSimulator get(Player player) {
+ return TNT_SIMULATOR_MAP.computeIfAbsent(player, p -> new TNTSimulator());
+ }
+
+ public static void openSimulator(Player player) {
+ TNTSimulator tntSimulator = get(player);
+
+ List> swListEntryList = new ArrayList<>();
+ tntSimulator.TNT_SPAWNS.forEach(tntSpawn -> {
+ List lore = new ArrayList<>();
+ lore.add("§7Klicken zum Konfigurieren");
+ lore.add("");
+ lore.add("§7TNT-Anzahl§8: §e" + tntSpawn.getCount());
+ lore.add("§7Tick§8: §e" + tntSpawn.getTickOffset());
+ lore.add("§7Fuse-Tick§8: §e" + tntSpawn.getFuseTicks());
+ lore.add("");
+ lore.add("§7X§8: §e" + tntSpawn.getPosition().getX());
+ lore.add("§7Y§8: §e" + tntSpawn.getPosition().getY());
+ lore.add("§7Z§8: §e" + tntSpawn.getPosition().getZ());
+ swListEntryList.add(new SWListInv.SWListEntry<>(new SWItem(Material.TNT, "§eTNT", lore, false, null), tntSpawn));
+ });
+ swListEntryList.sort(Comparator.comparing(SWListInv.SWListEntry::getObject));
+
+ SWListInv swListInv = new SWListInv<>(player, "Kanonensimulator", false, swListEntryList, (clickType, tntSpawn) -> {
+ editTNT(player, tntSpawn);
+ });
+ swListInv.setItem(51, new SWItem(Material.BARRIER, "§cTNT löschen", clickType -> {
+ tntSimulator.TNT_SPAWNS.clear();
+ openSimulator(player);
+ }));
+ swListInv.setItem(47, new SWItem(Material.FLINT_AND_STEEL, "§eStarten", clickType -> {
+ player.closeInventory();
+ startSimulation(player);
+ }));
+ swListInv.open();
+ }
+
+ static void editTNT(Player player, TNTSpawn tntSpawn) {
+ TNTSimulator tntSimulator = get(player);
+
+ SWInventory swInventory = new SWInventory(player, 54, "TNT");
+ swInventory.setItem(49, new SWItem(Material.REDSTONE_BLOCK, "§cZurück", clickType -> {
+ openSimulator(player);
+ }));
+
+ // Delete tnt
+ swInventory.setItem(53, new SWItem(Material.BARRIER, "§cEntfernen", clickType -> {
+ tntSimulator.TNT_SPAWNS.remove(tntSpawn);
+ openSimulator(player);
+ }));
+
+ // Change Count of spawned TNT
+ swInventory.setItem(10, new SWItem(SWItem.getDye(10), "§7+1", clickType -> {
+ tntSpawn.setCount(tntSpawn.getCount() + 1);
+ if (tntSpawn.getCount() > 400) {
+ tntSpawn.setCount(400);
+ }
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(19, new SWItem(Material.TNT, "§7Anzahl §8- §e" + tntSpawn.getCount(), LORE, false, clickType -> {
+ changeCount(player, "Anzahl TNT", tntSpawn.getCount(), count -> {
+ if (count < 1) count = 1;
+ if (count > 400) count = 400;
+ tntSpawn.setCount(count);
+ editTNT(player, tntSpawn);
+ }, () -> editTNT(player, tntSpawn));
+ }));
+ swInventory.setItem(28, new SWItem(SWItem.getDye(1), "§7-1", clickType -> {
+ tntSpawn.setCount(tntSpawn.getCount() - 1);
+ if (tntSpawn.getCount() < 1) {
+ tntSpawn.setCount(1);
+ }
+ editTNT(player, tntSpawn);
+ }));
+
+ // Change TickOffset
+ swInventory.setItem(11, new SWItem(SWItem.getDye(10), "§7+1", clickType -> {
+ tntSpawn.setTickOffset(tntSpawn.getTickOffset() + 1);
+ if (tntSpawn.getTickOffset() > 8000) {
+ tntSpawn.setTickOffset(8000);
+ }
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(20, new SWItem(Material.CLOCK, "§7Tick §8- §e" + tntSpawn.getTickOffset(), LORE, false, clickType -> {
+ changeCount(player, "Tick Offset", tntSpawn.getTickOffset(), tick -> {
+ if (tick < 0) tick = 0;
+ if (tick > 8000) tick = 8000;
+ tntSpawn.setTickOffset(tick);
+ editTNT(player, tntSpawn);
+ }, () -> editTNT(player, tntSpawn));
+ }));
+ swInventory.setItem(29, new SWItem(SWItem.getDye(1), "§7-1", clickType -> {
+ tntSpawn.setTickOffset(tntSpawn.getTickOffset() - 1);
+ if (tntSpawn.getTickOffset() < 0) {
+ tntSpawn.setTickOffset(0);
+ }
+ editTNT(player, tntSpawn);
+ }));
+
+ // Change FuseTicks
+ swInventory.setItem(12, new SWItem(SWItem.getDye(10), "§7+1", clickType -> {
+ tntSpawn.setFuseTicks(tntSpawn.getFuseTicks() + 1);
+ if (tntSpawn.getFuseTicks() > 80) {
+ tntSpawn.setFuseTicks(80);
+ }
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(21, new SWItem(Material.CLOCK, "§7Fuse-Ticks §8- §e" + tntSpawn.getFuseTicks(), LORE, false, clickType -> {
+ changeCount(player, "Fuse-Ticks", tntSpawn.getFuseTicks(), tick -> {
+ if (tick < 0) tick = 0;
+ if (tick > 80) tick = 80;
+ tntSpawn.setFuseTicks(tick);
+ editTNT(player, tntSpawn);
+ }, () -> editTNT(player, tntSpawn));
+ }));
+ swInventory.setItem(30, new SWItem(SWItem.getDye(1), "§7-1", clickType -> {
+ tntSpawn.setFuseTicks(tntSpawn.getFuseTicks() - 1);
+ if (tntSpawn.getFuseTicks() < 1) {
+ tntSpawn.setFuseTicks(1);
+ }
+ editTNT(player, tntSpawn);
+ }));
+
+ // Repeater before Comparator
+ swInventory.setItem(4, new SWItem(comparatorOrNot(tntSpawn.isComparator()), "§7Gezündet durch §8- §e" + (tntSpawn.isComparator() ? "Comparator" : "Repeater"), clickType -> {
+ tntSpawn.setComparator(!tntSpawn.isComparator());
+ editTNT(player, tntSpawn);
+ }));
+
+ // Velocity Settings
+ swInventory.setItem(13, new SWItem(activeOrNot(tntSpawn.isxVelocity()), "§7TNT §eSprung X §8- " + active(tntSpawn.isxVelocity()), clickType -> {
+ tntSpawn.setxVelocity(!tntSpawn.isxVelocity());
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(22, new SWItem(activeOrNot(tntSpawn.isyVelocity()), "§7TNT §eSprung Y §8- " + active(tntSpawn.isyVelocity()), clickType -> {
+ tntSpawn.setyVelocity(!tntSpawn.isyVelocity());
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(31, new SWItem(activeOrNot(tntSpawn.iszVelocity()), "§7TNT §eSprung Z §8- " + active(tntSpawn.iszVelocity()), clickType -> {
+ tntSpawn.setzVelocity(!tntSpawn.iszVelocity());
+ editTNT(player, tntSpawn);
+ }));
+
+ // X Position
+ swInventory.setItem(14, new SWItem(SWItem.getDye(10), "§7+0,0625", clickType -> {
+ tntSpawn.getPosition().add(X_VECTOR);
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(23, new SWItem(Material.PAPER, "§7x-Position §8- §e" + tntSpawn.getPosition().getX(), LORE, false, clickType -> {
+ changePosition(player, tntSpawn.getPosition().getX(), x -> {
+ tntSpawn.getPosition().setX(clamp(x));
+ editTNT(player, tntSpawn);
+ }, () -> editTNT(player, tntSpawn));
+ }));
+ swInventory.setItem(32, new SWItem(SWItem.getDye(1), "§7-0,0625", clickType -> {
+ tntSpawn.getPosition().add(NX_VECTOR);
+ editTNT(player, tntSpawn);
+ }));
+
+ // Y Position
+ swInventory.setItem(15, new SWItem(SWItem.getDye(10), "§7+0,0625", clickType -> {
+ tntSpawn.getPosition().add(Y_VECTOR);
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(24, new SWItem(Material.PAPER, "§7y-Position §8- §e" + tntSpawn.getPosition().getY(), LORE, false, clickType -> {
+ changePosition(player, tntSpawn.getPosition().getY(), y -> {
+ tntSpawn.getPosition().setY(clamp(y));
+ editTNT(player, tntSpawn);
+ }, () -> editTNT(player, tntSpawn));
+ }));
+ swInventory.setItem(33, new SWItem(SWItem.getDye(1), "§7-0,0625", clickType -> {
+ tntSpawn.getPosition().add(NY_VECTOR);
+ editTNT(player, tntSpawn);
+ }));
+
+ // Z Position
+ swInventory.setItem(16, new SWItem(SWItem.getDye(10), "§7+0,0625", clickType -> {
+ tntSpawn.getPosition().add(Z_VECTOR);
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.setItem(25, new SWItem(Material.PAPER, "§7z-Position §8- §e" + tntSpawn.getPosition().getZ(), LORE, false, clickType -> {
+ changePosition(player, tntSpawn.getPosition().getZ(), z -> {
+ tntSpawn.getPosition().setZ(clamp(z));
+ editTNT(player, tntSpawn);
+ }, () -> editTNT(player, tntSpawn));
+ }));
+ swInventory.setItem(34, new SWItem(SWItem.getDye(1), "§7-0,0625", clickType -> {
+ tntSpawn.getPosition().add(NZ_VECTOR);
+ editTNT(player, tntSpawn);
+ }));
+ swInventory.open();
+ }
+
+ static void startSimulation(Player player) {
+ TNT_SIMULATOR_MAP.getOrDefault(player, new TNTSimulator()).start();
+ }
+
+ static void addTNT(Player player, TNTSpawn tntSpawn) {
+ TNTSimulator tntSimulator = TNT_SIMULATOR_MAP.computeIfAbsent(player, player1 -> new TNTSimulator());
+ tntSimulator.TNT_SPAWNS.add(tntSpawn);
+ }
+
+ private static Material comparatorOrNot(boolean b) {
+ if (b) {
+ return SWItem.getMaterial("REDSTONE_COMPARATOR");
+ } else {
+ return SWItem.getMaterial("DIODE");
+ }
+ }
+
+ private static Material activeOrNot(boolean b) {
+ if (b) {
+ return VersionedCallable.call(new VersionedCallable<>(TNTSimulator_12::active, 8), new VersionedCallable<>(TNTSimulator_15::active, 14));
+ } else {
+ return VersionedCallable.call(new VersionedCallable<>(TNTSimulator_12::notActive, 8), new VersionedCallable<>(TNTSimulator_15::notActive, 14));
+ }
+ }
+
+ private static String active(boolean b) {
+ return b ? "§aan" : "§caus";
+ }
+
+ private static void changeCount(Player player, String name, int defaultValue, Consumer result, Runnable failure) {
+ SWAnvilInv swAnvilInv = new SWAnvilInv(player, name, defaultValue + "");
+ swAnvilInv.setItem(Material.PAPER);
+ swAnvilInv.setCallback(s -> {
+ try {
+ result.accept(Integer.parseInt(s));
+ } catch (NumberFormatException e) {
+ failure.run();
+ }
+ });
+ swAnvilInv.open();
+ }
+
+ private static void changePosition(Player player, double defaultValue, Consumer result, Runnable failure) {
+ SWAnvilInv swAnvilInv = new SWAnvilInv(player, "Position", defaultValue + "");
+ swAnvilInv.setItem(Material.PAPER);
+ swAnvilInv.setCallback(s -> {
+ try {
+ result.accept(Double.parseDouble(s.replace(',', '.')));
+ } catch (NumberFormatException e) {
+ failure.run();
+ }
+ });
+ swAnvilInv.open();
+ }
+
+ private static double clamp(double d) {
+ return (int)(d * 10000) * 0.0001;
+ }
+
+ public void delete() {
+ TNT_SPAWNS.clear();
+ }
+
+ public void start() {
+ Map> first = new HashMap<>();
+ Map> second = new HashMap<>();
+ int lastTick = 0;
+
+ for (TNTSpawn tntSpawn : TNT_SPAWNS) {
+ Map> list = tntSpawn.isComparator() ? second : first;
+ for (int i = 0; i < tntSpawn.getCount(); i++) {
+ list.computeIfAbsent(tntSpawn.getTickOffset(), integer -> new ArrayList<>()).add(tntSpawn);
+ }
+ if (lastTick < tntSpawn.getTickOffset()) {
+ lastTick = tntSpawn.getTickOffset();
+ }
+ }
+ int finalLastTick = lastTick;
+
+ AtomicInteger currentTick = new AtomicInteger(0);
+ Bukkit.getScheduler().runTaskTimer(BauSystem.getPlugin(), bukkitTask -> {
+ int tick = currentTick.get();
+ spawnRandomList(first.getOrDefault(tick, EMPTY));
+ spawnRandomList(second.getOrDefault(tick, EMPTY));
+ if (tick > finalLastTick) bukkitTask.cancel();
+ currentTick.incrementAndGet();
+ }, 1, 1);
+ }
+
+ private void spawnRandomList(List tntSpawns) {
+ if (tntSpawns.isEmpty()) return;
+ Collections.shuffle(tntSpawns);
+ for (TNTSpawn tntSpawn : tntSpawns) {
+ tntSpawn.spawn();
+ }
+ }
+
+ public static class TNTSpawn implements Comparable {
+
+ private static final World WORLD = Bukkit.getWorlds().get(0);
+
+ private final Vector position;
+ private int fuseTicks = 80;
+ private int count = 1;
+ private int tickOffset = 0;
+ private boolean xVelocity = true;
+ private boolean yVelocity = true;
+ private boolean zVelocity = true;
+ private boolean comparator = false;
+
+ public TNTSpawn(Vector position) {
+ this.position = position;
+ }
+
+ public void spawn() {
+ WORLD.spawn(position.toLocation(WORLD), TNTPrimed.class, tntPrimed -> {
+ tntPrimed.setFuseTicks(fuseTicks);
+ if (!xVelocity) tntPrimed.setVelocity(tntPrimed.getVelocity().setX(0));
+ if (!yVelocity) tntPrimed.setVelocity(tntPrimed.getVelocity().setY(0));
+ if (!zVelocity) tntPrimed.setVelocity(tntPrimed.getVelocity().setZ(0));
+ });
+ }
+
+ public Vector getPosition() {
+ return position;
+ }
+
+ public int getFuseTicks() {
+ return fuseTicks;
+ }
+
+ public void setFuseTicks(int fuseTicks) {
+ this.fuseTicks = fuseTicks;
+ }
+
+ public int getCount() {
+ return count;
+ }
+
+ public void setCount(int count) {
+ this.count = count;
+ }
+
+ public int getTickOffset() {
+ return tickOffset;
+ }
+
+ public void setTickOffset(int tickOffset) {
+ this.tickOffset = tickOffset;
+ }
+
+ public boolean isxVelocity() {
+ return xVelocity;
+ }
+
+ public void setxVelocity(boolean xVelocity) {
+ this.xVelocity = xVelocity;
+ }
+
+ public boolean isyVelocity() {
+ return yVelocity;
+ }
+
+ public void setyVelocity(boolean yVelocity) {
+ this.yVelocity = yVelocity;
+ }
+
+ public boolean iszVelocity() {
+ return zVelocity;
+ }
+
+ public void setzVelocity(boolean zVelocity) {
+ this.zVelocity = zVelocity;
+ }
+
+ public boolean isComparator() {
+ return comparator;
+ }
+
+ public void setComparator(boolean comparator) {
+ this.comparator = comparator;
+ }
+
+ @Override
+ public int compareTo(TNTSpawn tntSpawn) {
+ return -Integer.compare(tickOffset, tntSpawn.tickOffset);
+ }
+
+ }
+
+}
diff --git a/BauSystem_Main/src/de/steamwar/bausystem/world/TNTSimulatorListener.java b/BauSystem_Main/src/de/steamwar/bausystem/world/TNTSimulatorListener.java
new file mode 100644
index 0000000..e0af211
--- /dev/null
+++ b/BauSystem_Main/src/de/steamwar/bausystem/world/TNTSimulatorListener.java
@@ -0,0 +1,84 @@
+/*
+ *
+ * This file is a part of the SteamWar software.
+ *
+ * Copyright (C) 2020 SteamWar.de-Serverteam
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see .
+ * /
+ */
+
+package de.steamwar.bausystem.world;
+
+import de.steamwar.bausystem.BauSystem;
+import de.steamwar.bausystem.Permission;
+import org.bukkit.entity.Player;
+import org.bukkit.event.EventHandler;
+import org.bukkit.event.Listener;
+import org.bukkit.event.player.PlayerInteractEvent;
+import org.bukkit.event.player.PlayerQuitEvent;
+import org.bukkit.util.Vector;
+
+import static de.steamwar.bausystem.world.TNTSimulator.*;
+
+public class TNTSimulatorListener implements Listener {
+
+ private static final Vector HALF = new Vector(0.5, 0, 0.5);
+
+ private boolean permissionCheck(Player player) {
+ if (Welt.noPermission(player, Permission.world)) {
+ player.sendMessage(BauSystem.PREFIX + "§cDu darfst hier nicht den Simulator nutzen");
+ return false;
+ }
+ return true;
+ }
+
+ @EventHandler
+ public void onPlayerInteract(PlayerInteractEvent event) {
+ if (event.getItem() == null) {
+ return;
+ }
+ if (!event.getItem().isSimilar(WAND)) {
+ return;
+ }
+ event.setCancelled(true);
+ if (!permissionCheck(event.getPlayer())) {
+ return;
+ }
+
+ switch (event.getAction()) {
+ case LEFT_CLICK_BLOCK:
+ case LEFT_CLICK_AIR:
+ startSimulation(event.getPlayer());
+ break;
+ case RIGHT_CLICK_BLOCK:
+ Vector location = event.getClickedBlock().getLocation().toVector().add(event.getBlockFace().getDirection()).add(HALF);
+ TNTSpawn tntSpawn = new TNTSpawn(location);
+ addTNT(event.getPlayer(), tntSpawn);
+ editTNT(event.getPlayer(), tntSpawn);
+ break;
+ case RIGHT_CLICK_AIR:
+ openSimulator(event.getPlayer());
+ break;
+ default:
+ break;
+ }
+ }
+
+ @EventHandler
+ public void onPlayerQuit(PlayerQuitEvent event) {
+ TNT_SIMULATOR_MAP.remove(event.getPlayer());
+ }
+
+}
diff --git a/BauSystem_Main/src/plugin.yml b/BauSystem_Main/src/plugin.yml
index 8ac3fdc..113cb9a 100644
--- a/BauSystem_Main/src/plugin.yml
+++ b/BauSystem_Main/src/plugin.yml
@@ -36,4 +36,6 @@ commands:
detonator:
aliases: dt
script:
+ simulator:
+ aliases: sim
gui:
\ No newline at end of file