From b3555d92d89d6c0b0380851e30de86eab9b4d89e Mon Sep 17 00:00:00 2001 From: Allink <44676012+allinkdev@users.noreply.github.com> Date: Tue, 27 Dec 2022 17:50:26 +0000 Subject: [PATCH] Display prefixes and display names in tab (#332) --- src/main/java/pw/kaboom/extras/Main.java | 7 +- .../kaboom/extras/commands/CommandPrefix.java | 26 +-- .../extras/modules/player/PlayerChat.java | 30 ++- .../extras/modules/player/PlayerPrefix.java | 172 ++++++++++++++++++ 4 files changed, 196 insertions(+), 39 deletions(-) create mode 100644 src/main/java/pw/kaboom/extras/modules/player/PlayerPrefix.java diff --git a/src/main/java/pw/kaboom/extras/Main.java b/src/main/java/pw/kaboom/extras/Main.java index ee0140e..9535658 100644 --- a/src/main/java/pw/kaboom/extras/Main.java +++ b/src/main/java/pw/kaboom/extras/Main.java @@ -1,5 +1,7 @@ package pw.kaboom.extras; +import java.io.File; +import java.util.Collections; import org.bukkit.WorldCreator; import org.bukkit.WorldType; import org.bukkit.block.BlockFace; @@ -35,6 +37,7 @@ import pw.kaboom.extras.modules.player.PlayerCommand; import pw.kaboom.extras.modules.player.PlayerConnection; import pw.kaboom.extras.modules.player.PlayerDamage; import pw.kaboom.extras.modules.player.PlayerInteract; +import pw.kaboom.extras.modules.player.PlayerPrefix; import pw.kaboom.extras.modules.player.PlayerRecipe; import pw.kaboom.extras.modules.player.PlayerTeleport; import pw.kaboom.extras.modules.server.ServerCommand; @@ -42,9 +45,6 @@ import pw.kaboom.extras.modules.server.ServerGameRule; import pw.kaboom.extras.modules.server.ServerTabComplete; import pw.kaboom.extras.modules.server.ServerTick; -import java.io.File; -import java.util.Collections; - public final class Main extends JavaPlugin { private File prefixConfigFile; private FileConfiguration prefixConfig; @@ -110,6 +110,7 @@ public final class Main extends JavaPlugin { this.getServer().getPluginManager().registerEvents(new PlayerInteract(), this); this.getServer().getPluginManager().registerEvents(new PlayerRecipe(), this); this.getServer().getPluginManager().registerEvents(new PlayerTeleport(), this); + this.getServer().getPluginManager().registerEvents(new PlayerPrefix(), this); /* Server-related modules */ this.getServer().getPluginManager().registerEvents(new ServerCommand(), this); diff --git a/src/main/java/pw/kaboom/extras/commands/CommandPrefix.java b/src/main/java/pw/kaboom/extras/commands/CommandPrefix.java index c093d3f..e62c907 100644 --- a/src/main/java/pw/kaboom/extras/commands/CommandPrefix.java +++ b/src/main/java/pw/kaboom/extras/commands/CommandPrefix.java @@ -1,25 +1,17 @@ package pw.kaboom.extras.commands; +import javax.annotation.Nonnull; import net.kyori.adventure.text.Component; import net.kyori.adventure.text.format.NamedTextColor; -import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer; import org.bukkit.command.Command; import org.bukkit.command.CommandExecutor; import org.bukkit.command.CommandSender; import org.bukkit.command.ConsoleCommandSender; -import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.entity.Player; -import org.bukkit.plugin.java.JavaPlugin; -import pw.kaboom.extras.Main; - -import javax.annotation.Nonnull; -import java.io.File; +import pw.kaboom.extras.modules.player.PlayerPrefix; public final class CommandPrefix implements CommandExecutor { - private static final File PREFIX_CONFIG_FILE = JavaPlugin - .getPlugin(Main.class).getPrefixConfigFile(); - private static final FileConfiguration PREFIX_CONFIG = JavaPlugin - .getPlugin(Main.class).getPrefixConfig(); + public boolean onCommand(final @Nonnull CommandSender sender, final @Nonnull Command cmd, @@ -42,17 +34,15 @@ public final class CommandPrefix implements CommandExecutor { try { if ("off".equalsIgnoreCase(args[0])) { - PREFIX_CONFIG.set(player.getUniqueId().toString(), null); - PREFIX_CONFIG.save(PREFIX_CONFIG_FILE); + PlayerPrefix.removePrefix(player); player.sendMessage(Component .text("You no longer have a tag")); } else { - PREFIX_CONFIG.set(player.getUniqueId().toString(), String.join(" ", args)); - PREFIX_CONFIG.save(PREFIX_CONFIG_FILE); + final Component prefix = PlayerPrefix.setPrefix(player, String.join(" ", args)); + player.sendMessage(Component.text("You now have the tag: ") - .append(LegacyComponentSerializer.legacyAmpersand() - .deserialize(String.join(" ", args)))); - } + .append(prefix)); + } } catch (Exception exception) { player.sendMessage(Component .text("Something went wrong while saving the prefix. " + diff --git a/src/main/java/pw/kaboom/extras/modules/player/PlayerChat.java b/src/main/java/pw/kaboom/extras/modules/player/PlayerChat.java index f21fb60..b898478 100644 --- a/src/main/java/pw/kaboom/extras/modules/player/PlayerChat.java +++ b/src/main/java/pw/kaboom/extras/modules/player/PlayerChat.java @@ -2,30 +2,19 @@ package pw.kaboom.extras.modules.player; import io.papermc.paper.chat.ChatRenderer; import io.papermc.paper.event.player.AsyncChatEvent; +import java.io.IOException; +import java.util.UUID; import javax.annotation.Nonnull; import net.kyori.adventure.audience.Audience; import net.kyori.adventure.text.Component; import net.kyori.adventure.text.TextComponent; import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer; -import org.bukkit.configuration.file.FileConfiguration; import org.bukkit.entity.Player; import org.bukkit.event.EventHandler; import org.bukkit.event.EventPriority; import org.bukkit.event.Listener; -import org.bukkit.plugin.java.JavaPlugin; -import pw.kaboom.extras.Main; - -import java.util.UUID; public final class PlayerChat implements Listener { - private static final FileConfiguration CONFIG = JavaPlugin.getPlugin(Main.class).getConfig(); - private static final FileConfiguration PREFIX_CONFIG = JavaPlugin - .getPlugin(Main.class).getPrefixConfig(); - - private static final Component OP_TAG = LegacyComponentSerializer - .legacySection().deserialize(CONFIG.getString("opTag", "")); - private static final Component DEOP_TAG = LegacyComponentSerializer - .legacySection().deserialize(CONFIG.getString("deOpTag", "")); private static final PlayerChatRenderer CHAT_RENDERER = new PlayerChatRenderer(); @EventHandler(priority = EventPriority.HIGHEST) @@ -57,12 +46,17 @@ public final class PlayerChat implements Listener { @Nonnull Component component, @Nonnull Audience audience) { Component newComponent = Component.empty(); - final String legacyPrefix = PREFIX_CONFIG.getString(player.getUniqueId().toString()); - final Component prefix = legacyPrefix == null ? - ((player.isOp()) ? OP_TAG : DEOP_TAG) - : LegacyComponentSerializer.legacyAmpersand().deserialize(legacyPrefix) - .append(Component.space()); + final Component prefix; + Component prefix1; + try { + prefix1 = PlayerPrefix.getPrefix(player); + } catch (IOException e) { + e.printStackTrace(); + prefix1 = PlayerPrefix.getDefaultPrefix(player); + } + + prefix = prefix1; final String message = ((TextComponent) component).content(); newComponent = newComponent diff --git a/src/main/java/pw/kaboom/extras/modules/player/PlayerPrefix.java b/src/main/java/pw/kaboom/extras/modules/player/PlayerPrefix.java new file mode 100644 index 0000000..b8ef1a1 --- /dev/null +++ b/src/main/java/pw/kaboom/extras/modules/player/PlayerPrefix.java @@ -0,0 +1,172 @@ +package pw.kaboom.extras.modules.player; + +import java.io.File; +import java.io.IOException; +import java.util.Collection; +import java.util.HashMap; +import java.util.Map; +import java.util.UUID; +import net.kyori.adventure.text.Component; +import net.kyori.adventure.text.serializer.legacy.LegacyComponentSerializer; +import org.bukkit.Bukkit; +import org.bukkit.Server; +import org.bukkit.configuration.file.FileConfiguration; +import org.bukkit.entity.Player; +import org.bukkit.event.EventHandler; +import org.bukkit.event.EventPriority; +import org.bukkit.event.Listener; +import org.bukkit.event.player.PlayerLoginEvent; +import org.bukkit.event.player.PlayerQuitEvent; +import org.bukkit.plugin.java.JavaPlugin; +import org.bukkit.scheduler.BukkitScheduler; +import pw.kaboom.extras.Main; + +public class PlayerPrefix implements Listener { + private static final Main plugin = JavaPlugin.getPlugin(Main.class); + private static final File PREFIX_CONFIG_FILE = plugin.getPrefixConfigFile(); + private static final FileConfiguration PREFIX_CONFIG = plugin.getPrefixConfig(); + private static final FileConfiguration PLUGIN_CONFIGURATION = plugin.getConfig(); + private static final Component opTag; + private static final Component deOpTag; + private static final Map opMap = new HashMap<>(); + private static final Map displayNameMap = new HashMap<>(); + + static { + final String legacyOpTag = PLUGIN_CONFIGURATION.getString("opTag"); + final String legacyDeOpTag = PLUGIN_CONFIGURATION.getString("deOpTag"); + + if (legacyOpTag == null || legacyDeOpTag == null) { + throw new RuntimeException("Invalid plugin configuration!"); + } + + opTag = LegacyComponentSerializer.legacySection().deserialize(legacyOpTag); + deOpTag = LegacyComponentSerializer.legacySection().deserialize(legacyDeOpTag); + + final BukkitScheduler scheduler = Bukkit.getScheduler(); + + scheduler.runTaskTimerAsynchronously(plugin, PlayerPrefix::checkOpStatus, + 0L, 1L); + scheduler.runTaskTimerAsynchronously(plugin, PlayerPrefix::checkDisplayNames, + 0L, 1L); + } + + public static void removePrefix(Player player) throws IOException { + final UUID playerUUID = player.getUniqueId(); + final String stringifiedUUID = playerUUID.toString(); + + PREFIX_CONFIG.set(stringifiedUUID, null); + PREFIX_CONFIG.save(PREFIX_CONFIG_FILE); + + onUpdate(player); + } + + public static Component setPrefix(Player player, String legacyPrefix) throws IOException { + final Component prefix = LegacyComponentSerializer.legacySection() + .deserialize(legacyPrefix); + final UUID playerUUID = player.getUniqueId(); + final String stringifiedUUID = playerUUID.toString(); + + PREFIX_CONFIG.set(stringifiedUUID, legacyPrefix); + PREFIX_CONFIG.save(PREFIX_CONFIG_FILE); + + onUpdate(player); + return prefix; + } + + public static Component getPrefix(Player player) throws IOException { + final UUID playerUUID = player.getUniqueId(); + final String stringifiedUUID = playerUUID.toString(); + final String legacyPrefix = PREFIX_CONFIG.getString(stringifiedUUID); + + if (legacyPrefix == null) { + return player.isOp() ? opTag : deOpTag; + } + + return LegacyComponentSerializer.legacyAmpersand() + .deserialize(legacyPrefix) + .append(Component.space()); + } + + public static Component getDefaultPrefix(Player player) { + return player.isOp() ? opTag : deOpTag; + } + + private static void onUpdate(Player player) throws IOException { + final Component prefix = getPrefix(player); + final Component displayName = player.displayName(); + + player.playerListName(prefix.append(displayName)); + } + + @EventHandler(priority = EventPriority.MONITOR) + public void onPlayerLoginEvent(PlayerLoginEvent event) throws IOException { + final Player player = event.getPlayer(); + final boolean isOp = player.isOp(); + + opMap.put(player, isOp); + displayNameMap.put(player, player.displayName()); + onUpdate(player); + } + + @EventHandler(priority = EventPriority.MONITOR) + public void onPlayerQuitEvent(PlayerQuitEvent event) { + final Player player = event.getPlayer(); + + opMap.remove(player); + displayNameMap.remove(player); + } + + private static void checkOpStatus() { + final Server server = Bukkit.getServer(); + final Collection players = server.getOnlinePlayers(); + + for (Player player : players) { + final boolean isOp = player.isOp(); + + if (!opMap.containsKey(player)) { + return; + } + + final boolean storedOp = opMap.get(player); + + if (isOp == storedOp) { + continue; + } + + opMap.put(player, isOp); + + try { + onUpdate(player); + } catch (Exception e) { + throw new RuntimeException(e); + } + } + } + + private static void checkDisplayNames() { + final Server server = Bukkit.getServer(); + final Collection players = server.getOnlinePlayers(); + + for (Player player : players) { + final Component displayName = player.displayName(); + + if (!displayNameMap.containsKey(player)) { + return; + } + + final Component storedDisplayName = displayNameMap.get(player); + + if (displayName.equals(storedDisplayName)) { + continue; + } + + displayNameMap.put(player, displayName); + + try { + onUpdate(player); + } catch (Exception e) { + throw new RuntimeException(e); + } + } + } +}