diff options
13 files changed, 272 insertions, 76 deletions
diff --git a/src/main/java/de/hysky/skyblocker/SkyblockerMod.java b/src/main/java/de/hysky/skyblocker/SkyblockerMod.java index 83f41c0b..3fca09ce 100644 --- a/src/main/java/de/hysky/skyblocker/SkyblockerMod.java +++ b/src/main/java/de/hysky/skyblocker/SkyblockerMod.java @@ -14,6 +14,7 @@ import de.hysky.skyblocker.skyblock.dungeon.puzzle.waterboard.Waterboard; import de.hysky.skyblocker.skyblock.dungeon.secrets.DungeonManager; import de.hysky.skyblocker.skyblock.dungeon.secrets.SecretsTracker; import de.hysky.skyblocker.skyblock.dwarven.DwarvenHud; +import de.hysky.skyblocker.skyblock.end.BeaconHighlighter; import de.hysky.skyblocker.skyblock.item.*; import de.hysky.skyblocker.skyblock.item.tooltip.BackpackPreview; import de.hysky.skyblocker.skyblock.item.tooltip.ItemTooltip; @@ -135,6 +136,7 @@ public class SkyblockerMod implements ClientModInitializer { RenderHelper.init(); containerSolverManager.init(); statusBarTracker.init(); + BeaconHighlighter.init(); Scheduler.INSTANCE.scheduleCyclic(Utils::update, 20); Scheduler.INSTANCE.scheduleCyclic(DiscordRPCManager::updateDataAndPresence, 200); Scheduler.INSTANCE.scheduleCyclic(LividColor::update, 10); diff --git a/src/main/java/de/hysky/skyblocker/config/SkyblockerConfig.java b/src/main/java/de/hysky/skyblocker/config/SkyblockerConfig.java index cff06d32..a7569adb 100644 --- a/src/main/java/de/hysky/skyblocker/config/SkyblockerConfig.java +++ b/src/main/java/de/hysky/skyblocker/config/SkyblockerConfig.java @@ -97,6 +97,7 @@ public class SkyblockerConfig { public QuickNavItem button10 = new QuickNavItem(true, new ItemData("enchanting_table"), "Enchant Item", "/etable"); + @SerialEntry public QuickNavItem button11 = new QuickNavItem(true, new ItemData("anvil"), "Anvil", "/anvil"); @@ -169,7 +170,7 @@ public class SkyblockerConfig { @SerialEntry public boolean hideStatusEffectOverlay = false; - + @SerialEntry public boolean dontStripSkinAlphaValues = true; @@ -944,9 +945,20 @@ public class SkyblockerConfig { public static class Slayer { @SerialEntry + public EndermanSlayer endermanSlayer = new EndermanSlayer(); + + @SerialEntry public VampireSlayer vampireSlayer = new VampireSlayer(); } + public static class EndermanSlayer { + @SerialEntry + public boolean highlightNukekubiHeads = true; + + @SerialEntry + public boolean highlightBeacons = true; + } + public static class VampireSlayer { @SerialEntry public boolean enableEffigyWaypoints = true; diff --git a/src/main/java/de/hysky/skyblocker/config/categories/SlayersCategory.java b/src/main/java/de/hysky/skyblocker/config/categories/SlayersCategory.java index 7df95172..19b30937 100644 --- a/src/main/java/de/hysky/skyblocker/config/categories/SlayersCategory.java +++ b/src/main/java/de/hysky/skyblocker/config/categories/SlayersCategory.java @@ -17,6 +17,26 @@ public class SlayersCategory { return ConfigCategory.createBuilder() .name(Text.translatable("text.autoconfig.skyblocker.category.slayer")) + //Enderman Slayer + .group(OptionGroup.createBuilder() + .name(Text.translatable("text.autoconfig.skyblocker.option.slayer.endermanSlayer")) + .collapsed(true) + .option(Option.<Boolean>createBuilder() + .name(Text.translatable("text.autoconfig.skyblocker.option.slayer.endermanSlayer.highlightNukekubiHeads")) + .binding(defaults.slayer.endermanSlayer.highlightNukekubiHeads, + () -> config.slayer.endermanSlayer.highlightNukekubiHeads, + newValue -> config.slayer.endermanSlayer.highlightNukekubiHeads = newValue) + .controller(ConfigUtils::createBooleanController) + .build()) + .option(Option.<Boolean>createBuilder() + .name(Text.translatable("text.autoconfig.skyblocker.option.slayer.endermanSlayer.highlightBeacons")) + .binding(defaults.slayer.endermanSlayer.highlightBeacons, + () -> config.slayer.endermanSlayer.highlightBeacons, + newValue -> config.slayer.endermanSlayer.highlightBeacons = newValue) + .controller(ConfigUtils::createBooleanController) + .build()) + .build()) + //Vampire Slayer .group(OptionGroup.createBuilder() .name(Text.translatable("text.autoconfig.skyblocker.option.slayer.vampireSlayer")) diff --git a/src/main/java/de/hysky/skyblocker/mixin/ClientPlayNetworkHandlerMixin.java b/src/main/java/de/hysky/skyblocker/mixin/ClientPlayNetworkHandlerMixin.java index a8537088..1f56fe34 100644 --- a/src/main/java/de/hysky/skyblocker/mixin/ClientPlayNetworkHandlerMixin.java +++ b/src/main/java/de/hysky/skyblocker/mixin/ClientPlayNetworkHandlerMixin.java @@ -6,14 +6,18 @@ import com.llamalad7.mixinextras.sugar.Local; import de.hysky.skyblocker.skyblock.FishingHelper; import de.hysky.skyblocker.skyblock.dungeon.DungeonScore; import de.hysky.skyblocker.skyblock.dungeon.secrets.DungeonManager; +import de.hysky.skyblocker.skyblock.end.BeaconHighlighter; import de.hysky.skyblocker.skyblock.waypoint.MythologicalRitual; +import de.hysky.skyblocker.utils.SlayerUtils; import de.hysky.skyblocker.utils.Utils; +import net.minecraft.block.Blocks; import net.minecraft.client.MinecraftClient; import net.minecraft.client.network.ClientPlayNetworkHandler; import net.minecraft.entity.Entity; import net.minecraft.entity.EntityStatuses; import net.minecraft.entity.ItemEntity; import net.minecraft.entity.LivingEntity; +import net.minecraft.network.packet.s2c.play.BlockUpdateS2CPacket; import net.minecraft.network.packet.s2c.play.EntityStatusS2CPacket; import net.minecraft.network.packet.s2c.play.ParticleS2CPacket; import net.minecraft.network.packet.s2c.play.PlaySoundS2CPacket; @@ -27,13 +31,17 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; @Mixin(ClientPlayNetworkHandler.class) public abstract class ClientPlayNetworkHandlerMixin { - - @Inject(method = "onPlaySound", at = @At("RETURN")) - private void skyblocker$onPlaySound(PlaySoundS2CPacket packet, CallbackInfo ci) { - FishingHelper.onSound(packet); + @Inject(method = "onBlockUpdate", at = @At("RETURN")) + private void skyblocker$onBlockUpdate(BlockUpdateS2CPacket packet, CallbackInfo ci) { + if (Utils.isInTheEnd() && SlayerUtils.isInSlayer()) { + BeaconHighlighter.beaconPositions.remove(packet.getPos()); + if (packet.getState().isOf(Blocks.BEACON)) { + BeaconHighlighter.beaconPositions.add(packet.getPos()); + } + } } - @ModifyVariable(method = "onItemPickupAnimation", at = @At(value = "STORE", ordinal = 0)) + @ModifyVariable(method = "onItemPickupAnimation", at = @At(value = "STORE", ordinal = 0)) private ItemEntity skyblocker$onItemPickup(ItemEntity itemEntity, @Local LivingEntity collector) { DungeonManager.onItemPickup(itemEntity, collector, collector == MinecraftClient.getInstance().player); return itemEntity; @@ -44,14 +52,25 @@ public abstract class ClientPlayNetworkHandlerMixin { return !Utils.isOnHypixel(); } + @ModifyExpressionValue(method = "onEntityStatus", at = @At(value = "INVOKE", target = "Lnet/minecraft/network/packet/s2c/play/EntityStatusS2CPacket;getEntity(Lnet/minecraft/world/World;)Lnet/minecraft/entity/Entity;")) + private Entity skyblocker$onEntityDeath(Entity entity, @Local(argsOnly = true) EntityStatusS2CPacket packet) { + if (packet.getStatus() == EntityStatuses.PLAY_DEATH_SOUND_OR_ADD_PROJECTILE_HIT_PARTICLES) DungeonScore.handleEntityDeath(entity); + return entity; + } + @WrapWithCondition(method = "onPlayerList", at = @At(value = "INVOKE", target = "Lorg/slf4j/Logger;warn(Ljava/lang/String;Ljava/lang/Object;Ljava/lang/Object;)V", remap = false)) private boolean skyblocker$cancelPlayerListWarning(Logger instance, String format, Object arg1, Object arg2) { return !Utils.isOnHypixel(); } - @WrapWithCondition(method = "onTeam", at = @At(value = "INVOKE", target = "Lorg/slf4j/Logger;warn(Ljava/lang/String;[Ljava/lang/Object;)V", remap = false)) - private boolean skyblocker$cancelTeamWarning(Logger instance, String format, Object... arg) { - return !Utils.isOnHypixel(); + @Inject(method = "onPlaySound", at = @At("RETURN")) + private void skyblocker$onPlaySound(PlaySoundS2CPacket packet, CallbackInfo ci) { + FishingHelper.onSound(packet); + } + + @WrapWithCondition(method = "warnOnUnknownPayload", at = @At(value = "INVOKE", target = "Lorg/slf4j/Logger;warn(Ljava/lang/String;Ljava/lang/Object;)V", remap = false)) + private boolean skyblocker$dropBadlionPacketWarnings(Logger instance, String message, Object identifier) { + return !(Utils.isOnHypixel() && ((Identifier) identifier).getNamespace().equals("badlion")); } @WrapWithCondition(method = { "onScoreboardScoreUpdate", "onScoreboardScoreReset" }, at = @At(value = "INVOKE", target = "Lorg/slf4j/Logger;warn(Ljava/lang/String;Ljava/lang/Object;)V", remap = false)) @@ -59,19 +78,13 @@ public abstract class ClientPlayNetworkHandlerMixin { return !Utils.isOnHypixel(); } - @WrapWithCondition(method = "warnOnUnknownPayload", at = @At(value = "INVOKE", target = "Lorg/slf4j/Logger;warn(Ljava/lang/String;Ljava/lang/Object;)V", remap = false)) - private boolean skyblocker$dropBadlionPacketWarnings(Logger instance, String message, Object identifier) { - return !(Utils.isOnHypixel() && ((Identifier) identifier).getNamespace().equals("badlion")); + @WrapWithCondition(method = "onTeam", at = @At(value = "INVOKE", target = "Lorg/slf4j/Logger;warn(Ljava/lang/String;[Ljava/lang/Object;)V", remap = false)) + private boolean skyblocker$cancelTeamWarning(Logger instance, String format, Object... arg) { + return !Utils.isOnHypixel(); } @Inject(method = "onParticle", at = @At("RETURN")) private void skyblocker$onParticle(ParticleS2CPacket packet, CallbackInfo ci) { MythologicalRitual.onParticle(packet); } - - @ModifyExpressionValue(method = "onEntityStatus", at = @At(value = "INVOKE", target = "Lnet/minecraft/network/packet/s2c/play/EntityStatusS2CPacket;getEntity(Lnet/minecraft/world/World;)Lnet/minecraft/entity/Entity;")) - private Entity skyblocker$onEntityDeath(Entity entity, @Local(argsOnly = true) EntityStatusS2CPacket packet) { - if (packet.getStatus() == EntityStatuses.PLAY_DEATH_SOUND_OR_ADD_PROJECTILE_HIT_PARTICLES) DungeonScore.handleEntityDeath(entity); - return entity; - } } diff --git a/src/main/java/de/hysky/skyblocker/skyblock/end/BeaconHighlighter.java b/src/main/java/de/hysky/skyblocker/skyblock/end/BeaconHighlighter.java new file mode 100644 index 00000000..d2269482 --- /dev/null +++ b/src/main/java/de/hysky/skyblocker/skyblock/end/BeaconHighlighter.java @@ -0,0 +1,40 @@ +package de.hysky.skyblocker.skyblock.end; + +import de.hysky.skyblocker.config.SkyblockerConfigManager; +import de.hysky.skyblocker.utils.Utils; +import de.hysky.skyblocker.utils.render.RenderHelper; +import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderContext; +import net.fabricmc.fabric.api.client.rendering.v1.WorldRenderEvents; +import net.minecraft.util.math.BlockPos; + +import java.util.ArrayList; +import java.util.List; + +public class BeaconHighlighter { + public static final List<BlockPos> beaconPositions = new ArrayList<>(); + + /** + * Initializes the beacon highlighting system. + * {@link BeaconHighlighter#render(WorldRenderContext)} is called after translucent rendering. + */ + public static void init() { + WorldRenderEvents.AFTER_TRANSLUCENT.register(BeaconHighlighter::render); + } + + /** + * Renders the beacon glow around it. It is rendered in a red color with 50% opacity, and + * is visible through walls. + * + * @param context An instance of WorldRenderContext for the RenderHelper to use + */ + public static void render(WorldRenderContext context) { + if (Utils.isInTheEnd() && SkyblockerConfigManager.get().slayer.endermanSlayer.highlightBeacons) + beaconPositions.forEach((position) -> RenderHelper.renderFilled( + context, + position, + new float[]{1.0f, 0.0f, 0.0f}, + 0.5f, + false + )); + } +} diff --git a/src/main/java/de/hysky/skyblocker/skyblock/entity/MobGlow.java b/src/main/java/de/hysky/skyblocker/skyblock/entity/MobGlow.java index fa9f6e4f..d0d58606 100644 --- a/src/main/java/de/hysky/skyblocker/skyblock/entity/MobGlow.java +++ b/src/main/java/de/hysky/skyblocker/skyblock/entity/MobGlow.java @@ -1,66 +1,81 @@ package de.hysky.skyblocker.skyblock.entity; -import java.util.List; - import de.hysky.skyblocker.config.SkyblockerConfigManager; import de.hysky.skyblocker.skyblock.dungeon.LividColor; +import de.hysky.skyblocker.utils.SlayerUtils; import de.hysky.skyblocker.utils.Utils; import de.hysky.skyblocker.utils.render.culling.OcclusionCulling; import net.minecraft.entity.Entity; import net.minecraft.entity.decoration.ArmorStandEntity; import net.minecraft.entity.passive.BatEntity; import net.minecraft.entity.player.PlayerEntity; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NbtCompound; +import net.minecraft.nbt.NbtElement; import net.minecraft.predicate.entity.EntityPredicates; import net.minecraft.util.Formatting; import net.minecraft.util.math.Box; import net.minecraft.world.World; +import java.util.List; + public class MobGlow { public static boolean shouldMobGlow(Entity entity) { Box box = entity.getBoundingBox(); - if (!entity.isInvisible() && OcclusionCulling.getReducedCuller().isVisible(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ)) { + if (OcclusionCulling.getReducedCuller().isVisible(box.minX, box.minY, box.minZ, box.maxX, box.maxY, box.maxZ)) { String name = entity.getName().getString(); - // Dungeons - if (Utils.isInDungeons()) { + if (!entity.isInvisible()) { + + // Dungeons + if (Utils.isInDungeons()) { - // Minibosses - if (entity instanceof PlayerEntity) { - switch (name) { - case "Lost Adventurer", "Shadow Assassin", "Diamond Guy": return SkyblockerConfigManager.get().locations.dungeons.starredMobGlow; - case "Arcade Livid", "Crossed Livid", "Doctor Livid", "Frog Livid", "Hockey Livid", - "Purple Livid", "Scream Livid", "Smile Livid", "Vendetta Livid": return LividColor.shouldGlow(name); + // Minibosses + if (entity instanceof PlayerEntity) { + switch (name) { + case "Lost Adventurer", "Shadow Assassin", "Diamond Guy": return SkyblockerConfigManager.get().locations.dungeons.starredMobGlow; + case "Arcade Livid", "Crossed Livid", "Doctor Livid", "Frog Livid", "Hockey Livid", + "Purple Livid", "Scream Livid", "Smile Livid", "Vendetta Livid": return LividColor.shouldGlow(name); + } } - } - // Regular Mobs - if (!(entity instanceof ArmorStandEntity)) { - List<ArmorStandEntity> armorStands = getArmorStands(entity.getWorld(), box); + // Regular Mobs + if (!(entity instanceof ArmorStandEntity)) { + List<ArmorStandEntity> armorStands = getArmorStands(entity.getWorld(), box); - if (!armorStands.isEmpty() && armorStands.get(0).getName().getString().contains("✯")) return SkyblockerConfigManager.get().locations.dungeons.starredMobGlow; - } + if (!armorStands.isEmpty() && armorStands.get(0).getName().getString().contains("✯")) + return SkyblockerConfigManager.get().locations.dungeons.starredMobGlow; + } - // Bats - return SkyblockerConfigManager.get().locations.dungeons.starredMobGlow && entity instanceof BatEntity; - } + // Bats + return SkyblockerConfigManager.get().locations.dungeons.starredMobGlow && entity instanceof BatEntity; + } - // Rift - if (Utils.isInTheRift()) { - if (entity instanceof PlayerEntity) { - switch (name) { - // They have a space in their name for some reason... - case "Blobbercyst ": return SkyblockerConfigManager.get().locations.rift.blobbercystGlow; + // Rift + if (Utils.isInTheRift()) { + if (entity instanceof PlayerEntity) { + switch (name) { + // They have a space in their name for some reason... + case "Blobbercyst ": return SkyblockerConfigManager.get().locations.rift.blobbercystGlow; + } } } } + + // Enderman Slayer + // Highlights Nukekubi Heads + return SkyblockerConfigManager.get().slayer.endermanSlayer.highlightNukekubiHeads + && SlayerUtils.isInSlayer() + && entity instanceof ArmorStandEntity armorStandEntity + && isNukekubiHead(armorStandEntity); } return false; } private static List<ArmorStandEntity> getArmorStands(World world, Box box) { - return world.getEntitiesByClass(ArmorStandEntity.class, box.expand(0, 2, 0), EntityPredicates.NOT_MOUNTED); + return world.getEntitiesByClass(ArmorStandEntity.class, box.expand(0, 2, 0), EntityPredicates.NOT_MOUNTED); } public static int getGlowColor(Entity entity) { @@ -72,12 +87,39 @@ public class MobGlow { case "Shadow Assassin" -> 0x5b2cb2; case "Diamond Guy" -> 0x57c2f7; case "Arcade Livid", "Crossed Livid", "Doctor Livid", "Frog Livid", "Hockey Livid", - "Purple Livid", "Scream Livid", "Smile Livid", "Vendetta Livid" -> LividColor.getGlowColor(name); + "Purple Livid", "Scream Livid", "Smile Livid", "Vendetta Livid" -> LividColor.getGlowColor(name); case "Blobbercyst " -> Formatting.GREEN.getColorValue(); default -> 0xf57738; }; } + // copypaste nukekebi head logic + if (entity instanceof ArmorStandEntity armorStandEntity && isNukekubiHead(armorStandEntity)) return 0x990099; + return 0xf57738; } + + private static boolean isNukekubiHead(ArmorStandEntity entity) { + for (ItemStack armorItem : entity.getArmorItems()) { + // hacky way to check if an item is a player head w/o + // some shenanigans + if (!armorItem.toString().startsWith("1 player_head")) + continue; + + // eb07594e2df273921a77c101d0bfdfa1115abed5b9b2029eb496ceba9bdbb4b3 is texture id for the nukekubi head, + // compare against it to exclusively find armorstands that are nukekubi heads + NbtCompound skullOwner = armorItem.getSubNbt("SkullOwner"); + if (skullOwner != null) { + // get the texture of the nukekubi head item itself and compare it + String texture = skullOwner + .getCompound("Properties") + .getList("textures", NbtElement.COMPOUND_TYPE) + .getCompound(0) + .getString("Value"); + + return texture.contains("eyJ0ZXh0dXJlcyI6eyJTS0lOIjp7InVybCI6Imh0dHA6Ly90ZXh0dXJlcy5taW5lY3JhZnQubmV0L3RleHR1cmUvZWIwNzU5NGUyZGYyNzM5MjFhNzdjMTAxZDBiZmRmYTExMTVhYmVkNWI5YjIwMjllYjQ5NmNlYmE5YmRiYjRiMyJ9fX0="); + } + } + return false; + } } diff --git a/src/main/java/de/hysky/skyblocker/skyblock/tabhud/widget/JacobsContestWidget.java b/src/main/java/de/hysky/skyblocker/skyblock/tabhud/widget/JacobsContestWidget.java index 472e6d61..24dcc229 100644 --- a/src/main/java/de/hysky/skyblocker/skyblock/tabhud/widget/JacobsContestWidget.java +++ b/src/main/java/de/hysky/skyblocker/skyblock/tabhud/widget/JacobsContestWidget.java @@ -1,9 +1,5 @@ package de.hysky.skyblocker.skyblock.tabhud.widget; -import java.util.HashMap; -import java.util.regex.Matcher; -import java.util.regex.Pattern; - import de.hysky.skyblocker.skyblock.tabhud.util.Ico; import de.hysky.skyblocker.skyblock.tabhud.util.PlayerListMgr; import de.hysky.skyblocker.skyblock.tabhud.widget.component.IcoTextComponent; @@ -14,6 +10,12 @@ import net.minecraft.text.MutableText; import net.minecraft.text.Text; import net.minecraft.util.Formatting; +import java.util.Map; +import java.util.regex.Matcher; +import java.util.regex.Pattern; + +import static java.util.Map.entry; + // this widget shows info about the current jacob's contest (garden only) public class JacobsContestWidget extends Widget { @@ -22,23 +24,20 @@ public class JacobsContestWidget extends Widget { Formatting.BOLD); //TODO Properly match the contest placement and display it - private static final Pattern CROP_PATTERN = Pattern.compile("(?:☘|○) (?<crop>[A-Za-z ]+)(?:.+)?"); + private static final Pattern CROP_PATTERN = Pattern.compile("(?<fortune>[☘○]) (?<crop>[A-Za-z ]+).*"); - private static final HashMap<String, ItemStack> FARM_DATA = new HashMap<>(); - - // again, there HAS to be a better way to do this - static { - FARM_DATA.put("Wheat", new ItemStack(Items.WHEAT)); - FARM_DATA.put("Sugar Cane", new ItemStack(Items.SUGAR_CANE)); - FARM_DATA.put("Carrot", new ItemStack(Items.CARROT)); - FARM_DATA.put("Potato", new ItemStack(Items.POTATO)); - FARM_DATA.put("Melon", new ItemStack(Items.MELON_SLICE)); - FARM_DATA.put("Pumpkin", new ItemStack(Items.PUMPKIN)); - FARM_DATA.put("Cocoa Beans", new ItemStack(Items.COCOA_BEANS)); - FARM_DATA.put("Nether Wart", new ItemStack(Items.NETHER_WART)); - FARM_DATA.put("Cactus", new ItemStack(Items.CACTUS)); - FARM_DATA.put("Mushroom", new ItemStack(Items.RED_MUSHROOM)); - } + private static final Map<String, ItemStack> FARM_DATA = Map.ofEntries( + entry("Wheat", new ItemStack(Items.WHEAT)), + entry("Sugar Cane", new ItemStack(Items.SUGAR_CANE)), + entry("Carrot", new ItemStack(Items.CARROT)), + entry("Potato", new ItemStack(Items.POTATO)), + entry("Melon", new ItemStack(Items.MELON_SLICE)), + entry("Pumpkin", new ItemStack(Items.PUMPKIN)), + entry("Cocoa Beans", new ItemStack(Items.COCOA_BEANS)), + entry("Nether Wart", new ItemStack(Items.NETHER_WART)), + entry("Cactus", new ItemStack(Items.CACTUS)), + entry("Mushroom", new ItemStack(Items.RED_MUSHROOM)) + ); public JacobsContestWidget() { super(TITLE, Formatting.YELLOW.getColorValue()); @@ -54,7 +53,7 @@ public class JacobsContestWidget extends Widget { this.addSimpleIcoText(Ico.CLOCK, "Starts in:", Formatting.GOLD, 76); } - TableComponent tc = new TableComponent(1, 3, Formatting.YELLOW .getColorValue()); + TableComponent tc = new TableComponent(1, 3, Formatting.YELLOW.getColorValue()); for (int i = 77; i < 80; i++) { Matcher item = PlayerListMgr.regexAt(i, CROP_PATTERN); @@ -63,7 +62,11 @@ public class JacobsContestWidget extends Widget { itc = new IcoTextComponent(); } else { String cropName = item.group("crop").trim(); //Trimming is needed because during a contest the space separator will be caught - itc = new IcoTextComponent(FARM_DATA.get(cropName), Text.of(cropName)); + if (item.group("fortune").equals("☘")) { + itc = new IcoTextComponent(FARM_DATA.get(cropName), Text.literal(cropName).append(Text.literal(" ☘").formatted(Formatting.GOLD))); + } else { + itc = new IcoTextComponent(FARM_DATA.get(cropName), Text.of(cropName)); + } } tc.addToCell(0, i - 77, itc); } diff --git a/src/main/java/de/hysky/skyblocker/utils/Utils.java b/src/main/java/de/hysky/skyblocker/utils/Utils.java index 53c0ff4a..3f07622c 100644 --- a/src/main/java/de/hysky/skyblocker/utils/Utils.java +++ b/src/main/java/de/hysky/skyblocker/utils/Utils.java @@ -90,6 +90,14 @@ public class Utils { return getLocationRaw().equals(TheRift.LOCATION); } + /** + * @return if the player is in the end island + */ + public static boolean isInTheEnd() { + // /locraw returns "combat_3" when in The End + return getLocationRaw().equals("combat_3"); + } + public static boolean isInjected() { return isInjected; } diff --git a/src/main/resources/assets/skyblocker/lang/en_ca.json b/src/main/resources/assets/skyblocker/lang/en_ca.json index da8193d1..416f9d9b 100644 --- a/src/main/resources/assets/skyblocker/lang/en_ca.json +++ b/src/main/resources/assets/skyblocker/lang/en_ca.json @@ -27,5 +27,9 @@ "text.autoconfig.skyblocker.option.locations.dungeons.dungeonChestProfit.lossColor": "Loss Colour", "text.autoconfig.skyblocker.option.general.itemInfoDisplay.itemRarityBackgrounds.@Tooltip": "Displays a coloured background behind an item, the colour represents the item's rarity.", "text.autoconfig.skyblocker.option.general.itemTooltip.enableExoticTooltip.@Tooltip": "Displays the type of exotic below the item's name if an armour piece is exotic.", - "text.autoconfig.skyblocker.option.locations.dungeons.lividColor.enableLividColorGlow": "Enable Livid Colour Glow" + "text.autoconfig.skyblocker.option.locations.dungeons.lividColor.enableLividColorGlow": "Enable Livid Colour Glow", + "skyblocker.tips.customArmorDyeColors": "Apply a custom dye colour to your leather armour with /skyblocker custom dyeColor", + "skyblocker.tips.customArmorTrims": "You can set custom armour trims on your armour using /skyblocker custom armorTrim.", + "text.autoconfig.skyblocker.option.locations.dungeons.lividColor.enableLividColorTitle": "Enable Livid Colour Title", + "text.autoconfig.skyblocker.option.locations.dungeons.lividColor.enableLividColorTitle.@Tooltip": "Display the livid colour in the title during the Livid boss fight." } diff --git a/src/main/resources/assets/skyblocker/lang/en_us.json b/src/main/resources/assets/skyblocker/lang/en_us.json index 7afe4196..527205cf 100644 --- a/src/main/resources/assets/skyblocker/lang/en_us.json +++ b/src/main/resources/assets/skyblocker/lang/en_us.json @@ -311,6 +311,9 @@ "text.autoconfig.skyblocker.option.messages.hideDeath": "Hide Player Death Messages", "text.autoconfig.skyblocker.option.messages.hideDeath.@Tooltip": "Filters the player death messages from chat.", "text.autoconfig.skyblocker.category.slayer": "Slayers", + "text.autoconfig.skyblocker.option.slayer.endermanSlayer": "[Beta] Enderman Slayer", + "text.autoconfig.skyblocker.option.slayer.endermanSlayer.highlightNukekubiHeads": "Nukekubi Head Highlighting", + "text.autoconfig.skyblocker.option.slayer.endermanSlayer.highlightBeacons": "Beacon Highlighting", "text.autoconfig.skyblocker.option.slayer.vampireSlayer": "Vampire Slayer", "text.autoconfig.skyblocker.option.slayer.vampireSlayer.enableEffigyWaypoints": "Enable Effigy Waypoints", "text.autoconfig.skyblocker.option.slayer.vampireSlayer.compactEffigyWaypoints": "Compact Effigy Waypoints", @@ -456,4 +459,4 @@ "skyblocker.partyFinder.join": "Click to join", "emi.category.skyblocker.skyblock": "Skyblock" -}
\ No newline at end of file +} diff --git a/src/main/resources/assets/skyblocker/lang/pt_br.json b/src/main/resources/assets/skyblocker/lang/pt_br.json index 11242adf..02e52b02 100644 --- a/src/main/resources/assets/skyblocker/lang/pt_br.json +++ b/src/main/resources/assets/skyblocker/lang/pt_br.json @@ -105,7 +105,7 @@ "text.autoconfig.skyblocker.option.general.itemTooltip.avg": "Tipo Mediano", "text.autoconfig.skyblocker.option.general.itemTooltip.avg.ONE_DAY": "Preço de 1 dia", "text.autoconfig.skyblocker.option.general.itemTooltip.enableBazaarPrice": "Ativar Preço de compra/venda do Bazar", - "text.autoconfig.skyblocker.option.messages.hideAOTE": "Esconder Mensagens do AOTE", + "text.autoconfig.skyblocker.option.messages.hideAOTE": "Esconder Mensagens da Habilidade de Teleporte", "text.autoconfig.skyblocker.option.messages.hideTeleportPad": "Esconder Mensagens do Pad de Teleporte", "text.autoconfig.skyblocker.option.messages.hideShowOff": "Esconder Mensagens de Show Off", "text.autoconfig.skyblocker.option.slayer.vampireSlayer.effigyUpdateFrequency": "Frequência de Atualização (Ticks) de Waypoints de Effigy", @@ -280,5 +280,8 @@ "text.autoconfig.skyblocker.option.locations.dungeons.dungeonChestProfit.includeKismet.@Tooltip": "Se ativado, o preço de uma Kismet usada será subtraído no cálculo da margem de lucro", "text.autoconfig.skyblocker.option.locations.dungeons.dungeonChestProfit.includeEssence": "Incluir essência", "text.autoconfig.skyblocker.option.locations.dungeons.secretWaypoints.showSecretText": "Exibir texto secreto", - "text.autoconfig.skyblocker.option.quickNav.button.clickEvent": "Evento ao clicar" + "text.autoconfig.skyblocker.option.quickNav.button.clickEvent": "Evento ao clicar", + "text.autoconfig.skyblocker.option.general.waypoints.enableWaypoints": "Ativar Waypoints", + "text.autoconfig.skyblocker.option.general.waypoints.waypointType": "Tipo de Waypoint", + "text.autoconfig.skyblocker.option.general.waypoints.waypointType.generalNote": "\n\n\nEssa opção não aplica para todos os waypoints. Alguns waypoints como waypoints secretos tem seu próprio opção de tipo de waypoint." } diff --git a/src/main/resources/assets/skyblocker/lang/tr_tr.json b/src/main/resources/assets/skyblocker/lang/tr_tr.json index 362c7e55..b46463fb 100644 --- a/src/main/resources/assets/skyblocker/lang/tr_tr.json +++ b/src/main/resources/assets/skyblocker/lang/tr_tr.json @@ -50,7 +50,7 @@ "text.autoconfig.skyblocker.category.general": "Genel", "text.autoconfig.skyblocker.option.general.bars": "Can, Mana, Defans ve XP Barları", "text.autoconfig.skyblocker.option.general.bars.enableBars": "Barları Etkinleştir", - "text.autoconfig.skyblocker.option.general.bars.barpositions": "Bar Konumları", + "text.autoconfig.skyblocker.option.general.bars.barpositions": "Çubuk Konumlarını Ayarla", "text.autoconfig.skyblocker.option.general.bars.barpositions.NONE": "Devre dışı", "text.autoconfig.skyblocker.option.general.bars.barpositions.healthBarPosition": "Can barı konumu", "text.autoconfig.skyblocker.option.general.bars.barpositions.manaBarPosition": "Mana barı konumu", @@ -61,5 +61,43 @@ "text.autoconfig.skyblocker.option.general.fishing": "Balık Tutma Yardımcısı", "text.autoconfig.skyblocker.option.general.fishing.enableFishingHelper": "Balık tutma yardımcısını aktifleştir", "text.autoconfig.skyblocker.category.messages": "Mesajlar", - "text.autoconfig.skyblocker.option.messages.hideImplosion": "Implosion mesajını filtrele" + "text.autoconfig.skyblocker.option.messages.hideImplosion": "Implosion mesajını filtrele", + "key.skyblocker.toggleB": "Tab HUD'unda B ekranını aç", + "key.skyblocker.toggleA": "Tab HUD'unda A ekranını aç", + "text.autoconfig.skyblocker.option.general.mythologicalRitual": "Mitolojik Ayin Yardımcısı", + "text.autoconfig.skyblocker.option.general.mythologicalRitual.enableMythologicalRitualHelper": "Mitolojik Ayin Yardımcısını Etkinleştir", + "text.autoconfig.skyblocker.option.general.fairySouls.highlightFoundSouls": "Bulunmuş peri ruhlarını göster", + "text.autoconfig.skyblocker.option.general.fairySouls.highlightOnlyNearbySouls": "Sadece yakındaki peri ruhlarını göster", + "text.autoconfig.skyblocker.option.general.fairySouls.highlightOnlyNearbySouls.@Tooltip": "Etkinleştirildiğinde sadece 50 blokluk mesafedeki peri ruhları gösterilir", + "text.autoconfig.skyblocker.option.general.bars.barpositions.LAYER2": "Katman 2", + "text.autoconfig.skyblocker.option.general.shortcuts.config": "Kısayol Ayarları...", + "text.autoconfig.skyblocker.option.general.acceptReparty": "Tekrar parti davetini otomatik kabul et", + "text.autoconfig.skyblocker.option.general.experiments.enableUltrasequencerSolver": "Ultrasekans Çözücüsünü Etkinleştir", + "text.autoconfig.skyblocker.option.general.experiments.enableSuperpairsSolver": "Süperçiftler Çözücüsünü Etkinleştir", + "text.autoconfig.skyblocker.option.general.experiments": "Deney Çözücü", + "text.autoconfig.skyblocker.option.general.experiments.enableChronomatronSolver": "Chronomatron Çözücüsünü Etkinleştir", + "key.skyblocker.defaultTgl": "Tab HUD'unda varsayılan görünüme geç", + "text.autoconfig.skyblocker.option.general.bars.barpositions.RIGHT": "Sağ", + "text.autoconfig.skyblocker.option.general.fairySouls": "Peri Ruhları Yardımcısı", + "text.autoconfig.skyblocker.option.general.shortcuts.enableShortcuts.@Tooltip": "Vanilla dahil her yerde çalışır! Kısayolları \"/skyblocker shortcuts\" ile düzenleyebilirsiniz. Bu seçeneğin etki göstermesi için sıradaki seçeneklerden en az birinin etkinleştirilmiş olması gerekir.", + "text.autoconfig.skyblocker.option.general.shortcuts": "Kısayollar", + "text.autoconfig.skyblocker.option.general.shortcuts.enableCommandShortcuts": "Komut Kısayollarını Etkinleştir", + "text.autoconfig.skyblocker.option.general.shortcuts.enableShortcuts": "Kısayolları Etkinleştir", + "text.autoconfig.skyblocker.option.general.shortcuts.enableCommandShortcuts.@Tooltip": "Sadece bir kelimeden oluşan komutlar için kısayollar. Kısayolları \"/skyblocker shortcuts\" ile düzenleyebilirsiniz. Bu seçeneğin etki göstermesi için kısayolların etkinleştirilmiş olması gerekir.", + "text.autoconfig.skyblocker.option.general.etherwarpOverlay": "Etherwarp Kaplaması", + "text.autoconfig.skyblocker.option.general.fairySouls.enableFairySoulsHelper": "Peri Ruhları Yardımcısını Etkinleştir", + "text.autoconfig.skyblocker.option.general.shortcuts.enableCommandArgShortcuts": "Komut Argüman Kısayollarını Etkinleştir", + "text.autoconfig.skyblocker.option.general.waypoints": "İşaret Noktaları", + "text.autoconfig.skyblocker.option.general.waypoints.enableWaypoints": "İşaret Noktalarını Etkinleştir", + "text.autoconfig.skyblocker.option.general.waypoints.waypointType": "İşaret Noktası Tipi", + "text.autoconfig.skyblocker.option.general.waypoints.waypointType.@Tooltip": "Waypoint: İşaret noktasını renklendirir ve fener ışını gösterir\n\nOutlined Waypoint: İşaret noktasını ve kenar çizgilerini gösterir.\n\nHighlight: Sadece işaret noktasını renklendirir.\n\nOutlined Highlight: İşaret noktasını renklendirir ve kenar çizgilerini gösterir.\n\nOutline: Sadece kenar çizgilerini gösterir.", + "text.autoconfig.skyblocker.option.general.itemCooldown": "Eşya Bekleme Süresi", + "text.autoconfig.skyblocker.option.general.itemCooldown.enableItemCooldowns": "Eşya Bekleme Süresini Etkinleştir", + "text.skyblocker.open": "Aç", + "text.skyblocker.quit_config": "Değişikler Kaydedilmedi", + "text.skyblocker.quit_config_sure": "Ayarları düzenlemekten çıkmak istediğinize emin misiniz? Yaptığınız değişikler kaydedilmeyecek!", + "text.skyblocker.quit_discard": "Çık & Değişiklikleri Yoksay", + "text.autoconfig.skyblocker.option.general.bars.barpositions.LAYER1": "Katman 1", + "text.autoconfig.skyblocker.option.general.enableTips": "Tüyoları Etkinleştir", + "text.autoconfig.skyblocker.option.general.shortcuts.enableCommandArgShortcuts.@Tooltip": "Birden fazla kelime/argümandan oluşan komutların birden fazla komut/argümanını değiştiren kısayollar. Kısayolları \"/skyblocker shortcuts\" ile düzenleyebilirsiniz. Bu seçeneğin etki göstermesi için kısayolların etkinleştirilmiş olması gerekir." } diff --git a/src/main/resources/assets/skyblocker/lang/zh_cn.json b/src/main/resources/assets/skyblocker/lang/zh_cn.json index a268d5a5..4d058bf1 100644 --- a/src/main/resources/assets/skyblocker/lang/zh_cn.json +++ b/src/main/resources/assets/skyblocker/lang/zh_cn.json @@ -113,7 +113,7 @@ "skyblocker.fairySouls.markAllFound": "将当前岛屿上的全部仙女之魂标记为已发现", "text.autoconfig.skyblocker.option.slayer.vampireSlayer.steakStakeUpdateFrequency.@Tooltip": "值越小,更新越频繁(可能会导致卡顿)", "text.autoconfig.skyblocker.option.general.shortcuts": "更精简的命令", - "text.autoconfig.skyblocker.option.general.shortcuts.enableShortcuts.@Tooltip": "使用 \"/skyblocker shortcuts\" 以编辑命令的精简版本, 以下选项必须至少启用之一方可有效. (仅在Hypixel服务器可用)", + "text.autoconfig.skyblocker.option.general.shortcuts.enableShortcuts.@Tooltip": "使用 \"/skyblocker shortcuts\" 以编辑命令的精简版本, 以下选项必须至少启用之一方可有效. (此功能在空岛生存外也可使用)", "text.autoconfig.skyblocker.option.general.teleportOverlay": "传送类技能目标位置显示", "text.autoconfig.skyblocker.option.general.teleportOverlay.enableTeleportOverlays": "启用传送类技能目标位置显示", "text.autoconfig.skyblocker.option.general.teleportOverlay.enableWeirdTransmission": "启用 Weird Transmission 目标位置显示", @@ -149,5 +149,13 @@ "text.skyblocker.quit_config_sure": "确定退出吗? 你的修改将不会被保存!", "text.autoconfig.skyblocker.option.general.wikiLookup": "查阅 wiki", "text.autoconfig.skyblocker.option.general.wikiLookup.officialWiki": "使用Hypixel官方 Wiki", - "text.autoconfig.skyblocker.option.general.wikiLookup.officialWiki.@Tooltip": "在查阅时使用Hypixel 官方 wiki 代替 Fandom wiki" + "text.autoconfig.skyblocker.option.general.wikiLookup.officialWiki.@Tooltip": "在查阅时使用Hypixel 官方 wiki 代替 Fandom wiki", + "text.autoconfig.skyblocker.option.general.itemTooltip.enableObtainedDate": "显示获取时间", + "text.autoconfig.skyblocker.option.general.shortcuts.enableCommandShortcuts.@Tooltip": "此功能可用较短的别名替换较长的原始命令,使用 \"/skyblocker shortcuts\" 以编辑. (“更精简的命令”功能必须启用才可生效)", + "text.autoconfig.skyblocker.option.general.waypoints": "路径点", + "text.autoconfig.skyblocker.option.general.waypoints.enableWaypoints": "启用路径点", + "text.autoconfig.skyblocker.option.general.waypoints.waypointType": "路径点类型", + "text.skyblocker.open": "开启", + "text.autoconfig.skyblocker.option.general.wikiLookup.enableWikiLookup": "启用 wiki 查阅功能", + "text.autoconfig.skyblocker.option.general.wikiLookup.enableWikiLookup.@Tooltip": "指针悬停于物品之下按 F4 键打开 wiki 相关条目" } |