package com.redstoner.modules.saylol; import com.nemez.cmdmgr.Command; import com.redstoner.annotations.AutoRegisterListener; import com.redstoner.annotations.Commands; import com.redstoner.annotations.Version; import com.redstoner.coremods.moduleLoader.ModuleLoader; import com.redstoner.misc.CommandHolderType; import com.redstoner.misc.JsonManager; import com.redstoner.misc.Main; import com.redstoner.misc.Utils; import com.redstoner.modules.Module; import com.redstoner.modules.ignore.Ignore; import net.nemez.chatapi.ChatAPI; import net.nemez.chatapi.click.ClickCallback; import net.nemez.chatapi.click.Message; import org.bukkit.Bukkit; import org.bukkit.command.CommandSender; import org.bukkit.entity.Player; import org.bukkit.event.EventHandler; import org.bukkit.event.player.PlayerQuitEvent; import org.json.simple.JSONArray; import java.io.File; import java.util.*; @AutoRegisterListener @Commands (CommandHolderType.File) @Version (major = 5, minor = 2, revision = 0, compatible = 4) public class Saylol implements Module { private File lolLocation = new File(Main.plugin.getDataFolder(), "lol.json"); private JSONArray lols, handlers; private Map> searchCache = new HashMap<>(); private final String LOL_PREFIX = "§8[§blol§8] "; private final int PAGE_SIZE = 10; private long lastLol = 0; @SuppressWarnings ("unchecked") @Override public boolean onEnable() { lols = JsonManager.getArray(lolLocation); if (lols == null) lols = new JSONArray(); handlers = new JSONArray(); for (int i = 0; i < lols.size(); i++) { handlers.add(new ClickCallback(true, true, "") { @Override public void run(CommandSender sender) { if (handlers.contains(this)) clickAction((Player) sender, handlers.indexOf(this)); else getLogger().message(sender, true, "That lol no longer exists!"); } }); } return true; } @Override public void onDisable() { saveLolsSync(); } @SuppressWarnings ("unchecked") @Command (hook = "addlol") public boolean addLol(CommandSender sender, String text) { if (lols.contains(text)) { getLogger().message(sender, true, "This lol already exists!"); } else { lols.add("&e" + text); handlers.add(new ClickCallback(true, true, "") { @Override public void run(CommandSender sender) { if (handlers.contains(this)) clickAction((Player) sender, handlers.indexOf(this)); else getLogger().message(sender, true, "That lol no longer exists!"); } }); saveLols(); searchCache.clear(); getLogger().message(sender, "Successfully added a new lol!"); } return true; } @Command (hook = "dellol") public boolean delLol(CommandSender sender, int id) { if (warnNoLols(sender)) return true; if (warnLolOutOfBounds(sender, id)) return true; handlers.remove(id); saveLols(); searchCache.clear(); getLogger().message(sender, "Successfully deleted the lol: " + lols.remove(id)); return true; } @SuppressWarnings ("unchecked") @Command (hook = "setlol") public boolean setLol(CommandSender sender, int id, String text) { if (warnNoLols(sender)) return true; if (warnLolOutOfBounds(sender, id)) return true; lols.set(id, text); saveLols(); searchCache.clear(); getLogger().message(sender, "Successfully changed the lol: &e" + lols.get(id) + " &7to: &e" + text); return true; } @Command (hook = "lolid") public boolean lolId(CommandSender sender, int id) { if (warnNoLols(sender)) return true; if (warnLolOutOfBounds(sender, id)) return true; long time = System.currentTimeMillis(); if (warnTime(sender, time)) return true; String name = getSenderName(sender); Utils.broadcast( LOL_PREFIX, ChatAPI.colorify( null, name + "&8: &e" + lols.get(id) ), recipient -> recipient.hasPermission("utils.lol.see") ); lastLol = time; return true; } @Command (hook = "saylol") public boolean saylol(CommandSender sender) { if (warnNoLols(sender)) return true; long time = System.currentTimeMillis(); if (warnTime(sender, time)) return true; String name = getSenderName(sender); Random random = new Random(); int id = random.nextInt(lols.size()); Utils.broadcast( LOL_PREFIX, ChatAPI.colorify( null, name + "&8: &e" + lols.get(id) ), ModuleLoader.exists("Ignore") ? Ignore.getIgnoredBy(sender) : null ); lastLol = time; return true; } @Command (hook = "listlols") public boolean listLols(CommandSender sender, int page) { searchCache.put(sender, Arrays.asList(-1)); if (warnNoLols(sender)) return true; List ids = new ArrayList<>(); for (int i = 0; i < lols.size(); i++) { ids.add(i); } printPaged(sender, ids, page); return true; } @Command (hook = "listlolsdef") public boolean listLolsDefault(CommandSender sender) { return listLols(sender, 1); } @Command (hook = "searchlol") public boolean search(CommandSender sender, boolean sensitive, String text) { searchCache.remove(sender); List results = new ArrayList<>(); if (!sensitive) text = text.toLowerCase(); for (int i = 0; i < lols.size(); i++) { String lol = (String) lols.get(i); if ((sensitive ? lol : lol.toLowerCase()).contains(text)) results.add(i); } if (results.isEmpty()) { getLogger().message(sender, "&cCouldn't find any matching lols."); return true; } searchCache.put(sender, results); Message m = new Message(sender, null); m.appendText(getLogger().getHeader().replace("\n", "")); appendResults(m, results); m.send(); return true; } @Command (hook = "matchlol") public boolean match(CommandSender sender, boolean sensitive, String regex) { searchCache.remove(sender); List results = new ArrayList<>(); if (!sensitive) regex = regex.toLowerCase(); for (int i = 0; i < lols.size(); i++) { String lol = (String) lols.get(i); if ((sensitive ? lol : lol.toLowerCase()).matches(regex)) results.add(i); } if (results.isEmpty()) { getLogger().message(sender, "&cCouldn't find any matching lols."); return true; } searchCache.put(sender, results); Message m = new Message(sender, null); m.appendText(getLogger().getHeader().replace("\n", "")); appendResults(m, results); m.send(); return true; } @Command (hook = "page") public boolean page(CommandSender sender, int page) { List results = searchCache.get(sender); if (results == null || results.size() == 0) { getLogger().message(sender, true, "There's nothing to page through. This command pages through the last lol command's output."); return true; } if (results.get(0) == -1) { listLols(sender, page); } else { printPaged(sender, results, page); } return true; } @EventHandler public void onLeave(PlayerQuitEvent e) { searchCache.remove(e.getPlayer()); } private int getMaxPage(int size) { return (int) Math.ceil(size / (double) PAGE_SIZE); } private void saveLols() { JsonManager.save(lols, lolLocation); } private void saveLolsSync() { JsonManager.saveSync(lols, lolLocation); } private ClickCallback getCallback(int index) { return (ClickCallback) handlers.get(index); } private void clickAction(Player player, int index) { if (player.hasPermission("utils.lol.id")) Bukkit.getScheduler().callSyncMethod(ModuleLoader.getPlugin(), () -> Bukkit.dispatchCommand(player, "lol id " + index)); } private String getSenderName(CommandSender sender) { return sender instanceof Player ? ((Player) sender).getDisplayName() : "&9" + sender.getName(); } private boolean warnNoLols(CommandSender sender) { if (lols.size() == 0) { getLogger().message(sender, true, "There are no lols yet!"); return true; } return false; } private boolean warnTime(CommandSender sender, long time) { if (time - lastLol < 15000) { int secs = (14 - (int) Math.ceil((time - lastLol) / 1000)); getLogger().message(sender, true, "You can't use saylol for another " + secs + "s."); return true; } return false; } private boolean warnLolOutOfBounds(CommandSender sender, int id) { if (id < 0 || id >= lols.size()) { getLogger().message(sender, true, "The ID must be at least 0 and at most " + (lols.size() - 1)); return true; } return false; } private boolean warnPageOutOfBounds(CommandSender sender, int page, int pages) { if (page <= 0) { getLogger().message(sender, true, "Page number too small, must be at least 1!"); return true; } if (page > pages) { getLogger().message(sender, true, "Page number too big, must be at most " + pages + "!"); return true; } return false; } private void appendResults(Message m, List results) { int size = results.size(); if (size > PAGE_SIZE) m.appendText(" &ePage 1/" + getMaxPage(size) + ":"); for (int i = 0; i < size && i < PAGE_SIZE; i++) { int id = results.get(i); m.appendCallback("\n&a" + id + "&8: &e" + lols.get(id), getCallback(id)); } m.appendText("\n&7Use /lol page to look at other pages."); } private void printPaged(CommandSender sender, List results, int page) { page = page - 1; int start = page * PAGE_SIZE; int end = start + PAGE_SIZE; int pages = getMaxPage(results.size()); if (warnPageOutOfBounds(sender, page, pages)) return; Message m = new Message(sender, null); m.appendText(getLogger().getHeader().replace("\n", "")); m.appendText(" &ePage " + (page + 1) + "/" + pages + ":"); for (int i = start; i < end && i < results.size(); i++) { int id = results.get(i); m.appendCallback("\n&a" + id + "&8: &e" + lols.get(id), getCallback(id)); } m.send(); } }