From 1b3da6004cc0e2994de645fd1c8c2bcfe0136ed5 Mon Sep 17 00:00:00 2001 From: Chaoscaot Date: Tue, 24 Aug 2021 14:36:57 +0200 Subject: [PATCH] Warp Signed-off-by: Chaoscaot --- BauSystem_Main/src/BauSystem.properties | 13 +- .../bausystem/features/warp/Moon.java | 59 ++++++ .../bausystem/features/warp/Warp.java | 155 +++++++++++++++ .../bausystem/features/warp/WarpCommand.java | 178 ++++++++++++++++++ .../bausystem/features/warp/WarpGui.java | 96 ++++++++++ .../bausystem/worlddata/WorldData.java | 7 +- 6 files changed, 504 insertions(+), 4 deletions(-) create mode 100644 BauSystem_Main/src/de/steamwar/bausystem/features/warp/Moon.java create mode 100644 BauSystem_Main/src/de/steamwar/bausystem/features/warp/Warp.java create mode 100644 BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpCommand.java create mode 100644 BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpGui.java diff --git a/BauSystem_Main/src/BauSystem.properties b/BauSystem_Main/src/BauSystem.properties index fcf18e04..302865d8 100644 --- a/BauSystem_Main/src/BauSystem.properties +++ b/BauSystem_Main/src/BauSystem.properties @@ -499,12 +499,19 @@ REGION_TNT_BUILD=§cEine Explosion hätte Blöcke im Baubereich zerstört # Unsign Book UNSIGN_HELP_1=§8/§eunsign §8- §7Mache ein Buch beschreibbar - # Team LOCK_SCHEM_NO_USER=§7Dieser Spieler existiert nicht! LOCK_SCHEM_NO_SCHEM=§7Dieser Spieler besitzt keine Schematic mit diesem Namen! LOCK_SCHEM_LOCKED=§e{0} §7von §e{1} §7wurde von §e{2} §7auf §eNORMAL §7zurück gesetz. §f§lGrund: §f{3} LOCK_SCHEM_HELP=§8/§eschemlock §8[§7Owner§8] [§7Schematic§8] [§7Grund§8] - §7Sperre eine Schematic - AFK_KICK_MESSAGE=§cAuf diesem Server ist seit 5 Minuten nichts passiert. -AFK_WARNING_MESSAGE=§cDieser Server wird bei weiterer Inaktivität in einer Minute gestoppt \ No newline at end of file +AFK_WARNING_MESSAGE=§cDieser Server wird bei weiterer Inaktivität in einer Minute gestoppt +WARP_EXISTS=§7Der Warp mit dem namen §e{0} §7existiert bereits +WARP_NAME_RESERVED=§7Du kannst nicht §c{0} §7als name für einen Warp nutzen +WARP_CREATED=§7Der Warp §e{0} §7wurde erstellt +WARP_DELETED=§e{0} §7wurde gelöcht +WARP_GUI_NO=§cHier giebt es noch keine Warps +WARP_GUI_DISTANCE=§7Distanz: §e{0} §7Blöcke +WARP_INFO_NAME=§7Name: §e{0} +WARP_INFO_CREATOR=§7Ersteller: §e{0} +WARP_INFO_CREATED=§7Erstellt am: §e{0} \ No newline at end of file diff --git a/BauSystem_Main/src/de/steamwar/bausystem/features/warp/Moon.java b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/Moon.java new file mode 100644 index 00000000..02ed15e0 --- /dev/null +++ b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/Moon.java @@ -0,0 +1,59 @@ +/* + * This file is a part of the SteamWar software. + * + * Copyright (C) 2021 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.features.warp; + +import de.steamwar.bausystem.BauSystem; +import de.steamwar.inventory.SWItem; +import lombok.experimental.UtilityClass; +import org.bukkit.Bukkit; +import org.bukkit.Material; +import org.bukkit.Particle; +import org.bukkit.entity.Player; +import org.bukkit.potion.PotionEffect; +import org.bukkit.potion.PotionEffectType; +import org.bukkit.util.Vector; + +import java.util.concurrent.atomic.AtomicInteger; + +@UtilityClass +public class Moon { + + public static void startMoon(Player player) { + player.getInventory().setHelmet(new SWItem(Material.GLASS, "§3Atemkugel").getItemStack()); + AtomicInteger countDown = new AtomicInteger(5); + Bukkit.getScheduler().runTaskTimer(BauSystem.getInstance(), bukkitTask -> { + if (countDown.get() == 0) { + AtomicInteger iter = new AtomicInteger(1000); + Bukkit.getScheduler().runTaskTimer(BauSystem.getInstance(), bukkitTask1 -> { + if (player.getLocation().getY() > 300 || iter.getAndDecrement() <= 0) { + player.addPotionEffect(new PotionEffect(PotionEffectType.SLOW_FALLING, 60 * 5 * 20, 1, false, false)); + bukkitTask1.cancel(); + } else { + player.setVelocity(player.getVelocity().add(new Vector(0, 0.2, 0))); + player.getWorld().spawnParticle(Particle.FLAME, player.getLocation(), 5); + } + }, 0, 1); + bukkitTask.cancel(); + } else { + player.sendMessage("§7Noch §e§l" + countDown.getAndDecrement() + " §7Sekunden!"); + } + }, 0, 20); + } +} diff --git a/BauSystem_Main/src/de/steamwar/bausystem/features/warp/Warp.java b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/Warp.java new file mode 100644 index 00000000..0458670d --- /dev/null +++ b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/Warp.java @@ -0,0 +1,155 @@ +/* + * This file is a part of the SteamWar software. + * + * Copyright (C) 2021 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.features.warp; + +import de.steamwar.bausystem.worlddata.WorldData; +import lombok.Getter; +import org.bukkit.*; +import org.bukkit.entity.Player; +import org.bukkit.event.player.PlayerTeleportEvent; +import yapion.hierarchy.types.YAPIONArray; +import yapion.hierarchy.types.YAPIONObject; + +import java.time.Instant; +import java.util.ArrayList; +import java.util.List; +import java.util.Optional; + +@Getter +public class Warp { + + private final Instant created; + private final YAPIONObject object; + private String name; + private double x; + private double y; + private double z; + private float yaw; + private float pitch; + private Material mat; + private String creator; + + private Warp(YAPIONObject object) { + this.object = object; + name = object.getPlainValue("name"); + x = object.getPlainValue("x"); + y = object.getPlainValue("y"); + z = object.getPlainValue("z"); + yaw = object.getPlainValue("yaw"); + pitch = object.getPlainValue("pitch"); + mat = Material.getMaterial(object.getPlainValue("material")); + creator = object.getPlainValue("owner"); + created = Instant.ofEpochSecond(object.getPlainValue("time")); + } + + private Warp() { + object = new YAPIONObject(); + object.add("time", Instant.now().getEpochSecond()); + created = Instant.ofEpochSecond(object.getPlainValue("time")); + } + + public static List getWarps() { + List warpList = new ArrayList<>(); + YAPIONArray warpsObject = WorldData.getWarpData(); + warpsObject.forEach(yapionAnyType -> warpList.add(new Warp((YAPIONObject) yapionAnyType))); + return warpList; + } + + public static Optional getWarp(String name) { + YAPIONArray warpsObject = WorldData.getWarpData(); + return warpsObject.stream().filter(yapionAnyType -> name.equals(((YAPIONObject) yapionAnyType).getPlainValueOrDefault("name", null))).map(yapionAnyType -> new Warp((YAPIONObject) yapionAnyType)).findAny(); + } + + public static Warp createWarp(String name, double x, double y, double z, float yaw, float pitch, Material mat, String creator) { + Warp warp = new Warp(); + warp.setName(name); + warp.setX(x); + warp.setY(y); + warp.setZ(z); + warp.setYaw(yaw); + warp.setPitch(pitch); + warp.setMat(mat); + warp.setCreator(creator); + YAPIONArray warpsObject = WorldData.getWarpData(); + warpsObject.add(warp.object); + + return warp; + } + + public static Warp createWarp(String name, Player player, Material mat) { + Location loc = player.getLocation(); + return createWarp(name, loc.getX(), loc.getY(), loc.getZ(), loc.getYaw(), loc.getPitch(), mat, player.getName()); + } + + public void setName(String name) { + this.name = name; + object.add("name", name); + } + + public void setX(double x) { + this.x = x; + object.add("x", x); + } + + public void setY(double y) { + this.y = y; + object.add("y", y); + } + + public void setZ(double z) { + this.z = z; + object.add("z", z); + } + + public void setYaw(float yaw) { + this.yaw = yaw; + object.add("yaw", yaw); + } + + public void setPitch(float pitch) { + this.pitch = pitch; + object.add("pitch", pitch); + } + + public void setMat(Material mat) { + this.mat = mat; + object.add("material", mat.name()); + } + + public void setCreator(String creator) { + this.creator = creator; + object.add("owner", creator); + } + + public void delete() { + YAPIONArray warpsObject = WorldData.getWarpData(); + warpsObject.removeIf(yapionAnyType -> ((YAPIONObject) yapionAnyType).getPlainValue("name").equals(name)); + } + + public Location toLocation() { + return new Location(Bukkit.getWorlds().get(0), x, y, z, yaw, pitch); + } + + public void teleport(Player player) { + Location loc = toLocation(); + player.teleport(loc, PlayerTeleportEvent.TeleportCause.PLUGIN); + player.playSound(loc, Sound.ENTITY_ENDERMAN_TELEPORT, SoundCategory.PLAYERS, 1, 1); + } +} diff --git a/BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpCommand.java b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpCommand.java new file mode 100644 index 00000000..7de20794 --- /dev/null +++ b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpCommand.java @@ -0,0 +1,178 @@ +/* + * This file is a part of the SteamWar software. + * + * Copyright (C) 2021 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.features.warp; + +import de.steamwar.bausystem.BauSystem; +import de.steamwar.bausystem.Permission; +import de.steamwar.bausystem.config.ColorConfig; +import de.steamwar.bausystem.linkage.LinkageType; +import de.steamwar.bausystem.linkage.Linked; +import de.steamwar.command.SWCommand; +import de.steamwar.command.SWCommandUtils; +import de.steamwar.command.TypeMapper; +import net.md_5.bungee.api.ChatColor; +import net.md_5.bungee.api.chat.ClickEvent; +import net.md_5.bungee.api.chat.ComponentBuilder; +import net.md_5.bungee.api.chat.HoverEvent; +import net.md_5.bungee.api.chat.TextComponent; +import org.bukkit.Material; +import org.bukkit.entity.Player; + +import java.sql.Timestamp; +import java.util.List; +import java.util.stream.Collectors; + +@Linked(LinkageType.COMMAND) +public class WarpCommand extends SWCommand { + + private static final String[] FORBIDDEN_NAMES = new String[]{ + "add", "create", "delete", "list", "info", "gui" + }; + + protected WarpCommand() { + super("warp"); + } + + @ClassMapper(Warp.class) + public static TypeMapper getWarpMapper() { + return SWCommandUtils.createMapper(s -> Warp.getWarp(s).orElse(null), (commandSender, s) -> { + return Warp.getWarps().stream().map(Warp::getName).collect(Collectors.toList()); + }); + } + + @Register(help = true) + public void genericHelp(Player player, String... args) { + if (args.length > 0 && args[0].equals("moon")) { + Moon.startMoon(player); + return; + } + BauSystem.MESSAGE.sendPrefixless("COMMAND_HELP_HEAD", player, "Warp"); + } + + @Register("add") + @Register("create") + public void addWarp(Player player, String name) { + if (!permissionCheck(player)) return; + for (String forbiddenName : FORBIDDEN_NAMES) { + if (name.equalsIgnoreCase(forbiddenName)) { + BauSystem.MESSAGE.send("WARP_NAME_RESERVED", player, name); + return; + } + } + if (Warp.getWarp(name).isPresent()) { + BauSystem.MESSAGE.send("WARP_EXISTS", player, name); + return; + } + Warp.createWarp(name, player, Material.BEACON); + BauSystem.MESSAGE.send("WARP_CREATED", player, name); + } + + @Register + public void tpWarp(Player player, Warp warp) { + warp.teleport(player); + } + + @Register("delete") + public void deleteWarp(Player player, Warp warp) { + if (permissionCheck(player)) return; + warp.delete(); + BauSystem.MESSAGE.send("WARP_DELETED", player, warp.getName()); + } + + @Register("gui") + public void gui(Player player) { + WarpGui.openGui(player); + } + + @Register("list") + public void listWarps(Player player) { + listWarps(player, 0); + } + + @Register("list") + public void listWarps(Player player, int page) { + List warps = Warp.getWarps(); + int pageCount = (int) Math.ceil(warps.size() / 18d); + for (int i = page * 18; i < warps.size() && i < (page + 1) * 18; i++) { + Warp warp = warps.get(i); + TextComponent component = new TextComponent(); + component.setText(warp.getName()); + component.setClickEvent(new ClickEvent(ClickEvent.Action.RUN_COMMAND, "/warp " + warp.getName())); + component.setColor(ChatColor.YELLOW); + component.setHoverEvent(new HoverEvent(HoverEvent.Action.SHOW_TEXT, TextComponent.fromLegacyText("§7Zu §e" + warp.getName() + " §7teleportieren"))); + player.spigot().sendMessage(component); + } + + TextComponent beforePage = new TextComponent("««"); + if (page > 0) { + beforePage.setColor(ChatColor.YELLOW); + beforePage.setHoverEvent(new HoverEvent(HoverEvent.Action.SHOW_TEXT, new ComponentBuilder("§eVorherige Seite").create())); + beforePage.setClickEvent(new ClickEvent(ClickEvent.Action.RUN_COMMAND, "/warp list " + (page - 1))); + } else { + beforePage.setColor(ChatColor.RED); + } + + TextComponent nextPage = new TextComponent(" Seite (" + (page + 1) + "/" + Math.max(pageCount, 1) + ") »»"); + if (page < pageCount - 1) { + nextPage.setColor(ChatColor.YELLOW); + nextPage.setHoverEvent(new HoverEvent(HoverEvent.Action.SHOW_TEXT, new ComponentBuilder("§eNächste Seite").create())); + nextPage.setClickEvent(new ClickEvent(ClickEvent.Action.RUN_COMMAND, "/warp list " + (page + 1))); + } else { + nextPage.setColor(ChatColor.RED); + } + + beforePage.addExtra(nextPage); + player.spigot().sendMessage(beforePage); + } + + @Register("info") + public void warpInfo(Player player, Warp warp) { + BauSystem.MESSAGE.send("COMMAND_HELP_HEAD", player, warp.getName()); + BauSystem.MESSAGE.sendPrefixless("WARP_INFO_NAME", player, warp.getName()); + BauSystem.MESSAGE.sendPrefixless("WARP_INFO_CREATOR", player, warp.getCreator()); + BauSystem.MESSAGE.sendPrefixless("WARP_INFO_CREATED", player, Timestamp.from(warp.getCreated()).toLocalDateTime()); + player.sendMessage("§7X: §e" + warp.getX()); + player.sendMessage("§7Y: §e" + warp.getY()); + player.sendMessage("§7Z: §e" + warp.getZ()); + BauSystem.MESSAGE.sendPrefixless("WARP_GUI_DISTANCE", player, warp.toLocation().distance(player.getLocation())); + } + + @SuppressWarnings("BooleanMethodIsAlwaysInverted") + private boolean permissionCheck(Player player) { + if (!Permission.hasPermission(player, Permission.WORLD)) { + player.sendMessage(BauSystem.PREFIX + ColorConfig.DISABLE + "Du darfst hier nicht den Warp verändern"); + return false; + } + return true; + } + + @Linked(LinkageType.COMMAND) + public static class WarpsLink extends SWCommand { + + protected WarpsLink() { + super("warps"); + } + + @Register(help = true) + public void genericCommand(Player player, String... args) { + player.performCommand("warp list " + String.join(" ", args)); + } + } +} diff --git a/BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpGui.java b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpGui.java new file mode 100644 index 00000000..b1c7fc47 --- /dev/null +++ b/BauSystem_Main/src/de/steamwar/bausystem/features/warp/WarpGui.java @@ -0,0 +1,96 @@ +/* + * This file is a part of the SteamWar software. + * + * Copyright (C) 2021 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.features.warp; + +import de.steamwar.bausystem.BauSystem; +import de.steamwar.bausystem.Permission; +import de.steamwar.inventory.SWInventory; +import de.steamwar.inventory.SWItem; +import de.steamwar.inventory.SWListInv; +import org.bukkit.Material; +import org.bukkit.entity.Player; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +public class WarpGui { + + public static void openGui(Player player) { + List> entries = new ArrayList<>(); + Warp.getWarps().forEach(warp -> entries.add(new SWListInv.SWListEntry<>(new SWItem( + warp.getMat(), + "§e" + warp.getName(), + Arrays.asList("§7X: §e" + (int) warp.getX(), + "§7Y: §e" + (int) warp.getY(), + "§7Z: §e" + (int) warp.getZ(), + BauSystem.MESSAGE.parse("WARP_GUI_DISTANCE", player, (int) warp.toLocation().distance(player.getLocation()))), + false, + clickType -> { + } + ), warp))); + + SWListInv inv = new SWListInv<>(player, "Warps", false, entries, (clickType, warp) -> { + if (clickType.isRightClick() && Permission.hasPermission(player, Permission.WORLD)) { + openWarpGui(player, warp); + } else { + warp.teleport(player); + } + }); + + if (entries.isEmpty()) { + inv.setItem(22, new SWItem(Material.BARRIER, BauSystem.MESSAGE.parse("WARP_GUI_NO", player), clickType -> { + })); + } + + inv.open(); + } + + public static void openWarpGui(Player player, Warp warp) { + SWInventory inv = new SWInventory(player, 9, warp.getName()); + inv.setItem(0, new SWItem(Material.ENDER_PEARL, "§7Zu §e" + warp.getName() + " §7teleportieren", clickType -> { + player.closeInventory(); + warp.teleport(player); + })); + + inv.setItem(2, new SWItem(warp.getMat(), "§e" + warp.getMat().name(), clickType -> changeMaterial(player, warp))); + + inv.setItem(8, new SWItem(Material.BARRIER, "§e" + warp.getName() + " §7löschen", clickType -> { + player.closeInventory(); + warp.delete(); + })); + + inv.open(); + } + + public static void changeMaterial(Player player, Warp warp) { + List> materials = new ArrayList<>(); + for (Material value : Material.values()) { + if (value.isLegacy() || value.isAir()) continue; + materials.add(new SWListInv.SWListEntry<>(new SWItem(value, "§e" + value.name()), value)); + } + + SWListInv inv = new SWListInv<>(player, "Material auswählen", materials, (clickType, material) -> { + player.closeInventory(); + warp.setMat(material); + }); + inv.open(); + } +} diff --git a/BauSystem_Main/src/de/steamwar/bausystem/worlddata/WorldData.java b/BauSystem_Main/src/de/steamwar/bausystem/worlddata/WorldData.java index f5eab71f..62f54e8f 100644 --- a/BauSystem_Main/src/de/steamwar/bausystem/worlddata/WorldData.java +++ b/BauSystem_Main/src/de/steamwar/bausystem/worlddata/WorldData.java @@ -22,6 +22,7 @@ package de.steamwar.bausystem.worlddata; import lombok.experimental.UtilityClass; import org.bukkit.Bukkit; import yapion.hierarchy.output.FileOutput; +import yapion.hierarchy.types.YAPIONArray; import yapion.hierarchy.types.YAPIONObject; import yapion.parser.YAPIONParser; @@ -33,7 +34,7 @@ import java.io.IOException; @UtilityClass public class WorldData { - private File optionsFile = new File(Bukkit.getWorlds().get(0).getWorldFolder(), "options.yapion"); + private final File optionsFile = new File(Bukkit.getWorlds().get(0).getWorldFolder(), "options.yapion"); private YAPIONObject worldData; public YAPIONObject getWorldData() { @@ -47,6 +48,10 @@ public class WorldData { return getWorldData().getYAPIONObjectOrSetDefault("regions", new YAPIONObject()); } + public YAPIONArray getWarpData() { + return getWorldData().getYAPIONArrayOrSetDefault("warps", new YAPIONArray()); + } + private void read() { worldData = new YAPIONObject(); if (optionsFile.length() != 0) {