Upload via GUI (84 Dateien)

This commit is contained in:
2026-10-11 17:15:35 +00:00
parent 3a8fe5cf66
commit 3ec1d905dc
12 changed files with 780 additions and 765 deletions
+1 -1
View File
@@ -6,7 +6,7 @@
<groupId>de.nexuslobby</groupId> <groupId>de.nexuslobby</groupId>
<artifactId>NexusLobby</artifactId> <artifactId>NexusLobby</artifactId>
<version>1.9</version> <version>2.0</version>
<packaging>jar</packaging> <packaging>jar</packaging>
<name>NexusLobby</name> <name>NexusLobby</name>
@@ -173,22 +173,22 @@ public class ScoreboardModule implements Module, Listener {
playerBoards.put(player.getUniqueId(), Bukkit.getScoreboardManager().getNewScoreboard()); playerBoards.put(player.getUniqueId(), Bukkit.getScoreboardManager().getNewScoreboard());
} }
player.setScoreboard(playerBoards.get(player.getUniqueId())); player.setScoreboard(playerBoards.get(player.getUniqueId()));
player.sendMessage("§7[§6Nexus§7] §aScoreboard eingeschaltet."); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§aScoreboard eingeschaltet.");
updateSidebar(player); // Sofort aktualisieren updateSidebar(player); // Sofort aktualisieren
} else { } else {
hiddenPlayers.add(player.getUniqueId()); hiddenPlayers.add(player.getUniqueId());
player.setScoreboard(Bukkit.getScoreboardManager().getMainScoreboard()); player.setScoreboard(Bukkit.getScoreboardManager().getMainScoreboard());
player.sendMessage("§7[§6Nexus§7] §cScoreboard ausgeschaltet."); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§cScoreboard ausgeschaltet.");
} }
} }
public void setAdminMode(Player player, boolean admin) { public void setAdminMode(Player player, boolean admin) {
if (admin) { if (admin) {
adminModePlayers.add(player.getUniqueId()); adminModePlayers.add(player.getUniqueId());
player.sendMessage("§7[§6Nexus§7] §eModus: §cAdmin-Scoreboard §7(Owner-Sektion)"); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§eModus: §cAdmin-Scoreboard §7(Owner-Sektion)");
} else { } else {
adminModePlayers.remove(player.getUniqueId()); adminModePlayers.remove(player.getUniqueId());
player.sendMessage("§7[§6Nexus§7] §eModus: §6Spieler-Scoreboard §7(Default-Sektion)"); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§eModus: §6Spieler-Scoreboard §7(Default-Sektion)");
} }
updateSidebar(player); updateSidebar(player);
} }
@@ -1,196 +1,196 @@
package de.nexuslobby.modules.player; package de.nexuslobby.modules.player;
import de.nexuslobby.NexusLobby; import de.nexuslobby.NexusLobby;
import de.nexuslobby.api.Module; import de.nexuslobby.api.Module;
import me.clip.placeholderapi.PlaceholderAPI; import me.clip.placeholderapi.PlaceholderAPI;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;
import org.bukkit.Material; import org.bukkit.Material;
import org.bukkit.Statistic; import org.bukkit.Statistic;
import org.bukkit.entity.Player; import org.bukkit.entity.Player;
import org.bukkit.event.EventHandler; import org.bukkit.event.EventHandler;
import org.bukkit.event.Listener; import org.bukkit.event.Listener;
import org.bukkit.event.inventory.InventoryClickEvent; import org.bukkit.event.inventory.InventoryClickEvent;
import org.bukkit.event.player.PlayerInteractEntityEvent; import org.bukkit.event.player.PlayerInteractEntityEvent;
import org.bukkit.inventory.Inventory; import org.bukkit.inventory.Inventory;
import org.bukkit.inventory.ItemStack; import org.bukkit.inventory.ItemStack;
import org.bukkit.inventory.meta.ItemMeta; import org.bukkit.inventory.meta.ItemMeta;
import org.bukkit.inventory.meta.SkullMeta; import org.bukkit.inventory.meta.SkullMeta;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
/** /**
* Modul zur Inspektion von Spielern in der Lobby. * Modul zur Inspektion von Spielern in der Lobby.
* Zeigt detaillierte Statistiken in einer interaktiven GUI an. * Zeigt detaillierte Statistiken in einer interaktiven GUI an.
*/ */
public class PlayerInspectModule implements Module, Listener { public class PlayerInspectModule implements Module, Listener {
@Override @Override
public String getName() { public String getName() {
return "PlayerInspect"; return "PlayerInspect";
} }
@Override @Override
public void onEnable() { public void onEnable() {
Bukkit.getPluginManager().registerEvents(this, NexusLobby.getInstance()); Bukkit.getPluginManager().registerEvents(this, NexusLobby.getInstance());
} }
@Override @Override
public void onDisable() { public void onDisable() {
org.bukkit.event.HandlerList.unregisterAll(this); org.bukkit.event.HandlerList.unregisterAll(this);
} }
@EventHandler @EventHandler
public void onPlayerInteract(PlayerInteractEntityEvent event) { public void onPlayerInteract(PlayerInteractEntityEvent event) {
// Prüfen, ob ein Spieler rechtsgeklickt wurde // Prüfen, ob ein Spieler rechtsgeklickt wurde
if (event.getRightClicked() instanceof Player target) { if (event.getRightClicked() instanceof Player target) {
Player viewer = event.getPlayer(); Player viewer = event.getPlayer();
// GUI nur öffnen, wenn die Hand leer ist (verhindert Konflikte mit Items) // GUI nur öffnen, wenn die Hand leer ist (verhindert Konflikte mit Items)
if (viewer.getInventory().getItemInMainHand().getType() == Material.AIR) { if (viewer.getInventory().getItemInMainHand().getType() == Material.AIR) {
openDetailedInspectGUI(viewer, target); openDetailedInspectGUI(viewer, target);
} }
} }
} }
@EventHandler @EventHandler
public void onInventoryClick(InventoryClickEvent event) { public void onInventoryClick(InventoryClickEvent event) {
// Sicherstellen, dass es unser Statistik-Inventar ist anhand des Titels // Sicherstellen, dass es unser Statistik-Inventar ist anhand des Titels
if (event.getView().getTitle().contains("Statistiken")) { if (event.getView().getTitle().contains("Statistiken")) {
event.setCancelled(true); // Verhindert, dass Items herausgenommen werden event.setCancelled(true); // Verhindert, dass Items herausgenommen werden
ItemStack clickedItem = event.getCurrentItem(); ItemStack clickedItem = event.getCurrentItem();
if (clickedItem == null || clickedItem.getType() == Material.AIR) return; if (clickedItem == null || clickedItem.getType() == Material.AIR) return;
// Logik für den Schließen-Button (Barriere) // Logik für den Schließen-Button (Barriere)
if (clickedItem.getType() == Material.BARRIER) { if (clickedItem.getType() == Material.BARRIER) {
event.getWhoClicked().closeInventory(); event.getWhoClicked().closeInventory();
} }
} }
} }
public void openDetailedInspectGUI(Player viewer, Player target) { public void openDetailedInspectGUI(Player viewer, Player target) {
// Titel mit Farbcodes // Titel mit Farbcodes
String title = "§8» §3Statistiken: §b" + target.getName(); String title = "§8» §3Statistiken: §b" + target.getName();
Inventory gui = Bukkit.createInventory(null, 45, title); Inventory gui = Bukkit.createInventory(null, 45, title);
// --- Design: Hintergrund mit Glasscheiben füllen --- // --- Design: Hintergrund mit Glasscheiben füllen ---
ItemStack separator = createSimpleItem(Material.GRAY_STAINED_GLASS_PANE, " "); ItemStack separator = createSimpleItem(Material.GRAY_STAINED_GLASS_PANE, " ");
int[] borderSlots = { int[] borderSlots = {
0,1,2,3,4,5,6,7,8, 0,1,2,3,4,5,6,7,8,
9,17, 9,17,
18,26, 18,26,
27,35, 27,35,
36,37,38,39,41,42,43,44 36,37,38,39,41,42,43,44
}; };
for (int slot : borderSlots) gui.setItem(slot, separator); for (int slot : borderSlots) gui.setItem(slot, separator);
// --- Kopf des Spielers mit LuckPerms Prefix via PAPI --- // --- Kopf des Spielers mit LuckPerms Prefix via PAPI ---
ItemStack head = new ItemStack(Material.PLAYER_HEAD); ItemStack head = new ItemStack(Material.PLAYER_HEAD);
SkullMeta headMeta = (SkullMeta) head.getItemMeta(); SkullMeta headMeta = (SkullMeta) head.getItemMeta();
if (headMeta != null) { if (headMeta != null) {
headMeta.setOwningPlayer(target); headMeta.setOwningPlayer(target);
headMeta.setDisplayName("§e§l" + target.getName()); headMeta.setDisplayName("§e§l" + target.getName());
List<String> lore = new ArrayList<>(); List<String> lore = new ArrayList<>();
lore.add("§8§m-----------------------"); lore.add("§8§m-----------------------");
// LuckPerms Prefix über PlaceholderAPI auslesen (falls vorhanden) // LuckPerms Prefix über PlaceholderAPI auslesen (falls vorhanden)
String prefix = "%luckperms_prefix%"; String prefix = "%luckperms_prefix%";
if (Bukkit.getPluginManager().getPlugin("PlaceholderAPI") != null) { if (Bukkit.getPluginManager().getPlugin("PlaceholderAPI") != null) {
try { try {
prefix = PlaceholderAPI.setPlaceholders(target, prefix); prefix = PlaceholderAPI.setPlaceholders(target, prefix);
} catch (NoClassDefFoundError ignored) { } catch (NoClassDefFoundError ignored) {
// PlaceholderAPI fehlt zur Laufzeit // PlaceholderAPI fehlt zur Laufzeit
} }
} }
// KORREKTUR: Farbcodes (&) in echte Minecraft-Farben (§) umwandeln // KORREKTUR: Farbcodes (&) in echte Minecraft-Farben (§) umwandeln
prefix = ChatColor.translateAlternateColorCodes('&', prefix); prefix = ChatColor.translateAlternateColorCodes('&', prefix);
lore.add("§7Rang: " + (prefix.isEmpty() ? "§fSpieler" : prefix)); lore.add("§7Rang: " + (prefix.isEmpty() ? "§fSpieler" : prefix));
lore.add("§7Level: §a" + target.getLevel()); lore.add("§7Level: §a" + target.getLevel());
lore.add("§7Status: §aOnline"); lore.add("§7Status: §aOnline");
lore.add("§8§m-----------------------"); lore.add("§8§m-----------------------");
headMeta.setLore(lore); headMeta.setLore(lore);
head.setItemMeta(headMeta); head.setItemMeta(headMeta);
} }
gui.setItem(4, head); gui.setItem(4, head);
// --- Statistik Kategorie: KAMPF (Slot 19) --- // --- Statistik Kategorie: KAMPF (Slot 19) ---
gui.setItem(19, createStatsItem(Material.DIAMOND_SWORD, "§c§lKampf-Statistiken", gui.setItem(19, createStatsItem(Material.DIAMOND_SWORD, "§c§lKampf-Statistiken",
"§8» §7Spieler-Kills: §f" + target.getStatistic(Statistic.PLAYER_KILLS), "§8» §7Spieler-Kills: §f" + target.getStatistic(Statistic.PLAYER_KILLS),
"§8» §7Mob-Kills: §f" + target.getStatistic(Statistic.MOB_KILLS), "§8» §7Mob-Kills: §f" + target.getStatistic(Statistic.MOB_KILLS),
"§8» §7Tode gesamt: §f" + target.getStatistic(Statistic.DEATHS), "§8» §7Tode gesamt: §f" + target.getStatistic(Statistic.DEATHS),
"§8» §7Schaden verursacht: §f" + (target.getStatistic(Statistic.DAMAGE_DEALT) / 10) + " ❤")); "§8» §7Schaden verursacht: §f" + (target.getStatistic(Statistic.DAMAGE_DEALT) / 10) + " ❤"));
// --- Statistik Kategorie: ARBEIT (Slot 21) --- // --- Statistik Kategorie: ARBEIT (Slot 21) ---
// Optimierte Abfrage für wichtige Blöcke // Optimierte Abfrage für wichtige Blöcke
int totalBlocks = target.getStatistic(Statistic.MINE_BLOCK, Material.STONE) + int totalBlocks = target.getStatistic(Statistic.MINE_BLOCK, Material.STONE) +
target.getStatistic(Statistic.MINE_BLOCK, Material.DIRT) + target.getStatistic(Statistic.MINE_BLOCK, Material.DIRT) +
target.getStatistic(Statistic.MINE_BLOCK, Material.COBBLESTONE); target.getStatistic(Statistic.MINE_BLOCK, Material.COBBLESTONE);
gui.setItem(21, createStatsItem(Material.IRON_PICKAXE, "§e§lHandwerk & Fleiß", gui.setItem(21, createStatsItem(Material.IRON_PICKAXE, "§e§lHandwerk & Fleiß",
"§8» §7Blöcke (S/D/C): §f" + totalBlocks, "§8» §7Blöcke (S/D/C): §f" + totalBlocks,
"§8» §7Items gedroppt: §f" + target.getStatistic(Statistic.DROP_COUNT), "§8» §7Items gedroppt: §f" + target.getStatistic(Statistic.DROP_COUNT),
"§8» §7Fische gefangen: §f" + target.getStatistic(Statistic.FISH_CAUGHT), "§8» §7Fische gefangen: §f" + target.getStatistic(Statistic.FISH_CAUGHT),
"§8» §7Glocken geläutet: §f" + target.getStatistic(Statistic.BELL_RING))); "§8» §7Glocken geläutet: §f" + target.getStatistic(Statistic.BELL_RING)));
// --- Statistik Kategorie: BEWEGUNG (Slot 23) --- // --- Statistik Kategorie: BEWEGUNG (Slot 23) ---
double walkKm = target.getStatistic(Statistic.WALK_ONE_CM) / 100000.0; double walkKm = target.getStatistic(Statistic.WALK_ONE_CM) / 100000.0;
double flyKm = target.getStatistic(Statistic.FLY_ONE_CM) / 100000.0; double flyKm = target.getStatistic(Statistic.FLY_ONE_CM) / 100000.0;
gui.setItem(23, createStatsItem(Material.GOLDEN_BOOTS, "§b§lReise-Statistiken", gui.setItem(23, createStatsItem(Material.GOLDEN_BOOTS, "§b§lReise-Statistiken",
"§8» §7Gelaufen: §f" + String.format("%.2f", walkKm) + " km", "§8» §7Gelaufen: §f" + String.format("%.2f", walkKm) + " km",
"§8» §7Geflogen: §f" + String.format("%.2f", flyKm) + " km", "§8» §7Geflogen: §f" + String.format("%.2f", flyKm) + " km",
"§8» §7Sprünge: §f" + target.getStatistic(Statistic.JUMP))); "§8» §7Sprünge: §f" + target.getStatistic(Statistic.JUMP)));
// --- Statistik Kategorie: ZEIT (Slot 25) --- // --- Statistik Kategorie: ZEIT (Slot 25) ---
long ticks = target.getStatistic(Statistic.PLAY_ONE_MINUTE); long ticks = target.getStatistic(Statistic.PLAY_ONE_MINUTE);
long hours = ticks / 72000; long hours = ticks / 72000;
long mins = (ticks % 72000) / 1200; long mins = (ticks % 72000) / 1200;
gui.setItem(25, createStatsItem(Material.CLOCK, "§a§lZeit-Statistiken", gui.setItem(25, createStatsItem(Material.CLOCK, "§a§lZeit-Statistiken",
"§8» §7Spielzeit: §f" + hours + " Std. " + mins + " Min.", "§8» §7Spielzeit: §f" + hours + " Std. " + mins + " Min.",
"§8» §7Letzter Tod vor: §f" + (target.getStatistic(Statistic.TIME_SINCE_DEATH) / 1200) + " Min.", "§8» §7Letzter Tod vor: §f" + (target.getStatistic(Statistic.TIME_SINCE_DEATH) / 1200) + " Min.",
"§8» §7Tage auf Server: §f" + (target.getStatistic(Statistic.PLAY_ONE_MINUTE) / 1728000))); "§8» §7Tage auf Server: §f" + (target.getStatistic(Statistic.PLAY_ONE_MINUTE) / 1728000)));
// --- Schließen Button (Slot 40) --- // --- Schließen Button (Slot 40) ---
gui.setItem(40, createSimpleItem(Material.BARRIER, "§c§lMenü schließen")); gui.setItem(40, createSimpleItem(Material.BARRIER, "§c§lMenü schließen"));
// Inventar für den Zuschauer öffnen // Inventar für den Zuschauer öffnen
viewer.openInventory(gui); viewer.openInventory(gui);
} }
/** /**
* Erstellt ein ItemStack mit Name und Lore-Zeilen inklusive einer Leerzeile am Anfang. * Erstellt ein ItemStack mit Name und Lore-Zeilen inklusive einer Leerzeile am Anfang.
*/ */
private ItemStack createStatsItem(Material material, String displayName, String... loreLines) { private ItemStack createStatsItem(Material material, String displayName, String... loreLines) {
ItemStack item = new ItemStack(material); ItemStack item = new ItemStack(material);
ItemMeta meta = item.getItemMeta(); ItemMeta meta = item.getItemMeta();
if (meta != null) { if (meta != null) {
meta.setDisplayName(displayName); meta.setDisplayName(displayName);
List<String> lore = new ArrayList<>(); List<String> lore = new ArrayList<>();
lore.add(" "); // Leerzeile für sauberes Design lore.add(" "); // Leerzeile für sauberes Design
for (String line : loreLines) { for (String line : loreLines) {
lore.add(line); lore.add(line);
} }
meta.setLore(lore); meta.setLore(lore);
item.setItemMeta(meta); item.setItemMeta(meta);
} }
return item; return item;
} }
/** /**
* Erstellt ein einfaches ItemStack ohne Lore für Designzwecke. * Erstellt ein einfaches ItemStack ohne Lore für Designzwecke.
*/ */
private ItemStack createSimpleItem(Material material, String displayName) { private ItemStack createSimpleItem(Material material, String displayName) {
ItemStack item = new ItemStack(material); ItemStack item = new ItemStack(material);
ItemMeta meta = item.getItemMeta(); ItemMeta meta = item.getItemMeta();
if (meta != null) { if (meta != null) {
meta.setDisplayName(displayName); meta.setDisplayName(displayName);
item.setItemMeta(meta); item.setItemMeta(meta);
} }
return item; return item;
} }
} }
@@ -131,10 +131,10 @@ public class PortalManager implements Module, Listener {
p.sendMessage("§7§m----------------------------------"); p.sendMessage("§7§m----------------------------------");
if (volume < 500) { if (volume < 500) {
p.sendMessage("§e[Nexus] Kleiner Bereich erkannt (Portal-Größe)"); p.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§eKleiner Bereich erkannt (Portal-Größe)");
p.sendMessage("§fBefehl: §b/portal create <n> <server|world>"); p.sendMessage("§fBefehl: §b/portal create <n> <server|world>");
} else { } else {
p.sendMessage("§6[Nexus] Großer Bereich erkannt (WorldBorder-Größe)"); p.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§6Großer Bereich erkannt (WorldBorder-Größe)");
p.sendMessage("§fBefehl: §a/border square"); p.sendMessage("§fBefehl: §a/border square");
} }
p.sendMessage("§7§m----------------------------------"); p.sendMessage("§7§m----------------------------------");
@@ -1,135 +1,135 @@
package de.nexuslobby.modules.servers; package de.nexuslobby.modules.servers;
import de.nexuslobby.NexusLobby; import de.nexuslobby.NexusLobby;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import org.bukkit.ChatColor; import org.bukkit.ChatColor;
import org.bukkit.World; import org.bukkit.World;
import org.bukkit.entity.ArmorStand; import org.bukkit.entity.ArmorStand;
import org.bukkit.scheduler.BukkitTask; import org.bukkit.scheduler.BukkitTask;
import java.io.IOException; import java.io.IOException;
import java.net.InetSocketAddress; import java.net.InetSocketAddress;
import java.net.Socket; import java.net.Socket;
import java.util.concurrent.CompletableFuture; import java.util.concurrent.CompletableFuture;
public class ServerChecker { public class ServerChecker {
private static BukkitTask globalCheckerTask = null; private static BukkitTask globalCheckerTask = null;
/** /**
* Prüft asynchron, ob ein Server unter der angegebenen IP und Port erreichbar ist. * Prüft asynchron, ob ein Server unter der angegebenen IP und Port erreichbar ist.
*/ */
public static CompletableFuture<Boolean> isOnline(String ip, int port) { public static CompletableFuture<Boolean> isOnline(String ip, int port) {
return CompletableFuture.supplyAsync(() -> { return CompletableFuture.supplyAsync(() -> {
try (Socket socket = new Socket()) { try (Socket socket = new Socket()) {
// 500ms Timeout für stabilere Erkennung // 500ms Timeout für stabilere Erkennung
socket.connect(new InetSocketAddress(ip, port), 500); socket.connect(new InetSocketAddress(ip, port), 500);
return true; return true;
} catch (IOException e) { } catch (IOException e) {
return false; return false;
} }
}); });
} }
/** /**
* Startet den Scheduler, der alle ArmorStands in allen Welten regelmäßig prüft. * Startet den Scheduler, der alle ArmorStands in allen Welten regelmäßig prüft.
*/ */
public static void startGlobalChecker() { public static void startGlobalChecker() {
// Cancel alten Task falls vorhanden // Cancel alten Task falls vorhanden
stopGlobalChecker(); stopGlobalChecker();
// WICHTIG: runTaskTimer (synchron), um den Main-Thread für getEntitiesByClass zu nutzen // WICHTIG: runTaskTimer (synchron), um den Main-Thread für getEntitiesByClass zu nutzen
globalCheckerTask = Bukkit.getScheduler().runTaskTimer(NexusLobby.getInstance(), () -> { globalCheckerTask = Bukkit.getScheduler().runTaskTimer(NexusLobby.getInstance(), () -> {
for (World world : Bukkit.getWorlds()) { for (World world : Bukkit.getWorlds()) {
// Das Abrufen der Entities muss auf dem Main-Thread passieren // Das Abrufen der Entities muss auf dem Main-Thread passieren
for (ArmorStand as : world.getEntitiesByClass(ArmorStand.class)) { for (ArmorStand as : world.getEntitiesByClass(ArmorStand.class)) {
checkAndUpdateArmorStand(as); checkAndUpdateArmorStand(as);
} }
} }
}, 100L, 200L); }, 100L, 200L);
} }
/** /**
* Stoppt den Server-Checker Task * Stoppt den Server-Checker Task
*/ */
public static void stopGlobalChecker() { public static void stopGlobalChecker() {
if (globalCheckerTask != null && !globalCheckerTask.isCancelled()) { if (globalCheckerTask != null && !globalCheckerTask.isCancelled()) {
globalCheckerTask.cancel(); globalCheckerTask.cancel();
globalCheckerTask = null; globalCheckerTask = null;
} }
} }
/** /**
* Analysiert die Tags eines ArmorStands und aktualisiert den Namen basierend auf dem Serverstatus. * Analysiert die Tags eines ArmorStands und aktualisiert den Namen basierend auf dem Serverstatus.
*/ */
private static void checkAndUpdateArmorStand(ArmorStand as) { private static void checkAndUpdateArmorStand(ArmorStand as) {
for (String tag : as.getScoreboardTags()) { for (String tag : as.getScoreboardTags()) {
// Erwartetes Format: ascmd:slot1:slot2:type:command // Erwartetes Format: ascmd:slot1:slot2:type:command
if (tag.startsWith("ascmd:")) { if (tag.startsWith("ascmd:")) {
String[] parts = tag.split(":"); String[] parts = tag.split(":");
if (parts.length < 5) continue; if (parts.length < 5) continue;
String type = parts[3].toLowerCase(); String type = parts[3].toLowerCase();
if (!type.equals("bungee")) continue; if (!type.equals("bungee")) continue;
String serverName = parts[4]; String serverName = parts[4];
// Suche den passenden Key in der Config // Suche den passenden Key in der Config
String configKey = null; String configKey = null;
if (NexusLobby.getInstance().getConfig().getConfigurationSection("servers") != null) { if (NexusLobby.getInstance().getConfig().getConfigurationSection("servers") != null) {
for (String key : NexusLobby.getInstance().getConfig().getConfigurationSection("servers").getKeys(false)) { for (String key : NexusLobby.getInstance().getConfig().getConfigurationSection("servers").getKeys(false)) {
if (key.equalsIgnoreCase(serverName)) { if (key.equalsIgnoreCase(serverName)) {
configKey = key; configKey = key;
break; break;
} }
} }
} }
if (configKey == null) continue; if (configKey == null) continue;
String ip = NexusLobby.getInstance().getConfig().getString("servers." + configKey + ".ip"); String ip = NexusLobby.getInstance().getConfig().getString("servers." + configKey + ".ip");
int port = NexusLobby.getInstance().getConfig().getInt("servers." + configKey + ".port"); int port = NexusLobby.getInstance().getConfig().getInt("servers." + configKey + ".port");
if (ip == null) continue; if (ip == null) continue;
// Der Ping selbst läuft asynchron weg vom Main-Thread // Der Ping selbst läuft asynchron weg vom Main-Thread
isOnline(ip, port).thenAccept(online -> { isOnline(ip, port).thenAccept(online -> {
// Zurück zum Main-Thread für die Änderung des ArmorStands // Zurück zum Main-Thread für die Änderung des ArmorStands
Bukkit.getScheduler().runTask(NexusLobby.getInstance(), () -> { Bukkit.getScheduler().runTask(NexusLobby.getInstance(), () -> {
if (!as.isValid()) return; // Sicherheitscheck falls AS gelöscht wurde if (!as.isValid()) return; // Sicherheitscheck falls AS gelöscht wurde
if (online) { if (online) {
restoreName(as); restoreName(as);
} else { } else {
String offlineText = "§c● §lOFFLINE §c●"; String offlineText = "§c● §lOFFLINE §c●";
if (!offlineText.equals(as.getCustomName())) { if (!offlineText.equals(as.getCustomName())) {
as.setCustomName(offlineText); as.setCustomName(offlineText);
as.setCustomNameVisible(true); as.setCustomNameVisible(true);
} }
} }
}); });
}); });
break; break;
} }
} }
} }
/** /**
* Stellt den ursprünglichen Namen des ArmorStands wieder her. * Stellt den ursprünglichen Namen des ArmorStands wieder her.
* Nutzt den Tag "asname:NAME" als Backup. * Nutzt den Tag "asname:NAME" als Backup.
*/ */
private static void restoreName(ArmorStand as) { private static void restoreName(ArmorStand as) {
for (String t : as.getScoreboardTags()) { for (String t : as.getScoreboardTags()) {
if (t.startsWith("asname:")) { if (t.startsWith("asname:")) {
String originalName = t.substring(7); String originalName = t.substring(7);
String translatedName = ChatColor.translateAlternateColorCodes('&', originalName); String translatedName = ChatColor.translateAlternateColorCodes('&', originalName);
if (!translatedName.equals(as.getCustomName())) { if (!translatedName.equals(as.getCustomName())) {
as.setCustomName(translatedName); as.setCustomName(translatedName);
as.setCustomNameVisible(true); as.setCustomNameVisible(true);
} }
return; return;
} }
} }
} }
} }
@@ -178,7 +178,7 @@ public class ServerSwitcherListener implements Listener, CommandExecutor {
private void connectBungee(Player player, String serverName) { private void connectBungee(Player player, String serverName) {
if (!Bukkit.getMessenger().isOutgoingChannelRegistered( if (!Bukkit.getMessenger().isOutgoingChannelRegistered(
NexusLobby.getInstance(), "BungeeCord")) { NexusLobby.getInstance(), "BungeeCord")) {
player.sendMessage("§8[§6Nexus§8] §cKein BungeeCord-Kanal registriert."); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§cKein BungeeCord-Kanal registriert.");
return; return;
} }
try { try {
@@ -187,9 +187,9 @@ public class ServerSwitcherListener implements Listener, CommandExecutor {
out.writeUTF("Connect"); out.writeUTF("Connect");
out.writeUTF(serverName); out.writeUTF(serverName);
player.sendPluginMessage(NexusLobby.getInstance(), "BungeeCord", b.toByteArray()); player.sendPluginMessage(NexusLobby.getInstance(), "BungeeCord", b.toByteArray());
player.sendMessage("§8[§6Nexus§8] §7Verbinde mit §e" + serverName + "§7..."); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§7Verbinde mit §e" + serverName + "§7...");
} catch (java.io.IOException ex) { } catch (java.io.IOException ex) {
player.sendMessage("§8[§6Nexus§8] §cFehler beim Verbinden: " + ex.getMessage()); player.sendMessage(de.nexuslobby.utils.LangManager.getPrefix() + "§cFehler beim Verbinden: " + ex.getMessage());
} }
} }
} }
@@ -1,155 +1,156 @@
package de.nexuslobby.utils; package de.nexuslobby.utils;
import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.configuration.file.FileConfiguration;
import org.bukkit.plugin.java.JavaPlugin; import org.bukkit.plugin.java.JavaPlugin;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
/** /**
* Validiert Config-Werte und setzt Default-Werte wenn nötig * Validiert Config-Werte und setzt Default-Werte wenn nötig
*/ */
public class ConfigValidator { public class ConfigValidator {
private final JavaPlugin plugin; private final JavaPlugin plugin;
private final FileConfiguration config; private final FileConfiguration config;
private final List<String> warnings = new ArrayList<>(); private final List<String> warnings = new ArrayList<>();
private boolean modified = false; private boolean modified = false;
public ConfigValidator(JavaPlugin plugin, FileConfiguration config) { public ConfigValidator(JavaPlugin plugin, FileConfiguration config) {
this.plugin = plugin; this.plugin = plugin;
this.config = config; this.config = config;
} }
/** /**
* Validiert alle Config-Werte und gibt Warnings aus * Validiert alle Config-Werte und gibt Warnings aus
*/ */
public void validate() { public void validate() {
validateSpawn(); ensureDefault("prefix", "&8[&6Nexus&8] ");
validateLobbySettings(); validateSpawn();
validateTablist(); validateLobbySettings();
validateBall(); validateTablist();
validateModules(); validateBall();
validateModules();
// Warnings ausgeben
if (!warnings.isEmpty()) { // Warnings ausgeben
plugin.getLogger().warning("=== Config-Validierung ==="); if (!warnings.isEmpty()) {
warnings.forEach(msg -> plugin.getLogger().warning(" " + msg)); plugin.getLogger().warning("=== Config-Validierung ===");
plugin.getLogger().warning("========================="); warnings.forEach(msg -> plugin.getLogger().warning(" " + msg));
} plugin.getLogger().warning("=========================");
}
// Config speichern wenn Änderungen vorgenommen wurden
if (modified) { // Config speichern wenn Änderungen vorgenommen wurden
plugin.saveConfig(); if (modified) {
plugin.getLogger().info("Config wurde mit Default-Werten aktualisiert."); plugin.saveConfig();
} plugin.getLogger().info("Config wurde mit Default-Werten aktualisiert.");
} }
}
private void validateSpawn() {
ensureDefault("spawn.world", "world"); private void validateSpawn() {
ensureDefault("spawn.x", 0.5); ensureDefault("spawn.world", "world");
ensureDefault("spawn.y", 64.0); ensureDefault("spawn.x", 0.5);
ensureDefault("spawn.z", 0.5); ensureDefault("spawn.y", 64.0);
ensureDefault("spawn.yaw", 0.0); ensureDefault("spawn.z", 0.5);
ensureDefault("spawn.pitch", 0.0); ensureDefault("spawn.yaw", 0.0);
ensureDefault("spawn.pitch", 0.0);
// Validiere Y-Koordinate
double y = config.getDouble("spawn.y", 64.0); // Validiere Y-Koordinate
if (y < -64 || y > 320) { double y = config.getDouble("spawn.y", 64.0);
warnings.add("spawn.y (" + y + ") außerhalb des gültigen Bereichs (-64 bis 320)"); if (y < -64 || y > 320) {
} warnings.add("spawn.y (" + y + ") außerhalb des gültigen Bereichs (-64 bis 320)");
} }
}
private void validateLobbySettings() {
ensureDefault("lobby.allow-fly", false); private void validateLobbySettings() {
ensureDefault("lobby.pvp-enabled", false); ensureDefault("lobby.allow-fly", false);
ensureDefault("lobby.build-enabled", false); ensureDefault("lobby.pvp-enabled", false);
ensureDefault("lobby.default-gamemode", "Adventure"); ensureDefault("lobby.build-enabled", false);
ensureDefault("lobby.clear-inventory-on-join", true); ensureDefault("lobby.default-gamemode", "Adventure");
ensureDefault("lobby.clear-inventory-on-join", true);
// Validiere GameMode
String gamemode = config.getString("lobby.default-gamemode", "Adventure"); // Validiere GameMode
if (!isValidGameMode(gamemode)) { String gamemode = config.getString("lobby.default-gamemode", "Adventure");
warnings.add("lobby.default-gamemode '" + gamemode + "' ist ungültig. Nutze: Survival, Creative, Adventure oder Spectator"); if (!isValidGameMode(gamemode)) {
} warnings.add("lobby.default-gamemode '" + gamemode + "' ist ungültig. Nutze: Survival, Creative, Adventure oder Spectator");
} }
}
private void validateTablist() {
ensureDefault("tablist.enabled", true); private void validateTablist() {
ensureDefault("tablist.header", "&6Willkommen auf &eNexusLobby"); ensureDefault("tablist.enabled", true);
ensureDefault("tablist.footer", "&7Viel Spaß!"); ensureDefault("tablist.header", "&6Willkommen auf &eNexusLobby");
ensureDefault("tablist.refresh-interval", 40); ensureDefault("tablist.footer", "&7Viel Spaß!");
ensureDefault("tablist.refresh-interval", 40);
// Validiere Refresh-Interval
int interval = config.getInt("tablist.refresh-interval", 40); // Validiere Refresh-Interval
if (interval < 1) { int interval = config.getInt("tablist.refresh-interval", 40);
warnings.add("tablist.refresh-interval (" + interval + ") ist zu klein. Minimum ist 1 Tick."); if (interval < 1) {
config.set("tablist.refresh-interval", 1); warnings.add("tablist.refresh-interval (" + interval + ") ist zu klein. Minimum ist 1 Tick.");
modified = true; config.set("tablist.refresh-interval", 1);
} else if (interval > 200) { modified = true;
warnings.add("tablist.refresh-interval (" + interval + ") ist sehr hoch. Empfohlen: 20-100 Ticks."); } else if (interval > 200) {
} warnings.add("tablist.refresh-interval (" + interval + ") ist sehr hoch. Empfohlen: 20-100 Ticks.");
} }
}
private void validateBall() {
ensureDefault("ball.respawn_delay", 60); private void validateBall() {
ensureDefault("ball.respawn_delay", 60);
// Validiere Respawn-Delay
long delay = config.getLong("ball.respawn_delay", 60); // Validiere Respawn-Delay
if (delay < 5) { long delay = config.getLong("ball.respawn_delay", 60);
warnings.add("ball.respawn_delay (" + delay + "s) ist zu kurz. Minimum empfohlen: 5 Sekunden."); if (delay < 5) {
} else if (delay > 600) { warnings.add("ball.respawn_delay (" + delay + "s) ist zu kurz. Minimum empfohlen: 5 Sekunden.");
warnings.add("ball.respawn_delay (" + delay + "s) ist sehr lang. Empfohlen: 30-120 Sekunden."); } else if (delay > 600) {
} warnings.add("ball.respawn_delay (" + delay + "s) ist sehr lang. Empfohlen: 30-120 Sekunden.");
}
// Prüfe ob Spawn gesetzt ist
if (!config.contains("ball.spawn")) { // Prüfe ob Spawn gesetzt ist
warnings.add("ball.spawn nicht gesetzt. Nutze /nexuslobby ball setspawn"); if (!config.contains("ball.spawn")) {
} warnings.add("ball.spawn nicht gesetzt. Nutze /nexuslobby ball setspawn");
} }
}
private void validateModules() {
// Worldborder private void validateModules() {
if (config.contains("worldborder.enabled")) { // Worldborder
ensureDefault("worldborder.type", "SQUARE"); if (config.contains("worldborder.enabled")) {
ensureDefault("worldborder.radius", 50.0); ensureDefault("worldborder.type", "SQUARE");
ensureDefault("worldborder.radius", 50.0);
double radius = config.getDouble("worldborder.radius", 50.0);
if (radius < 10) { double radius = config.getDouble("worldborder.radius", 50.0);
warnings.add("worldborder.radius (" + radius + ") ist sehr klein. Minimum empfohlen: 10 Blöcke."); if (radius < 10) {
} else if (radius > 10000) { warnings.add("worldborder.radius (" + radius + ") ist sehr klein. Minimum empfohlen: 10 Blöcke.");
warnings.add("worldborder.radius (" + radius + ") ist extrem groß. Performance-Warnung!"); } else if (radius > 10000) {
} warnings.add("worldborder.radius (" + radius + ") ist extrem groß. Performance-Warnung!");
}
String type = config.getString("worldborder.type", "SQUARE");
if (!type.equalsIgnoreCase("SQUARE") && !type.equalsIgnoreCase("CIRCLE")) { String type = config.getString("worldborder.type", "SQUARE");
warnings.add("worldborder.type '" + type + "' ist ungültig. Nutze: SQUARE oder CIRCLE"); if (!type.equalsIgnoreCase("SQUARE") && !type.equalsIgnoreCase("CIRCLE")) {
} warnings.add("worldborder.type '" + type + "' ist ungültig. Nutze: SQUARE oder CIRCLE");
} }
}
// Items Modul
if (config.contains("items.lobby-tools")) { // Items Modul
// Prüfe ob Slot-Nummern gültig sind (0-8) if (config.contains("items.lobby-tools")) {
for (String toolKey : config.getConfigurationSection("items.lobby-tools").getKeys(false)) { // Prüfe ob Slot-Nummern gültig sind (0-8)
int slot = config.getInt("items.lobby-tools." + toolKey + ".slot", -1); for (String toolKey : config.getConfigurationSection("items.lobby-tools").getKeys(false)) {
if (slot < 0 || slot > 8) { int slot = config.getInt("items.lobby-tools." + toolKey + ".slot", -1);
warnings.add("items.lobby-tools." + toolKey + ".slot (" + slot + ") ist ungültig (0-8)"); if (slot < 0 || slot > 8) {
} warnings.add("items.lobby-tools." + toolKey + ".slot (" + slot + ") ist ungültig (0-8)");
} }
} }
} }
}
private void ensureDefault(String path, Object defaultValue) {
if (!config.contains(path)) { private void ensureDefault(String path, Object defaultValue) {
config.set(path, defaultValue); if (!config.contains(path)) {
modified = true; config.set(path, defaultValue);
} modified = true;
} }
}
private boolean isValidGameMode(String mode) {
return mode.equalsIgnoreCase("Survival") || private boolean isValidGameMode(String mode) {
mode.equalsIgnoreCase("Creative") || return mode.equalsIgnoreCase("Survival") ||
mode.equalsIgnoreCase("Adventure") || mode.equalsIgnoreCase("Creative") ||
mode.equalsIgnoreCase("Spectator"); mode.equalsIgnoreCase("Adventure") ||
} mode.equalsIgnoreCase("Spectator");
} }
}
@@ -1,32 +1,43 @@
package de.nexuslobby.utils; package de.nexuslobby.utils;
import org.bukkit.plugin.java.JavaPlugin; import de.nexuslobby.NexusLobby;
import org.yaml.snakeyaml.Yaml; import org.bukkit.ChatColor;
import org.bukkit.plugin.java.JavaPlugin;
import java.io.InputStream; import org.yaml.snakeyaml.Yaml;
import java.util.Map;
import java.io.InputStream;
public class LangManager { import java.util.Map;
private static Map<String, Map<String, String>> langMap;
private static String currentLang = "de"; public class LangManager {
private static Map<String, Map<String, String>> langMap;
public static void load(JavaPlugin plugin) { private static String currentLang = "de";
Yaml yaml = new Yaml();
try (InputStream in = plugin.getResource("lang.yml")) { public static void load(JavaPlugin plugin) {
langMap = yaml.load(in); Yaml yaml = new Yaml();
} catch (Exception e) { try (InputStream in = plugin.getResource("lang.yml")) {
e.printStackTrace(); langMap = yaml.load(in);
} } catch (Exception e) {
} e.printStackTrace();
}
public static void setLanguage(String lang) { }
currentLang = lang;
} public static void setLanguage(String lang) {
currentLang = lang;
public static String get(String key) { }
if (langMap == null) return key;
Map<String, String> translations = langMap.get(key); public static String get(String key) {
if (translations == null) return key; if (langMap == null) return key;
return translations.getOrDefault(currentLang, key); Map<String, String> translations = langMap.get(key);
} if (translations == null) return key;
} return translations.getOrDefault(currentLang, key)
.replace("§8[§6Nexus§8] ", getPrefix());
}
public static String getPrefix() {
NexusLobby plugin = NexusLobby.getInstance();
String prefix = plugin == null
? "&8[&6Nexus&8] "
: plugin.getConfig().getString("prefix", "&8[&6Nexus&8] ");
return ChatColor.translateAlternateColorCodes('&', prefix);
}
}
@@ -1,36 +1,36 @@
package de.nexuslobby.utils; package de.nexuslobby.utils;
import de.nexuslobby.NexusLobby; import de.nexuslobby.NexusLobby;
import org.bukkit.Bukkit; import org.bukkit.Bukkit;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.net.URL; import java.net.URL;
import java.util.Scanner; import java.util.Scanner;
import java.util.function.Consumer; import java.util.function.Consumer;
public class UpdateChecker { public class UpdateChecker {
private final NexusLobby plugin; private final NexusLobby plugin;
private static final int RESOURCE_ID = 132388; private static final int RESOURCE_ID = 132388;
public UpdateChecker(NexusLobby plugin) { public UpdateChecker(NexusLobby plugin) {
this.plugin = plugin; this.plugin = plugin;
} }
public void getVersion(final Consumer<String> consumer) { public void getVersion(final Consumer<String> consumer) {
Bukkit.getScheduler().runTaskAsynchronously(this.plugin, () -> { Bukkit.getScheduler().runTaskAsynchronously(this.plugin, () -> {
try (InputStream is = new URL( try (InputStream is = new URL(
"https://api.spigotmc.org/legacy/update.php?resource=" + RESOURCE_ID + "/~").openStream(); "https://api.spigotmc.org/legacy/update.php?resource=" + RESOURCE_ID + "/~").openStream();
Scanner scanner = new Scanner(is)) { Scanner scanner = new Scanner(is)) {
if (scanner.hasNext()) { if (scanner.hasNext()) {
consumer.accept(scanner.next()); consumer.accept(scanner.next());
} }
} catch (IOException e) { } catch (IOException e) {
plugin.getLogger().warning("Update-Check fehlgeschlagen: " + e.getMessage()); plugin.getLogger().warning("Update-Check fehlgeschlagen: " + e.getMessage());
} }
}); });
} }
} }
+3
View File
@@ -20,6 +20,9 @@
# Verfügbare Optionen: de (Deutsch), en (Englisch), fr (Französisch) # Verfügbare Optionen: de (Deutsch), en (Englisch), fr (Französisch)
language: de language: de
# Prefix vor Plugin-Nachrichten im Chat (&-Farbcodes sind erlaubt)
prefix: "&8[&6Nexus&8] "
# ══════════════════════════════════════════════════════════════════════════════ # ══════════════════════════════════════════════════════════════════════════════
# SPAWN EINSTELLUNGEN # SPAWN EINSTELLUNGEN
# ══════════════════════════════════════════════════════════════════════════════ # ══════════════════════════════════════════════════════════════════════════════
+203 -203
View File
@@ -1,203 +1,203 @@
# _ __ __ __ __ # _ __ __ __ __
# / | / /__ _ ____ _______/ / ____ / /_ / /_ __ __ # / | / /__ _ ____ _______/ / ____ / /_ / /_ __ __
# / |/ / _ \| |/_/ / / / ___/ / / __ \/ __ \/ __ \/ / / / # / |/ / _ \| |/_/ / / / ___/ / / __ \/ __ \/ __ \/ / / /
# / /| / __/> </ /_/ (__ ) /___/ /_/ / /_/ / /_/ / /_/ / # / /| / __/> </ /_/ (__ ) /___/ /_/ / /_/ / /_/ / /_/ /
# /_/ |_/\___/_/|_|\__,_/____/_____/\____/_.___/_.___/\__, / # /_/ |_/\___/_/|_|\__,_/____/_____/\____/_.___/_.___/\__, /
# /____/ # /____/
# #
# ===================================================== # =====================================================
# DEFAULT Language # DEFAULT Language
# ===================================================== # =====================================================
soccer_module_not_loaded: soccer_module_not_loaded:
de: "§cDas Fußball-Modul ist nicht geladen." de: "§cDas Fußball-Modul ist nicht geladen."
en: "§cThe soccer module is not loaded." en: "§cThe soccer module is not loaded."
parkour_usage: parkour_usage:
de: "§8[§6Nexus§8] §7Nutze: §e/nexus parkour <setstart|setfinish|setcheckpoint|reset|clear|removeall>" de: "§8[§6Nexus§8] §7Nutze: §e/nexus parkour <setstart|setfinish|setcheckpoint|reset|clear|removeall>"
en: "§8[§6Nexus§8] §7Usage: §e/nexus parkour <setstart|setfinish|setcheckpoint|reset|clear|removeall>" en: "§8[§6Nexus§8] §7Usage: §e/nexus parkour <setstart|setfinish|setcheckpoint|reset|clear|removeall>"
parkour_run_aborted: parkour_run_aborted:
de: "§8[§6Nexus§8] §7Dein aktueller Lauf wurde abgebrochen." de: "§8[§6Nexus§8] §7Dein aktueller Lauf wurde abgebrochen."
en: "§8[§6Nexus§8] §7Your current run was aborted." en: "§8[§6Nexus§8] §7Your current run was aborted."
parkour_besttimes_cleared: parkour_besttimes_cleared:
de: "§8[§6Nexus§8] §aAlle Parkour-Bestzeiten wurden gelöscht!" de: "§8[§6Nexus§8] §aAlle Parkour-Bestzeiten wurden gelöscht!"
en: "§8[§6Nexus§8] §aAll parkour best times have been cleared!" en: "§8[§6Nexus§8] §aAll parkour best times have been cleared!"
parkour_track_removed: parkour_track_removed:
de: "§8[§6Nexus§8] §cDie gesamte Strecke (Checkpoints & Ziel) wurde gelöscht!" de: "§8[§6Nexus§8] §cDie gesamte Strecke (Checkpoints & Ziel) wurde gelöscht!"
en: "§8[§6Nexus§8] §cThe entire track (checkpoints & finish) has been removed!" en: "§8[§6Nexus§8] §cThe entire track (checkpoints & finish) has been removed!"
unknown_subcommand: unknown_subcommand:
de: "§cUnbekannter Unterbefehl." de: "§cUnbekannter Unterbefehl."
en: "§cUnknown subcommand." en: "§cUnknown subcommand."
parkour_npc_marked: parkour_npc_marked:
de: "§8[§6Nexus§8] §aArmorStand als Parkour-NPC markiert!" de: "§8[§6Nexus§8] §aArmorStand als Parkour-NPC markiert!"
en: "§8[§6Nexus§8] §aArmorStand marked as parkour NPC!" en: "§8[§6Nexus§8] §aArmorStand marked as parkour NPC!"
parkour_start_set: parkour_start_set:
de: "§8[§6Nexus§8] §aParkour-Startpunkt an deiner Position gesetzt!" de: "§8[§6Nexus§8] §aParkour-Startpunkt an deiner Position gesetzt!"
en: "§8[§6Nexus§8] §aParkour start set at your position!" en: "§8[§6Nexus§8] §aParkour start set at your position!"
scoreboard_usage: scoreboard_usage:
de: "§cBenutzung: /nexus sb <on|off|admin|spieler>" de: "§cBenutzung: /nexus sb <on|off|admin|spieler>"
en: "§cUsage: /nexus sb <on|off|admin|player>" en: "§cUsage: /nexus sb <on|off|admin|player>"
scoreboard_module_disabled: scoreboard_module_disabled:
de: "§cScoreboard-Modul ist deaktiviert." de: "§cScoreboard-Modul ist deaktiviert."
en: "§cScoreboard module is disabled." en: "§cScoreboard module is disabled."
info_header: info_header:
de: "§8§m--------------------------------------" de: "§8§m--------------------------------------"
en: "§8§m--------------------------------------" en: "§8§m--------------------------------------"
info_title: info_title:
de: "§6§lNexusLobby §7- Informationen" de: "§6§lNexusLobby §7- Informationen"
en: "§6§lNexusLobby §7- Information" en: "§6§lNexusLobby §7- Information"
info_spawn: info_spawn:
de: "§f/spawn §7- Zum Spawn" de: "§f/spawn §7- Zum Spawn"
en: "§f/spawn §7- To spawn" en: "§f/spawn §7- To spawn"
info_parkour: info_parkour:
de: "§f/setstart §8| §f/setcheckpoint §8| §f/setfinish" de: "§f/setstart §8| §f/setcheckpoint §8| §f/setfinish"
en: "§f/setstart §8| §f/setcheckpoint §8| §f/setfinish" en: "§f/setstart §8| §f/setcheckpoint §8| §f/setfinish"
info_removeall: info_removeall:
de: "§f/nexus parkour removeall §7- Strecke löschen" de: "§f/nexus parkour removeall §7- Strecke löschen"
en: "§f/nexus parkour removeall §7- Remove track" en: "§f/nexus parkour removeall §7- Remove track"
info_ball: info_ball:
de: "§f/nexus ball setspawn §7- Fußball Spawn setzen" de: "§f/nexus ball setspawn §7- Fußball Spawn setzen"
en: "§f/nexus ball setspawn §7- Set soccer spawn" en: "§f/nexus ball setspawn §7- Set soccer spawn"
info_setspawn: info_setspawn:
de: "§f/nexus setspawn §7- Spawn setzen" de: "§f/nexus setspawn §7- Spawn setzen"
en: "§f/nexus setspawn §7- Set spawn" en: "§f/nexus setspawn §7- Set spawn"
info_scoreboard: info_scoreboard:
de: "§f/nexus sb <on|off> §7- Scoreboard" de: "§f/nexus sb <on|off> §7- Scoreboard"
en: "§f/nexus sb <on|off> §7- Scoreboard" en: "§f/nexus sb <on|off> §7- Scoreboard"
info_reload: info_reload:
de: "§f/nexus reload §7- Config laden" de: "§f/nexus reload §7- Config laden"
en: "§f/nexus reload §7- Reload config" en: "§f/nexus reload §7- Reload config"
info_footer: info_footer:
de: "§8§m--------------------------------------" de: "§8§m--------------------------------------"
en: "§8§m--------------------------------------" en: "§8§m--------------------------------------"
parkour_trainer_greeting: parkour_trainer_greeting:
de: "§6§lTrainer §8» §aViel Erfolg beim Parkour! Gib dein Bestes!" de: "§6§lTrainer §8» §aViel Erfolg beim Parkour! Gib dein Bestes!"
en: "§6§lTrainer §8» §aGood luck with the parkour! Give it your best!" en: "§6§lTrainer §8» §aGood luck with the parkour! Give it your best!"
update_available: update_available:
de: "§8[§6Nexus§8] §aEin neues §6Update §afür §eNexusLobby §aist verfügbar!" de: "§8[§6Nexus§8] §aEin neues §6Update §afür §eNexusLobby §aist verfügbar!"
en: "§8[§6Nexus§8] §aA new §6update §afor §eNexusLobby §ais available!" en: "§8[§6Nexus§8] §aA new §6update §afor §eNexusLobby §ais available!"
update_version: update_version:
de: "§8» §7Version: §c{old} §8-> §a{new}" de: "§8» §7Version: §c{old} §8-> §a{new}"
en: "§8» §7Version: §c{old} §8-> §a{new}" en: "§8» §7Version: §c{old} §8-> §a{new}"
update_download_link: update_download_link:
de: "§8» §6Klicke §e§l[HIER] §6zum Herunterladen." de: "§8» §6Klicke §e§l[HIER] §6zum Herunterladen."
en: "§8» §6Click §e§l[HERE] §6to download." en: "§8» §6Click §e§l[HERE] §6to download."
update_download_hover: update_download_hover:
de: "§7Öffnet die Release-Seite" de: "§7Öffnet die Release-Seite"
en: "§7Opens the release page" en: "§7Opens the release page"
hider_all: hider_all:
de: "§aAlle Spieler" de: "§aAlle Spieler"
en: "§aAll players" en: "§aAll players"
hider_none: hider_none:
de: "§cKeine Spieler" de: "§cKeine Spieler"
en: "§cNo players" en: "§cNo players"
void_protection_message: void_protection_message:
de: "§cDu wurdest vor dem Void gerettet!" de: "§cDu wurdest vor dem Void gerettet!"
en: "§cYou were saved from the void!" en: "§cYou were saved from the void!"
proxy_not_registered: proxy_not_registered:
de: "§cProxy-Verbindung nicht möglich (BungeeCord Kanal nicht registriert)." de: "§cProxy-Verbindung nicht möglich (BungeeCord Kanal nicht registriert)."
en: "§cProxy connection not possible (BungeeCord channel not registered)." en: "§cProxy connection not possible (BungeeCord channel not registered)."
connecting_to_server: connecting_to_server:
de: "§eVerbinde zu: §f{server}" de: "§eVerbinde zu: §f{server}"
en: "§eConnecting to: §f{server}" en: "§eConnecting to: §f{server}"
server_connect_error: server_connect_error:
de: "§cFehler beim Verbinden zum Server." de: "§cFehler beim Verbinden zum Server."
en: "§cError connecting to server." en: "§cError connecting to server."
proxy_connect_error: proxy_connect_error:
de: "§cProxy-Verbindung nicht möglich." de: "§cProxy-Verbindung nicht möglich."
en: "§cProxy connection not possible." en: "§cProxy connection not possible."
armorstand_lookat_required: armorstand_lookat_required:
de: "§cDu musst einen ArmorStand direkt anschauen (Fadenkreuz)!" de: "§cDu musst einen ArmorStand direkt anschauen (Fadenkreuz)!"
en: "§cYou must look directly at an ArmorStand (crosshair)!" en: "§cYou must look directly at an ArmorStand (crosshair)!"
conv_link_usage: conv_link_usage:
de: "§cNutze: /nexuscmd conv link <Dialog-ID>" de: "§cNutze: /nexuscmd conv link <Dialog-ID>"
en: "§cUsage: /nexuscmd conv link <Dialog-ID>" en: "§cUsage: /nexuscmd conv link <Dialog-ID>"
conv_mark_npcs: conv_mark_npcs:
de: "§cBitte markiere mindestens die ersten beiden NPCs (select1 & select2)!" de: "§cBitte markiere mindestens die ersten beiden NPCs (select1 & select2)!"
en: "§cPlease mark at least the first two NPCs (select1 & select2)!" en: "§cPlease mark at least the first two NPCs (select1 & select2)!"
conv_link_created: conv_link_created:
de: "§a§lDauerhafte Verknüpfung erstellt!" de: "§a§lDauerhafte Verknüpfung erstellt!"
en: "§a§lPermanent link created!" en: "§a§lPermanent link created!"
conv_link_npcs: conv_link_npcs:
de: "§7Beteiligte NPCs: §e{count}" de: "§7Beteiligte NPCs: §e{count}"
en: "§7Linked NPCs: §e{count}" en: "§7Linked NPCs: §e{count}"
conv_speaker_not_found: conv_speaker_not_found:
de: "§cFehler: Sprecher 1 nicht gefunden." de: "§cFehler: Sprecher 1 nicht gefunden."
en: "§cError: Speaker 1 not found." en: "§cError: Speaker 1 not found."
conv_unlink_lookat: conv_unlink_lookat:
de: "§cSchau den NPC an, dessen Verknüpfung du lösen willst!" de: "§cSchau den NPC an, dessen Verknüpfung du lösen willst!"
en: "§cLook at the NPC you want to unlink!" en: "§cLook at the NPC you want to unlink!"
conv_unlinked: conv_unlinked:
de: "§eNPC-Verknüpfung wurde aufgehoben." de: "§eNPC-Verknüpfung wurde aufgehoben."
en: "§eNPC link has been removed." en: "§eNPC link has been removed."
conv_start_usage: conv_start_usage:
de: "§cNutze: /nexuscmd conv start <ID>" de: "§cNutze: /nexuscmd conv start <ID>"
en: "§cUsage: /nexuscmd conv start <ID>" en: "§cUsage: /nexuscmd conv start <ID>"
conv_mark_two_npcs: conv_mark_two_npcs:
de: "§cBitte markiere mindestens zwei NPCs!" de: "§cBitte markiere mindestens zwei NPCs!"
en: "§cPlease mark at least two NPCs!" en: "§cPlease mark at least two NPCs!"
npc_bubble_sent: npc_bubble_sent:
de: "§aNPC-Sprechblase gesendet." de: "§aNPC-Sprechblase gesendet."
en: "§aNPC speech bubble sent." en: "§aNPC speech bubble sent."
lookat_off: lookat_off:
de: "§cBlickkontakt aus." de: "§cBlickkontakt aus."
en: "§cLook-at disabled." en: "§cLook-at disabled."
lookat_on: lookat_on:
de: "§aBlickkontakt an." de: "§aBlickkontakt an."
en: "§aLook-at enabled." en: "§aLook-at enabled."
name_removed: name_removed:
de: "§eName entfernt." de: "§eName entfernt."
en: "§eName removed." en: "§eName removed."
name_set: name_set:
de: "§7Name gesetzt: {name}" de: "§7Name gesetzt: {name}"
en: "§7Name set: {name}" en: "§7Name set: {name}"
status_backup_saved: status_backup_saved:
de: "§8(Status-Backup wurde gespeichert)" de: "§8(Status-Backup wurde gespeichert)"
en: "§8(Status backup saved)" en: "§8(Status backup saved)"
command_bound: command_bound:
de: "§aBefehl gebunden." de: "§aBefehl gebunden."
en: "§aCommand bound." en: "§aCommand bound."
no_target: no_target:
de: "§cKein Ziel!" de: "§cKein Ziel!"
en: "§cNo target!" en: "§cNo target!"
commands_and_tags: commands_and_tags:
de: "§6§lBefehle & Tags:" de: "§6§lBefehle & Tags:"
en: "§6§lCommands & Tags:" en: "§6§lCommands & Tags:"
commands_removed: commands_removed:
de: "§eAlle Befehle gelöscht." de: "§eAlle Befehle gelöscht."
en: "§eAll commands removed." en: "§eAll commands removed."
welcome: welcome:
de: "Willkommen auf dem Server!" de: "Willkommen auf dem Server!"
en: "Welcome to the server!" en: "Welcome to the server!"
no_permission: no_permission:
de: "§cKeine Berechtigung." de: "§cKeine Berechtigung."
en: "§cNo permission." en: "§cNo permission."
only_player: only_player:
de: "§cDieser Befehl ist nur für Spieler!" de: "§cDieser Befehl ist nur für Spieler!"
en: "§cThis command is for players only!" en: "§cThis command is for players only!"
parkour_checkpoint_set: parkour_checkpoint_set:
de: "§8[§6Nexus§8] §aParkour-Checkpoint gesetzt!" de: "§8[§6Nexus§8] §aParkour-Checkpoint gesetzt!"
en: "§8[§6Nexus§8] §aParkour checkpoint set!" en: "§8[§6Nexus§8] §aParkour checkpoint set!"
parkour_finish_set: parkour_finish_set:
de: "§8[§6Nexus§8] §aParkour-Zielpunkt gesetzt!" de: "§8[§6Nexus§8] §aParkour-Zielpunkt gesetzt!"
en: "§8[§6Nexus§8] §aParkour finish set!" en: "§8[§6Nexus§8] §aParkour finish set!"
teleport_spawn: teleport_spawn:
de: "§8[§6Nexus§8] §aDu wurdest zum Spawn teleportiert." de: "§8[§6Nexus§8] §aDu wurdest zum Spawn teleportiert."
en: "§8[§6Nexus§8] §aYou have been teleported to spawn." en: "§8[§6Nexus§8] §aYou have been teleported to spawn."
spawn_world_missing: spawn_world_missing:
de: "§cFehler: Die Spawn-Welt existiert nicht." de: "§cFehler: Die Spawn-Welt existiert nicht."
en: "§cError: The spawn world does not exist." en: "§cError: The spawn world does not exist."
spawn_not_set: spawn_not_set:
de: "§cEs wurde noch kein Spawn gesetzt." de: "§cEs wurde noch kein Spawn gesetzt."
en: "§cNo spawn has been set yet." en: "§cNo spawn has been set yet."
plugin_reloaded: plugin_reloaded:
de: "§8[§6Nexus§8] §aPlugin erfolgreich neu geladen!" de: "§8[§6Nexus§8] §aPlugin erfolgreich neu geladen!"
en: "§8[§6Nexus§8] §aPlugin successfully reloaded!" en: "§8[§6Nexus§8] §aPlugin successfully reloaded!"
spawn_set: spawn_set:
de: "§8[§6Nexus§8] §aLobby-Spawn erfolgreich gesetzt!" de: "§8[§6Nexus§8] §aLobby-Spawn erfolgreich gesetzt!"
en: "§8[§6Nexus§8] §aLobby spawn set successfully!" en: "§8[§6Nexus§8] §aLobby spawn set successfully!"
silentjoin_on: silentjoin_on:
de: "§8[§6Nexus§8] §7Silent Join: §aAktiviert" de: "§8[§6Nexus§8] §7Silent Join: §aAktiviert"
en: "§8[§6Nexus§8] §7Silent Join: §aEnabled" en: "§8[§6Nexus§8] §7Silent Join: §aEnabled"
silentjoin_off: silentjoin_off:
de: "§8[§6Nexus§8] §7Silent Join: §cDeaktiviert" de: "§8[§6Nexus§8] §7Silent Join: §cDeaktiviert"
en: "§8[§6Nexus§8] §7Silent Join: §cDisabled" en: "§8[§6Nexus§8] §7Silent Join: §cDisabled"
+1 -1
View File
@@ -1,6 +1,6 @@
name: NexusLobby name: NexusLobby
main: de.nexuslobby.NexusLobby main: de.nexuslobby.NexusLobby
version: "1.9" version: "2.0"
api-version: "1.21" api-version: "1.21"
author: M_Viper author: M_Viper
description: Modular Lobby Plugin with an invisible Particle-Parkour system. description: Modular Lobby Plugin with an invisible Particle-Parkour system.