From 57328808e6cd8c2140f5a71b4c2605ac71e1b553 Mon Sep 17 00:00:00 2001 From: Kevinthegreat <92656833+kevinthegreat1@users.noreply.github.com> Date: Thu, 29 Jun 2023 11:15:58 +0800 Subject: Add Shortcuts --- .../java/me/xmrvizzy/skyblocker/SkyblockerMod.java | 2 + .../skyblocker/config/SkyblockerConfig.java | 13 ++ .../skyblocker/mixin/accessor/FrustumInvoker.java | 7 +- .../skyblocker/skyblock/shortcut/Shortcuts.java | 166 +++++++++++++++++++++ .../me/xmrvizzy/skyblocker/utils/FrustumUtils.java | 2 +- .../java/me/xmrvizzy/skyblocker/utils/Utils.java | 37 +++-- 6 files changed, 213 insertions(+), 14 deletions(-) create mode 100644 src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java (limited to 'src/main/java') diff --git a/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java b/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java index 3692db1b..0263f20c 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java +++ b/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java @@ -16,6 +16,7 @@ import me.xmrvizzy.skyblocker.skyblock.item.WikiLookup; import me.xmrvizzy.skyblocker.skyblock.itemlist.ItemRegistry; import me.xmrvizzy.skyblocker.skyblock.quicknav.QuickNav; import me.xmrvizzy.skyblocker.skyblock.rift.TheRift; +import me.xmrvizzy.skyblocker.skyblock.shortcut.Shortcuts; import me.xmrvizzy.skyblocker.skyblock.tabhud.TabHud; import me.xmrvizzy.skyblocker.skyblock.tabhud.util.PlayerListMgr; import me.xmrvizzy.skyblocker.utils.*; @@ -76,6 +77,7 @@ public class SkyblockerMod implements ClientModInitializer { QuickNav.init(); DwarvenHud.init(); ChatMessageListener.init(); + Shortcuts.init(); DiscordRPCManager.init(); LividColor.init(); FishingHelper.init(); diff --git a/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java b/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java index 04cfaea3..8c7d2f71 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java +++ b/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java @@ -161,6 +161,10 @@ public class SkyblockerConfig implements ConfigData { @ConfigEntry.Gui.CollapsibleObject() public FairySouls fairySouls = new FairySouls(); + @ConfigEntry.Category("shortcuts") + @ConfigEntry.Gui.CollapsibleObject() + public Shortcuts shortcuts = new Shortcuts(); + @ConfigEntry.Category("itemList") @ConfigEntry.Gui.CollapsibleObject() public ItemList itemList = new ItemList(); @@ -264,6 +268,15 @@ public class SkyblockerConfig implements ConfigData { public boolean enableFairySoulsHelper = false; } + public static class Shortcuts { + @ConfigEntry.Gui.Tooltip() + public boolean enableShortcuts = true; + @ConfigEntry.Gui.Tooltip() + public boolean enableCommandShortcuts = true; + @ConfigEntry.Gui.Tooltip() + public boolean enableCommandArgShortcuts = true; + } + public static class Hitbox { public boolean oldFarmlandHitbox = true; public boolean oldLeverHitbox = false; diff --git a/src/main/java/me/xmrvizzy/skyblocker/mixin/accessor/FrustumInvoker.java b/src/main/java/me/xmrvizzy/skyblocker/mixin/accessor/FrustumInvoker.java index 108a7344..3cde115e 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/mixin/accessor/FrustumInvoker.java +++ b/src/main/java/me/xmrvizzy/skyblocker/mixin/accessor/FrustumInvoker.java @@ -1,15 +1,14 @@ package me.xmrvizzy.skyblocker.mixin.accessor; -import me.xmrvizzy.skyblocker.utils.FrustumUtils; import net.minecraft.client.render.Frustum; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.gen.Invoker; /** - * Use {@link FrustumUtils#isVisible(double, double, double, double, double, double) FrustumUtils#isVisible} which is shorter. For the purpose of avoiding object allocations! + * Use {@link me.xmrvizzy.skyblocker.utils.FrustumUtils#isVisible(double, double, double, double, double, double) FrustumUtils#isVisible} which is shorter. For the purpose of avoiding object allocations! */ @Mixin(Frustum.class) public interface FrustumInvoker { - @Invoker("isVisible") - boolean isVisible(double minX, double minY, double minZ, double maxX, double maxY, double maxZ); + @Invoker + boolean invokeIsVisible(double minX, double minY, double minZ, double maxX, double maxY, double maxZ); } diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java new file mode 100644 index 00000000..dcd98e79 --- /dev/null +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java @@ -0,0 +1,166 @@ +package me.xmrvizzy.skyblocker.skyblock.shortcut; + +import com.mojang.brigadier.Command; +import me.xmrvizzy.skyblocker.SkyblockerMod; +import me.xmrvizzy.skyblocker.config.SkyblockerConfig; +import me.xmrvizzy.skyblocker.utils.Utils; +import net.fabricmc.fabric.api.client.command.v2.ClientCommandRegistrationCallback; +import net.fabricmc.fabric.api.client.command.v2.FabricClientCommandSource; +import net.fabricmc.fabric.api.client.message.v1.ClientSendMessageEvents; +import net.minecraft.text.Text; + +import java.util.HashMap; +import java.util.Map; + +import static net.fabricmc.fabric.api.client.command.v2.ClientCommandManager.literal; + +public class Shortcuts { + public static final Map commands = new HashMap<>(); + public static final Map commandArgs = new HashMap<>(); + + public static void init() { + commands.put("/s", "/skyblock"); + commands.put("/sk", "/skyblock"); + commands.put("/sky", "/skyblock"); + commands.put("/i", "/is"); + commands.put("/h", "/hub"); + commands.put("/hu", "/hub"); + + commands.put("/d", "/warp dungeon_hub"); + commands.put("/dn", "/warp dungeon_hub"); + commands.put("/dun", "/warp dungeon_hub"); + commands.put("/dungeon", "/warp dungeon_hub"); + + commands.put("/bl", "/warp nether"); + commands.put("/blazing", "/warp nether"); + commands.put("/fortress", "/warp nether"); + commands.put("/crimson", "/warp nether"); + commands.put("/isles", "/warp nether"); + commands.put("/ci", "/warp nether"); + commands.put("/crimson isles", "/warp nether"); + commands.put("/n", "/warp nether"); + commands.put("/nether", "/warp nether"); + + commands.put("/deep", "/warp deep"); + commands.put("/cavern", "/warp deep"); + commands.put("/caverns", "/warp deep"); + + commands.put("/dw", "/warp mines"); + commands.put("/dwarven", "/warp mines"); + commands.put("/mi", "/warp mines"); + commands.put("/mines", "/warp mines"); + + commands.put("/fo", "/warp forge"); + commands.put("/for", "/warp forge"); + commands.put("/forge", "/warp forge"); + + commands.put("/cry", "/warp crystals"); + commands.put("/crystal", "/warp crystals"); + commands.put("/ho", "/warp crystals"); + commands.put("/hollows", "/warp crystals"); + commands.put("/ch", "/warp crystals"); + commands.put("/crystal hollows", "/warp crystals"); + + commands.put("/ga", "/warp garden"); + commands.put("/garden", "/warp garden"); + commands.put("/go", "/warp gold"); + commands.put("/gold", "/warp gold"); + + commands.put("/des", "/warp desert"); + commands.put("/desert", "/warp desert"); + commands.put("/mu", "/warp desert"); + commands.put("/mushroom", "/warp desert"); + + commands.put("/sp", "/warp spider"); + commands.put("/spider", "/warp spider"); + commands.put("/spiders", "/warp spider"); + + commands.put("/ba", "/warp barn"); + commands.put("/barn", "/warp barn"); + + commands.put("/e", "/warp end"); + commands.put("/end", "/warp end"); + + commands.put("/park", "/warp park"); + + commands.put("/castle", "/warp castle"); + commands.put("/museum", "/warp museum"); + commands.put("/da", "/warp da"); + commands.put("/dark", "/warp da"); + commands.put("/crypt", "/warp crypt"); + commands.put("/crypts", "/warp crypt"); + commands.put("/nest", "/warp nest"); + commands.put("/magma", "/warp magma"); + commands.put("/void", "/warp void"); + commands.put("/drag", "/warp drag"); + commands.put("/dragon", "/warp drag"); + commands.put("/jungle", "/warp jungle"); + commands.put("/howl", "/warp howl"); + + commands.put("/ca", "/chat all"); + commands.put("/cp", "/chat party"); + commands.put("/cg", "/chat guild"); + commands.put("/co", "/chat officer"); + commands.put("/cc", "/chat coop"); + + commandArgs.put("/m", "/msg"); + + commandArgs.put("/pa", "/p accept"); + commands.put("/pv", "/p leave"); + commands.put("/pd", "/p disband"); + commands.put("/rp", "/reparty"); + commands.put("/pr", "/reparty"); + + commandArgs.put("/v", "/visit"); + commands.put("/vp", "/visit portalhub"); + commands.put("/visit p", "/visit portalhub"); + + ClientCommandRegistrationCallback.EVENT.register((dispatcher, registryAccess) -> { + for (String key : commands.keySet()) { + if (key.startsWith("/")) { + dispatcher.register(literal(key.substring(1))); + } + } + for (String key : commandArgs.keySet()) { + if (key.startsWith("/")) { + dispatcher.register(literal(key.substring(1))); + } + } + dispatcher.register(literal(SkyblockerMod.NAMESPACE).then(literal("help").executes(context -> { + FabricClientCommandSource source = context.getSource(); + String status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; + source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Shortcuts" + status)); + for (Map.Entry command : commands.entrySet()) { + source.sendFeedback(Text.of("§7" + command.getKey() + " §f→ §7" + command.getValue())); + } + status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; + source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Argument Shortcuts" + status)); + for (Map.Entry commandArg : commandArgs.entrySet()) { + source.sendFeedback(Text.of("§7" + commandArg.getKey() + " §f→ §7" + commandArg.getValue())); + } + source.sendFeedback(Text.of("§e§lSkyblocker §fCommands")); + for (String command : dispatcher.getSmartUsage(dispatcher.getRoot().getChild(SkyblockerMod.NAMESPACE), source).values()) { + source.sendFeedback(Text.of("§7/" + SkyblockerMod.NAMESPACE + " " + command)); + } + return Command.SINGLE_SUCCESS; + }))); + }); + ClientSendMessageEvents.MODIFY_COMMAND.register(command -> { + if (Utils.isOnHypixel() && SkyblockerConfig.get().general.shortcuts.enableShortcuts) { + command = '/' + command; + if (SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts) { + command = commands.getOrDefault(command, command); + } + if (SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts) { + String[] messageArgs = command.split(" "); + for (int i = 0; i < messageArgs.length; i++) { + messageArgs[i] = commandArgs.getOrDefault(messageArgs[i], messageArgs[i]); + } + command = String.join(" ", messageArgs); + } + return command.substring(1); + } + return command; + }); + } +} diff --git a/src/main/java/me/xmrvizzy/skyblocker/utils/FrustumUtils.java b/src/main/java/me/xmrvizzy/skyblocker/utils/FrustumUtils.java index 9ea90c16..565bd7a8 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/utils/FrustumUtils.java +++ b/src/main/java/me/xmrvizzy/skyblocker/utils/FrustumUtils.java @@ -17,6 +17,6 @@ public class FrustumUtils { } public static boolean isVisible(double minX, double minY, double minZ, double maxX, double maxY, double maxZ) { - return ((FrustumInvoker) getFrustum()).isVisible(minX, minY, minZ, maxX, maxY, maxZ); + return ((FrustumInvoker) getFrustum()).invokeIsVisible(minX, minY, minZ, maxX, maxY, maxZ); } } \ No newline at end of file diff --git a/src/main/java/me/xmrvizzy/skyblocker/utils/Utils.java b/src/main/java/me/xmrvizzy/skyblocker/utils/Utils.java index 35dfd368..71e3b44f 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/utils/Utils.java +++ b/src/main/java/me/xmrvizzy/skyblocker/utils/Utils.java @@ -29,6 +29,7 @@ import java.util.List; */ public class Utils { private static final String PROFILE_PREFIX = "Profile: "; + private static boolean isOnHypixel = false; private static boolean isOnSkyblock = false; private static boolean isInDungeons = false; private static boolean isInjected = false; @@ -45,6 +46,10 @@ public class Utils { private static boolean sentLocRaw = false; private static long lastLocRaw = 0; + public static boolean isOnHypixel() { + return isOnHypixel; + } + public static boolean isOnSkyblock() { return isOnSkyblock; } @@ -126,21 +131,35 @@ public class Utils { String string = sidebar.toString(); if (sidebar.isEmpty()) return; - if (sidebar.get(0).contains("SKYBLOCK") || sidebar.get(0).contains("SKIBLOCK")) { - if (!isOnSkyblock) { - if (!isInjected) { - isInjected = true; - ItemTooltipCallback.EVENT.register(PriceInfoTooltip::onInjectTooltip); + if (sidebar.get(sidebar.size() - 1).equals("www.hypixel.net")) { + if (!isOnHypixel) { + isOnHypixel = true; + } + if (sidebar.get(0).contains("SKYBLOCK") || sidebar.get(0).contains("SKIBLOCK")) { + if (!isOnSkyblock) { + if (!isInjected) { + isInjected = true; + ItemTooltipCallback.EVENT.register(PriceInfoTooltip::onInjectTooltip); + } + isOnSkyblock = true; + SkyblockEvents.JOIN.invoker().onSkyblockJoin(); } - isOnSkyblock = true; - SkyblockEvents.JOIN.invoker().onSkyblockJoin(); + } else { + leaveSkyblock(); } - } else if (isOnSkyblock) { + isInDungeons = isOnSkyblock && string.contains("The Catacombs"); + } else if (isOnHypixel) { + isOnHypixel = false; + leaveSkyblock(); + } + } + + private static void leaveSkyblock() { + if (isOnSkyblock) { isOnSkyblock = false; isInDungeons = false; SkyblockEvents.LEAVE.invoker().onSkyblockLeave(); } - isInDungeons = isOnSkyblock && string.contains("The Catacombs"); } public static String getLocation() { -- cgit From 931ea3749ba94d1b7de4577722246df1a4e9cced Mon Sep 17 00:00:00 2001 From: Kevinthegreat <92656833+kevinthegreat1@users.noreply.github.com> Date: Thu, 29 Jun 2023 20:47:50 +0800 Subject: Add shortcuts loading and saving --- .../skyblocker/skyblock/shortcut/Shortcuts.java | 143 ++++++++++++++------- 1 file changed, 100 insertions(+), 43 deletions(-) (limited to 'src/main/java') diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java index dcd98e79..f6483e52 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java @@ -1,24 +1,60 @@ package me.xmrvizzy.skyblocker.skyblock.shortcut; +import com.google.gson.JsonObject; +import com.google.gson.reflect.TypeToken; import com.mojang.brigadier.Command; +import com.mojang.brigadier.CommandDispatcher; import me.xmrvizzy.skyblocker.SkyblockerMod; import me.xmrvizzy.skyblocker.config.SkyblockerConfig; import me.xmrvizzy.skyblocker.utils.Utils; import net.fabricmc.fabric.api.client.command.v2.ClientCommandRegistrationCallback; import net.fabricmc.fabric.api.client.command.v2.FabricClientCommandSource; +import net.fabricmc.fabric.api.client.event.lifecycle.v1.ClientLifecycleEvents; import net.fabricmc.fabric.api.client.message.v1.ClientSendMessageEvents; +import net.minecraft.client.MinecraftClient; +import net.minecraft.command.CommandRegistryAccess; import net.minecraft.text.Text; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import java.io.*; +import java.lang.reflect.Type; import java.util.HashMap; import java.util.Map; +import java.util.concurrent.CompletableFuture; import static net.fabricmc.fabric.api.client.command.v2.ClientCommandManager.literal; public class Shortcuts { + private static final Logger LOGGER = LoggerFactory.getLogger(Shortcuts.class); + private static final File SHORTCUTS_FILE = SkyblockerMod.CONFIG_DIR.resolve("shortcuts.json").toFile(); + private static CompletableFuture shortcutsLoaded; public static final Map commands = new HashMap<>(); public static final Map commandArgs = new HashMap<>(); public static void init() { + shortcutsLoaded = CompletableFuture.runAsync(Shortcuts::loadShortcuts); + ClientLifecycleEvents.CLIENT_STOPPING.register(Shortcuts::saveShortcuts); + ClientCommandRegistrationCallback.EVENT.register(Shortcuts::registerCommands); + ClientSendMessageEvents.MODIFY_COMMAND.register(Shortcuts::modifyCommand); + } + + private static void loadShortcuts() { + try (BufferedReader reader = new BufferedReader(new FileReader(SHORTCUTS_FILE))) { + Type shortcutsType = new TypeToken>>() {}.getType(); + Map> shortcuts = SkyblockerMod.GSON.fromJson(reader, shortcutsType); + commands.putAll(shortcuts.get("commands")); + commandArgs.putAll(shortcuts.get("commandArgs")); + LOGGER.info("[Skyblocker] Loaded {} command shortcuts and {} command argument shortcuts", commands.size(), commandArgs.size()); + } catch (FileNotFoundException e) { + registerDefaultShortcuts(); + LOGGER.warn("[Skyblocker] Shortcuts file not found, using default shortcuts. This is normal when using for the first time.", e); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load shortcuts file", e); + } + } + + private static void registerDefaultShortcuts() { commands.put("/s", "/skyblock"); commands.put("/sk", "/skyblock"); commands.put("/sky", "/skyblock"); @@ -114,53 +150,74 @@ public class Shortcuts { commandArgs.put("/v", "/visit"); commands.put("/vp", "/visit portalhub"); commands.put("/visit p", "/visit portalhub"); + } - ClientCommandRegistrationCallback.EVENT.register((dispatcher, registryAccess) -> { - for (String key : commands.keySet()) { - if (key.startsWith("/")) { - dispatcher.register(literal(key.substring(1))); - } + private static void saveShortcuts(MinecraftClient client) { + JsonObject shortcutsJson = new JsonObject(); + shortcutsJson.add("commands", SkyblockerMod.GSON.toJsonTree(commands)); + shortcutsJson.add("commandArgs", SkyblockerMod.GSON.toJsonTree(commandArgs)); + try (BufferedWriter writer = new BufferedWriter(new FileWriter(SHORTCUTS_FILE))) { + SkyblockerMod.GSON.toJson(shortcutsJson, writer); + LOGGER.info("[Skyblocker] Saved {} command shortcuts and {} command argument shortcuts", commands.size(), commandArgs.size()); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to save shortcuts file", e); + } + } + + private static void registerCommands(CommandDispatcher dispatcher, CommandRegistryAccess registryAccess) { + for (String key : commands.keySet()) { + if (key.startsWith("/")) { + dispatcher.register(literal(key.substring(1))); } - for (String key : commandArgs.keySet()) { - if (key.startsWith("/")) { - dispatcher.register(literal(key.substring(1))); - } + } + for (String key : commandArgs.keySet()) { + if (key.startsWith("/")) { + dispatcher.register(literal(key.substring(1))); } - dispatcher.register(literal(SkyblockerMod.NAMESPACE).then(literal("help").executes(context -> { - FabricClientCommandSource source = context.getSource(); - String status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; - source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Shortcuts" + status)); - for (Map.Entry command : commands.entrySet()) { - source.sendFeedback(Text.of("§7" + command.getKey() + " §f→ §7" + command.getValue())); - } - status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; - source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Argument Shortcuts" + status)); - for (Map.Entry commandArg : commandArgs.entrySet()) { - source.sendFeedback(Text.of("§7" + commandArg.getKey() + " §f→ §7" + commandArg.getValue())); - } - source.sendFeedback(Text.of("§e§lSkyblocker §fCommands")); - for (String command : dispatcher.getSmartUsage(dispatcher.getRoot().getChild(SkyblockerMod.NAMESPACE), source).values()) { - source.sendFeedback(Text.of("§7/" + SkyblockerMod.NAMESPACE + " " + command)); - } - return Command.SINGLE_SUCCESS; - }))); - }); - ClientSendMessageEvents.MODIFY_COMMAND.register(command -> { - if (Utils.isOnHypixel() && SkyblockerConfig.get().general.shortcuts.enableShortcuts) { - command = '/' + command; - if (SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts) { - command = commands.getOrDefault(command, command); - } - if (SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts) { - String[] messageArgs = command.split(" "); - for (int i = 0; i < messageArgs.length; i++) { - messageArgs[i] = commandArgs.getOrDefault(messageArgs[i], messageArgs[i]); - } - command = String.join(" ", messageArgs); + } + dispatcher.register(literal(SkyblockerMod.NAMESPACE).then(literal("help").executes(context -> { + FabricClientCommandSource source = context.getSource(); + String status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; + source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Shortcuts" + status)); + if (!shortcutsLoaded.isDone()) { + source.sendFeedback(Text.of("§c§lShortcuts not loaded yet")); + } else for (Map.Entry command : commands.entrySet()) { + source.sendFeedback(Text.of("§7" + command.getKey() + " §f→ §7" + command.getValue())); + } + status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; + source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Argument Shortcuts" + status)); + if (!shortcutsLoaded.isDone()) { + source.sendFeedback(Text.of("§c§lShortcuts not loaded yet")); + } else for (Map.Entry commandArg : commandArgs.entrySet()) { + source.sendFeedback(Text.of("§7" + commandArg.getKey() + " §f→ §7" + commandArg.getValue())); + } + source.sendFeedback(Text.of("§e§lSkyblocker §fCommands")); + for (String command : dispatcher.getSmartUsage(dispatcher.getRoot().getChild(SkyblockerMod.NAMESPACE), source).values()) { + source.sendFeedback(Text.of("§7/" + SkyblockerMod.NAMESPACE + " " + command)); + } + return Command.SINGLE_SUCCESS; + }))); + } + + private static String modifyCommand(String command) { + if (Utils.isOnHypixel() && SkyblockerConfig.get().general.shortcuts.enableShortcuts) { + if (!shortcutsLoaded.isDone()) { + LOGGER.warn("[Skyblocker] Shortcuts not loaded yet, skipping shortcut for command: {}", command); + return command; + } + command = '/' + command; + if (SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts) { + command = commands.getOrDefault(command, command); + } + if (SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts) { + String[] messageArgs = command.split(" "); + for (int i = 0; i < messageArgs.length; i++) { + messageArgs[i] = commandArgs.getOrDefault(messageArgs[i], messageArgs[i]); } - return command.substring(1); + command = String.join(" ", messageArgs); } - return command; - }); + return command.substring(1); + } + return command; } } -- cgit From 04a598fa906928c0f706b0ce6cd3d3add30faed2 Mon Sep 17 00:00:00 2001 From: Kevinthegreat <92656833+kevinthegreat1@users.noreply.github.com> Date: Thu, 29 Jun 2023 22:59:34 +0800 Subject: Add Shortcuts config screen --- .../skyblocker/skyblock/shortcut/Shortcuts.java | 8 ++ .../shortcut/ShortcutsConfigListWidget.java | 148 +++++++++++++++++++++ .../skyblock/shortcut/ShortcutsConfigScreen.java | 23 ++++ 3 files changed, 179 insertions(+) create mode 100644 src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java create mode 100644 src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java (limited to 'src/main/java') diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java index f6483e52..2fbe4315 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java @@ -32,6 +32,10 @@ public class Shortcuts { public static final Map commands = new HashMap<>(); public static final Map commandArgs = new HashMap<>(); + public static boolean isShortcutsLoaded() { + return shortcutsLoaded.isDone(); + } + public static void init() { shortcutsLoaded = CompletableFuture.runAsync(Shortcuts::loadShortcuts); ClientLifecycleEvents.CLIENT_STOPPING.register(Shortcuts::saveShortcuts); @@ -196,6 +200,10 @@ public class Shortcuts { source.sendFeedback(Text.of("§7/" + SkyblockerMod.NAMESPACE + " " + command)); } return Command.SINGLE_SUCCESS; + })).then(literal("shortcuts").executes(context -> { + // Queue the screen or else the screen will be immediately closed after executing this command + SkyblockerMod.getInstance().scheduler.queueOpenScreen(ShortcutsConfigScreen::new); + return Command.SINGLE_SUCCESS; }))); } diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java new file mode 100644 index 00000000..893d9169 --- /dev/null +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java @@ -0,0 +1,148 @@ +package me.xmrvizzy.skyblocker.skyblock.shortcut; + +import net.minecraft.client.MinecraftClient; +import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.Element; +import net.minecraft.client.gui.Selectable; +import net.minecraft.client.gui.screen.narration.NarrationMessageBuilder; +import net.minecraft.client.gui.screen.narration.NarrationPart; +import net.minecraft.client.gui.widget.ElementListWidget; +import net.minecraft.client.gui.widget.TextFieldWidget; +import net.minecraft.text.Text; + +import java.util.List; + +public class ShortcutsConfigListWidget extends ElementListWidget { + public ShortcutsConfigListWidget(MinecraftClient minecraftClient, int width, int height, int top, int bottom, int itemHeight) { + super(minecraftClient, width, height, top, bottom, itemHeight); + ShortcutCategoryEntry commandCategory = new ShortcutCategoryEntry("skyblocker.shortcuts.targetCommand", "skyblocker.shortcuts.replacementCommand"); + addEntry(commandCategory); + if (!Shortcuts.isShortcutsLoaded()) { + addEntry(new ShortcutLoadingEntry()); + } else { + Shortcuts.commands.keySet().stream().sorted().forEach(commandTarget -> addEntry(new ShortcutEntry(commandTarget, Shortcuts.commands.get(commandTarget), commandCategory))); + } + ShortcutCategoryEntry commandArgCategory = new ShortcutCategoryEntry("skyblocekr.shortcuts.targetCommandArg", "skyblocker.shortcuts.replacementCommandArg"); + addEntry(commandArgCategory); + if (!Shortcuts.isShortcutsLoaded()) { + addEntry(new ShortcutLoadingEntry()); + } else { + Shortcuts.commandArgs.keySet().stream().sorted().forEach(commandArgTarget -> addEntry(new ShortcutEntry(commandArgTarget, Shortcuts.commandArgs.get(commandArgTarget), commandArgCategory))); + } + } + + @Override + public int getRowWidth() { + return super.getRowWidth() + 100; + } + + @Override + protected int getScrollbarPositionX() { + return super.getScrollbarPositionX() + 50; + } + + protected abstract static class AbstractShortcutEntry extends ElementListWidget.Entry { + } + + private class ShortcutCategoryEntry extends AbstractShortcutEntry { + private final Text targetName; + private final Text replacementName; + + private ShortcutCategoryEntry(String targetName, String replacementName) { + this.targetName = Text.translatable(targetName); + this.replacementName = Text.translatable(replacementName); + } + + @Override + public List children() { + return List.of(); + } + + @Override + public List selectableChildren() { + return List.of(new Selectable() { + @Override + public SelectionType getType() { + return SelectionType.HOVERED; + } + + @Override + public void appendNarrations(NarrationMessageBuilder builder) { + builder.put(NarrationPart.TITLE, targetName, replacementName); + } + }); + } + + @Override + public void render(DrawContext context, int index, int y, int x, int entryWidth, int entryHeight, int mouseX, int mouseY, boolean hovered, float tickDelta) { + context.drawCenteredTextWithShadow(client.textRenderer, targetName, width / 2 - 85, y + 5, 0xFFFFFF); + context.drawCenteredTextWithShadow(client.textRenderer, replacementName, width / 2 + 85, y + 5, 0xFFFFFF); + } + } + + private class ShortcutLoadingEntry extends AbstractShortcutEntry { + private final Text text; + + private ShortcutLoadingEntry() { + this.text = Text.of("§c§lShortcuts not loaded yet"); + } + + @Override + public List children() { + return List.of(); + } + + @Override + public List selectableChildren() { + return List.of(new Selectable() { + @Override + public SelectionType getType() { + return SelectionType.HOVERED; + } + + @Override + public void appendNarrations(NarrationMessageBuilder builder) { + builder.put(NarrationPart.TITLE, text); + } + }); + } + + @Override + public void render(DrawContext context, int index, int y, int x, int entryWidth, int entryHeight, int mouseX, int mouseY, boolean hovered, float tickDelta) { + context.drawCenteredTextWithShadow(client.textRenderer, text, width / 2, y + 5, 0xFFFFFF); + } + } + + private class ShortcutEntry extends AbstractShortcutEntry { + private final List children; + private final TextFieldWidget target; + private final TextFieldWidget replacement; + + private ShortcutEntry(String target, String replacement, ShortcutCategoryEntry category) { + this.target = new TextFieldWidget(MinecraftClient.getInstance().textRenderer, width / 2 - 160, 5, 150, 20, category.targetName); + this.replacement = new TextFieldWidget(MinecraftClient.getInstance().textRenderer, width / 2 + 10, 5, 150, 20, category.replacementName); + this.target.setText(target); + this.replacement.setText(replacement); + children = List.of(this.target, this.replacement); + } + + @Override + public List children() { + return children; + } + + @Override + public List selectableChildren() { + return children; + } + + @Override + public void render(DrawContext context, int index, int y, int x, int entryWidth, int entryHeight, int mouseX, int mouseY, boolean hovered, float tickDelta) { + target.setY(y); + replacement.setY(y); + target.render(context, mouseX, mouseY, tickDelta); + replacement.render(context, mouseX, mouseY, tickDelta); + context.drawCenteredTextWithShadow(client.textRenderer, "→", width / 2, y + 5, 0xFFFFFF); + } + } +} diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java new file mode 100644 index 00000000..2f020604 --- /dev/null +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java @@ -0,0 +1,23 @@ +package me.xmrvizzy.skyblocker.skyblock.shortcut; + +import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.screen.Screen; +import net.minecraft.text.Text; + +public class ShortcutsConfigScreen extends Screen { + public ShortcutsConfigScreen() { + super(Text.translatable("skyblocker.shortcuts.config")); + } + + @Override + protected void init() { + super.init(); + addDrawableChild(new ShortcutsConfigListWidget(client, width, height, 32, height - 32, 25)); + } + + @Override + public void render(DrawContext context, int mouseX, int mouseY, float delta) { + super.render(context, mouseX, mouseY, delta); + context.drawCenteredTextWithShadow(this.textRenderer, this.title, this.width / 2, 16, 0xFFFFFF); + } +} -- cgit From 6e1dcf2861e6f084e75a9602cc270aaecb151bdc Mon Sep 17 00:00:00 2001 From: Kevinthegreat <92656833+kevinthegreat1@users.noreply.github.com> Date: Fri, 30 Jun 2023 18:39:32 +0800 Subject: Add shortcuts editing --- .../skyblocker/skyblock/shortcut/Shortcuts.java | 52 ++++++---- .../shortcut/ShortcutsConfigListWidget.java | 110 +++++++++++++++++---- .../skyblock/shortcut/ShortcutsConfigScreen.java | 66 ++++++++++++- 3 files changed, 189 insertions(+), 39 deletions(-) (limited to 'src/main/java') diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java index 2fbe4315..799eab7c 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java @@ -14,6 +14,7 @@ import net.fabricmc.fabric.api.client.message.v1.ClientSendMessageEvents; import net.minecraft.client.MinecraftClient; import net.minecraft.command.CommandRegistryAccess; import net.minecraft.text.Text; +import org.jetbrains.annotations.Nullable; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -28,37 +29,48 @@ import static net.fabricmc.fabric.api.client.command.v2.ClientCommandManager.lit public class Shortcuts { private static final Logger LOGGER = LoggerFactory.getLogger(Shortcuts.class); private static final File SHORTCUTS_FILE = SkyblockerMod.CONFIG_DIR.resolve("shortcuts.json").toFile(); + @Nullable private static CompletableFuture shortcutsLoaded; public static final Map commands = new HashMap<>(); public static final Map commandArgs = new HashMap<>(); public static boolean isShortcutsLoaded() { - return shortcutsLoaded.isDone(); + return shortcutsLoaded != null && shortcutsLoaded.isDone(); } public static void init() { - shortcutsLoaded = CompletableFuture.runAsync(Shortcuts::loadShortcuts); + loadShortcuts(); ClientLifecycleEvents.CLIENT_STOPPING.register(Shortcuts::saveShortcuts); ClientCommandRegistrationCallback.EVENT.register(Shortcuts::registerCommands); ClientSendMessageEvents.MODIFY_COMMAND.register(Shortcuts::modifyCommand); } - private static void loadShortcuts() { - try (BufferedReader reader = new BufferedReader(new FileReader(SHORTCUTS_FILE))) { - Type shortcutsType = new TypeToken>>() {}.getType(); - Map> shortcuts = SkyblockerMod.GSON.fromJson(reader, shortcutsType); - commands.putAll(shortcuts.get("commands")); - commandArgs.putAll(shortcuts.get("commandArgs")); - LOGGER.info("[Skyblocker] Loaded {} command shortcuts and {} command argument shortcuts", commands.size(), commandArgs.size()); - } catch (FileNotFoundException e) { - registerDefaultShortcuts(); - LOGGER.warn("[Skyblocker] Shortcuts file not found, using default shortcuts. This is normal when using for the first time.", e); - } catch (IOException e) { - LOGGER.error("[Skyblocker] Failed to load shortcuts file", e); + protected static void loadShortcuts() { + if (shortcutsLoaded != null && !isShortcutsLoaded()) { + return; } + shortcutsLoaded = CompletableFuture.runAsync(() -> { + try (BufferedReader reader = new BufferedReader(new FileReader(SHORTCUTS_FILE))) { + Type shortcutsType = new TypeToken>>() { + }.getType(); + Map> shortcuts = SkyblockerMod.GSON.fromJson(reader, shortcutsType); + commands.clear(); + commandArgs.clear(); + commands.putAll(shortcuts.get("commands")); + commandArgs.putAll(shortcuts.get("commandArgs")); + LOGGER.info("[Skyblocker] Loaded {} command shortcuts and {} command argument shortcuts", commands.size(), commandArgs.size()); + } catch (FileNotFoundException e) { + registerDefaultShortcuts(); + LOGGER.warn("[Skyblocker] Shortcuts file not found, using default shortcuts. This is normal when using for the first time.", e); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load shortcuts file", e); + } + }); } private static void registerDefaultShortcuts() { + commands.clear(); + commandArgs.clear(); commands.put("/s", "/skyblock"); commands.put("/sk", "/skyblock"); commands.put("/sky", "/skyblock"); @@ -156,7 +168,7 @@ public class Shortcuts { commands.put("/visit p", "/visit portalhub"); } - private static void saveShortcuts(MinecraftClient client) { + protected static void saveShortcuts(MinecraftClient client) { JsonObject shortcutsJson = new JsonObject(); shortcutsJson.add("commands", SkyblockerMod.GSON.toJsonTree(commands)); shortcutsJson.add("commandArgs", SkyblockerMod.GSON.toJsonTree(commandArgs)); @@ -183,15 +195,15 @@ public class Shortcuts { FabricClientCommandSource source = context.getSource(); String status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Shortcuts" + status)); - if (!shortcutsLoaded.isDone()) { - source.sendFeedback(Text.of("§c§lShortcuts not loaded yet")); + if (!isShortcutsLoaded()) { + source.sendFeedback(Text.translatable("skyblocker.shortcuts.notLoaded")); } else for (Map.Entry command : commands.entrySet()) { source.sendFeedback(Text.of("§7" + command.getKey() + " §f→ §7" + command.getValue())); } status = SkyblockerConfig.get().general.shortcuts.enableShortcuts && SkyblockerConfig.get().general.shortcuts.enableCommandArgShortcuts ? "§a§l (Enabled)" : "§c§l (Disabled)"; source.sendFeedback(Text.of("§e§lSkyblocker §fCommand Argument Shortcuts" + status)); - if (!shortcutsLoaded.isDone()) { - source.sendFeedback(Text.of("§c§lShortcuts not loaded yet")); + if (!isShortcutsLoaded()) { + source.sendFeedback(Text.translatable("skyblocker.shortcuts.notLoaded")); } else for (Map.Entry commandArg : commandArgs.entrySet()) { source.sendFeedback(Text.of("§7" + commandArg.getKey() + " §f→ §7" + commandArg.getValue())); } @@ -209,7 +221,7 @@ public class Shortcuts { private static String modifyCommand(String command) { if (Utils.isOnHypixel() && SkyblockerConfig.get().general.shortcuts.enableShortcuts) { - if (!shortcutsLoaded.isDone()) { + if (!isShortcutsLoaded()) { LOGGER.warn("[Skyblocker] Shortcuts not loaded yet, skipping shortcut for command: {}", command); return command; } diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java index 893d9169..210f0bd6 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java @@ -9,25 +9,35 @@ import net.minecraft.client.gui.screen.narration.NarrationPart; import net.minecraft.client.gui.widget.ElementListWidget; import net.minecraft.client.gui.widget.TextFieldWidget; import net.minecraft.text.Text; +import org.jetbrains.annotations.Nullable; +import java.util.ArrayList; import java.util.List; +import java.util.Map; +import java.util.Optional; public class ShortcutsConfigListWidget extends ElementListWidget { - public ShortcutsConfigListWidget(MinecraftClient minecraftClient, int width, int height, int top, int bottom, int itemHeight) { + private final ShortcutsConfigScreen screen; + protected final List categories = new ArrayList<>(); + + public ShortcutsConfigListWidget(MinecraftClient minecraftClient, ShortcutsConfigScreen screen, int width, int height, int top, int bottom, int itemHeight) { super(minecraftClient, width, height, top, bottom, itemHeight); - ShortcutCategoryEntry commandCategory = new ShortcutCategoryEntry("skyblocker.shortcuts.targetCommand", "skyblocker.shortcuts.replacementCommand"); + this.screen = screen; + ShortcutCategoryEntry commandCategory = new ShortcutCategoryEntry("skyblocker.shortcuts.command.target", "skyblocker.shortcuts.command.replacement"); + categories.add(commandCategory); addEntry(commandCategory); if (!Shortcuts.isShortcutsLoaded()) { addEntry(new ShortcutLoadingEntry()); } else { - Shortcuts.commands.keySet().stream().sorted().forEach(commandTarget -> addEntry(new ShortcutEntry(commandTarget, Shortcuts.commands.get(commandTarget), commandCategory))); + Shortcuts.commands.keySet().stream().sorted().forEach(commandTarget -> addEntry(new ShortcutEntry(commandCategory, commandTarget, Shortcuts.commands.get(commandTarget)))); } - ShortcutCategoryEntry commandArgCategory = new ShortcutCategoryEntry("skyblocekr.shortcuts.targetCommandArg", "skyblocker.shortcuts.replacementCommandArg"); + ShortcutCategoryEntry commandArgCategory = new ShortcutCategoryEntry("skyblocker.shortcuts.commandArg.target", "skyblocker.shortcuts.commandArg.replacement", "skyblocker.shortcuts.commandArg.tooltip"); + categories.add(commandArgCategory); addEntry(commandArgCategory); if (!Shortcuts.isShortcutsLoaded()) { addEntry(new ShortcutLoadingEntry()); } else { - Shortcuts.commandArgs.keySet().stream().sorted().forEach(commandArgTarget -> addEntry(new ShortcutEntry(commandArgTarget, Shortcuts.commandArgs.get(commandArgTarget), commandArgCategory))); + Shortcuts.commandArgs.keySet().stream().sorted().forEach(commandArgTarget -> addEntry(new ShortcutEntry(commandArgCategory, commandArgTarget, Shortcuts.commandArgs.get(commandArgTarget)))); } } @@ -41,16 +51,62 @@ public class ShortcutsConfigListWidget extends ElementListWidget { + protected Optional getCategory() { + if (getSelectedOrNull() instanceof ShortcutCategoryEntry category) { + return Optional.of(category); + } else if (getSelectedOrNull() instanceof ShortcutEntry shortcutEntry) { + return Optional.of(shortcutEntry.category); + } + return Optional.empty(); + } + + protected Map getShortcutsMap(ShortcutCategoryEntry category) { + return switch (categories.indexOf(category)) { + case 0 -> Shortcuts.commands; + case 1 -> Shortcuts.commandArgs; + default -> throw new IllegalStateException("Unexpected category: " + category); + }; + } + + @Override + public void setSelected(@Nullable ShortcutsConfigListWidget.AbstractShortcutEntry entry) { + super.setSelected(entry); + screen.updateButtons(); + } + + protected void addShortcutAfterSelected() { + getCategory().ifPresent(category -> { + children().add(children().indexOf(getSelectedOrNull()) + 1, new ShortcutEntry(category)); + getShortcutsMap(category).put("", ""); + }); + } + + @Override + protected boolean removeEntry(AbstractShortcutEntry entry) { + return super.removeEntry(entry); + } + + protected static abstract class AbstractShortcutEntry extends ElementListWidget.Entry { } - private class ShortcutCategoryEntry extends AbstractShortcutEntry { + protected class ShortcutCategoryEntry extends AbstractShortcutEntry { private final Text targetName; private final Text replacementName; + @Nullable + private final Text tooltip; private ShortcutCategoryEntry(String targetName, String replacementName) { + this(targetName, replacementName, (Text) null); + } + + private ShortcutCategoryEntry(String targetName, String replacementName, String tooltip) { + this(targetName, replacementName, Text.translatable(tooltip)); + } + + private ShortcutCategoryEntry(String targetName, String replacementName, @Nullable Text tooltip) { this.targetName = Text.translatable(targetName); this.replacementName = Text.translatable(replacementName); + this.tooltip = tooltip; } @Override @@ -77,6 +133,9 @@ public class ShortcutsConfigListWidget extends ElementListWidget children; - private final TextFieldWidget target; - private final TextFieldWidget replacement; - - private ShortcutEntry(String target, String replacement, ShortcutCategoryEntry category) { - this.target = new TextFieldWidget(MinecraftClient.getInstance().textRenderer, width / 2 - 160, 5, 150, 20, category.targetName); - this.replacement = new TextFieldWidget(MinecraftClient.getInstance().textRenderer, width / 2 + 10, 5, 150, 20, category.replacementName); - this.target.setText(target); - this.replacement.setText(replacement); - children = List.of(this.target, this.replacement); + protected final ShortcutCategoryEntry category; + protected final TextFieldWidget target; + protected final TextFieldWidget replacement; + private String oldTarget; + + protected ShortcutEntry(ShortcutCategoryEntry category) { + this(category, "", ""); + } + + private ShortcutEntry(ShortcutCategoryEntry category, String targetString, String replacementString) { + this.category = category; + target = new TextFieldWidget(MinecraftClient.getInstance().textRenderer, width / 2 - 160, 5, 150, 20, category.targetName); + replacement = new TextFieldWidget(MinecraftClient.getInstance().textRenderer, width / 2 + 10, 5, 150, 20, category.replacementName); + oldTarget = targetString; + target.setText(targetString); + replacement.setText(replacementString); + target.setChangedListener(newTarget -> { + Map map = getShortcutsMap(category); + map.remove(oldTarget); + map.put(newTarget, replacement.getText()); + oldTarget = newTarget; + }); + replacement.setChangedListener(newReplacement -> getShortcutsMap(category).put(target.getText(), newReplacement)); + children = List.of(target, replacement); } @Override diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java index 2f020604..49581761 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java @@ -1,18 +1,76 @@ package me.xmrvizzy.skyblocker.skyblock.shortcut; import net.minecraft.client.gui.DrawContext; +import net.minecraft.client.gui.screen.ConfirmScreen; import net.minecraft.client.gui.screen.Screen; +import net.minecraft.client.gui.tooltip.Tooltip; +import net.minecraft.client.gui.widget.ButtonWidget; +import net.minecraft.client.gui.widget.GridWidget; +import net.minecraft.client.gui.widget.SimplePositioningWidget; +import net.minecraft.screen.ScreenTexts; import net.minecraft.text.Text; public class ShortcutsConfigScreen extends Screen { + + private ShortcutsConfigListWidget shortcutsConfigListWidget; + private ButtonWidget buttonDelete; + private ButtonWidget buttonNew; + private ButtonWidget buttonDone; + private double scrollAmount; + public ShortcutsConfigScreen() { super(Text.translatable("skyblocker.shortcuts.config")); } + @Override + public void setTooltip(Text tooltip) { + super.setTooltip(tooltip); + } + @Override protected void init() { super.init(); - addDrawableChild(new ShortcutsConfigListWidget(client, width, height, 32, height - 32, 25)); + shortcutsConfigListWidget = new ShortcutsConfigListWidget(client, this, width, height, 32, height - 64, 25); + addDrawableChild(shortcutsConfigListWidget); + GridWidget gridWidget = new GridWidget(); + gridWidget.getMainPositioner().marginX(5).marginY(2); + GridWidget.Adder adder = gridWidget.createAdder(2); + buttonDelete = ButtonWidget.builder(Text.translatable("selectServer.delete"), button -> { + if (client != null && shortcutsConfigListWidget.getSelectedOrNull() instanceof ShortcutsConfigListWidget.ShortcutEntry shortcutEntry) { + scrollAmount = shortcutsConfigListWidget.getScrollAmount(); + client.setScreen(new ConfirmScreen(this::deleteEntry, Text.translatable("skyblocker.shortcuts.deleteQuestion"), Text.translatable("skyblocker.shortcuts.deleteWarning", shortcutEntry.target.getText() + " → " + shortcutEntry.replacement.getText()), Text.translatable("selectServer.deleteButton"), ScreenTexts.CANCEL)); + } + }).build(); + adder.add(buttonDelete); + buttonNew = ButtonWidget.builder(Text.translatable("skyblocker.shortcuts.new"), buttonNew -> shortcutsConfigListWidget.addShortcutAfterSelected()).build(); + adder.add(buttonNew); + adder.add(ButtonWidget.builder(ScreenTexts.CANCEL, button -> { + if (client != null) { + client.setScreen(null); + } + Shortcuts.loadShortcuts(); // Cancel changes by reloading shortcuts from disk + }).build()); + buttonDone = ButtonWidget.builder(ScreenTexts.DONE, button -> { + if (client != null) { + client.setScreen(null); + Shortcuts.saveShortcuts(client); // Save shortcuts to disk + } + }).tooltip(Tooltip.of(Text.translatable("skyblocker.shortcuts.commandSuggestionTooltip"))).build(); + adder.add(buttonDone); + gridWidget.refreshPositions(); + SimplePositioningWidget.setPos(gridWidget, 0, this.height - 64, this.width, 64); + gridWidget.forEachChild(this::addDrawableChild); + updateButtons(); + } + + private void deleteEntry(boolean confirmedAction) { + if (client != null) { + if (confirmedAction && shortcutsConfigListWidget.getSelectedOrNull() instanceof ShortcutsConfigListWidget.ShortcutEntry shortcutEntry) { + shortcutsConfigListWidget.getShortcutsMap(shortcutEntry.category).remove(shortcutEntry.target.getText()); + } + client.setScreen(this); // Re-inits the screen and creates a new instance of ShortcutsConfigListWidget + shortcutsConfigListWidget.setScrollAmount(scrollAmount); + } } @Override @@ -20,4 +78,10 @@ public class ShortcutsConfigScreen extends Screen { super.render(context, mouseX, mouseY, delta); context.drawCenteredTextWithShadow(this.textRenderer, this.title, this.width / 2, 16, 0xFFFFFF); } + + protected void updateButtons() { + buttonDelete.active = Shortcuts.isShortcutsLoaded() && shortcutsConfigListWidget.getSelectedOrNull() instanceof ShortcutsConfigListWidget.ShortcutEntry; + buttonNew.active = Shortcuts.isShortcutsLoaded() && shortcutsConfigListWidget.getCategory().isPresent(); + buttonDone.active = Shortcuts.isShortcutsLoaded(); + } } -- cgit From b4882519e945f5d4a03fb3c11c21e871f5d28cbb Mon Sep 17 00:00:00 2001 From: Kevinthegreat <92656833+kevinthegreat1@users.noreply.github.com> Date: Mon, 3 Jul 2023 09:42:08 +0800 Subject: Only save when the done button is pressed --- .../shortcut/ShortcutsConfigListWidget.java | 32 ++++++++++------------ .../skyblock/shortcut/ShortcutsConfigScreen.java | 13 ++++++--- 2 files changed, 24 insertions(+), 21 deletions(-) (limited to 'src/main/java') diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java index 210f0bd6..9fe30a87 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigListWidget.java @@ -11,20 +11,18 @@ import net.minecraft.client.gui.widget.TextFieldWidget; import net.minecraft.text.Text; import org.jetbrains.annotations.Nullable; -import java.util.ArrayList; import java.util.List; import java.util.Map; import java.util.Optional; public class ShortcutsConfigListWidget extends ElementListWidget { private final ShortcutsConfigScreen screen; - protected final List categories = new ArrayList<>(); + protected final List categories; public ShortcutsConfigListWidget(MinecraftClient minecraftClient, ShortcutsConfigScreen screen, int width, int height, int top, int bottom, int itemHeight) { super(minecraftClient, width, height, top, bottom, itemHeight); this.screen = screen; ShortcutCategoryEntry commandCategory = new ShortcutCategoryEntry("skyblocker.shortcuts.command.target", "skyblocker.shortcuts.command.replacement"); - categories.add(commandCategory); addEntry(commandCategory); if (!Shortcuts.isShortcutsLoaded()) { addEntry(new ShortcutLoadingEntry()); @@ -32,13 +30,13 @@ public class ShortcutsConfigListWidget extends ElementListWidget addEntry(new ShortcutEntry(commandCategory, commandTarget, Shortcuts.commands.get(commandTarget)))); } ShortcutCategoryEntry commandArgCategory = new ShortcutCategoryEntry("skyblocker.shortcuts.commandArg.target", "skyblocker.shortcuts.commandArg.replacement", "skyblocker.shortcuts.commandArg.tooltip"); - categories.add(commandArgCategory); addEntry(commandArgCategory); if (!Shortcuts.isShortcutsLoaded()) { addEntry(new ShortcutLoadingEntry()); } else { Shortcuts.commandArgs.keySet().stream().sorted().forEach(commandArgTarget -> addEntry(new ShortcutEntry(commandArgCategory, commandArgTarget, Shortcuts.commandArgs.get(commandArgTarget)))); } + categories = List.of(commandCategory, commandArgCategory); } @Override @@ -75,10 +73,7 @@ public class ShortcutsConfigListWidget extends ElementListWidget { - children().add(children().indexOf(getSelectedOrNull()) + 1, new ShortcutEntry(category)); - getShortcutsMap(category).put("", ""); - }); + getCategory().ifPresent(category -> children().add(children().indexOf(getSelectedOrNull()) + 1, new ShortcutEntry(category))); } @Override @@ -86,6 +81,18 @@ public class ShortcutsConfigListWidget extends ElementListWidget { } @@ -177,7 +184,6 @@ public class ShortcutsConfigListWidget extends ElementListWidget { - Map map = getShortcutsMap(category); - map.remove(oldTarget); - map.put(newTarget, replacement.getText()); - oldTarget = newTarget; - }); - replacement.setChangedListener(newReplacement -> getShortcutsMap(category).put(target.getText(), newReplacement)); children = List.of(target, replacement); } diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java index 49581761..72861493 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/ShortcutsConfigScreen.java @@ -16,6 +16,7 @@ public class ShortcutsConfigScreen extends Screen { private ButtonWidget buttonDelete; private ButtonWidget buttonNew; private ButtonWidget buttonDone; + private boolean initialized; private double scrollAmount; public S