From 73b458edfacf9711c85893a171e89be6b0ce54a6 Mon Sep 17 00:00:00 2001 From: Grayray75 <69988482+Grayray75@users.noreply.github.com> Date: Sat, 16 Sep 2023 19:57:35 +0200 Subject: [PATCH 1/5] Add hidden relic helper --- .../me/xmrvizzy/skyblocker/SkyblockerMod.java | 2 + .../skyblocker/config/SkyblockerConfig.java | 17 +- .../skyblocker/skyblock/FairySouls.java | 112 +++++++------ .../skyblocker/skyblock/dungeon/Trivia.java | 31 ++-- .../skyblock/shortcut/Shortcuts.java | 2 +- .../skyblock/spidersden/Relics.java | 141 +++++++++++++++++ .../xmrvizzy/skyblocker/utils/PosUtils.java | 14 ++ .../assets/skyblocker/lang/en_us.json | 4 + .../assets/skyblocker/spidersden/relics.json | 149 ++++++++++++++++++ 9 files changed, 406 insertions(+), 66 deletions(-) create mode 100644 src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java create mode 100644 src/main/java/me/xmrvizzy/skyblocker/utils/PosUtils.java create mode 100644 src/main/resources/assets/skyblocker/spidersden/relics.json diff --git a/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java b/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java index b630e5f5c1..b28ad3d4ad 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java +++ b/src/main/java/me/xmrvizzy/skyblocker/SkyblockerMod.java @@ -13,6 +13,7 @@ import me.xmrvizzy.skyblocker.skyblock.rift.TheRift; import me.xmrvizzy.skyblocker.skyblock.shortcut.Shortcuts; import me.xmrvizzy.skyblocker.skyblock.special.SpecialEffects; +import me.xmrvizzy.skyblocker.skyblock.spidersden.Relics; import me.xmrvizzy.skyblocker.skyblock.tabhud.TabHud; import me.xmrvizzy.skyblocker.skyblock.tabhud.screenbuilder.ScreenMaster; import me.xmrvizzy.skyblocker.skyblock.tabhud.util.PlayerListMgr; @@ -74,6 +75,7 @@ public void onInitializeClient() { ItemRegistry.init(); NEURepo.init(); FairySouls.init(); + Relics.init(); BackpackPreview.init(); QuickNav.init(); DwarvenHud.init(); diff --git a/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java b/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java index 58fc690c25..d6e3f0fec0 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java +++ b/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java @@ -278,7 +278,6 @@ public static class BarPositions { public BarPosition defenceBarPosition = BarPosition.LAYER1; @ConfigEntry.Gui.EnumHandler(option = ConfigEntry.Gui.EnumHandler.EnumDisplayOption.BUTTON) public BarPosition experienceBarPosition = BarPosition.LAYER1; - } public enum BarPosition { @@ -315,6 +314,7 @@ public static class Fishing { public static class FairySouls { public boolean enableFairySoulsHelper = false; public boolean highlightFoundSouls = true; + @ConfigEntry.Gui.Tooltip() public boolean highlightOnlyNearbySouls = false; } @@ -438,6 +438,10 @@ public static class Locations { @ConfigEntry.Gui.CollapsibleObject() public Barn barn = new Barn(); + @ConfigEntry.Category("spidersden") + @ConfigEntry.Gui.CollapsibleObject() + public SpidersDen spidersden = new SpidersDen(); + @ConfigEntry.Category("dungeons") @ConfigEntry.Gui.CollapsibleObject() public Dungeons dungeons = new Dungeons(); @@ -561,6 +565,17 @@ public static class Rift { public int mcGrubberStacks = 0; } + public static class SpidersDen { + @ConfigEntry.Category("relics") + @ConfigEntry.Gui.CollapsibleObject() + public Relics relics = new Relics(); + } + + public static class Relics { + public boolean enableRelicsHelper = false; + public boolean highlightFoundRelics = true; + } + public static class Slayer { @ConfigEntry.Category("vampire") @ConfigEntry.Gui.CollapsibleObject() diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java index e6b7515299..f1de63e58d 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java @@ -5,17 +5,21 @@ import com.google.gson.JsonElement; import com.google.gson.JsonObject; import com.google.gson.JsonParser; +import com.mojang.brigadier.CommandDispatcher; import me.xmrvizzy.skyblocker.SkyblockerMod; import me.xmrvizzy.skyblocker.config.SkyblockerConfig; import me.xmrvizzy.skyblocker.utils.NEURepo; +import me.xmrvizzy.skyblocker.utils.PosUtils; import me.xmrvizzy.skyblocker.utils.Utils; import me.xmrvizzy.skyblocker.utils.render.RenderHelper; 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.ClientReceiveMessageEvents; import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderContext; import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderEvents; import net.minecraft.client.MinecraftClient; +import net.minecraft.command.CommandRegistryAccess; import net.minecraft.entity.player.PlayerEntity; import net.minecraft.text.Text; import net.minecraft.util.DyeColor; @@ -45,11 +49,19 @@ public static CompletableFuture runAsyncAfterFairySoulsLoad(Runnable runna return fairySoulsLoaded.thenRunAsync(runnable); } - public static int getFairySoulsSize(@Nullable String location) { + public static int getFairySoulsAmount(@Nullable String location) { return location == null ? maxSouls : fairySouls.get(location).size(); } public static void init() { + loadFairySouls(); + ClientLifecycleEvents.CLIENT_STOPPING.register(FairySouls::saveFairySouls); + ClientReceiveMessageEvents.GAME.register(FairySouls::onChatMessage); + WorldRenderEvents.AFTER_TRANSLUCENT.register(FairySouls::render); + ClientCommandRegistrationCallback.EVENT.register(FairySouls::registerCommands); + } + + private static void loadFairySouls() { fairySoulsLoaded = NEURepo.runAsyncAfterLoad(() -> { try { BufferedReader reader = new BufferedReader(new FileReader(NEURepo.LOCAL_REPO_DIR.resolve("constants").resolve("fairy_souls.json").toFile())); @@ -62,53 +74,39 @@ public static void init() { } ImmutableSet.Builder fairySoulsForLocation = ImmutableSet.builder(); for (JsonElement fairySoul : fairySoulJson.getValue().getAsJsonArray().asList()) { - fairySoulsForLocation.add(parseBlockPos(fairySoul)); + fairySoulsForLocation.add(PosUtils.parsePosString(fairySoul.getAsString())); } fairySouls.put(fairySoulJson.getKey(), fairySoulsForLocation.build()); } - reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile())); + reader.close(); + LOGGER.info("[Skyblocker] Loaded fairy soul locations"); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load fairy soul locations", e); + } + + try { + BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile())); for (Map.Entry foundFairiesForProfileJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { Map> foundFairiesForProfile = new HashMap<>(); for (Map.Entry foundFairiesForLocationJson : foundFairiesForProfileJson.getValue().getAsJsonObject().asMap().entrySet()) { Set foundFairiesForLocation = new HashSet<>(); for (JsonElement foundFairy : foundFairiesForLocationJson.getValue().getAsJsonArray().asList()) { - foundFairiesForLocation.add(parseBlockPos(foundFairy)); + foundFairiesForLocation.add(PosUtils.parsePosString(foundFairy.getAsString())); } foundFairiesForProfile.put(foundFairiesForLocationJson.getKey(), foundFairiesForLocation); } foundFairies.put(foundFairiesForProfileJson.getKey(), foundFairiesForProfile); } reader.close(); + LOGGER.info("[Skyblocker] Loaded found fairy souls"); + } catch (FileNotFoundException ignored) { } catch (IOException e) { - LOGGER.error("Failed to load found fairy souls", e); - } catch (Exception e) { - LOGGER.error("Encountered unknown exception loading fairy souls", e); + LOGGER.error("[Skyblocker] Failed to load found fairy souls", e); } }); - - ClientLifecycleEvents.CLIENT_STOPPING.register(FairySouls::saveFoundFairySouls); - WorldRenderEvents.AFTER_TRANSLUCENT.register(FairySouls::render); - ClientReceiveMessageEvents.GAME.register(FairySouls::onChatMessage); - ClientCommandRegistrationCallback.EVENT.register((dispatcher, registryAccess) -> dispatcher.register(literal(SkyblockerMod.NAMESPACE) - .then(literal("fairySouls") - .then(literal("markAllInCurrentIslandFound").executes(context -> { - FairySouls.markAllFairiesFound(); - context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllFound")); - return 1; - })) - .then(literal("markAllInCurrentIslandMissing").executes(context -> { - FairySouls.markAllFairiesNotFound(); - context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllMissing")); - return 1; - }))))); - } - - private static BlockPos parseBlockPos(JsonElement posJson) { - String[] posArray = posJson.getAsString().split(","); - return new BlockPos(Integer.parseInt(posArray[0]), Integer.parseInt(posArray[1]), Integer.parseInt(posArray[2])); } - public static void saveFoundFairySouls(MinecraftClient client) { + private static void saveFairySouls(MinecraftClient client) { try { BufferedWriter writer = new BufferedWriter(new FileWriter(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile())); JsonObject foundFairiesJson = new JsonObject(); @@ -117,7 +115,7 @@ public static void saveFoundFairySouls(MinecraftClient client) { for (Map.Entry> foundFairiesForLocation : foundFairiesForProfile.getValue().entrySet()) { JsonArray foundFairiesForLocationJson = new JsonArray(); for (BlockPos foundFairy : foundFairiesForLocation.getValue()) { - foundFairiesForLocationJson.add(foundFairy.getX() + "," + foundFairy.getY() + "," + foundFairy.getZ()); + foundFairiesForLocationJson.add(PosUtils.getPosString(foundFairy)); } foundFairiesForProfileJson.add(foundFairiesForLocation.getKey(), foundFairiesForLocationJson); } @@ -125,12 +123,35 @@ public static void saveFoundFairySouls(MinecraftClient client) { } SkyblockerMod.GSON.toJson(foundFairiesJson, writer); writer.close(); + LOGGER.info("[Skyblocker] Saved found fairy souls"); } catch (IOException e) { - LOGGER.error("Failed to write found fairy souls to file."); + LOGGER.error("[Skyblocker] Failed to write found fairy souls to file", e); } } - public static void render(WorldRenderContext context) { + private static void registerCommands(CommandDispatcher dispatcher, CommandRegistryAccess registryAccess) { + dispatcher.register(literal(SkyblockerMod.NAMESPACE) + .then(literal("fairySouls") + .then(literal("markAllInCurrentIslandFound").executes(context -> { + FairySouls.markAllFairiesOnCurrentIslandFound(); + context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllFound")); + return 1; + })) + .then(literal("markAllInCurrentIslandMissing").executes(context -> { + FairySouls.markAllFairiesOnCurrentIslandMissing(); + context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllMissing")); + return 1; + })))); + } + + private static void onChatMessage(Text text, boolean overlay) { + String message = text.getString(); + if (message.equals("You have already found that Fairy Soul!") || message.equals("§d§lSOUL! §fYou found a §dFairy Soul§f!")) { + markClosestFairyFound(); + } + } + + private static void render(WorldRenderContext context) { SkyblockerConfig.FairySouls fairySoulsConfig = SkyblockerConfig.get().general.fairySouls; if (fairySoulsConfig.enableFairySoulsHelper && fairySoulsLoaded.isDone() && fairySouls.containsKey(Utils.getLocationRaw())) { @@ -157,35 +178,28 @@ private static boolean isFairySoulNotFound(BlockPos fairySoulPos) { return !foundFairiesForProfileAndLocation.contains(fairySoulPos); } - public static void onChatMessage(Text text, boolean overlay) { - String message = text.getString(); - if (message.equals("You have already found that Fairy Soul!") || message.equals("§d§lSOUL! §fYou found a §dFairy Soul§f!")) { - markClosestFairyFound(); - } - } - private static void markClosestFairyFound() { PlayerEntity player = MinecraftClient.getInstance().player; if (player == null) { - LOGGER.warn("Failed to mark closest fairy soul as found because player is null."); + LOGGER.warn("[Skyblocker] Failed to mark closest fairy soul as found because player is null"); return; } fairySouls.get(Utils.getLocationRaw()).stream() - .filter(FairySouls::isFairySoulNotFound) - .min(Comparator.comparingDouble(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()))) - .filter(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()) <= 16) - .ifPresent(fairySoulPos -> { - initializeFoundFairiesForCurrentProfileAndLocation(); - foundFairies.get(Utils.getProfile()).get(Utils.getLocationRaw()).add(fairySoulPos); - }); + .filter(FairySouls::isFairySoulNotFound) + .min(Comparator.comparingDouble(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()))) + .filter(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()) <= 16) + .ifPresent(fairySoulPos -> { + initializeFoundFairiesForCurrentProfileAndLocation(); + foundFairies.get(Utils.getProfile()).get(Utils.getLocationRaw()).add(fairySoulPos); + }); } - public static void markAllFairiesFound() { + public static void markAllFairiesOnCurrentIslandFound() { initializeFoundFairiesForCurrentProfileAndLocation(); foundFairies.get(Utils.getProfile()).get(Utils.getLocationRaw()).addAll(fairySouls.get(Utils.getLocationRaw())); } - public static void markAllFairiesNotFound() { + public static void markAllFairiesOnCurrentIslandMissing() { Map> foundFairiesForProfile = foundFairies.get(Utils.getProfile()); if (foundFairiesForProfile != null) { foundFairiesForProfile.remove(Utils.getLocationRaw()); diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java index 8497041b3c..f1b886c205 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java @@ -1,9 +1,9 @@ package me.xmrvizzy.skyblocker.skyblock.dungeon; import me.xmrvizzy.skyblocker.config.SkyblockerConfig; +import me.xmrvizzy.skyblocker.skyblock.FairySouls; import me.xmrvizzy.skyblocker.utils.chat.ChatFilterResult; import me.xmrvizzy.skyblocker.utils.chat.ChatPatternListener; -import me.xmrvizzy.skyblocker.skyblock.FairySouls; import net.minecraft.client.MinecraftClient; import net.minecraft.client.network.ClientPlayerEntity; import net.minecraft.text.Text; @@ -77,24 +77,25 @@ private void updateSolutions(String question) { answers.put("Which of these enemies does not spawn in the Spider's Den?", new String[]{"Zombie Spider", "Cave Spider", "Wither Skeleton", "Dashing Spooder", "Broodfather", "Night Spider"}); answers.put("Which of these monsters only spawns at night?", new String[]{"Zombie Villager", "Ghast"}); answers.put("Which of these is not a dragon in The End?", new String[]{"Zoomer Dragon", "Weak Dragon", "Stonk Dragon", "Holy Dragon", "Boomer Dragon", "Booger Dragon", "Older Dragon", "Elder Dragon", "Stable Dragon", "Professor Dragon"}); + FairySouls.runAsyncAfterFairySoulsLoad(() -> { - answers.put("How many total Fairy Souls are there?", getFairySoulsSizeString(null)); - answers.put("How many Fairy Souls are there in Spider's Den?", getFairySoulsSizeString("combat_1")); - answers.put("How many Fairy Souls are there in The End?", getFairySoulsSizeString("combat_3")); - answers.put("How many Fairy Souls are there in The Farming Islands?", getFairySoulsSizeString("farming_1")); - answers.put("How many Fairy Souls are there in Crimson Isle?", getFairySoulsSizeString("crimson_isle")); - answers.put("How many Fairy Souls are there in The Park?", getFairySoulsSizeString("foraging_1")); - answers.put("How many Fairy Souls are there in Jerry's Workshop?", getFairySoulsSizeString("winter")); - answers.put("How many Fairy Souls are there in Hub?", getFairySoulsSizeString("hub")); - answers.put("How many Fairy Souls are there in The Hub?", getFairySoulsSizeString("hub")); - answers.put("How many Fairy Souls are there in Deep Caverns?", getFairySoulsSizeString("mining_2")); - answers.put("How many Fairy Souls are there in Gold Mine?", getFairySoulsSizeString("mining_1")); - answers.put("How many Fairy Souls are there in Dungeon Hub?", getFairySoulsSizeString("dungeon_hub")); + answers.put("How many total Fairy Souls are there?", getFairySoulsAmountString(null)); + answers.put("How many Fairy Souls are there in Spider's Den?", getFairySoulsAmountString("combat_1")); + answers.put("How many Fairy Souls are there in The End?", getFairySoulsAmountString("combat_3")); + answers.put("How many Fairy Souls are there in The Farming Islands?", getFairySoulsAmountString("farming_1")); + answers.put("How many Fairy Souls are there in Crimson Isle?", getFairySoulsAmountString("crimson_isle")); + answers.put("How many Fairy Souls are there in The Park?", getFairySoulsAmountString("foraging_1")); + answers.put("How many Fairy Souls are there in Jerry's Workshop?", getFairySoulsAmountString("winter")); + answers.put("How many Fairy Souls are there in Hub?", getFairySoulsAmountString("hub")); + answers.put("How many Fairy Souls are there in The Hub?", getFairySoulsAmountString("hub")); + answers.put("How many Fairy Souls are there in Deep Caverns?", getFairySoulsAmountString("mining_2")); + answers.put("How many Fairy Souls are there in Gold Mine?", getFairySoulsAmountString("mining_1")); + answers.put("How many Fairy Souls are there in Dungeon Hub?", getFairySoulsAmountString("dungeon_hub")); }); } @NotNull - private static String[] getFairySoulsSizeString(@Nullable String location) { - return new String[]{"%d Fairy Souls".formatted(FairySouls.getFairySoulsSize(location))}; + private static String[] getFairySoulsAmountString(@Nullable String location) { + return new String[]{"%d Fairy Souls".formatted(FairySouls.getFairySoulsAmount(location))}; } } 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 89329c6c08..14bc1db4c5 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/shortcut/Shortcuts.java @@ -63,7 +63,7 @@ protected static void loadShortcuts() { 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); + LOGGER.warn("[Skyblocker] Shortcuts file not found, using default shortcuts. This is normal when using for the first time."); } catch (IOException e) { LOGGER.error("[Skyblocker] Failed to load shortcuts file", e); } diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java new file mode 100644 index 0000000000..6f7f1ee693 --- /dev/null +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java @@ -0,0 +1,141 @@ +package me.xmrvizzy.skyblocker.skyblock.spidersden; + +import com.google.gson.JsonArray; +import com.google.gson.JsonElement; +import com.google.gson.JsonObject; +import com.google.gson.JsonParser; +import me.xmrvizzy.skyblocker.SkyblockerMod; +import me.xmrvizzy.skyblocker.config.SkyblockerConfig; +import me.xmrvizzy.skyblocker.utils.PosUtils; +import me.xmrvizzy.skyblocker.utils.Utils; +import me.xmrvizzy.skyblocker.utils.render.RenderHelper; +import net.fabricmc.fabric.api.client.event.lifecycle.v1.ClientLifecycleEvents; +import net.fabricmc.fabric.api.client.message.v1.ClientReceiveMessageEvents; +import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderContext; +import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderEvents; +import net.minecraft.client.MinecraftClient; +import net.minecraft.entity.player.PlayerEntity; +import net.minecraft.text.Text; +import net.minecraft.util.DyeColor; +import net.minecraft.util.Identifier; +import net.minecraft.util.math.BlockPos; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; + +import java.io.*; +import java.util.*; + +public class Relics { + private static final Logger LOGGER = LoggerFactory.getLogger(Relics.class); + private static int totalRelics = 0; + private static final List relics = new ArrayList<>(); + private static final Map> foundRelics = new HashMap<>(); + + public static void init() { + ClientLifecycleEvents.CLIENT_STARTED.register(Relics::onClientStarted); + ClientLifecycleEvents.CLIENT_STOPPING.register(Relics::onClientStopping); + ClientReceiveMessageEvents.GAME.register(Relics::onChatMessage); + WorldRenderEvents.AFTER_TRANSLUCENT.register(Relics::render); + } + + private static void onClientStarted(MinecraftClient client) { + try { + BufferedReader reader = client.getResourceManager().openAsReader(new Identifier(SkyblockerMod.NAMESPACE, "spidersden/relics.json")); + for (Map.Entry json : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { + if (json.getKey().equals("total")) { + totalRelics = json.getValue().getAsInt(); + } else if (json.getKey().equals("locations")) { + for (JsonElement locationJson : json.getValue().getAsJsonArray().asList()) { + JsonObject posData = locationJson.getAsJsonObject(); + relics.add(new BlockPos(posData.get("x").getAsInt(), posData.get("y").getAsInt(), posData.get("z").getAsInt())); + } + } + } + reader.close(); + LOGGER.info("[Skyblocker] Loaded relics locations"); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load relics locations", e); + } + + try { + BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile())); + for (Map.Entry profileJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { + Set foundRelicsForProfile = new HashSet<>(); + for (JsonElement foundRelicsJson : profileJson.getValue().getAsJsonArray().asList()) { + foundRelicsForProfile.add(PosUtils.parsePosString(foundRelicsJson.getAsString())); + } + foundRelics.put(profileJson.getKey(), foundRelicsForProfile); + } + reader.close(); + LOGGER.info("[Skyblocker] Loaded found relics"); + } catch (FileNotFoundException ignored) { + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load found relics", e); + } + } + + private static void onClientStopping(MinecraftClient client) { + try { + BufferedWriter writer = new BufferedWriter(new FileWriter(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile())); + JsonObject json = new JsonObject(); + for (Map.Entry> foundRelicsForProfile : foundRelics.entrySet()) { + JsonArray foundRelicsJson = new JsonArray(); + for (BlockPos foundRelic : foundRelicsForProfile.getValue()) { + foundRelicsJson.add(PosUtils.getPosString(foundRelic)); + } + json.add(foundRelicsForProfile.getKey(), foundRelicsJson); + } + SkyblockerMod.GSON.toJson(json, writer); + writer.close(); + LOGGER.info("[Skyblocker] Saved found relics"); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to write found relics to file", e); + } + } + + private static void onChatMessage(Text text, boolean overlay) { + String message = text.getString(); + if (message.equals("You've already found this relic!") || message.startsWith("+10,000 Coins! (") && message.endsWith("/28 Relics)")) { + markClosestRelicFound(); + } + } + + private static void render(WorldRenderContext context) { + SkyblockerConfig.Relics config = SkyblockerConfig.get().locations.spidersden.relics; + + if (config.enableRelicsHelper && Utils.getLocationRaw().equals("combat_1")) { + for (BlockPos fairySoulPos : relics) { + boolean isRelicFound = isRelicFound(fairySoulPos); + if (isRelicFound && !config.highlightFoundRelics) { + continue; + } + float[] colorComponents = isRelicFound ? DyeColor.BROWN.getColorComponents() : DyeColor.YELLOW.getColorComponents(); + RenderHelper.renderFilledThroughWallsWithBeaconBeam(context, fairySoulPos, colorComponents, 0.5F); + } + } + } + + private static boolean isRelicFound(BlockPos pos) { + Set foundRelicsForProfile = foundRelics.get(Utils.getProfile()); + if (foundRelicsForProfile == null) { + return false; + } + return foundRelicsForProfile.contains(pos); + } + + private static void markClosestRelicFound() { + PlayerEntity player = MinecraftClient.getInstance().player; + if (player == null) { + LOGGER.warn("[Skyblocker] Failed to mark closest relic as found because player is null"); + return; + } + relics.stream() + .filter((relicPos) -> !Relics.isRelicFound(relicPos)) + .min(Comparator.comparingDouble(relicPos -> relicPos.getSquaredDistance(player.getPos()))) + .filter(relicPos -> relicPos.getSquaredDistance(player.getPos()) <= 16) + .ifPresent(relicPos -> { + foundRelics.computeIfAbsent(Utils.getProfile(), profileKey -> new HashSet<>()); + foundRelics.get(Utils.getProfile()).add(relicPos); + }); + } +} diff --git a/src/main/java/me/xmrvizzy/skyblocker/utils/PosUtils.java b/src/main/java/me/xmrvizzy/skyblocker/utils/PosUtils.java new file mode 100644 index 0000000000..4f32292c6b --- /dev/null +++ b/src/main/java/me/xmrvizzy/skyblocker/utils/PosUtils.java @@ -0,0 +1,14 @@ +package me.xmrvizzy.skyblocker.utils; + +import net.minecraft.util.math.BlockPos; + +public final class PosUtils { + public static BlockPos parsePosString(String posData) { + String[] posArray = posData.split(","); + return new BlockPos(Integer.parseInt(posArray[0]), Integer.parseInt(posArray[1]), Integer.parseInt(posArray[2])); + } + + public static String getPosString(BlockPos blockPos) { + return blockPos.getX() + "," + blockPos.getY() + "," + blockPos.getZ(); + } +} diff --git a/src/main/resources/assets/skyblocker/lang/en_us.json b/src/main/resources/assets/skyblocker/lang/en_us.json index cdaa760249..d8d1050751 100644 --- a/src/main/resources/assets/skyblocker/lang/en_us.json +++ b/src/main/resources/assets/skyblocker/lang/en_us.json @@ -209,6 +209,10 @@ "text.autoconfig.skyblocker.option.locations.barn": "Barn", "text.autoconfig.skyblocker.option.locations.barn.solveHungryHiker": "Solve Hungry Hiker", "text.autoconfig.skyblocker.option.locations.barn.solveTreasureHunter": "Solve Treasure Hunter", + "text.autoconfig.skyblocker.option.locations.spidersden": "Spider's Den", + "text.autoconfig.skyblocker.option.locations.spidersden.relics": "Hidden Relics Helper", + "text.autoconfig.skyblocker.option.locations.spidersden.relics.enableRelicsHelper": "Enable Hidden Relics Helper", + "text.autoconfig.skyblocker.option.locations.spidersden.relics.highlightFoundRelics": "Highlight found relics", "text.autoconfig.skyblocker.option.locations.dungeons": "Dungeons", "text.autoconfig.skyblocker.option.locations.dungeons.secretWaypoints": "Dungeon Secret Waypoints", "text.autoconfig.skyblocker.option.locations.dungeons.secretWaypoints.enableSecretWaypoints": "Enable Dungeon Secret Waypoints", diff --git a/src/main/resources/assets/skyblocker/spidersden/relics.json b/src/main/resources/assets/skyblocker/spidersden/relics.json new file mode 100644 index 0000000000..4610423b43 --- /dev/null +++ b/src/main/resources/assets/skyblocker/spidersden/relics.json @@ -0,0 +1,149 @@ +{ + "source": { + "link": "https://hypixel-skyblock.fandom.com/wiki/Relics", + "license": "CC-BY-SA " + }, + "total": 28, + "locations": [ + { + "x": -342, + "y": 122, + "z": -253 + }, + { + "x": -384, + "y": 89, + "z": -225 + }, + { + "x": -274, + "y": 100, + "z": -178 + }, + { + "x": -178, + "y": 136, + "z": -297 + }, + { + "x": -147, + "y": 83, + "z": -335 + }, + { + "x": -188, + "y": 80, + "z": -346 + }, + { + "x": -206, + "y": 63, + "z": -301 + }, + { + "x": -342, + "y": 89, + "z": -221 + }, + { + "x": -355, + "y": 86, + "z": -213 + }, + { + "x": -372, + "y": 89, + "z": -242 + }, + { + "x": -354, + "y": 73, + "z": -285 + }, + { + "x": -317, + "y": 69, + "z": -273 + }, + { + "x": -296, + "y": 37, + "z": -270 + }, + { + "x": -275, + "y": 64, + "z": -272 + }, + { + "x": -303, + "y": 71, + "z": -318 + }, + { + "x": -311, + "y": 69, + "z": -251 + }, + { + "x": -348, + "y": 65, + "z": -202 + }, + { + "x": -328, + "y": 50, + "z": -238 + }, + { + "x": -313, + "y": 58, + "z": -250 + }, + { + "x": -300, + "y": 51, + "z": -254 + }, + { + "x": -284, + "y": 49, + "z": -234 + }, + { + "x": -300, + "y": 50, + "z": -218 + }, + { + "x": -236, + "y": 51, + "z": -239 + }, + { + "x": -183, + "y": 51, + "z": -252 + }, + { + "x": -217, + "y": 58, + "z": -304 + }, + { + "x": -272, + "y": 48, + "z": -291 + }, + { + "x": -225, + "y": 70, + "z": -316 + }, + { + "x": -254, + "y": 57, + "z": -279 + } + ] +} From 7ca3ad2eabafce7f07949f6ee9904c9741c2ca2e Mon Sep 17 00:00:00 2001 From: Grayray75 <69988482+Grayray75@users.noreply.github.com> Date: Sat, 16 Sep 2023 22:11:48 +0200 Subject: [PATCH 2/5] Changes 1 --- .../skyblocker/config/SkyblockerConfig.java | 8 ++--- .../skyblocker/skyblock/FairySouls.java | 35 ++++++++----------- .../skyblocker/skyblock/dungeon/Trivia.java | 28 +++++++-------- .../skyblock/spidersden/Relics.java | 26 +++++--------- 4 files changed, 42 insertions(+), 55 deletions(-) diff --git a/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java b/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java index d6e3f0fec0..476af0a80b 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java +++ b/src/main/java/me/xmrvizzy/skyblocker/config/SkyblockerConfig.java @@ -438,10 +438,6 @@ public static class Locations { @ConfigEntry.Gui.CollapsibleObject() public Barn barn = new Barn(); - @ConfigEntry.Category("spidersden") - @ConfigEntry.Gui.CollapsibleObject() - public SpidersDen spidersden = new SpidersDen(); - @ConfigEntry.Category("dungeons") @ConfigEntry.Gui.CollapsibleObject() public Dungeons dungeons = new Dungeons(); @@ -453,6 +449,10 @@ public static class Locations { @ConfigEntry.Category("rift") @ConfigEntry.Gui.CollapsibleObject() public Rift rift = new Rift(); + + @ConfigEntry.Category("spidersden") + @ConfigEntry.Gui.CollapsibleObject() + public SpidersDen spidersDen = new SpidersDen(); } public static class Dungeons { diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java index f1de63e58d..be1c1dcdef 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java @@ -49,13 +49,13 @@ public static CompletableFuture runAsyncAfterFairySoulsLoad(Runnable runna return fairySoulsLoaded.thenRunAsync(runnable); } - public static int getFairySoulsAmount(@Nullable String location) { + public static int getFairySoulsSize(@Nullable String location) { return location == null ? maxSouls : fairySouls.get(location).size(); } public static void init() { loadFairySouls(); - ClientLifecycleEvents.CLIENT_STOPPING.register(FairySouls::saveFairySouls); + ClientLifecycleEvents.CLIENT_STOPPING.register(FairySouls::saveFoundFairySouls); ClientReceiveMessageEvents.GAME.register(FairySouls::onChatMessage); WorldRenderEvents.AFTER_TRANSLUCENT.register(FairySouls::render); ClientCommandRegistrationCallback.EVENT.register(FairySouls::registerCommands); @@ -63,8 +63,7 @@ public static void init() { private static void loadFairySouls() { fairySoulsLoaded = NEURepo.runAsyncAfterLoad(() -> { - try { - BufferedReader reader = new BufferedReader(new FileReader(NEURepo.LOCAL_REPO_DIR.resolve("constants").resolve("fairy_souls.json").toFile())); + try (BufferedReader reader = new BufferedReader(new FileReader(NEURepo.LOCAL_REPO_DIR.resolve("constants").resolve("fairy_souls.json").toFile()))) { for (Map.Entry fairySoulJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { if (fairySoulJson.getKey().equals("//") || fairySoulJson.getKey().equals("Max Souls")) { if (fairySoulJson.getKey().equals("Max Souls")) { @@ -78,14 +77,12 @@ private static void loadFairySouls() { } fairySouls.put(fairySoulJson.getKey(), fairySoulsForLocation.build()); } - reader.close(); - LOGGER.info("[Skyblocker] Loaded fairy soul locations"); + LOGGER.debug("[Skyblocker] Loaded fairy soul locations"); } catch (IOException e) { LOGGER.error("[Skyblocker] Failed to load fairy soul locations", e); } - try { - BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile())); + try (BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile()))) { for (Map.Entry foundFairiesForProfileJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { Map> foundFairiesForProfile = new HashMap<>(); for (Map.Entry foundFairiesForLocationJson : foundFairiesForProfileJson.getValue().getAsJsonObject().asMap().entrySet()) { @@ -97,8 +94,7 @@ private static void loadFairySouls() { } foundFairies.put(foundFairiesForProfileJson.getKey(), foundFairiesForProfile); } - reader.close(); - LOGGER.info("[Skyblocker] Loaded found fairy souls"); + LOGGER.debug("[Skyblocker] Loaded found fairy souls"); } catch (FileNotFoundException ignored) { } catch (IOException e) { LOGGER.error("[Skyblocker] Failed to load found fairy souls", e); @@ -106,9 +102,8 @@ private static void loadFairySouls() { }); } - private static void saveFairySouls(MinecraftClient client) { - try { - BufferedWriter writer = new BufferedWriter(new FileWriter(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile())); + private static void saveFoundFairySouls(MinecraftClient client) { + try (BufferedWriter writer = new BufferedWriter(new FileWriter(SkyblockerMod.CONFIG_DIR.resolve("found_fairy_souls.json").toFile()))) { JsonObject foundFairiesJson = new JsonObject(); for (Map.Entry>> foundFairiesForProfile : foundFairies.entrySet()) { JsonObject foundFairiesForProfileJson = new JsonObject(); @@ -144,13 +139,6 @@ private static void registerCommands(CommandDispatcher> foundFairiesForProfile = foundFairies.get(Utils.getProfile()); if (foundFairiesForProfile == null) { diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java index f1b886c205..f4ea1ee9c1 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java @@ -79,23 +79,23 @@ private void updateSolutions(String question) { answers.put("Which of these is not a dragon in The End?", new String[]{"Zoomer Dragon", "Weak Dragon", "Stonk Dragon", "Holy Dragon", "Boomer Dragon", "Booger Dragon", "Older Dragon", "Elder Dragon", "Stable Dragon", "Professor Dragon"}); FairySouls.runAsyncAfterFairySoulsLoad(() -> { - answers.put("How many total Fairy Souls are there?", getFairySoulsAmountString(null)); - answers.put("How many Fairy Souls are there in Spider's Den?", getFairySoulsAmountString("combat_1")); - answers.put("How many Fairy Souls are there in The End?", getFairySoulsAmountString("combat_3")); - answers.put("How many Fairy Souls are there in The Farming Islands?", getFairySoulsAmountString("farming_1")); - answers.put("How many Fairy Souls are there in Crimson Isle?", getFairySoulsAmountString("crimson_isle")); - answers.put("How many Fairy Souls are there in The Park?", getFairySoulsAmountString("foraging_1")); - answers.put("How many Fairy Souls are there in Jerry's Workshop?", getFairySoulsAmountString("winter")); - answers.put("How many Fairy Souls are there in Hub?", getFairySoulsAmountString("hub")); - answers.put("How many Fairy Souls are there in The Hub?", getFairySoulsAmountString("hub")); - answers.put("How many Fairy Souls are there in Deep Caverns?", getFairySoulsAmountString("mining_2")); - answers.put("How many Fairy Souls are there in Gold Mine?", getFairySoulsAmountString("mining_1")); - answers.put("How many Fairy Souls are there in Dungeon Hub?", getFairySoulsAmountString("dungeon_hub")); + answers.put("How many total Fairy Souls are there?", getFairySoulsSizeString(null)); + answers.put("How many Fairy Souls are there in Spider's Den?", getFairySoulsSizeString("combat_1")); + answers.put("How many Fairy Souls are there in The End?", getFairySoulsSizeString("combat_3")); + answers.put("How many Fairy Souls are there in The Farming Islands?", getFairySoulsSizeString("farming_1")); + answers.put("How many Fairy Souls are there in Crimson Isle?", getFairySoulsSizeString("crimson_isle")); + answers.put("How many Fairy Souls are there in The Park?", getFairySoulsSizeString("foraging_1")); + answers.put("How many Fairy Souls are there in Jerry's Workshop?", getFairySoulsSizeString("winter")); + answers.put("How many Fairy Souls are there in Hub?", getFairySoulsSizeString("hub")); + answers.put("How many Fairy Souls are there in The Hub?", getFairySoulsSizeString("hub")); + answers.put("How many Fairy Souls are there in Deep Caverns?", getFairySoulsSizeString("mining_2")); + answers.put("How many Fairy Souls are there in Gold Mine?", getFairySoulsSizeString("mining_1")); + answers.put("How many Fairy Souls are there in Dungeon Hub?", getFairySoulsSizeString("dungeon_hub")); }); } @NotNull - private static String[] getFairySoulsAmountString(@Nullable String location) { - return new String[]{"%d Fairy Souls".formatted(FairySouls.getFairySoulsAmount(location))}; + private static String[] getFairySoulsSizeString(@Nullable String location) { + return new String[]{"%d Fairy Souls".formatted(FairySouls.getFairySoulsSize(location))}; } } diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java index 6f7f1ee693..c09d895fe8 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java @@ -33,14 +33,13 @@ public class Relics { public static void init() { ClientLifecycleEvents.CLIENT_STARTED.register(Relics::onClientStarted); - ClientLifecycleEvents.CLIENT_STOPPING.register(Relics::onClientStopping); + ClientLifecycleEvents.CLIENT_STOPPING.register(Relics::saveFoundRelics); ClientReceiveMessageEvents.GAME.register(Relics::onChatMessage); WorldRenderEvents.AFTER_TRANSLUCENT.register(Relics::render); } private static void onClientStarted(MinecraftClient client) { - try { - BufferedReader reader = client.getResourceManager().openAsReader(new Identifier(SkyblockerMod.NAMESPACE, "spidersden/relics.json")); + try (BufferedReader reader = client.getResourceManager().openAsReader(new Identifier(SkyblockerMod.NAMESPACE, "spidersden/relics.json"))) { for (Map.Entry json : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { if (json.getKey().equals("total")) { totalRelics = json.getValue().getAsInt(); @@ -51,14 +50,12 @@ private static void onClientStarted(MinecraftClient client) { } } } - reader.close(); LOGGER.info("[Skyblocker] Loaded relics locations"); } catch (IOException e) { LOGGER.error("[Skyblocker] Failed to load relics locations", e); } - try { - BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile())); + try (BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile()))) { for (Map.Entry profileJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { Set foundRelicsForProfile = new HashSet<>(); for (JsonElement foundRelicsJson : profileJson.getValue().getAsJsonArray().asList()) { @@ -66,17 +63,15 @@ private static void onClientStarted(MinecraftClient client) { } foundRelics.put(profileJson.getKey(), foundRelicsForProfile); } - reader.close(); - LOGGER.info("[Skyblocker] Loaded found relics"); + LOGGER.debug("[Skyblocker] Loaded found relics"); } catch (FileNotFoundException ignored) { } catch (IOException e) { LOGGER.error("[Skyblocker] Failed to load found relics", e); } } - private static void onClientStopping(MinecraftClient client) { - try { - BufferedWriter writer = new BufferedWriter(new FileWriter(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile())); + private static void saveFoundRelics(MinecraftClient client) { + try (BufferedWriter writer = new BufferedWriter(new FileWriter(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile()))) { JsonObject json = new JsonObject(); for (Map.Entry> foundRelicsForProfile : foundRelics.entrySet()) { JsonArray foundRelicsJson = new JsonArray(); @@ -86,8 +81,7 @@ private static void onClientStopping(MinecraftClient client) { json.add(foundRelicsForProfile.getKey(), foundRelicsJson); } SkyblockerMod.GSON.toJson(json, writer); - writer.close(); - LOGGER.info("[Skyblocker] Saved found relics"); + LOGGER.debug("[Skyblocker] Saved found relics"); } catch (IOException e) { LOGGER.error("[Skyblocker] Failed to write found relics to file", e); } @@ -101,14 +95,12 @@ private static void onChatMessage(Text text, boolean overlay) { } private static void render(WorldRenderContext context) { - SkyblockerConfig.Relics config = SkyblockerConfig.get().locations.spidersden.relics; + SkyblockerConfig.Relics config = SkyblockerConfig.get().locations.spidersDen.relics; if (config.enableRelicsHelper && Utils.getLocationRaw().equals("combat_1")) { for (BlockPos fairySoulPos : relics) { boolean isRelicFound = isRelicFound(fairySoulPos); - if (isRelicFound && !config.highlightFoundRelics) { - continue; - } + if (isRelicFound && !config.highlightFoundRelics) continue; float[] colorComponents = isRelicFound ? DyeColor.BROWN.getColorComponents() : DyeColor.YELLOW.getColorComponents(); RenderHelper.renderFilledThroughWallsWithBeaconBeam(context, fairySoulPos, colorComponents, 0.5F); } From 926502768c4691025e8416981be554c500746bf2 Mon Sep 17 00:00:00 2001 From: Grayray75 <69988482+Grayray75@users.noreply.github.com> Date: Sat, 16 Sep 2023 22:15:07 +0200 Subject: [PATCH 3/5] Revert some changes --- .../xmrvizzy/skyblocker/skyblock/FairySouls.java | 14 +++++++------- .../skyblocker/skyblock/dungeon/Trivia.java | 3 +-- 2 files changed, 8 insertions(+), 9 deletions(-) diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java index be1c1dcdef..5ad6eb8399 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java @@ -154,13 +154,6 @@ private static void render(WorldRenderContext context) { } } - private static void onChatMessage(Text text, boolean overlay) { - String message = text.getString(); - if (message.equals("You have already found that Fairy Soul!") || message.equals("§d§lSOUL! §fYou found a §dFairy Soul§f!")) { - markClosestFairyFound(); - } - } - private static boolean isFairySoulNotFound(BlockPos fairySoulPos) { Map> foundFairiesForProfile = foundFairies.get(Utils.getProfile()); if (foundFairiesForProfile == null) { @@ -173,6 +166,13 @@ private static boolean isFairySoulNotFound(BlockPos fairySoulPos) { return !foundFairiesForProfileAndLocation.contains(fairySoulPos); } + private static void onChatMessage(Text text, boolean overlay) { + String message = text.getString(); + if (message.equals("You have already found that Fairy Soul!") || message.equals("§d§lSOUL! §fYou found a §dFairy Soul§f!")) { + markClosestFairyFound(); + } + } + private static void markClosestFairyFound() { PlayerEntity player = MinecraftClient.getInstance().player; if (player == null) { diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java index f4ea1ee9c1..8497041b3c 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/dungeon/Trivia.java @@ -1,9 +1,9 @@ package me.xmrvizzy.skyblocker.skyblock.dungeon; import me.xmrvizzy.skyblocker.config.SkyblockerConfig; -import me.xmrvizzy.skyblocker.skyblock.FairySouls; import me.xmrvizzy.skyblocker.utils.chat.ChatFilterResult; import me.xmrvizzy.skyblocker.utils.chat.ChatPatternListener; +import me.xmrvizzy.skyblocker.skyblock.FairySouls; import net.minecraft.client.MinecraftClient; import net.minecraft.client.network.ClientPlayerEntity; import net.minecraft.text.Text; @@ -77,7 +77,6 @@ private void updateSolutions(String question) { answers.put("Which of these enemies does not spawn in the Spider's Den?", new String[]{"Zombie Spider", "Cave Spider", "Wither Skeleton", "Dashing Spooder", "Broodfather", "Night Spider"}); answers.put("Which of these monsters only spawns at night?", new String[]{"Zombie Villager", "Ghast"}); answers.put("Which of these is not a dragon in The End?", new String[]{"Zoomer Dragon", "Weak Dragon", "Stonk Dragon", "Holy Dragon", "Boomer Dragon", "Booger Dragon", "Older Dragon", "Elder Dragon", "Stable Dragon", "Professor Dragon"}); - FairySouls.runAsyncAfterFairySoulsLoad(() -> { answers.put("How many total Fairy Souls are there?", getFairySoulsSizeString(null)); answers.put("How many Fairy Souls are there in Spider's Den?", getFairySoulsSizeString("combat_1")); From b0f8a76671e1f65aa1e865486c5d003559974800 Mon Sep 17 00:00:00 2001 From: Grayray75 <69988482+Grayray75@users.noreply.github.com> Date: Sun, 17 Sep 2023 13:18:57 +0200 Subject: [PATCH 4/5] Update Relics.java --- .../me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java index c09d895fe8..885d5d1c04 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java @@ -109,10 +109,7 @@ private static void render(WorldRenderContext context) { private static boolean isRelicFound(BlockPos pos) { Set foundRelicsForProfile = foundRelics.get(Utils.getProfile()); - if (foundRelicsForProfile == null) { - return false; - } - return foundRelicsForProfile.contains(pos); + return (foundRelicsForProfile == null) ? false : foundRelicsForProfile.contains(pos); } private static void markClosestRelicFound() { From e23a93bab7678b54d57062908dd0e9b780b8ba3f Mon Sep 17 00:00:00 2001 From: Kevinthegreat <92656833+kevinthegreat1@users.noreply.github.com> Date: Sun, 17 Sep 2023 21:47:37 -0400 Subject: [PATCH 5/5] Refactor FairySouls and Relics --- .../skyblocker/skyblock/FairySouls.java | 68 ++++----- .../skyblock/spidersden/Relics.java | 130 ++++++++++++------ .../assets/skyblocker/lang/en_us.json | 14 +- 3 files changed, 128 insertions(+), 84 deletions(-) diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java index 5ad6eb8399..fcd6be7aa6 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/FairySouls.java @@ -41,6 +41,7 @@ public class FairySouls { private static final Map> fairySouls = new HashMap<>(); private static final Map>> foundFairies = new HashMap<>(); + @SuppressWarnings("UnusedReturnValue") public static CompletableFuture runAsyncAfterFairySoulsLoad(Runnable runnable) { if (fairySoulsLoaded == null) { LOGGER.error("Fairy Souls have not being initialized yet! Please ensure the Fairy Souls module is initialized before modules calling this method in SkyblockerMod#onInitializeClient. This error can be safely ignore in a test environment."); @@ -56,9 +57,9 @@ public static int getFairySoulsSize(@Nullable String location) { public static void init() { loadFairySouls(); ClientLifecycleEvents.CLIENT_STOPPING.register(FairySouls::saveFoundFairySouls); - ClientReceiveMessageEvents.GAME.register(FairySouls::onChatMessage); - WorldRenderEvents.AFTER_TRANSLUCENT.register(FairySouls::render); ClientCommandRegistrationCallback.EVENT.register(FairySouls::registerCommands); + WorldRenderEvents.AFTER_TRANSLUCENT.register(FairySouls::render); + ClientReceiveMessageEvents.GAME.register(FairySouls::onChatMessage); } private static void loadFairySouls() { @@ -126,17 +127,17 @@ private static void saveFoundFairySouls(MinecraftClient client) { private static void registerCommands(CommandDispatcher dispatcher, CommandRegistryAccess registryAccess) { dispatcher.register(literal(SkyblockerMod.NAMESPACE) - .then(literal("fairySouls") - .then(literal("markAllInCurrentIslandFound").executes(context -> { - FairySouls.markAllFairiesOnCurrentIslandFound(); - context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllFound")); - return 1; - })) - .then(literal("markAllInCurrentIslandMissing").executes(context -> { - FairySouls.markAllFairiesOnCurrentIslandMissing(); - context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllMissing")); - return 1; - })))); + .then(literal("fairySouls") + .then(literal("markAllInCurrentIslandFound").executes(context -> { + FairySouls.markAllFairiesOnCurrentIslandFound(); + context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllFound")); + return 1; + })) + .then(literal("markAllInCurrentIslandMissing").executes(context -> { + FairySouls.markAllFairiesOnCurrentIslandMissing(); + context.getSource().sendFeedback(Text.translatable("skyblocker.fairySouls.markAllMissing")); + return 1; + })))); } private static void render(WorldRenderContext context) { @@ -144,7 +145,7 @@ private static void render(WorldRenderContext context) { if (fairySoulsConfig.enableFairySoulsHelper && fairySoulsLoaded.isDone() && fairySouls.containsKey(Utils.getLocationRaw())) { for (BlockPos fairySoulPos : fairySouls.get(Utils.getLocationRaw())) { - boolean fairySoulNotFound = isFairySoulNotFound(fairySoulPos); + boolean fairySoulNotFound = isFairySoulMissing(fairySoulPos); if (!fairySoulsConfig.highlightFoundSouls && !fairySoulNotFound || fairySoulsConfig.highlightOnlyNearbySouls && fairySoulPos.getSquaredDistance(context.camera().getPos()) > 2500) { continue; } @@ -154,18 +155,6 @@ private static void render(WorldRenderContext context) { } } - private static boolean isFairySoulNotFound(BlockPos fairySoulPos) { - Map> foundFairiesForProfile = foundFairies.get(Utils.getProfile()); - if (foundFairiesForProfile == null) { - return true; - } - Set foundFairiesForProfileAndLocation = foundFairiesForProfile.get(Utils.getLocationRaw()); - if (foundFairiesForProfileAndLocation == null) { - return true; - } - return !foundFairiesForProfileAndLocation.contains(fairySoulPos); - } - private static void onChatMessage(Text text, boolean overlay) { String message = text.getString(); if (message.equals("You have already found that Fairy Soul!") || message.equals("§d§lSOUL! §fYou found a §dFairy Soul§f!")) { @@ -174,19 +163,32 @@ private static void onChatMessage(Text text, boolean overlay) { } private static void markClosestFairyFound() { + if (!fairySoulsLoaded.isDone()) return; PlayerEntity player = MinecraftClient.getInstance().player; if (player == null) { LOGGER.warn("[Skyblocker] Failed to mark closest fairy soul as found because player is null"); return; } fairySouls.get(Utils.getLocationRaw()).stream() - .filter(FairySouls::isFairySoulNotFound) - .min(Comparator.comparingDouble(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()))) - .filter(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()) <= 16) - .ifPresent(fairySoulPos -> { - initializeFoundFairiesForCurrentProfileAndLocation(); - foundFairies.get(Utils.getProfile()).get(Utils.getLocationRaw()).add(fairySoulPos); - }); + .filter(FairySouls::isFairySoulMissing) + .min(Comparator.comparingDouble(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()))) + .filter(fairySoulPos -> fairySoulPos.getSquaredDistance(player.getPos()) <= 16) + .ifPresent(fairySoulPos -> { + initializeFoundFairiesForCurrentProfileAndLocation(); + foundFairies.get(Utils.getProfile()).get(Utils.getLocationRaw()).add(fairySoulPos); + }); + } + + private static boolean isFairySoulMissing(BlockPos fairySoulPos) { + Map> foundFairiesForProfile = foundFairies.get(Utils.getProfile()); + if (foundFairiesForProfile == null) { + return true; + } + Set foundFairiesForProfileAndLocation = foundFairiesForProfile.get(Utils.getLocationRaw()); + if (foundFairiesForProfileAndLocation == null) { + return true; + } + return !foundFairiesForProfileAndLocation.contains(fairySoulPos); } public static void markAllFairiesOnCurrentIslandFound() { diff --git a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java index 885d5d1c04..12ce07150d 100644 --- a/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java +++ b/src/main/java/me/xmrvizzy/skyblocker/skyblock/spidersden/Relics.java @@ -4,16 +4,20 @@ import com.google.gson.JsonElement; import com.google.gson.JsonObject; import com.google.gson.JsonParser; +import com.mojang.brigadier.CommandDispatcher; import me.xmrvizzy.skyblocker.SkyblockerMod; import me.xmrvizzy.skyblocker.config.SkyblockerConfig; import me.xmrvizzy.skyblocker.utils.PosUtils; import me.xmrvizzy.skyblocker.utils.Utils; import me.xmrvizzy.skyblocker.utils.render.RenderHelper; +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.ClientReceiveMessageEvents; import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderContext; import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderEvents; import net.minecraft.client.MinecraftClient; +import net.minecraft.command.CommandRegistryAccess; import net.minecraft.entity.player.PlayerEntity; import net.minecraft.text.Text; import net.minecraft.util.DyeColor; @@ -24,50 +28,58 @@ import java.io.*; import java.util.*; +import java.util.concurrent.CompletableFuture; + +import static net.fabricmc.fabric.api.client.command.v2.ClientCommandManager.literal; public class Relics { private static final Logger LOGGER = LoggerFactory.getLogger(Relics.class); + private static CompletableFuture relicsLoaded; + @SuppressWarnings({"unused", "FieldCanBeLocal"}) private static int totalRelics = 0; private static final List relics = new ArrayList<>(); private static final Map> foundRelics = new HashMap<>(); public static void init() { - ClientLifecycleEvents.CLIENT_STARTED.register(Relics::onClientStarted); + ClientLifecycleEvents.CLIENT_STARTED.register(Relics::loadRelics); ClientLifecycleEvents.CLIENT_STOPPING.register(Relics::saveFoundRelics); - ClientReceiveMessageEvents.GAME.register(Relics::onChatMessage); + ClientCommandRegistrationCallback.EVENT.register(Relics::registerCommands); WorldRenderEvents.AFTER_TRANSLUCENT.register(Relics::render); + ClientReceiveMessageEvents.GAME.register(Relics::onChatMessage); } - private static void onClientStarted(MinecraftClient client) { - try (BufferedReader reader = client.getResourceManager().openAsReader(new Identifier(SkyblockerMod.NAMESPACE, "spidersden/relics.json"))) { - for (Map.Entry json : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { - if (json.getKey().equals("total")) { - totalRelics = json.getValue().getAsInt(); - } else if (json.getKey().equals("locations")) { - for (JsonElement locationJson : json.getValue().getAsJsonArray().asList()) { - JsonObject posData = locationJson.getAsJsonObject(); - relics.add(new BlockPos(posData.get("x").getAsInt(), posData.get("y").getAsInt(), posData.get("z").getAsInt())); + private static void loadRelics(MinecraftClient client) { + relicsLoaded = CompletableFuture.runAsync(() -> { + try (BufferedReader reader = client.getResourceManager().openAsReader(new Identifier(SkyblockerMod.NAMESPACE, "spidersden/relics.json"))) { + for (Map.Entry json : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { + if (json.getKey().equals("total")) { + totalRelics = json.getValue().getAsInt(); + } else if (json.getKey().equals("locations")) { + for (JsonElement locationJson : json.getValue().getAsJsonArray().asList()) { + JsonObject posData = locationJson.getAsJsonObject(); + relics.add(new BlockPos(posData.get("x").getAsInt(), posData.get("y").getAsInt(), posData.get("z").getAsInt())); + } } } + LOGGER.info("[Skyblocker] Loaded relics locations"); + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load relics locations", e); } - LOGGER.info("[Skyblocker] Loaded relics locations"); - } catch (IOException e) { - LOGGER.error("[Skyblocker] Failed to load relics locations", e); - } - try (BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile()))) { - for (Map.Entry profileJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { - Set foundRelicsForProfile = new HashSet<>(); - for (JsonElement foundRelicsJson : profileJson.getValue().getAsJsonArray().asList()) { - foundRelicsForProfile.add(PosUtils.parsePosString(foundRelicsJson.getAsString())); + try (BufferedReader reader = new BufferedReader(new FileReader(SkyblockerMod.CONFIG_DIR.resolve("found_relics.json").toFile()))) { + for (Map.Entry profileJson : JsonParser.parseReader(reader).getAsJsonObject().asMap().entrySet()) { + Set foundRelicsForProfile = new HashSet<>(); + for (JsonElement foundRelicsJson : profileJson.getValue().getAsJsonArray().asList()) { + foundRelicsForProfile.add(PosUtils.parsePosString(foundRelicsJson.getAsString())); + } + foundRelics.put(profileJson.getKey(), foundRelicsForProfile); } - foundRelics.put(profileJson.getKey(), foundRelicsForProfile); + LOGGER.debug("[Skyblocker] Loaded found relics"); + } catch (FileNotFoundException ignored) { + } catch (IOException e) { + LOGGER.error("[Skyblocker] Failed to load found relics", e); } - LOGGER.debug("[Skyblocker] Loaded found relics"); - } catch (FileNotFoundException ignored) { - } catch (IOException e) { - LOGGER.error("[Skyblocker] Failed to load found relics", e); - } + }); } private static void saveFoundRelics(MinecraftClient client) { @@ -87,44 +99,72 @@ private static void saveFoundRelics(MinecraftClient client) { } } - private static void onChatMessage(Text text, boolean overlay) { - String message = text.getString(); - if (message.equals("You've already found this relic!") || message.startsWith("+10,000 Coins! (") && message.endsWith("/28 Relics)")) { - markClosestRelicFound(); - } + private static void registerCommands(CommandDispatcher dispatcher, CommandRegistryAccess registryAccess) { + dispatcher.register(literal(SkyblockerMod.NAMESPACE) + .then(literal("relics") + .then(literal("markAllFound").executes(context -> { + Relics.markAllFound(); + context.getSource().sendFeedback(Text.translatable("skyblocker.relics.markAllFound")); + return 1; + })) + .then(literal("markAllMissing").executes(context -> { + Relics.markAllMissing(); + context.getSource().sendFeedback(Text.translatable("skyblocker.relics.markAllMissing")); + return 1; + })))); } private static void render(WorldRenderContext context) { SkyblockerConfig.Relics config = SkyblockerConfig.get().locations.spidersDen.relics; - if (config.enableRelicsHelper && Utils.getLocationRaw().equals("combat_1")) { + if (config.enableRelicsHelper && relicsLoaded.isDone() && Utils.getLocationRaw().equals("combat_1")) { for (BlockPos fairySoulPos : relics) { - boolean isRelicFound = isRelicFound(fairySoulPos); - if (isRelicFound && !config.highlightFoundRelics) continue; - float[] colorComponents = isRelicFound ? DyeColor.BROWN.getColorComponents() : DyeColor.YELLOW.getColorComponents(); + boolean isRelicMissing = isRelicMissing(fairySoulPos); + if (!isRelicMissing && !config.highlightFoundRelics) continue; + float[] colorComponents = isRelicMissing ? DyeColor.YELLOW.getColorComponents() : DyeColor.BROWN.getColorComponents(); RenderHelper.renderFilledThroughWallsWithBeaconBeam(context, fairySoulPos, colorComponents, 0.5F); } } } - private static boolean isRelicFound(BlockPos pos) { - Set foundRelicsForProfile = foundRelics.get(Utils.getProfile()); - return (foundRelicsForProfile == null) ? false : foundRelicsForProfile.contains(pos); + private static void onChatMessage(Text text, boolean overlay) { + String message = text.getString(); + if (message.equals("You've already found this relic!") || message.startsWith("+10,000 Coins! (") && message.endsWith("/28 Relics)")) { + markClosestRelicFound(); + } } private static void markClosestRelicFound() { + if (!relicsLoaded.isDone()) return; PlayerEntity player = MinecraftClient.getInstance().player; if (player == null) { LOGGER.warn("[Skyblocker] Failed to mark closest relic as found because player is null"); return; } relics.stream() - .filter((relicPos) -> !Relics.isRelicFound(relicPos)) - .min(Comparator.comparingDouble(relicPos -> relicPos.getSquaredDistance(player.getPos()))) - .filter(relicPos -> relicPos.getSquaredDistance(player.getPos()) <= 16) - .ifPresent(relicPos -> { - foundRelics.computeIfAbsent(Utils.getProfile(), profileKey -> new HashSet<>()); - foundRelics.get(Utils.getProfile()).add(relicPos); - }); + .filter(Relics::isRelicMissing) + .min(Comparator.comparingDouble(relicPos -> relicPos.getSquaredDistance(player.getPos()))) + .filter(relicPos -> relicPos.getSquaredDistance(player.getPos()) <= 16) + .ifPresent(relicPos -> { + foundRelics.computeIfAbsent(Utils.getProfile(), profileKey -> new HashSet<>()); + foundRelics.get(Utils.getProfile()).add(relicPos); + }); + } + + private static boolean isRelicMissing(BlockPos relicPos) { + Set foundRelicsForProfile = foundRelics.get(Utils.getProfile()); + return foundRelicsForProfile == null || !foundRelicsForProfile.contains(relicPos); + } + + private static void markAllFound() { + foundRelics.computeIfAbsent(Utils.getProfile(), profileKey -> new HashSet<>()); + foundRelics.get(Utils.getProfile()).addAll(relics); + } + + private static void markAllMissing() { + Set foundRelicsForProfile = foundRelics.get(Utils.getProfile()); + if (foundRelicsForProfile != null) { + foundRelicsForProfile.clear(); + } } } diff --git a/src/main/resources/assets/skyblocker/lang/en_us.json b/src/main/resources/assets/skyblocker/lang/en_us.json index d8d1050751..273cbb31d5 100644 --- a/src/main/resources/assets/skyblocker/lang/en_us.json +++ b/src/main/resources/assets/skyblocker/lang/en_us.json @@ -209,10 +209,10 @@ "text.autoconfig.skyblocker.option.locations.barn": "Barn", "text.autoconfig.skyblocker.option.locations.barn.solveHungryHiker": "Solve Hungry Hiker", "text.autoconfig.skyblocker.option.locations.barn.solveTreasureHunter": "Solve Treasure Hunter", - "text.autoconfig.skyblocker.option.locations.spidersden": "Spider's Den", - "text.autoconfig.skyblocker.option.locations.spidersden.relics": "Hidden Relics Helper", - "text.autoconfig.skyblocker.option.locations.spidersden.relics.enableRelicsHelper": "Enable Hidden Relics Helper", - "text.autoconfig.skyblocker.option.locations.spidersden.relics.highlightFoundRelics": "Highlight found relics", + "text.autoconfig.skyblocker.option.locations.spidersDen": "Spider's Den", + "text.autoconfig.skyblocker.option.locations.spidersDen.relics": "Hidden Relics Helper", + "text.autoconfig.skyblocker.option.locations.spidersDen.relics.enableRelicsHelper": "Enable Hidden Relics Helper", + "text.autoconfig.skyblocker.option.locations.spidersDen.relics.highlightFoundRelics": "Highlight found relics", "text.autoconfig.skyblocker.option.locations.dungeons": "Dungeons", "text.autoconfig.skyblocker.option.locations.dungeons.secretWaypoints": "Dungeon Secret Waypoints", "text.autoconfig.skyblocker.option.locations.dungeons.secretWaypoints.enableSecretWaypoints": "Enable Dungeon Secret Waypoints", @@ -330,8 +330,10 @@ "skyblocker.rift.iceNow": "Ice now!", "skyblocker.rift.mania": "Mania!", "skyblocker.rift.stakeNow": "Stake now!", - "skyblocker.fairySouls.markAllFound": "Marked all fairy souls in the current island as found", - "skyblocker.fairySouls.markAllMissing": "Marked all fairy souls in the current island as missing", + "skyblocker.fairySouls.markAllFound": "§b[§6Skyblocker§b] §rMarked all fairy souls in the current island as found", + "skyblocker.fairySouls.markAllMissing": "§b[§6Skyblocker§b] §rMarked all fairy souls in the current island as missing", + "skyblocker.relics.markAllFound": "§b[§6Skyblocker§b] §rMarked all relics as found", + "skyblocker.relics.markAllMissing": "§b[§6Skyblocker§b] §rMarked all relics as missing", "skyblocker.shortcuts.config": "Shortcuts Config", "skyblocker.shortcuts.notLoaded": "§c§lShortcuts not loaded yet", "skyblocker.shortcuts.command.target": "Target Command",