From 26835af63de4f0f6808c55ee7f249827df3c58db Mon Sep 17 00:00:00 2001 From: J10a1n15 <45315647+j10a1n15@users.noreply.github.com> Date: Sat, 26 Oct 2024 02:53:19 +0200 Subject: [PATCH 001/105] Improvement + Fix: Profile Type in Custom Scoreboard (#2810) --- .../gui/customscoreboard/DisplayConfig.java | 5 +++++ .../elements/ScoreboardElementProfile.kt | 17 +++++++++++++++-- .../events/ScoreboardEventBroodmother.kt | 2 +- 3 files changed, 21 insertions(+), 3 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/gui/customscoreboard/DisplayConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/gui/customscoreboard/DisplayConfig.java index b54d7519d213..26c6b125ece6 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/features/gui/customscoreboard/DisplayConfig.java +++ b/src/main/java/at/hannibal2/skyhanni/config/features/gui/customscoreboard/DisplayConfig.java @@ -149,6 +149,11 @@ public String toString() { @ConfigEditorDropdown public RenderUtils.HorizontalAlignment textAlignment = RenderUtils.HorizontalAlignment.LEFT; + @Expose + @ConfigOption(name = "Show Profile Name", desc = "Show profile name instead of the type in the profile element.") + @ConfigEditorBoolean + public boolean showProfileName = false; + @Expose @ConfigOption(name = "Date in Lobby Code", desc = "Show the current date infront of the server name, like Hypixel does.") @ConfigEditorBoolean diff --git a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementProfile.kt b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementProfile.kt index c8a4bc99368c..2d85d67766c4 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementProfile.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementProfile.kt @@ -1,15 +1,28 @@ package at.hannibal2.skyhanni.features.gui.customscoreboard.elements import at.hannibal2.skyhanni.data.HypixelData +import at.hannibal2.skyhanni.features.gui.customscoreboard.CustomScoreboard import at.hannibal2.skyhanni.features.gui.customscoreboard.CustomScoreboardUtils import at.hannibal2.skyhanni.utils.StringUtils.firstLetterUppercase // internal and scoreboard // island change event object ScoreboardElementProfile : ScoreboardElement() { - override fun getDisplay() = CustomScoreboardUtils.getProfileTypeSymbol() + HypixelData.profileName.firstLetterUppercase() + override fun getDisplay() = buildString { + append(CustomScoreboardUtils.getProfileTypeSymbol()) + if (CustomScoreboard.displayConfig.showProfileName) { + append(HypixelData.profileName.firstLetterUppercase()) + } else { + when { + HypixelData.ironman -> append("Ironman") + HypixelData.stranded -> append("Stranded") + HypixelData.bingo -> append("Bingo") + else -> append("Normal") + } + } + } - override val configLine = "§7♲ Blueberry" + override val configLine = "§7♲ Ironman" } // click: does a command for profile management exist? diff --git a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/events/ScoreboardEventBroodmother.kt b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/events/ScoreboardEventBroodmother.kt index 2d10a18477b8..3b6a23a185f1 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/events/ScoreboardEventBroodmother.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/events/ScoreboardEventBroodmother.kt @@ -7,7 +7,7 @@ import at.hannibal2.skyhanni.utils.LorenzUtils.isInIsland // scoreboard // widget update event object ScoreboardEventBroodmother : ScoreboardEvent() { - override fun getDisplay() = TabWidget.BROODMOTHER.lines + override fun getDisplay() = TabWidget.BROODMOTHER.lines.map { it.trim() } override val configLine = "Broodmother§7: §eDormant" From 31d2b539f480a75066f6ab967bcd299df4d023e5 Mon Sep 17 00:00:00 2001 From: J10a1n15 <45315647+j10a1n15@users.noreply.github.com> Date: Sat, 26 Oct 2024 02:53:52 +0200 Subject: [PATCH 002/105] Fix: Colored Classlevel Tablist (#2814) --- src/main/java/at/hannibal2/skyhanni/utils/RegexUtils.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/utils/RegexUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/RegexUtils.kt index 91a53f62bad4..1a4574be8809 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/RegexUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/RegexUtils.kt @@ -79,7 +79,7 @@ object RegexUtils { */ fun Matcher.groupOrNull(groupName: String): String? = runCatching { group(groupName) }.getOrNull() - fun Matcher.groupOrEmpty(groupName: String): String = runCatching { group(groupName) }.getOrDefault("") + fun Matcher.groupOrEmpty(groupName: String): String = groupOrNull(groupName).orEmpty() fun Matcher.hasGroup(groupName: String): Boolean = groupOrNull(groupName) != null From ceba80c79f22ede70d7dd24d44b2243a2006bc06 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Linnea=20Gr=C3=A4f?= Date: Sat, 26 Oct 2024 03:13:09 +0200 Subject: [PATCH 003/105] Fix: Own player messages not being rewritten by chat formatting (#2806) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../data/hypixel/chat/PlayerChatManager.kt | 3 +- .../data/hypixel/chat/PlayerNameFormatter.kt | 87 ++++++++++++------- .../skyhanni/utils/ComponentMatcherUtils.kt | 2 +- .../hannibal2/skyhanni/utils/StringUtils.kt | 1 + 4 files changed, 60 insertions(+), 33 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt b/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt index 5199e8b7e230..2529e7ff1fde 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt @@ -32,10 +32,11 @@ object PlayerChatManager { /** * REGEX-TEST: [58] §7nea89o§7: haiiiii * REGEX-TEST: [266] ♫ §b[MVP§d+§b] lrg89§f: a + * REGEX-TEST: [302] ♫ [MVP+] lrg89: problematic */ private val globalPattern by patternGroup.pattern( "global", - "(?:\\[(?\\d+)] )?(?.+)(?§f|§7): (?.*)" + "(?:\\[(?\\d+)] )?(?.+?)(?§f|§7|): (?.*)" ) /** diff --git a/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerNameFormatter.kt b/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerNameFormatter.kt index 35356f32f3bf..bd7a407dfa7b 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerNameFormatter.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerNameFormatter.kt @@ -15,6 +15,7 @@ import at.hannibal2.skyhanni.features.misc.MarkedPlayerManager import at.hannibal2.skyhanni.features.misc.compacttablist.AdvancedPlayerList import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.ChatUtils.changeColor +import at.hannibal2.skyhanni.utils.ComponentMatcherUtils.intoSpan import at.hannibal2.skyhanni.utils.ComponentMatcherUtils.matchStyledMatcher import at.hannibal2.skyhanni.utils.ComponentSpan import at.hannibal2.skyhanni.utils.LorenzColor @@ -22,12 +23,15 @@ import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.StringUtils import at.hannibal2.skyhanni.utils.StringUtils.applyFormattingFrom import at.hannibal2.skyhanni.utils.StringUtils.cleanPlayerName +import at.hannibal2.skyhanni.utils.StringUtils.removeColor import at.hannibal2.skyhanni.utils.StringUtils.toCleanChatComponent import at.hannibal2.skyhanni.utils.chat.Text +import at.hannibal2.skyhanni.utils.chat.Text.style import at.hannibal2.skyhanni.utils.repopatterns.RepoPattern import com.google.gson.JsonArray import com.google.gson.JsonNull import net.minecraft.util.ChatComponentText +import net.minecraft.util.EnumChatFormatting import net.minecraft.util.IChatComponent import net.minecraftforge.fml.common.eventhandler.SubscribeEvent @@ -51,7 +55,7 @@ object PlayerNameFormatter { */ private val emblemPattern by patternGroup.pattern( "emblem", - "(?(?:§.){0,2}.) (?.*)" + "(?(?:§.){0,2}.) (?.*)", ) @SubscribeEvent @@ -72,7 +76,7 @@ object PlayerNameFormatter { levelColor?.toString(), level = levelComponent, privateIslandRank = privateIslandRank, - privateIslandGuest = privateIslandGuest + privateIslandGuest = privateIslandGuest, ) val all = ChatComponentText("") all.appendSibling(name) @@ -91,7 +95,7 @@ object PlayerNameFormatter { appendSibling(nameFormat(event.authorComponent)) appendText("§f: ") appendSibling(event.messageComponent.intoComponent()) - } + }, ) ?: return } @@ -104,7 +108,7 @@ object PlayerNameFormatter { appendSibling(nameFormat(event.authorComponent, guildRank = event.guildRank)) appendText("§f: ") appendSibling(event.messageComponent.intoComponent()) - } + }, ) ?: return } @@ -117,23 +121,22 @@ object PlayerNameFormatter { appendSibling(nameFormat(event.authorComponent)) appendText("§f: ") appendSibling(event.messageComponent.intoComponent()) - } + }, ) ?: return } @SubscribeEvent fun onPrivateChat(event: PrivateMessageChatEvent) { if (!isEnabled()) return - event.chatComponent = - StringUtils.replaceIfNeeded( - event.chatComponent, - Text.text("§d${event.direction}") { - appendText(" ") - appendSibling(nameFormat(event.authorComponent)) - appendText("§f: ") - appendSibling(event.messageComponent.intoComponent()) - } - ) ?: return + event.chatComponent = StringUtils.replaceIfNeeded( + event.chatComponent, + Text.text("§d${event.direction}") { + appendText(" ") + appendSibling(nameFormat(event.authorComponent)) + appendText("§f: ") + appendSibling(event.messageComponent.intoComponent()) + }, + ) ?: return } @SubscribeEvent @@ -146,8 +149,8 @@ object PlayerNameFormatter { nameFormat( event.authorComponent, levelColor = event.levelComponent?.sampleStyleAtStart()?.color?.toString(), - level = event.levelComponent - ) + level = event.levelComponent, + ), ) appendText(" ") @@ -155,7 +158,7 @@ object PlayerNameFormatter { appendText(" ") appendSibling(event.item.intoComponent()) - } + }, ) ?: return } @@ -175,7 +178,7 @@ object PlayerNameFormatter { cleanAuthor = groupOrThrow("author").stripHypixelMessage() } - val name = formatAuthor(cleanAuthor.getText(), levelColor).applyFormattingFrom(cleanAuthor) + val name = formatAuthor(cleanAuthor, levelColor) val levelFormat = formatLevel(levelColor, level) val guildRankFormat = guildRank?.intoComponent() val privateIslandRankFormat = privateIslandRank?.intoComponent() @@ -192,7 +195,7 @@ object PlayerNameFormatter { val map = mutableMapOf() map[PlayerMessagesConfig.MessagePart.SKYBLOCK_LEVEL] = levelFormat map[PlayerMessagesConfig.MessagePart.EMBLEM] = emblemFormat - map[PlayerMessagesConfig.MessagePart.PLAYER_NAME] = name + map[PlayerMessagesConfig.MessagePart.PLAYER_NAME] = name.intoComponent() map[PlayerMessagesConfig.MessagePart.CRIMSON_FACTION] = faction map[PlayerMessagesConfig.MessagePart.MODE_IRONMAN] = ironman map[PlayerMessagesConfig.MessagePart.BINGO_LEVEL] = bingo @@ -229,19 +232,41 @@ object PlayerNameFormatter { return author.stripHypixelMessage().removePrefix("§f") } - private fun formatAuthor(author: String, levelColor: String?): String { - if (author.contains("ADMIN")) return author - if (config.ignoreYouTube && author.contains("YOUTUBE")) return author + private fun ComponentSpan.splitPlayerNameAndExtras(): Pair { + val space = getText().indexOf(' ') + if (space < 0) return Pair(null, this) + return Pair(slice(0, space + 1), slice(space + 1)) + } - var result = author.cleanPlayerName(displayName = true) - levelColor?.let { - if (config.useLevelColorForName) { - val cleanPlayerName = author.cleanPlayerName() - result = result.replace(cleanPlayerName, it + cleanPlayerName) - } - } + private fun formatAuthor(author: ComponentSpan, levelColor: String?): ComponentSpan { + if (author.getText().contains("ADMIN")) return author + if (config.ignoreYouTube && author.getText().contains("YOUTUBE")) return author + val (rank, name) = author.splitPlayerNameAndExtras() + val coloredName = createColoredName(name, levelColor, name.getText().removeColor()) + return if (config.playerRankHider || rank == null) coloredName else rank + coloredName + } + + private fun createColoredName( + name: ComponentSpan, + levelColor: String?, + removeColor: String, + ): ComponentSpan = when { + MarkedPlayerManager.isMarkedPlayer(removeColor) && MarkedPlayerManager.config.highlightInChat -> + ChatComponentText(MarkedPlayerManager.replaceInChat(removeColor)) + .setChatStyle(name.sampleStyleAtStart()).intoSpan() + + levelColor != null && config.useLevelColorForName -> + ChatComponentText(levelColor + removeColor) + .setChatStyle(name.sampleStyleAtStart()) + .intoSpan() + + config.playerRankHider -> + ChatComponentText(removeColor) + .setChatStyle(name.sampleStyleAtStart()?.createShallowCopy()) + .style { color = EnumChatFormatting.AQUA } + .intoSpan() - return MarkedPlayerManager.replaceInChat(result) + else -> name } fun isEnabled() = LorenzUtils.inSkyBlock && config.enable diff --git a/src/main/java/at/hannibal2/skyhanni/utils/ComponentMatcherUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/ComponentMatcherUtils.kt index f332cc05e1d9..f13f8b66e5cd 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/ComponentMatcherUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/ComponentMatcherUtils.kt @@ -165,7 +165,7 @@ class ComponentSpan internal constructor( */ fun slice(start: Int = 0, end: Int = length): ComponentSpan { require(0 <= start) { "start is bigger than 0: start=$start, cachedText=$cachedText" } - require(start <= end) { "start is bigger than length: start=$start, length=$length, cachedText=$cachedText" } + require(start <= end) { "start is bigger than end: start=$start, end=$end, cachedText=$cachedText" } require(end <= length) { "end is bigger than length: end=$end, length=$length, cachedText=$cachedText" } return ComponentSpan(textComponent, cachedText, this.start + start, this.start + end) } diff --git a/src/main/java/at/hannibal2/skyhanni/utils/StringUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/StringUtils.kt index b6d38fd7ff33..160b8ffd1621 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/StringUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/StringUtils.kt @@ -509,6 +509,7 @@ object StringUtils { fun String.toCleanChatComponent(): IChatComponent = ChatComponentText(this) + @Deprecated("This function strips internal formatting changes like the color of the pluses of the MVP+ rank") fun IChatComponent.cleanPlayerName(displayName: Boolean = false): IChatComponent = formattedText.cleanPlayerName(displayName).applyFormattingFrom(this) From 9436627b03dcb9a32e713f4967c59471afde77b6 Mon Sep 17 00:00:00 2001 From: Thunderblade73 <85900443+Thunderblade73@users.noreply.github.com> Date: Sat, 26 Oct 2024 03:51:22 +0200 Subject: [PATCH 004/105] Backend; Contributing.md Added our two Optional Plugins (#2817) --- CONTRIBUTING.md | 54 ++++++++++++++++++++++++++++--------------------- 1 file changed, 31 insertions(+), 23 deletions(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 8229a00d5835..53ec5bc2772e 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -153,6 +153,37 @@ for more information and usages. - When updating a config option variable, use the `ConfigUpdaterMigrator.ConfigFixEvent` with event.move() when moving a value, and event.transform() when updating a value. [For Example](https://github.com/hannibal002/SkyHanni/blob/e88f416c48f9659f89b7047d7629cd9a1d1535bc/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/CustomScoreboard.kt#L276). - Use American English spelling conventions (e.g., "color" not "colour"). +## Additional Useful Development Tools + +### DevAuth + +[DevAuth](https://github.com/DJtheRedstoner/DevAuth) is a tool that allows logging in to a Minecraft account while +debugging in IntelliJ. This is very useful for coding live on Hypixel without the need to compile a jar. + +- The library is already downloaded by Gradle. +- SkyHanni will automatically set up DevAuth. +- Start Minecraft inside IntelliJ normally. + - Click on the link in the console and verify with a Microsoft account. + - The verification process will reappear every few days (after the session token expires). + +### Hot Swap + +Hot Swap allows reloading edited code while debugging, removing the need to restart the whole game every time. + +We use [dcevm](https://dcevm.github.io/) and the IntelliJ +Plugin [HotSwap Agent](https://plugins.jetbrains.com/plugin/9552-hotswapagent) to quickly reload code changes. + +Follow [this](https://forums.Minecraftforge.net/topic/82228-1152-3110-intellij-and-gradlew-forge-hotswap-and-dcevm-tutorial/) +tutorial. + +### [Live Plugin](https://plugins.jetbrains.com/plugin/7282-liveplugin) + +Allows project specific plugins to run. Eg: Regex Intention + +### [Live Templates Sharing](https://plugins.jetbrains.com/plugin/25007-live-templates-sharing) + +Imports our custom live templates automatically. Live Templates allow for quicker code writing. + ## Software Used in SkyHanni ### Basics @@ -218,29 +249,6 @@ For info on usage, look at [DiscordRPCManager.kt](https://github.com/hannibal002 We use the [auto update library](https://github.com/nea89o/libautoupdate) from nea89. -## Additional Useful Development Tools - -### DevAuth - -[DevAuth](https://github.com/DJtheRedstoner/DevAuth) is a tool that allows logging in to a Minecraft account while -debugging in IntelliJ. This is very useful for coding live on Hypixel without the need to compile a jar. - -- The library is already downloaded by Gradle. -- SkyHanni will automatically set up DevAuth. -- Start Minecraft inside IntelliJ normally. - - Click on the link in the console and verify with a Microsoft account. - - The verification process will reappear every few days (after the session token expires). - -### Hot Swap - -Hot Swap allows reloading edited code while debugging, removing the need to restart the whole game every time. - -We use [dcevm](https://dcevm.github.io/) and the IntelliJ -Plugin [HotSwap Agent](https://plugins.jetbrains.com/plugin/9552-hotswapagent) to quickly reload code changes. - -Follow [this](https://forums.Minecraftforge.net/topic/82228-1152-3110-intellij-and-gradlew-forge-hotswap-and-dcevm-tutorial/) -tutorial. - ## 1.21 / Modern version development You might have noticed that while the SkyHanni source code is found in `src/`, the actual tasks for compiling, building and running the mod From 697e9e2dd6e5bb1d32e5b330623199099d9750bf Mon Sep 17 00:00:00 2001 From: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Date: Sat, 26 Oct 2024 13:16:26 +1100 Subject: [PATCH 005/105] Backend: Add in event handler check to SkyHanni Events (#2755) --- .../skyhanni/api/event/EventHandler.kt | 26 ++++++++++++++++--- .../skyhanni/config/ConfigManager.kt | 3 ++- .../hannibal2/skyhanni/utils/ConfigUtils.kt | 3 ++- .../utils/repopatterns/RepoPatternManager.kt | 9 +++---- 4 files changed, 30 insertions(+), 11 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/api/event/EventHandler.kt b/src/main/java/at/hannibal2/skyhanni/api/event/EventHandler.kt index 63d3e14cfb21..040ecc43c9a7 100644 --- a/src/main/java/at/hannibal2/skyhanni/api/event/EventHandler.kt +++ b/src/main/java/at/hannibal2/skyhanni/api/event/EventHandler.kt @@ -2,12 +2,15 @@ package at.hannibal2.skyhanni.api.event import at.hannibal2.skyhanni.SkyHanniMod import at.hannibal2.skyhanni.data.IslandType +import at.hannibal2.skyhanni.mixins.hooks.getValue +import at.hannibal2.skyhanni.mixins.hooks.setValue import at.hannibal2.skyhanni.test.command.ErrorManager import at.hannibal2.skyhanni.utils.ChatUtils import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.LorenzUtils.inAnyIsland import at.hannibal2.skyhanni.utils.StringUtils import at.hannibal2.skyhanni.utils.chat.Text +import at.hannibal2.skyhanni.utils.system.PlatformUtils class EventHandler private constructor( val name: String, @@ -21,9 +24,24 @@ class EventHandler private constructor( constructor(event: Class, listeners: List) : this( (event.name.split(".").lastOrNull() ?: event.name).replace("$", "."), listeners.sortedBy { it.options.priority }.toList(), - listeners.any { it.options.receiveCancelled } + listeners.any { it.options.receiveCancelled }, ) + companion object { + private var eventHandlerDepth by object : ThreadLocal() { + override fun initialValue(): Int { + return 0 + } + } + + /** + * Returns true if the current thread is in an event handler. This is because the event handler catches exceptions which means + * that we are free to throw exceptions in the event handler without crashing the game. + * We also return true if we are in a dev environment to alert the developer of any errors effectively. + */ + val isInEventHandler get() = eventHandlerDepth > 0 || PlatformUtils.isDevEnvironment + } + fun post(event: T, onError: ((Throwable) -> Unit)? = null): Boolean { invokeCount++ if (this.listeners.isEmpty()) return false @@ -32,6 +50,7 @@ class EventHandler private constructor( var errors = 0 + eventHandlerDepth++ for (listener in listeners) { if (!shouldInvoke(event, listener)) continue try { @@ -48,13 +67,14 @@ class EventHandler private constructor( } if (event.isCancelled && !canReceiveCancelled) break } + eventHandlerDepth-- if (errors > 3) { val hiddenErrors = errors - 3 ChatUtils.chat( Text.text( - "§c[SkyHanni/${SkyHanniMod.version}] $hiddenErrors more errors in $name are hidden!" - ) + "§c[SkyHanni/${SkyHanniMod.version}] $hiddenErrors more errors in $name are hidden!", + ), ) } return event.isCancelled diff --git a/src/main/java/at/hannibal2/skyhanni/config/ConfigManager.kt b/src/main/java/at/hannibal2/skyhanni/config/ConfigManager.kt index b82d4d8f9909..a534eac89193 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/ConfigManager.kt +++ b/src/main/java/at/hannibal2/skyhanni/config/ConfigManager.kt @@ -1,6 +1,7 @@ package at.hannibal2.skyhanni.config import at.hannibal2.skyhanni.SkyHanniMod +import at.hannibal2.skyhanni.api.event.EventHandler import at.hannibal2.skyhanni.config.core.config.Position import at.hannibal2.skyhanni.config.core.config.PositionList import at.hannibal2.skyhanni.data.jsonobjects.local.FriendsJson @@ -96,7 +97,7 @@ class ConfigManager { try { findPositionLinks(features, mutableSetOf()) } catch (e: Exception) { - if (LorenzEvent.isInGuardedEventHandler) throw e + if (LorenzEvent.isInGuardedEventHandler || EventHandler.isInEventHandler) throw e } } diff --git a/src/main/java/at/hannibal2/skyhanni/utils/ConfigUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/ConfigUtils.kt index 94d981d8ef61..bcf8e45b25d4 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/ConfigUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/ConfigUtils.kt @@ -1,6 +1,7 @@ package at.hannibal2.skyhanni.utils import at.hannibal2.skyhanni.SkyHanniMod +import at.hannibal2.skyhanni.api.event.EventHandler import at.hannibal2.skyhanni.config.ConfigGuiManager import at.hannibal2.skyhanni.config.HasLegacyId import at.hannibal2.skyhanni.events.LorenzEvent @@ -86,7 +87,7 @@ object ConfigUtils { if (tryJumpToEditor(ConfigGuiManager.getEditorInstance())) return // TODO create utils function "crashIfInDevEnv" - if (LorenzEvent.isInGuardedEventHandler) { + if (LorenzEvent.isInGuardedEventHandler || EventHandler.isInEventHandler) { throw Error("can not jump to editor $name") } ErrorManager.logErrorStateWithData( diff --git a/src/main/java/at/hannibal2/skyhanni/utils/repopatterns/RepoPatternManager.kt b/src/main/java/at/hannibal2/skyhanni/utils/repopatterns/RepoPatternManager.kt index ad10ba19529d..8bef5061f82d 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/repopatterns/RepoPatternManager.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/repopatterns/RepoPatternManager.kt @@ -1,6 +1,7 @@ package at.hannibal2.skyhanni.utils.repopatterns import at.hannibal2.skyhanni.SkyHanniMod +import at.hannibal2.skyhanni.api.event.EventHandler import at.hannibal2.skyhanni.api.event.HandleEvent import at.hannibal2.skyhanni.config.ConfigManager import at.hannibal2.skyhanni.config.features.dev.RepoPatternConfig @@ -60,11 +61,6 @@ object RepoPatternManager { private var usedKeys: NavigableMap> = TreeMap() private var wasPreInitialized = false - private val isInDevEnv = try { - Launch.blackboard["fml.deobfuscatedEnvironment"] as Boolean - } catch (_: Exception) { - true - } private val insideTest = Launch.blackboard == null @@ -88,8 +84,9 @@ object RepoPatternManager { * Crash if in a development environment, or if inside a guarded event handler. */ fun crash(reason: String) { - if (isInDevEnv || LorenzEvent.isInGuardedEventHandler) + if (LorenzEvent.isInGuardedEventHandler || EventHandler.isInEventHandler) { throw RuntimeException(reason) + } } /** From 9d21e7b150a88df224bd35e702bf71e456019db1 Mon Sep 17 00:00:00 2001 From: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Date: Sat, 26 Oct 2024 13:18:15 +1100 Subject: [PATCH 006/105] Backend: Fix code in PlayerChatManager (#2756) --- .../skyhanni/data/hypixel/chat/PlayerChatManager.kt | 12 ++++-------- 1 file changed, 4 insertions(+), 8 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt b/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt index 2529e7ff1fde..eb48bb4e9b97 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/hypixel/chat/PlayerChatManager.kt @@ -206,24 +206,20 @@ object PlayerChatManager { private fun sendSystemMessage(event: LorenzChatEvent) { with(SystemMessageEvent(event.message, event.chatComponent)) { - val cancelled = postAndCatch() - event.handleChat(cancelled, blockedReason, chatComponent) + postAndCatch() + event.handleChat(blockedReason, chatComponent) } } private fun AbstractChatEvent.postChat(event: LorenzChatEvent) { - val cancelled = postAndCatch() - event.handleChat(cancelled, blockedReason, chatComponent) + postAndCatch() + event.handleChat(blockedReason, chatComponent) } private fun LorenzChatEvent.handleChat( - cancelled: Boolean, blockedReason: String?, chatComponent: IChatComponent, ) { - if (cancelled) { - this.cancel() - } blockedReason?.let { this.blockedReason = it } From c84af157a6c82ac25baf60431e1e839bc58fb517 Mon Sep 17 00:00:00 2001 From: NeoNyaa <56982408+NeoNyaa@users.noreply.github.com> Date: Sat, 26 Oct 2024 05:03:02 +0100 Subject: [PATCH 007/105] Backend: Reworded a previous commit (#2818) --- CONTRIBUTING.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 53ec5bc2772e..a30f9178b6b3 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -85,7 +85,7 @@ out [their guide](https://github.com/NotEnoughUpdates/NotEnoughUpdates/blob/mast If you are not very familiar with git, you might want to try this out: https://learngitbranching.js.org/. -Proposed changes are better off being in their own branch, you can do this by doing the following from within IntelliJ with the SkyHanni project already open. +Proposed changes are better off being in their own branch as this makes development easier for both you and the maintainers of this repository, you can do this by following the instructions from within the IntelliJ window with the SkyHanni project already open. - Click the beta dropdown at the top of IntelliJ - Click new branch - Give the branch a name relating to the changes you plan to make From 742d175b2f9d103e7af8adf2aee11882be3107b8 Mon Sep 17 00:00:00 2001 From: David Cole <40234707+DavidArthurCole@users.noreply.github.com> Date: Sat, 26 Oct 2024 04:37:28 -0400 Subject: [PATCH 008/105] Backend Fix: Detekt Artifact not Uploading (#2822) --- .github/workflows/detekt.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/detekt.yml b/.github/workflows/detekt.yml index 97909596a3e3..a258661f1dfd 100644 --- a/.github/workflows/detekt.yml +++ b/.github/workflows/detekt.yml @@ -43,7 +43,7 @@ jobs: chmod +x .github/scripts/process_detekt_sarif.sh ./.github/scripts/process_detekt_sarif.sh versions/1.8.9/build/reports/detekt/main.sarif | tee detekt_output.txt - name: Upload detekt output as artifact - if: ${{ steps.check_sarif.outputs.exists == 'true' }} + if: ${{ !cancelled() && steps.check_sarif.outputs.exists == 'true' }} uses: actions/upload-artifact@v4 with: name: detekt-output From 69e74cce8912fe00dac3120b465f413870ec2526 Mon Sep 17 00:00:00 2001 From: Phoebe <77941535+catgirlseraid@users.noreply.github.com> Date: Sun, 27 Oct 2024 06:19:12 +1300 Subject: [PATCH 009/105] Fix: update dungeon potion regex (#2825) --- .../features/inventory/ItemDisplayOverlayFeatures.kt | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/ItemDisplayOverlayFeatures.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/ItemDisplayOverlayFeatures.kt index e8cd7cdae80a..97a5a5737320 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/ItemDisplayOverlayFeatures.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/ItemDisplayOverlayFeatures.kt @@ -78,9 +78,14 @@ object ItemDisplayOverlayFeatures { "harvest", "§7§7You may harvest §6(?.).*", ) + + /** + * REGEX-TEST: Dungeon VII Potion + * REGEX-TEST: Dungeon VII Potion x1 + */ private val dungeonPotionPattern by patternGroup.pattern( "dungeonpotion", - "Dungeon (?.*) Potion", + "Dungeon (?.*) Potion(?: x1)?", ) private val bingoGoalRankPattern by patternGroup.pattern( "bingogoalrank", From 79580af37a5ea70511717b8e34a4607db46583f9 Mon Sep 17 00:00:00 2001 From: Phoebe <77941535+catgirlseraid@users.noreply.github.com> Date: Sun, 27 Oct 2024 06:30:20 +1300 Subject: [PATCH 010/105] Fix: brewing stand shift click close button (#2824) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt index 65c0d3940cb9..824d95789b3b 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt @@ -11,6 +11,7 @@ import net.minecraftforge.fml.common.eventhandler.SubscribeEvent @SkyHanniModule object ShiftClickBrewing { + private val closeButtonIndex = 49 @SubscribeEvent fun onSlotClick(event: GuiContainerEvent.SlotClickEvent) { @@ -19,7 +20,7 @@ object ShiftClickBrewing { if (event.gui !is GuiChest) return - if (event.slot == null) return + if (event.slot == null || event.slotId == closeButtonIndex) return val chestName = InventoryUtils.openInventoryName() if (!chestName.startsWith("Brewing Stand")) return From 1f6b0995cbb82aef2842f4ea4f4019de8864b28d Mon Sep 17 00:00:00 2001 From: David Cole <40234707+DavidArthurCole@users.noreply.github.com> Date: Sat, 26 Oct 2024 13:31:28 -0400 Subject: [PATCH 011/105] Fix: Typo in Rabbit the Fish Config (#2820) --- .../at/hannibal2/skyhanni/config/ConfigUpdaterMigrator.kt | 2 +- .../config/features/event/hoppity/HoppityEggsConfig.java | 4 ++-- .../skyhanni/features/event/hoppity/HoppityEventSummary.kt | 6 ++++++ .../features/event/hoppity/HoppityRabbitTheFishChecker.kt | 2 +- 4 files changed, 10 insertions(+), 4 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/config/ConfigUpdaterMigrator.kt b/src/main/java/at/hannibal2/skyhanni/config/ConfigUpdaterMigrator.kt index f8afe645cf85..d90ce7730e61 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/ConfigUpdaterMigrator.kt +++ b/src/main/java/at/hannibal2/skyhanni/config/ConfigUpdaterMigrator.kt @@ -12,7 +12,7 @@ import com.google.gson.JsonPrimitive object ConfigUpdaterMigrator { val logger = LorenzLogger("ConfigMigration") - const val CONFIG_VERSION = 63 + const val CONFIG_VERSION = 64 fun JsonElement.at(chain: List, init: Boolean): JsonElement? { if (chain.isEmpty()) return this if (this !is JsonObject) return null diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/event/hoppity/HoppityEggsConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/event/hoppity/HoppityEggsConfig.java index f34959bd8a97..e339574e4f0e 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/features/event/hoppity/HoppityEggsConfig.java +++ b/src/main/java/at/hannibal2/skyhanni/config/features/event/hoppity/HoppityEggsConfig.java @@ -218,8 +218,8 @@ public String toString() { public boolean petWarning = false; @Expose - @ConfigOption(name = "Prevent Missing Fish the Rabbit", desc = "Prevent closing a Meal Egg's inventory if Fish the Rabbit is present.") + @ConfigOption(name = "Prevent Missing Rabbit the Fish", desc = "Prevent closing a Meal Egg's inventory if Rabbit the Fish is present.") @ConfigEditorBoolean @FeatureToggle - public boolean preventMissingFish = true; + public boolean preventMissingRabbitTheFish = true; } diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityEventSummary.kt b/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityEventSummary.kt index 41d5142d8ca4..a7c731a18827 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityEventSummary.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityEventSummary.kt @@ -2,6 +2,7 @@ package at.hannibal2.skyhanni.features.event.hoppity import at.hannibal2.skyhanni.SkyHanniMod import at.hannibal2.skyhanni.api.event.HandleEvent +import at.hannibal2.skyhanni.config.ConfigUpdaterMigrator import at.hannibal2.skyhanni.config.features.event.hoppity.HoppityEventSummaryConfig.HoppityStat import at.hannibal2.skyhanni.config.storage.ProfileSpecificStorage.HoppityEventStats import at.hannibal2.skyhanni.config.storage.ProfileSpecificStorage.HoppityEventStats.RabbitData @@ -48,6 +49,11 @@ object HoppityEventSummary { if (event.chocGained > 0) stats.dupeChocolateGained += event.chocGained } + @SubscribeEvent + fun onConfigFix(event: ConfigUpdaterMigrator.ConfigFixEvent) { + event.move(64, "event.hoppity.preventMissingFish", "event.hoppity.preventMissingRabbitTheFish") + } + @SubscribeEvent fun onSecondPassed(event: SecondPassedEvent) { if (!LorenzUtils.inSkyBlock) return diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityRabbitTheFishChecker.kt b/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityRabbitTheFishChecker.kt index 02e800dccbc3..f1f9eee07762 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityRabbitTheFishChecker.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/hoppity/HoppityRabbitTheFishChecker.kt @@ -94,5 +94,5 @@ object HoppityRabbitTheFishChecker { return shouldContinue } - private fun isEnabled() = LorenzUtils.inSkyBlock && HoppityAPI.isHoppityEvent() && config.preventMissingFish + private fun isEnabled() = LorenzUtils.inSkyBlock && HoppityAPI.isHoppityEvent() && config.preventMissingRabbitTheFish } From f226fc113014dea6c8fcccd7e00d52a610f8f8bc Mon Sep 17 00:00:00 2001 From: Kaeso <24925519+ptlthg@users.noreply.github.com> Date: Sat, 26 Oct 2024 13:32:36 -0400 Subject: [PATCH 012/105] Fix: Catch JSON Parse Errors in APIUtils (#2819) --- .../java/at/hannibal2/skyhanni/utils/APIUtils.kt | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/utils/APIUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/APIUtils.kt index f331ab3e3d17..9524836e427f 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/APIUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/APIUtils.kt @@ -181,9 +181,16 @@ object APIUtils { private fun readResponse(entity: HttpEntity): JsonObject { val retSrc = EntityUtils.toString(entity) ?: return JsonObject() - val parsed = parser.parse(retSrc) - if (parsed.isJsonNull) return JsonObject() - return parsed as JsonObject + + try { + val parsed = parser.parse(retSrc) + if (parsed.isJsonNull) return JsonObject() + + return parsed as JsonObject + } catch (_: Throwable) { + // This causes content types that aren't JSON to be ignored + return JsonObject() + } } fun postJSONIsSuccessful(url: String, body: String, silentError: Boolean = false): Boolean { From 257640fdd4708356cebf8898d43e8ec4d7bd7351 Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal00212@users.noreply.github.com> Date: Sat, 26 Oct 2024 20:14:40 +0200 Subject: [PATCH 013/105] fixed detekt and wording --- src/main/java/at/hannibal2/skyhanni/data/IslandGraphs.kt | 2 +- .../hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/data/IslandGraphs.kt b/src/main/java/at/hannibal2/skyhanni/data/IslandGraphs.kt index 386fb8bbf489..acf1b6e0c2dc 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/IslandGraphs.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/IslandGraphs.kt @@ -466,7 +466,7 @@ object IslandGraphs { componentText.onClick( onClick = { stop() - "§e[SkyHanni] Navigation manually stopped!".asComponent().send(PATHFIND_ID) + "§e[SkyHanni] Navigation stopped!".asComponent().send(PATHFIND_ID) }, ) componentText.hover = "§eClick to stop navigating!".asComponent() diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt index 824d95789b3b..141ec75850b6 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/ShiftClickBrewing.kt @@ -11,7 +11,7 @@ import net.minecraftforge.fml.common.eventhandler.SubscribeEvent @SkyHanniModule object ShiftClickBrewing { - private val closeButtonIndex = 49 + private const val closeButtonIndex = 49 @SubscribeEvent fun onSlotClick(event: GuiContainerEvent.SlotClickEvent) { From 6b4f3a330869360b55a9f55fc0f9dc554e195feb Mon Sep 17 00:00:00 2001 From: martimavocado <39881008+martimavocado@users.noreply.github.com> Date: Sat, 26 Oct 2024 19:14:57 +0100 Subject: [PATCH 014/105] Fix: Great Spook mob cooldown and timer (#2804) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../config/features/dev/DebugConfig.java | 5 + .../data/jsonobjects/repo/EventsJson.kt | 9 + .../features/event/spook/TheGreatSpook.kt | 188 ++++++++++++++---- .../at/hannibal2/skyhanni/utils/ChatUtils.kt | 16 +- 4 files changed, 178 insertions(+), 40 deletions(-) create mode 100644 src/main/java/at/hannibal2/skyhanni/data/jsonobjects/repo/EventsJson.kt diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java index 56a17dfb921b..9f92436cfa3c 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java +++ b/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java @@ -162,6 +162,11 @@ public class DebugConfig { @ConfigEditorBoolean public boolean alwaysHoppitys = false; + @Expose + @ConfigOption(name = "Always Great Spook", desc = "Assumes the Great Spook is always active.") + @ConfigEditorBoolean + public Property forceGreatSpook = Property.of(false); + // Does not have a config element! @Expose public Position trackSoundPosition = new Position(0, 0); diff --git a/src/main/java/at/hannibal2/skyhanni/data/jsonobjects/repo/EventsJson.kt b/src/main/java/at/hannibal2/skyhanni/data/jsonobjects/repo/EventsJson.kt new file mode 100644 index 000000000000..cab8ae7fe625 --- /dev/null +++ b/src/main/java/at/hannibal2/skyhanni/data/jsonobjects/repo/EventsJson.kt @@ -0,0 +1,9 @@ +package at.hannibal2.skyhanni.data.jsonobjects.repo + +import at.hannibal2.skyhanni.utils.SimpleTimeMark +import com.google.gson.annotations.Expose +import com.google.gson.annotations.SerializedName + +data class EventsJson( + @Expose @SerializedName("great_spook") val greatSpook: Map, +) diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt b/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt index 4e88237e0f12..9125f25a2ee0 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt @@ -1,84 +1,167 @@ package at.hannibal2.skyhanni.features.event.spook import at.hannibal2.skyhanni.SkyHanniMod +import at.hannibal2.skyhanni.data.jsonobjects.repo.EventsJson import at.hannibal2.skyhanni.data.model.SkyblockStat +import at.hannibal2.skyhanni.events.ConfigLoadEvent +import at.hannibal2.skyhanni.events.DebugDataCollectEvent import at.hannibal2.skyhanni.events.GuiRenderEvent +import at.hannibal2.skyhanni.events.IslandChangeEvent import at.hannibal2.skyhanni.events.LorenzChatEvent +import at.hannibal2.skyhanni.events.RepositoryReloadEvent import at.hannibal2.skyhanni.events.SecondPassedEvent import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.ChatUtils +import at.hannibal2.skyhanni.utils.ConditionalUtils.afterChange import at.hannibal2.skyhanni.utils.DelayedRun import at.hannibal2.skyhanni.utils.HypixelCommands import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.NEUCalculator import at.hannibal2.skyhanni.utils.RegexUtils.matchMatcher +import at.hannibal2.skyhanni.utils.RegexUtils.matches +import at.hannibal2.skyhanni.utils.RenderUtils.renderRenderable import at.hannibal2.skyhanni.utils.RenderUtils.renderString +import at.hannibal2.skyhanni.utils.SimpleTimeMark import at.hannibal2.skyhanni.utils.SoundUtils import at.hannibal2.skyhanni.utils.StringUtils -import at.hannibal2.skyhanni.utils.TabListData +import at.hannibal2.skyhanni.utils.TimeUnit +import at.hannibal2.skyhanni.utils.TimeUtils.format +import at.hannibal2.skyhanni.utils.renderables.Renderable import at.hannibal2.skyhanni.utils.repopatterns.RepoPattern import net.minecraftforge.fml.common.eventhandler.SubscribeEvent +import kotlin.time.Duration.Companion.minutes +import kotlin.time.Duration.Companion.seconds @SkyHanniModule object TheGreatSpook { - - // §r§cPrimal Fears§r§7: §r§6§lREADY!! private val config get() = SkyHanniMod.feature.event.spook - private var displayTimer = "" - private var displayTimeLeft = "" - private var notificationSeconds = 0 + + private var isGreatSpookActive = false + private var greatSpookTimeRange: ClosedRange? = null + private var greatSpookEndTime = SimpleTimeMark.farPast() + + private var displayMobCooldown: Renderable? = null + private var displayGreatSpookEnd: Renderable? = null + + private var timeUntilNextMob = SimpleTimeMark.farPast() + + private val patternGroup = RepoPattern.group("event.greatspook") + + /** + * REGEX-TEST: §d§lQUICK MATHS! §r§7Solve: §r§e(10*2)+12*5 + */ + private val mathFearMessagePattern by patternGroup.pattern( + "chat.math", + "§d§lQUICK MATHS! §r§7Solve: §r§e(?.*)", + ) + + /** + * REGEX-TEST: §4[FEAR] Public Speaking Demon§r§f: Speak PlasticEating! + */ + private val speakingFearMessagePattern by patternGroup.pattern( + "chat.speaking", + "§4\\[FEAR] Public Speaking Demon§r§f: (Speak|Say something interesting) (?.*)!", + ) + + /** + * REGEX-TEST: §5§lFEAR. §r§eA §r§dPrimal Fear §r§ehas been summoned! + */ + private val primalFearSpawnPattern by patternGroup.pattern( + "mob.spawn", + "§5§lFEAR\\. §r§eA §r§dPrimal Fear §r§ehas been summoned!", + ) @SubscribeEvent fun onSecondPassed(event: SecondPassedEvent) { if (!LorenzUtils.inSkyBlock) return + if (!isGreatSpookActive) return + + val fear = SkyblockStat.FEAR.lastKnownValue ?: 0.0 + val mobCooldown = timeUntilNextMob.minus((3 * fear).seconds) + val mobCooldownString = if (mobCooldown.isInFuture()) { + "§5Next fear in: §b${ + mobCooldown.timeUntil().format( + biggestUnit = TimeUnit.MINUTE, + showMilliSeconds = false, + showSmallerUnits = false, + ) + }" + } else { + "§5§lPrimal Fear Ready!" + } + displayMobCooldown = Renderable.string(mobCooldownString) - if (config.primalFearTimer || config.primalFearNotification) displayTimer = checkTabList(" §r§cPrimal Fears§r§7: ") - if (config.greatSpookTimeLeft) displayTimeLeft = checkTabList(" §r§dEnds In§r§7: ") - if (config.primalFearNotification) { - if (displayTimer.endsWith("READY!!")) { - if (notificationSeconds > 0) { - SoundUtils.playBeepSound() - notificationSeconds-- + if (config.primalFearNotification && mobCooldown.isInFuture()) { + SoundUtils.playPlingSound() + } + + val greatSpookEnd = greatSpookTimeRange?.endInclusive ?: return + val timeLeftString = if (greatSpookEnd.isInFuture()) { + "§5Great Spook time left: §b${ + greatSpookEnd.timeUntil().format( + biggestUnit = TimeUnit.DAY, + maxUnits = 2, + ) + }" + } else { + "§5§lThe Great Spook has ended!" + } + displayGreatSpookEnd = Renderable.string(timeLeftString) + } + + @SubscribeEvent + fun onConfigLoad(event: ConfigLoadEvent) { + val config = SkyHanniMod.feature.dev.debug.forceGreatSpook + config.afterChange { + if (config.get()) { + isGreatSpookActive = true + greatSpookEndTime = SimpleTimeMark.farFuture() + } else { + val timeRange = greatSpookTimeRange + if (timeRange == null) { + isGreatSpookActive = false + greatSpookEndTime = SimpleTimeMark.farPast() + return@afterChange } - } else if (displayTimer.isNotEmpty()) { - notificationSeconds = 5 + isGreatSpookActive = SimpleTimeMark.now() in timeRange + greatSpookEndTime = timeRange.endInclusive } } } - private fun checkTabList(matchString: String): String { - return (TabListData.getTabList().find { it.contains(matchString) }.orEmpty()).trim() + @SubscribeEvent + fun onWorldSwitch(event: IslandChangeEvent) { + val currentTime = SimpleTimeMark.now() + val timeRange = greatSpookTimeRange ?: run { + isGreatSpookActive = false + return + } + + isGreatSpookActive = currentTime in timeRange } @SubscribeEvent fun onRenderOverlay(event: GuiRenderEvent.GuiOverlayRenderEvent) { if (!LorenzUtils.inSkyBlock) return + if (!isGreatSpookActive) return - if (config.primalFearTimer) config.positionTimer.renderString(displayTimer, posLabel = "Primal Fear Timer") + if (config.primalFearTimer) { + displayMobCooldown.let { + config.positionTimer.renderRenderable(it, posLabel = "Primal Fear Timer") + } + } if (config.fearStatDisplay) { SkyblockStat.FEAR.displayValue?.let { config.positionFear.renderString(it, posLabel = "Fear Stat Display") } } - if (config.greatSpookTimeLeft) config.positionTimeLeft.renderString(displayTimeLeft, posLabel = "Time Left Display") + if (config.greatSpookTimeLeft) { + displayGreatSpookEnd.let { + config.positionTimeLeft.renderRenderable(it, posLabel = "Great Spook Time Left") + } + } } - /** - * REGEX-TEST: §d§lQUICK MATHS! §r§7Solve: §r§e(10*2)+12*5 - */ - private val mathFearMessagePattern by RepoPattern.pattern( - "chat.math", - "§d§lQUICK MATHS! §r§7Solve: §r§e(?.*)", - ) - - /** - * REGEX-TEST: §4[FEAR] Public Speaking Demon§r§f: Speak PlasticEating! - */ - private val speakingFearMessagePattern by RepoPattern.pattern( - "chat.speaking", - "§4\\[FEAR] Public Speaking Demon§r§f: (Speak|Say something interesting) (?.*)!", - ) - private fun mathSolver(query: String?) { val answer = query?.let { NEUCalculator.calculateOrNull(it)?.toInt() } ?: run { ChatUtils.userError("Failed to solve $query!") @@ -108,6 +191,18 @@ object TheGreatSpook { @SubscribeEvent fun onChat(event: LorenzChatEvent) { if (!LorenzUtils.inSkyBlock) return + if (!isGreatSpookActive) return + + if (primalFearSpawnPattern.matches(event.message)) { + timeUntilNextMob = SimpleTimeMark.now().plus(6.minutes) + if (SkyblockStat.FEAR.lastKnownValue == null && (config.primalFearNotification || config.primalFearTimer)) { + ChatUtils.userError( + "Fear stat not found! Please enable the Stats widget and enable the Fear stat for the best results.", + replaceSameMessage = true, + ) + } + return + } if (config.primalFearSolver.math) { mathFearMessagePattern.matchMatcher(event.message) { @@ -125,4 +220,27 @@ object TheGreatSpook { } } } + + @SubscribeEvent + fun onRepoReload(event: RepositoryReloadEvent) { + val data = event.getConstant("Events").greatSpook + + val startTime = data["start_time"] ?: SimpleTimeMark.farPast() + val endTime = data["end_time"] ?: SimpleTimeMark.farPast() + + greatSpookTimeRange = startTime..endTime + greatSpookEndTime = if (SkyHanniMod.feature.dev.debug.forceGreatSpook.get()) SimpleTimeMark.farFuture() else endTime + } + + @SubscribeEvent + fun onDebug(event: DebugDataCollectEvent) { + event.title("Great Spook") + + event.addIrrelevant { + add("isActive: $isGreatSpookActive") + add("activeTimeRange: $greatSpookTimeRange") + add("eventEndTime: $greatSpookEndTime") + add("timeUntilNextMob: $timeUntilNextMob") + } + } } diff --git a/src/main/java/at/hannibal2/skyhanni/utils/ChatUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/ChatUtils.kt index 1547e39b5216..d48c8d8a79de 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/ChatUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/ChatUtils.kt @@ -44,8 +44,11 @@ object ChatUtils { * * @see DEBUG_PREFIX */ - fun debug(message: String) { - if (LorenzUtils.debug && internalChat(DEBUG_PREFIX + message)) { + fun debug( + message: String, + replaceSameMessage: Boolean = false, + ) { + if (LorenzUtils.debug && internalChat(DEBUG_PREFIX + message, replaceSameMessage)) { LorenzUtils.consoleLog("[Debug] $message") } } @@ -58,8 +61,11 @@ object ChatUtils { * * @see USER_ERROR_PREFIX */ - fun userError(message: String) { - internalChat(USER_ERROR_PREFIX + message) + fun userError( + message: String, + replaceSameMessage: Boolean = false, + ) { + internalChat(USER_ERROR_PREFIX + message, replaceSameMessage) } /** @@ -87,7 +93,7 @@ object ChatUtils { private fun internalChat( message: String, - replaceSameMessage: Boolean = false, + replaceSameMessage: Boolean, ): Boolean { val text = ChatComponentText(message) From 6b27638c293da2ff318ac5b0f99c7bc2f5ea488d Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal00212@users.noreply.github.com> Date: Sat, 26 Oct 2024 21:04:57 +0200 Subject: [PATCH 015/105] Version 0.28 Beta 8 --- docs/CHANGELOG.md | 22 ++++++++++++++++++++++ root.gradle.kts | 2 +- 2 files changed, 23 insertions(+), 1 deletion(-) diff --git a/docs/CHANGELOG.md b/docs/CHANGELOG.md index 086b77122221..f91b89c13179 100644 --- a/docs/CHANGELOG.md +++ b/docs/CHANGELOG.md @@ -95,6 +95,15 @@ + Improved the Time Tower Usage Warning so it doesn't spam messages. - MTOnline (https://github.com/hannibal002/SkyHanni/pull/2730) +#### Great Spook Improvements + ++ Highlight Great Spook's answer in blue. - not_a_cow (https://github.com/hannibal002/SkyHanni/pull/2798) + +#### Custom Scoreboard Improvements + ++ Added the date to the Custom Scoreboard Lobby code. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2802) ++ Added an option to display the profile type instead of the name in the Custom Scoreboard. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2810) + #### Misc Improvements + Added distance display to waypoints created by Patcher's Send Coords feature. - jani (https://github.com/hannibal002/SkyHanni/pull/2704) @@ -128,6 +137,8 @@ + Fixed Compact Item Stars. - Empa, Fazfoxy (https://github.com/hannibal002/SkyHanni/pull/2741) + Fixed an Estimated Item Value issue where +10 stars were accidentally added to certain items and unstarred items were not showing stars. - Fazfoxy and Empa (https://github.com/hannibal002/SkyHanni/pull/2758) + Fixed an issue with Estimated Item Value erroring when multiple mods affect the same item. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2787) ++ Fixed "Dungeon Potion level as stack size" not working in shop menus. - phoebe (https://github.com/hannibal002/SkyHanni/pull/2825) ++ Fixed being unable to use the "Close" button when "Change all clicks to shift clicks in brewing stands" is enabled. - phoebe (https://github.com/hannibal002/SkyHanni/pull/2824) #### Combat Fixes @@ -144,6 +155,7 @@ + Fixed Custom Scoreboard duplicating the Party Leader. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2780) + Fixed some Custom Scoreboard errors. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2779) + Fixed party leader not displaying correctly in the Custom Scoreboard. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2783) ++ Fixed the Broodmother line in the Custom Scoreboard having a leading space. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2810) #### Hoppity Fixes @@ -151,11 +163,14 @@ + Fixed El Dorado not receiving a compacted chat message. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2742) + Fixed issues with El Dorado stray detection. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2786) + Fixed an error when Rabbit the Fish was found in Meal Eggs. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2785) ++ Fixed dyes being incorrectly modified in Hoppity's Collection after disabling "Re-Color Missing Rabbit Dyes". - MTOnline (https://github.com/hannibal002/SkyHanni/pull/2803) #### Garden Fixes + Fixed farming weight not disappearing when the config option is off. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2731) + Fixed New Visitor Ping triggering too late if the player is actively farming. - Luna (https://github.com/hannibal002/SkyHanni/pull/2767) ++ Fixed the mouse not unlocking when teleporting to the Barn. - not_a_cow (https://github.com/hannibal002/SkyHanni/pull/2799) ++ Fixed API error when sending Jacob Contests. - Ke5o (https://github.com/hannibal002/SkyHanni/pull/2819) #### Crimson Isle Fixes @@ -183,6 +198,7 @@ + Fixed Fear Stat Display. - Fazfoxy (https://github.com/hannibal002/SkyHanni/pull/2766) + Fixed Carnival Goal display rarely showing outside the Hub Island. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2772) ++ Fixed the Great Spook features. - martimavocado (https://github.com/hannibal002/SkyHanni/pull/2804) #### Rift Fixes @@ -191,6 +207,8 @@ #### Chat Fixes + Fixed item stash messages not being compacted correctly. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2781) ++ Fixed own player messages not being reformatted by chat formatting. - !nea (https://github.com/hannibal002/SkyHanni/pull/2806) + + Also fixed ranks losing their "+" colors. #### Misc Fixes @@ -198,6 +216,7 @@ + Fixed the formatting of negative durations. - Empa (https://github.com/hannibal002/SkyHanni/pull/2726) + Fixed debug messages not sending when debug mode is enabled. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2793) + Fixed TPS display not working outside Skyblock. - Empa (https://github.com/hannibal002/SkyHanni/pull/2791) ++ Fixed the "Colored Class Level" tab list displaying "null". - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2814) ### Technical Details @@ -227,6 +246,9 @@ + Added informative comments on PRs when failures are detected. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2790) + Added in-file annotations when 'Detekt' failures occur. - CalMWolfs (https://github.com/hannibal002/SkyHanni/pull/2790) + Added some preprocessing mappings. - CalMWolfs (https://github.com/hannibal002/SkyHanni/pull/2776) ++ Added Shot support to the multi-version build. - !nea (https://github.com/hannibal002/SkyHanni/pull/2800) + + This allows adding nullability annotations (and other simple annotations) to vanilla code. ++ Added an event handler check to SkyHanni Events. - CalMWolfs (https://github.com/hannibal002/SkyHanni/pull/2755) ## Version 0.27 diff --git a/root.gradle.kts b/root.gradle.kts index 46d24729e9a4..11cd8a409819 100644 --- a/root.gradle.kts +++ b/root.gradle.kts @@ -14,7 +14,7 @@ plugins { allprojects { group = "at.hannibal2.skyhanni" - version = "0.28.Beta.7" + version = "0.28.Beta.8" repositories { mavenCentral() mavenLocal() From b87483b531cbbd295ab335531dfa5ac6a4697f8e Mon Sep 17 00:00:00 2001 From: Luna Date: Sat, 26 Oct 2024 22:55:45 +0200 Subject: [PATCH 016/105] Fix: Primal Fear Notify backwards logic (#2831) --- .../at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt b/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt index 9125f25a2ee0..22408ebfba4c 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt @@ -91,7 +91,7 @@ object TheGreatSpook { } displayMobCooldown = Renderable.string(mobCooldownString) - if (config.primalFearNotification && mobCooldown.isInFuture()) { + if (config.primalFearNotification && mobCooldown.isInPast()) { SoundUtils.playPlingSound() } From d030f24e0a721a50d22d494c46b1a5d273ffce65 Mon Sep 17 00:00:00 2001 From: J10a1n15 <45315647+j10a1n15@users.noreply.github.com> Date: Sat, 26 Oct 2024 22:56:43 +0200 Subject: [PATCH 017/105] Fix: "null" in Custom Scoreboard LobbyCode (#2832) --- .../customscoreboard/elements/ScoreboardElementLobbyCode.kt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementLobbyCode.kt b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementLobbyCode.kt index f4f64ed17e3d..fcb07f2a3d0b 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementLobbyCode.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementLobbyCode.kt @@ -13,8 +13,8 @@ object ScoreboardElementLobbyCode : ScoreboardElement() { override fun getDisplay() = buildString { if (CustomScoreboard.displayConfig.dateInLobbyCode) append("§7${LocalDate.now().format(formatter)} ") - append(HypixelData.serverId?.let { "§8$it" }) - append(DungeonAPI.getRoomID()?.let { " §8$it" }) + HypixelData.serverId?.let { append("§8$it") } + DungeonAPI.getRoomID()?.let { append(" §8$it") } } override val configLine = "§710/23/2024 §8mega77CK" From 4750db953c4bec0b3fb22b1f57633a7cf3f1dc71 Mon Sep 17 00:00:00 2001 From: Empa <42304516+ItsEmpa@users.noreply.github.com> Date: Sun, 27 Oct 2024 10:25:30 +0100 Subject: [PATCH 018/105] Improvement: ScoreboardUpdateEvent (#2765) Co-authored-by: Empa Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- src/main/java/at/hannibal2/skyhanni/data/BitsAPI.kt | 2 +- src/main/java/at/hannibal2/skyhanni/data/HotmData.kt | 2 +- src/main/java/at/hannibal2/skyhanni/data/MiningAPI.kt | 2 +- src/main/java/at/hannibal2/skyhanni/data/PurseAPI.kt | 8 ++++---- .../java/at/hannibal2/skyhanni/data/ScoreboardData.kt | 5 +++-- .../at/hannibal2/skyhanni/events/PurseChangeEvent.kt | 2 +- .../hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt | 9 ++++++++- .../hannibal2/skyhanni/features/garden/pests/PestAPI.kt | 2 +- 8 files changed, 20 insertions(+), 12 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/data/BitsAPI.kt b/src/main/java/at/hannibal2/skyhanni/data/BitsAPI.kt index 022a18d926e3..a501ba25f99c 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/BitsAPI.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/BitsAPI.kt @@ -146,7 +146,7 @@ object BitsAPI { @SubscribeEvent fun onScoreboardChange(event: ScoreboardUpdateEvent) { if (!isEnabled()) return - for (line in event.scoreboard) { + for (line in event.added) { val message = line.trimWhiteSpace().removeResets() bitsScoreboardPattern.matchMatcher(message) { diff --git a/src/main/java/at/hannibal2/skyhanni/data/HotmData.kt b/src/main/java/at/hannibal2/skyhanni/data/HotmData.kt index beb7581b0d0d..614772b1971e 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/HotmData.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/HotmData.kt @@ -680,7 +680,7 @@ enum class HotmData( fun onScoreboardUpdate(event: ScoreboardUpdateEvent) { if (!LorenzUtils.inSkyBlock) return - ScoreboardPattern.powderPattern.firstMatcher(event.scoreboard) { + ScoreboardPattern.powderPattern.firstMatcher(event.added) { val type = HotmAPI.PowderType.entries.firstOrNull { it.displayName == group("type") } ?: return val amount = group("amount").formatLong() val difference = amount - type.getCurrent() diff --git a/src/main/java/at/hannibal2/skyhanni/data/MiningAPI.kt b/src/main/java/at/hannibal2/skyhanni/data/MiningAPI.kt index fbe304098299..0289d5e0ed53 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/MiningAPI.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/MiningAPI.kt @@ -165,7 +165,7 @@ object MiningAPI { @SubscribeEvent fun onScoreboardChange(event: ScoreboardUpdateEvent) { - val newCold = coldPattern.firstMatcher(event.scoreboard) { + val newCold = coldPattern.firstMatcher(event.added) { group("cold").toInt().absoluteValue } ?: return diff --git a/src/main/java/at/hannibal2/skyhanni/data/PurseAPI.kt b/src/main/java/at/hannibal2/skyhanni/data/PurseAPI.kt index 0f029a1f2e2e..6b080c394248 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/PurseAPI.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/PurseAPI.kt @@ -7,7 +7,7 @@ import at.hannibal2.skyhanni.events.ScoreboardUpdateEvent import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.NumberUtil.formatDouble import at.hannibal2.skyhanni.utils.NumberUtil.million -import at.hannibal2.skyhanni.utils.RegexUtils.matchFirst +import at.hannibal2.skyhanni.utils.RegexUtils.firstMatcher import at.hannibal2.skyhanni.utils.SimpleTimeMark import at.hannibal2.skyhanni.utils.repopatterns.RepoPattern import net.minecraft.client.Minecraft @@ -19,7 +19,7 @@ object PurseAPI { private val patternGroup = RepoPattern.group("data.purse") val coinsPattern by patternGroup.pattern( "coins", - "(§.)*(Piggy|Purse): §6(?[\\d,.]+)( ?(§.)*\\([+-](?[\\d,.]+)\\)?|.*)?$", + "(?:§.)*(?:Piggy|Purse): §6(?[\\d,.]+)(?: ?(?:§.)*\\([+-](?[\\d,.]+)\\)?|.*)?$", ) val piggyPattern by patternGroup.pattern( "piggy", @@ -37,13 +37,13 @@ object PurseAPI { @SubscribeEvent fun onScoreboardChange(event: ScoreboardUpdateEvent) { - event.scoreboard.matchFirst(coinsPattern) { + coinsPattern.firstMatcher(event.added) { val newPurse = group("coins").formatDouble() val diff = newPurse - currentPurse if (diff == 0.0) return currentPurse = newPurse - PurseChangeEvent(diff, getCause(diff)).postAndCatch() + PurseChangeEvent(diff, currentPurse, getCause(diff)).postAndCatch() } } diff --git a/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt b/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt index 42de7a75b1f1..7b40e6d6bd3f 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt @@ -110,15 +110,16 @@ object ScoreboardData { val list = fetchScoreboardLines().reversed() val semiFormatted = list.map { cleanSB(it) } if (semiFormatted != sidebarLines) { - RawScoreboardUpdateEvent(semiFormatted).postAndCatch() sidebarLines = semiFormatted + RawScoreboardUpdateEvent(semiFormatted).postAndCatch() } sidebarLinesRaw = list val new = formatLines(list) if (new != sidebarLinesFormatted) { - ScoreboardUpdateEvent(new).postAndCatch() + val old = sidebarLinesFormatted sidebarLinesFormatted = new + ScoreboardUpdateEvent(old, new).postAndCatch() } } diff --git a/src/main/java/at/hannibal2/skyhanni/events/PurseChangeEvent.kt b/src/main/java/at/hannibal2/skyhanni/events/PurseChangeEvent.kt index d776fe32b672..776a226d63e9 100644 --- a/src/main/java/at/hannibal2/skyhanni/events/PurseChangeEvent.kt +++ b/src/main/java/at/hannibal2/skyhanni/events/PurseChangeEvent.kt @@ -1,6 +1,6 @@ package at.hannibal2.skyhanni.events -class PurseChangeEvent(val coins: Double, val reason: PurseChangeCause) : LorenzEvent() +class PurseChangeEvent(val coins: Double, val purse: Double, val reason: PurseChangeCause) : LorenzEvent() enum class PurseChangeCause { GAIN_MOB_KILL, diff --git a/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt b/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt index 9480e8061690..59fb9493cbe6 100644 --- a/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt +++ b/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt @@ -1,3 +1,10 @@ package at.hannibal2.skyhanni.events -class ScoreboardUpdateEvent(val scoreboard: List) : LorenzEvent() +class ScoreboardUpdateEvent( + val old: List, + val scoreboard: List, +) : LorenzEvent() { + + val added by lazy { scoreboard - old.toSet() } + val removed by lazy { old - scoreboard.toSet() } +} diff --git a/src/main/java/at/hannibal2/skyhanni/features/garden/pests/PestAPI.kt b/src/main/java/at/hannibal2/skyhanni/features/garden/pests/PestAPI.kt index e239caeab5b3..d6ab8873c601 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/garden/pests/PestAPI.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/garden/pests/PestAPI.kt @@ -223,7 +223,7 @@ object PestAPI { fun onScoreboardChange(event: ScoreboardUpdateEvent) { if (!GardenAPI.inGarden()) return if (!firstScoreboardCheck) return - checkScoreboardLines(event.scoreboard) + checkScoreboardLines(event.added) } @SubscribeEvent From 6ff118b5211031743ef929e3b5ef2a2c3f06f12d Mon Sep 17 00:00:00 2001 From: Empa <42304516+ItsEmpa@users.noreply.github.com> Date: Sun, 27 Oct 2024 12:48:37 +0100 Subject: [PATCH 019/105] Backend: Scoreboard Event lazy (#2835) Co-authored-by: Empa --- src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt | 2 +- .../at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt | 6 +++--- .../skyhanni/features/slayer/SlayerQuestWarning.kt | 4 ++-- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt b/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt index 7b40e6d6bd3f..cf2e93a9d5bc 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/ScoreboardData.kt @@ -119,7 +119,7 @@ object ScoreboardData { if (new != sidebarLinesFormatted) { val old = sidebarLinesFormatted sidebarLinesFormatted = new - ScoreboardUpdateEvent(old, new).postAndCatch() + ScoreboardUpdateEvent(new, old).postAndCatch() } } diff --git a/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt b/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt index 59fb9493cbe6..e2efcbaf2675 100644 --- a/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt +++ b/src/main/java/at/hannibal2/skyhanni/events/ScoreboardUpdateEvent.kt @@ -1,10 +1,10 @@ package at.hannibal2.skyhanni.events class ScoreboardUpdateEvent( + val full: List, val old: List, - val scoreboard: List, ) : LorenzEvent() { - val added by lazy { scoreboard - old.toSet() } - val removed by lazy { old - scoreboard.toSet() } + val added: List = full - old.toSet() + val removed: List = old - full.toSet() } diff --git a/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerQuestWarning.kt b/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerQuestWarning.kt index c879c202b42d..ecfc439230a5 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerQuestWarning.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerQuestWarning.kt @@ -44,8 +44,8 @@ object SlayerQuestWarning { @SubscribeEvent fun onScoreboardChange(event: ScoreboardUpdateEvent) { - val slayerType = event.scoreboard.nextAfter("Slayer Quest") - val slayerProgress = event.scoreboard.nextAfter("Slayer Quest", skip = 2) ?: "no slayer" + val slayerType = event.full.nextAfter("Slayer Quest") + val slayerProgress = event.full.nextAfter("Slayer Quest", skip = 2) ?: "no slayer" val new = slayerProgress.removeColor() val slayerData = getSlayerData() From 200f6712797e59998f41ed5c7162727b7ccf71c7 Mon Sep 17 00:00:00 2001 From: Obsidian <108832807+Obsidianninja11@users.noreply.github.com> Date: Sun, 27 Oct 2024 05:11:26 -0800 Subject: [PATCH 020/105] Fix: Typos in Primal fear solver (#2834) --- .../skyhanni/features/event/spook/TheGreatSpook.kt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt b/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt index 22408ebfba4c..4eab98851626 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/spook/TheGreatSpook.kt @@ -168,9 +168,9 @@ object TheGreatSpook { return } ChatUtils.clickToActionOrDisable( - "The answer is §b$answer§e.", + "The answer is: §b$answer§e.", config.primalFearSolver::math, - actionName = "Send the answer", + actionName = "send the answer", action = { HypixelCommands.allChat(answer.toString()) }, @@ -179,9 +179,9 @@ object TheGreatSpook { private fun publicSpeakingSolver() { ChatUtils.clickToActionOrDisable( - "Solving Public Speak puzzle for you.", + "Solving Public Speaking puzzle for you.", config.primalFearSolver::publicSpeaking, - actionName = "send a random string.", + actionName = "send a random string", action = { HypixelCommands.allChat("I looove SkyHanni! ${StringUtils.generateRandomString(4)}") }, From 1a9f6fed7297be659fe6a0f5a114bab06aedd437 Mon Sep 17 00:00:00 2001 From: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Date: Mon, 28 Oct 2024 00:20:43 +1100 Subject: [PATCH 021/105] Fix: Downloading forge multiple times (#2836) --- build.gradle.kts | 32 ++++++++++++++++++++------------ 1 file changed, 20 insertions(+), 12 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index 400dd12b1e8d..e031582127ad 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -15,6 +15,8 @@ import org.jetbrains.kotlin.gradle.dsl.JvmTarget import org.jetbrains.kotlin.gradle.tasks.KotlinCompile import skyhannibuildsystem.ChangelogVerification import skyhannibuildsystem.DownloadBackupRepo +import java.io.Serializable +import java.nio.file.Path import java.util.zip.ZipFile import java.util.zip.ZipOutputStream import kotlin.io.path.moveTo @@ -424,17 +426,13 @@ tasks.withType().configureEach { outputs.cacheIf { false } // Custom rules won't work if cached } -abstract class ShotApplicationJarProcessor @Inject constructor(val shots: Shots) : MinecraftJarProcessor { - private class EnsureCompile(shots: Shots) : ShotApplicationJarProcessor(shots) - override fun buildSpec(context: SpecContext?): MinecraftJarProcessor.Spec? { - return object : MinecraftJarProcessor.Spec {} - } +abstract class ShotApplicationJarProcessor @Inject constructor(private val shots: Shots) : + MinecraftJarProcessor, + Serializable { + + override fun buildSpec(context: SpecContext?): MinecraftJarProcessor.Spec? = ShotSpec(shots) - override fun processJar( - source: java.nio.file.Path, - spec: MinecraftJarProcessor.Spec, - context: ProcessorContext? - ) { + override fun processJar(source: Path, spec: MinecraftJarProcessor.Spec?, context: ProcessorContext?) { val dest = source.resolveSibling(source.fileName.toString() + "-temp-shot") ZipFile(source.toFile()).use { input -> ZipOutputStream(dest.outputStream()).use { output -> @@ -444,7 +442,17 @@ abstract class ShotApplicationJarProcessor @Inject constructor(val shots: Shots) dest.moveTo(source, overwrite = true) } - override fun getName(): String { - return "Shots" + override fun getName(): String = "Shots" + + private class ShotSpec(val shots: Shots) : MinecraftJarProcessor.Spec, Serializable { + override fun equals(other: Any?): Boolean { + if (this === other) return true + if (other !is ShotSpec) return false + return shots == other.shots + } + + override fun hashCode(): Int { + return shots.hashCode() + } } } From 22e21badc099cab973b78785856aad7e458b63c7 Mon Sep 17 00:00:00 2001 From: Obsidian <108832807+Obsidianninja11@users.noreply.github.com> Date: Sun, 27 Oct 2024 06:33:40 -0800 Subject: [PATCH 022/105] Fix: Compact stash (#2821) Co-authored-by: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../config/features/chat/StashConfig.java | 7 +- .../skyhanni/features/chat/StashCompact.kt | 68 +++++++++---------- 2 files changed, 38 insertions(+), 37 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/chat/StashConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/chat/StashConfig.java index 738f24c93193..378242b7b926 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/features/chat/StashConfig.java +++ b/src/main/java/at/hannibal2/skyhanni/config/features/chat/StashConfig.java @@ -23,6 +23,11 @@ public class StashConfig { @ConfigEditorInfoText public String notice = ""; + @Expose + @ConfigOption(name = "Hide Added Messages", desc = "Hide the messages when something is added to your stash.") + @ConfigEditorBoolean + public boolean hideAddedMessages = true; + @Expose @ConfigOption(name = "Hide Duplicate Warnings", desc = "Hide duplicate warnings for previously reported stash counts.") @ConfigEditorBoolean @@ -30,7 +35,7 @@ public class StashConfig { @Expose @ConfigOption(name = "Hide Low Warnings", desc = "Hide warnings with a total count below this number.") - @ConfigEditorSlider(minValue = 0, maxValue = 1000000, minStep = 100) + @ConfigEditorSlider(minValue = 0, maxValue = 1_000_000, minStep = 100) public int hideLowWarningsThreshold = 0; @Expose diff --git a/src/main/java/at/hannibal2/skyhanni/features/chat/StashCompact.kt b/src/main/java/at/hannibal2/skyhanni/features/chat/StashCompact.kt index 4c0a574fe3e5..be8c2cc07385 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/chat/StashCompact.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/chat/StashCompact.kt @@ -6,8 +6,8 @@ import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.ChatUtils import at.hannibal2.skyhanni.utils.HypixelCommands import at.hannibal2.skyhanni.utils.LorenzUtils -import at.hannibal2.skyhanni.utils.NumberUtil.formatIntOrNull -import at.hannibal2.skyhanni.utils.RegexUtils.groupOrNull +import at.hannibal2.skyhanni.utils.NumberUtil.formatInt +import at.hannibal2.skyhanni.utils.NumberUtil.shortFormat import at.hannibal2.skyhanni.utils.RegexUtils.matchMatcher import at.hannibal2.skyhanni.utils.RegexUtils.matches import at.hannibal2.skyhanni.utils.StringUtils @@ -63,66 +63,62 @@ object StashCompact { private val config get() = SkyHanniMod.feature.chat.filterType.stashMessages - private var lastMaterialCount = 0 - private var lastDifferingMaterialsCount = 0 - private var lastType = "" + private var currentMessage: StashMessage? = null + private var lastMessage: StashMessage? = null - private var lastSentMaterialCount = 0 - private var lastSentType = "" + data class StashMessage(val materialCount: Int, val type: String) { + var differingMaterialsCount: Int? = null + } @SubscribeEvent fun onChat(event: LorenzChatEvent) { if (!isEnabled()) return - genericAddedToStashPattern.matchMatcher(event.message) { - event.blockedReason = "stash_compact" - } - + // TODO make a system for detecting message "groups" (multiple consecutive messages) materialCountPattern.matchMatcher(event.message) { - groupOrNull("count")?.formatIntOrNull()?.let { count -> - lastMaterialCount = count - } + currentMessage = StashMessage(group("count").formatInt(), group("type")) event.blockedReason = "stash_compact" } differingMaterialsCountPattern.matchMatcher(event.message) { - groupOrNull("count")?.formatIntOrNull()?.let { count -> - lastDifferingMaterialsCount = count - } - groupOrNull("type")?.let { type -> - lastType = type - } + currentMessage?.differingMaterialsCount = group("count").formatInt() event.blockedReason = "stash_compact" } if (pickupStashPattern.matches(event.message)) { event.blockedReason = "stash_compact" - if (lastMaterialCount <= config.hideLowWarningsThreshold) return - if (config.hideDuplicateCounts && lastMaterialCount == lastSentMaterialCount && lastType == lastSentType) return + val current = currentMessage ?: return + if (current.materialCount <= config.hideLowWarningsThreshold) return + if (config.hideDuplicateCounts && current == lastMessage) return - sendCompactedStashMessage() + current.sendCompactedStashMessage() } - } - private fun sendCompactedStashMessage() { - val typeNameFormat = StringUtils.pluralize(lastMaterialCount, lastType) - val typeStringExtra = lastDifferingMaterialsCount.let { - if (it == 0) "." else ", §etotalling §6$it ${StringUtils.pluralize(it, "type")}§6." + if (!config.hideAddedMessages) return + genericAddedToStashPattern.matchMatcher(event.message) { + event.blockedReason = "stash_compact" } + } + + private fun StashMessage.sendCompactedStashMessage() { + val typeNameFormat = StringUtils.pluralize(materialCount, type) + val (mainColor, accentColor) = if (type == "item") "§e" to "§6" else "§b" to "§3" + val typeStringExtra = differingMaterialsCount?.let { + ", ${mainColor}totalling $accentColor$it ${StringUtils.pluralize(it, "type")}$mainColor" + }.orEmpty() + val action = if (config.useViewStash) "view" else "pickup" ChatUtils.clickableChat( - "§eYou have §6$lastMaterialCount §e$typeNameFormat in stash§6$typeStringExtra " + - "§eClick to ${if (config.useViewStash) "§6view" else "§6pickup"} §eyour stash!", + "${mainColor}You have $accentColor${materialCount.shortFormat()} $mainColor$typeNameFormat in stash$typeStringExtra. " + + "${mainColor}Click to $accentColor$action ${mainColor}your stash!", onClick = { - if (config.useViewStash) HypixelCommands.viewStash(lastType) + if (config.useViewStash) HypixelCommands.viewStash(type) else HypixelCommands.pickupStash() }, + hover = "§eClick to $action your $type stash!", ) - lastSentMaterialCount = lastMaterialCount - lastSentType = lastType - // Dirty, but item stash doesn't always have differing materials count, - // and we don't compare this value to the last one, so we can reset it here - lastDifferingMaterialsCount = 0 + currentMessage = null + lastMessage = this } private fun isEnabled() = LorenzUtils.inSkyBlock && config.enabled From 519629cfb9b8f33ca06aae5f7db8ef601cef68f8 Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal002@users.noreply.github.com> Date: Sun, 27 Oct 2024 15:52:28 +0100 Subject: [PATCH 023/105] Fix: async map clear (#2833) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../SuperpairDataDisplay.kt | 52 ++++++++++--------- 1 file changed, 27 insertions(+), 25 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/experimentationtable/SuperpairDataDisplay.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/experimentationtable/SuperpairDataDisplay.kt index 9fa9a7571226..0713baf73920 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/experimentationtable/SuperpairDataDisplay.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/experimentationtable/SuperpairDataDisplay.kt @@ -43,14 +43,14 @@ object SuperpairDataDisplay { private val emptySuperpairItem = SuperpairItem(-1, "", -1) private var display = emptyList() - private var uncoveredItems = mutableMapOf() + private var uncoveredItems = mapOf() private val found = mutableMapOf>() @SubscribeEvent fun onInventoryClose(event: InventoryCloseEvent) { display = emptyList() - uncoveredItems = mutableMapOf() + uncoveredItems = emptyMap() found.clear() } @@ -81,68 +81,70 @@ object SuperpairDataDisplay { val clicksItem = InventoryUtils.getItemAtSlotIndex(4) // TODO add variable name to indicate what is going on here - if (uncoveredItems.none { it.value.index == event.slotId && it.key == uncoveredItems.keys.max() }) { + val items = uncoveredItems.toMutableMap() + if (items.none { it.value.index == event.slotId && it.key == items.keys.max() }) { if (clicksItem != null) { remainingClicksPattern.matchMatcher(clicksItem.displayName.removeColor()) { if (group("clicks").toInt() == 0) return } } - handleItem(event.slotId) + handleItem(items, event.slotId) } + uncoveredItems = items } - private fun handleItem(slot: Int) = DelayedRun.runDelayed(200.milliseconds) { + private fun handleItem(items: MutableMap, slot: Int) = DelayedRun.runDelayed(200.milliseconds) { val itemNow = InventoryUtils.getItemAtSlotIndex(slot) ?: return@runDelayed val itemName = itemNow.displayName.removeColor() val reward = convertToReward(itemNow) val itemData = SuperpairItem(slot, reward, itemNow.itemDamage) - val uncovered = uncoveredItems.keys.maxOrNull() ?: -1 + val uncovered = items.keys.maxOrNull() ?: -1 if (isWaiting(itemName)) return@runDelayed - if (uncoveredItems.none { it.key == uncovered && it.value.index == slot }) uncoveredItems[uncovered + 1] = itemData + if (items.none { it.key == uncovered && it.value.index == slot }) items[uncovered + 1] = itemData when { - isPowerUp(reward) -> handlePowerUp(itemData, uncovered + 1) - isReward(itemName) -> handleReward(itemData, uncovered + 1) + isPowerUp(reward) -> handlePowerUp(items, itemData, uncovered + 1) + isReward(itemName) -> handleReward(items, itemData, uncovered + 1) } - val since = clicksSinceSeparator(uncoveredItems) + val since = clicksSinceSeparator(items) - val lastReward = uncoveredItems.entries.last().value.reward + val lastReward = items.entries.last().value.reward // TODO use repo patterns for "Instant Find" - if ((since >= 2 || (since == -1 && uncoveredItems.size >= 2)) && lastReward != "Instant Find") uncoveredItems[uncovered + 2] = + if ((since >= 2 || (since == -1 && items.size >= 2)) && lastReward != "Instant Find") items[uncovered + 2] = emptySuperpairItem display = drawDisplay() } - private fun handlePowerUp(item: SuperpairItem, uncovered: Int) { + private fun handlePowerUp(items: MutableMap, item: SuperpairItem, uncovered: Int) { // TODO use repo patterns for "Instant Find" - if (item.reward != "Instant Find") uncoveredItems.remove(uncovered) + if (item.reward != "Instant Find") items.remove(uncovered) val itemData = FoundData(item = item) found.getOrPut(FoundType.POWERUP) { mutableListOf(itemData) }.apply { if (!contains(itemData)) add(itemData) } } - private fun handleReward(item: SuperpairItem, uncovered: Int) { - val last = uncoveredItems.getOrDefault(uncovered - 1, item) + private fun handleReward(items: MutableMap, item: SuperpairItem, uncovered: Int) { + val last = items.getOrDefault(uncovered - 1, item) if (isWaiting(last.reward)) return when { // TODO use repo patterns for "Instant Find" - last.reward == "Instant Find" -> handleInstantFind(item, uncovered) + last.reward == "Instant Find" -> handleInstantFind(items, item, uncovered) hasFoundPair(item, last) -> handleFoundPair(item, last) - hasFoundMatch(item) -> handleFoundMatch(item) + hasFoundMatch(items, item) -> handleFoundMatch(items, item) else -> handleNormalReward(item) } println(found) } - private fun handleInstantFind(item: SuperpairItem, uncovered: Int) { - uncoveredItems[uncovered - 1] = item - uncoveredItems[uncovered] = emptySuperpairItem + private fun handleInstantFind(items: MutableMap, item: SuperpairItem, uncovered: Int) { + items[uncovered - 1] = item + items[uncovered] = emptySuperpairItem handleFoundPair(item, emptySuperpairItem) } @@ -164,9 +166,9 @@ object SuperpairDataDisplay { found.getOrPut(FoundType.PAIR) { mutableListOf(pairData) }.apply { if (!contains(pairData)) add(pairData) } } - private fun handleFoundMatch(item: SuperpairItem) { + private fun handleFoundMatch(items: MutableMap, item: SuperpairItem) { // TODO better name - val match = uncoveredItems.values.find { it.index != item.index && it.sameAs(item) } ?: return + val match = items.values.find { it.index != item.index && it.sameAs(item) } ?: return found.entries.forEach { when { @@ -269,8 +271,8 @@ object SuperpairDataDisplay { ) = first.index != second.index && first.sameAs(second) // TODO extract logic greatly - private fun hasFoundMatch(firstItem: SuperpairItem) = - uncoveredItems.any { it.value.index != firstItem.index && it.value.sameAs(firstItem) } && + private fun hasFoundMatch(items: Map, firstItem: SuperpairItem) = + items.any { it.value.index != firstItem.index && it.value.sameAs(firstItem) } && found.entries.none { it.key.isAnyOf(FoundType.PAIR, FoundType.MATCH) && it.value.any { data -> From ed924d10fe10e89ac58299f8a4c60b970b400be1 Mon Sep 17 00:00:00 2001 From: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Date: Mon, 28 Oct 2024 02:00:41 +1100 Subject: [PATCH 024/105] Backend: Data Class (#2840) --- build.gradle.kts | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/build.gradle.kts b/build.gradle.kts index e031582127ad..cbd8eda3a2f7 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -444,15 +444,5 @@ abstract class ShotApplicationJarProcessor @Inject constructor(private val shots override fun getName(): String = "Shots" - private class ShotSpec(val shots: Shots) : MinecraftJarProcessor.Spec, Serializable { - override fun equals(other: Any?): Boolean { - if (this === other) return true - if (other !is ShotSpec) return false - return shots == other.shots - } - - override fun hashCode(): Int { - return shots.hashCode() - } - } + private data class ShotSpec(val shots: Shots) : MinecraftJarProcessor.Spec, Serializable } From 31c884c8123ad5f6c9376503effce3fb2ded5d55 Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal002@users.noreply.github.com> Date: Sun, 27 Oct 2024 16:26:04 +0100 Subject: [PATCH 025/105] Refactor: Optimize NEUInternalName class caching and naming (#2841) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../skyhanni/utils/NEUInternalName.kt | 68 +++++++++---------- 1 file changed, 31 insertions(+), 37 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/utils/NEUInternalName.kt b/src/main/java/at/hannibal2/skyhanni/utils/NEUInternalName.kt index 50444f71118d..3b155c642071 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/NEUInternalName.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/NEUInternalName.kt @@ -6,73 +6,67 @@ class NEUInternalName private constructor(private val internalName: String) { companion object { - private val map = mutableMapOf() + private val internalNameMap = mutableMapOf() - val NONE = "NONE".asInternalName() - val MISSING_ITEM = "MISSING_ITEM".asInternalName() + val NONE = "NONE".toInternalName() + val MISSING_ITEM = "MISSING_ITEM".toInternalName() - val JASPER_CRYSTAL = "JASPER_CRYSTAL".asInternalName() - val RUBY_CRYSTAL = "RUBY_CRYSTAL".asInternalName() - val SKYBLOCK_COIN = "SKYBLOCK_COIN".asInternalName() - val WISP_POTION = "WISP_POTION".asInternalName() + val JASPER_CRYSTAL = "JASPER_CRYSTAL".toInternalName() + val RUBY_CRYSTAL = "RUBY_CRYSTAL".toInternalName() + val SKYBLOCK_COIN = "SKYBLOCK_COIN".toInternalName() + val WISP_POTION = "WISP_POTION".toInternalName() - fun String.asInternalName(): NEUInternalName { - val internalName = uppercase().replace(" ", "_") - return map.getOrPut(internalName) { NEUInternalName(internalName) } + @Deprecated("Name changed", ReplaceWith("this.toInternalName()")) + fun String.asInternalName() = toInternalName() + + fun String.toInternalName(): NEUInternalName = uppercase().replace(" ", "_").let { + internalNameMap.getOrPut(it) { NEUInternalName(it) } } - fun fromItemNameOrNull(itemName: String): NEUInternalName? = - ItemNameResolver.getInternalNameOrNull(itemName.removeSuffix(" Pet")) ?: getCoins(itemName) + private val itemNameCache = mutableMapOf() - fun fromItemNameOrInternalName(itemName: String): NEUInternalName = - fromItemNameOrNull(itemName) ?: itemName.asInternalName() + fun fromItemNameOrNull(itemName: String): NEUInternalName? = itemNameCache.getOrPut(itemName) { + ItemNameResolver.getInternalNameOrNull(itemName.removeSuffix(" Pet")) ?: getCoins(itemName) + } - private fun getCoins(itemName: String): NEUInternalName? = if (isCoins(itemName)) SKYBLOCK_COIN else null + fun fromItemNameOrInternalName(itemName: String): NEUInternalName = fromItemNameOrNull(itemName) ?: itemName.toInternalName() - private fun isCoins(itemName: String): Boolean = - itemName.lowercase().let { - when (it) { - "coin", "coins", - "skyblock coin", "skyblock coins", - "skyblock_coin", "skyblock_coins", - -> true + private fun getCoins(itemName: String): NEUInternalName? = when { + isCoins(itemName) -> SKYBLOCK_COIN + else -> null + } - else -> false - } - } + private val coinNames = setOf( + "coin", "coins", + "skyblock coin", "skyblock coins", + "skyblock_coin", "skyblock_coins", + ) + private fun isCoins(itemName: String): Boolean = itemName.lowercase() in coinNames fun fromItemName(itemName: String): NEUInternalName = fromItemNameOrNull(itemName) ?: run { val name = "itemName:$itemName" ItemUtils.addMissingRepoItem(name, "Could not find internal name for $name") - return MISSING_ITEM + MISSING_ITEM } } fun asString() = internalName - override fun equals(other: Any?): Boolean { - if (other is NEUInternalName) { - return internalName == other.internalName - } - return super.equals(other) - } + override fun equals(other: Any?) = other is NEUInternalName && internalName == other.internalName override fun toString(): String = "internalName:$internalName" override fun hashCode(): Int = internalName.hashCode() - @Suppress("WrongEqualsTypeParameter") - fun equals(other: String) = internalName == other - fun contains(other: String) = internalName.contains(other) fun startsWith(other: String) = internalName.startsWith(other) fun endsWith(other: String) = internalName.endsWith(other) - fun replace(oldValue: String, newValue: String) = - internalName.replace(oldValue.uppercase(), newValue.uppercase()).asInternalName() + fun replace(oldValue: String, newValue: String): NEUInternalName = + internalName.replace(oldValue, newValue, ignoreCase = true).toInternalName() fun isKnownItem(): Boolean = getItemStackOrNull() != null || this == SKYBLOCK_COIN } From a420116af642a1eb8b257e8a88cece92eecc6def Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal00212@users.noreply.github.com> Date: Sun, 27 Oct 2024 22:42:58 +0100 Subject: [PATCH 026/105] added response to /shcopylocation --- .../skyhanni/test/SkyHanniDebugsAndTests.kt | 19 ++++++++----------- 1 file changed, 8 insertions(+), 11 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/test/SkyHanniDebugsAndTests.kt b/src/main/java/at/hannibal2/skyhanni/test/SkyHanniDebugsAndTests.kt index ae9b5e45b285..4a19357f1377 100644 --- a/src/main/java/at/hannibal2/skyhanni/test/SkyHanniDebugsAndTests.kt +++ b/src/main/java/at/hannibal2/skyhanni/test/SkyHanniDebugsAndTests.kt @@ -328,18 +328,15 @@ object SkyHanniDebugsAndTests { val x = (location.x + 0.001).roundTo(1) val y = (location.y + 0.001).roundTo(1) val z = (location.z + 0.001).roundTo(1) - if (args.size == 1) { - if (args[0].equals("json", false)) { - OSUtils.copyToClipboard("\"$x:$y:$z\"") - return - } - if (args[0].equals("pathfind", false)) { - OSUtils.copyToClipboard("`/shtestwaaypoint $x $y $z pathfind`") - return - } - } + val (clipboard, format) = formatLocation(x, y, z, args.getOrNull(0)) + OSUtils.copyToClipboard(clipboard) + ChatUtils.chat("Copied the current location to clipboard ($format format)!", replaceSameMessage = true) + } - OSUtils.copyToClipboard("LorenzVec($x, $y, $z)") + private fun formatLocation(x: Double, y: Double, z: Double, parameter: String?): Pair = when (parameter) { + "json" -> "$x:$y:$z" to "json" + "pathfind" -> "`/shtestwaypoint $x $y $z pathfind`" to "pathfind" + else -> "LorenzVec($x, $y, $z)" to "LorenzVec" } fun debugVersion() { From 2490f8524a7faffb1dc8345f31b1d6d952682712 Mon Sep 17 00:00:00 2001 From: Vixid <52578495+VixidDev@users.noreply.github.com> Date: Sun, 27 Oct 2024 21:56:32 +0000 Subject: [PATCH 027/105] Backend: Better Enchant Detection and Error Logging (#2816) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> Co-authored-by: hannibal2 <24389977+hannibal002@users.noreply.github.com> --- .../misc/items/enchants/EnchantParser.kt | 40 ++++++++++++------- .../misc/items/enchants/EnchantsJson.kt | 15 ++++--- .../misc/items/enchants/FormattedEnchant.kt | 8 ++-- 3 files changed, 38 insertions(+), 25 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantParser.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantParser.kt index 1c859828b662..e353ea1cddac 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantParser.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantParser.kt @@ -39,6 +39,16 @@ object EnchantParser { private val config get() = SkyHanniMod.feature.inventory.enchantParsing val patternGroup = RepoPattern.group("misc.items.enchantparsing") + // Pattern to check that the line contains ONLY enchants (and the other bits that come with a valid enchant line) + /** + * REGEX-TEST: §d§l§d§lWisdom V§9, §9Depth Strider III§9, §9Feather Falling X + * REGEX-TEST: §9Compact X§9, §9Efficiency V§9, §9Experience IV + */ + val enchantmentExclusivePattern by patternGroup.pattern( + "exclusive", + "(?:(?:§7§l|§d§l|§9)+([A-Za-z][A-Za-z '-]+) (?:[IVXLCDM]+|[0-9]+)(?:[§r]?§9, |\$| §8\\d{1,3}(?:,\\d{3})*))+\$", + ) + // Above regex tests apply to this pattern also val enchantmentPattern by patternGroup.pattern( "enchants.new", "(§7§l|§d§l|§9)(?[A-Za-z][A-Za-z '-]+) (?[IVXLCDM]+|[0-9]+)(?(§r)?§9, |\$| §8\\d{1,3}(,\\d{3})*)", @@ -186,20 +196,6 @@ object EnchantParser { return } - // Remove enchantment lines so we can insert ours - try { - loreList.subList(startEnchant, endEnchant + 1).clear() - } catch (e: IndexOutOfBoundsException) { - ErrorManager.logErrorWithData( - e, - "Error parsing enchantment info from item", - "loreList" to loreList, - "startEnchant" to startEnchant, - "endEnchant" to endEnchant, - ) - return - } - val insertEnchants: MutableList = mutableListOf() // Format enchants based on format config option @@ -220,10 +216,24 @@ object EnchantParser { "ConcurrentModificationException whilst formatting enchants", "loreList" to loreList, "format" to config.format.get(), - "orderedEnchants" to orderedEnchants + "orderedEnchants" to orderedEnchants.toString() ) } + // Remove enchantment lines so we can insert ours + try { + loreList.subList(startEnchant, endEnchant + 1).clear() + } catch (e: IndexOutOfBoundsException) { + ErrorManager.logErrorWithData( + e, + "Error parsing enchantment info from item", + "loreList" to loreList, + "startEnchant" to startEnchant, + "endEnchant" to endEnchant, + ) + return + } + // Add our parsed enchants back into the lore loreList.addAll(startEnchant, insertEnchants) // Cache parsed lore diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantsJson.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantsJson.kt index 6e1550a974a2..863e019fb4e3 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantsJson.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/EnchantsJson.kt @@ -1,6 +1,5 @@ package at.hannibal2.skyhanni.features.misc.items.enchants -import at.hannibal2.skyhanni.features.misc.items.enchants.EnchantParser.enchantmentPattern import com.google.gson.annotations.Expose import com.google.gson.annotations.SerializedName @@ -27,15 +26,21 @@ class EnchantsJson { } fun containsEnchantment(enchants: Map, line: String): Boolean { - val matcher = enchantmentPattern.matcher(line) + val exclusiveMatch = EnchantParser.enchantmentExclusivePattern.matcher(line) + if (!exclusiveMatch.find()) return false // This is the case that the line is not exclusively enchants + + val matcher = EnchantParser.enchantmentPattern.matcher(line) while (matcher.find()) { val enchant = this.getFromLore(matcher.group("enchant")) if (enchants.isNotEmpty()) { if (enchants.containsKey(enchant.nbtName)) return true } else { - if (normal.containsKey(enchant.loreName.lowercase())) return true - if (ultimate.containsKey(enchant.loreName.lowercase())) return true - if (stacking.containsKey(enchant.loreName.lowercase())) return true + val key = enchant.loreName.lowercase() + if (normal.containsKey(key) || + ultimate.containsKey(key) || + stacking.containsKey(key) + ) + return true } } return false diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/FormattedEnchant.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/FormattedEnchant.kt index 834959fbba85..11f6e77c2752 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/FormattedEnchant.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/items/enchants/FormattedEnchant.kt @@ -3,14 +3,12 @@ package at.hannibal2.skyhanni.features.misc.items.enchants import at.hannibal2.skyhanni.utils.NumberUtil.toRoman import net.minecraft.item.ItemStack -class FormattedEnchant( +data class FormattedEnchant( private val enchant: Enchant, private val level: Int, - stacking: String, + private val stacking: String, private val isRoman: Boolean, ) : Comparable { - private val stacking: String = stacking - get() = "§8$field" private val loreDescription: MutableList = mutableListOf() fun addLore(lineOfLore: String) = loreDescription.add(lineOfLore) @@ -23,6 +21,6 @@ class FormattedEnchant( val builder = StringBuilder() builder.append(enchant.getFormattedName(level, itemStack)).append(" ").append(if (isRoman) level.toRoman() else level) - return if (!stacking.contains("empty")) builder.append(stacking).toString() else builder.toString() + return if (!stacking.contains("empty")) builder.append("§8$stacking").toString() else builder.toString() } } From bf53508d3a8adf52e85b36c4f08414805cebd05b Mon Sep 17 00:00:00 2001 From: Luna Date: Sun, 27 Oct 2024 23:00:06 +0100 Subject: [PATCH 028/105] Fix: Kick Duration not matching certain messages (#2837) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../features/misc/SkyBlockKickDuration.kt | 25 +++++++++++++++++-- 1 file changed, 23 insertions(+), 2 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt index 8a309ad0b33b..89f80fb734cd 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt @@ -6,10 +6,12 @@ import at.hannibal2.skyhanni.events.LorenzChatEvent import at.hannibal2.skyhanni.events.LorenzWorldChangeEvent import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.LorenzUtils +import at.hannibal2.skyhanni.utils.RegexUtils.matches import at.hannibal2.skyhanni.utils.RenderUtils.renderString import at.hannibal2.skyhanni.utils.SimpleTimeMark import at.hannibal2.skyhanni.utils.SoundUtils import at.hannibal2.skyhanni.utils.TimeUtils.format +import at.hannibal2.skyhanni.utils.repopatterns.RepoPattern import net.minecraftforge.fml.common.eventhandler.SubscribeEvent import kotlin.time.Duration.Companion.minutes import kotlin.time.Duration.Companion.seconds @@ -24,11 +26,30 @@ object SkyBlockKickDuration { private var lastKickTime = SimpleTimeMark.farPast() private var hasWarned = false + private val patternGroup = RepoPattern.group("misc.kickduration") + + /** + * REGEX-TEST: §cYou were kicked while joining that server! + * REGEX-TEST: §cA kick occurred in your connection, so you were put in the SkyBlock lobby! + */ + private val kickPattern by patternGroup.pattern( + "kicked", + "§c(?:You were kicked while joining that server!|A kick occurred in your connection, so you were put in the SkyBlock lobby!)", + ) + + /** + * REGEX-TEST: §cThere was a problem joining SkyBlock, try again in a moment! + */ + private val problemJoiningPattern by patternGroup.pattern( + "problemjoining", + "§cThere was a problem joining SkyBlock, try again in a moment!", + ) + @SubscribeEvent fun onChat(event: LorenzChatEvent) { if (!isEnabled()) return - if (event.message == "§cYou were kicked while joining that server!") { + if (kickPattern.matches(event.message)) { if (LorenzUtils.onHypixel && !LorenzUtils.inSkyBlock) { kickMessage = false showTime = true @@ -38,7 +59,7 @@ object SkyBlockKickDuration { } } - if (event.message == "§cThere was a problem joining SkyBlock, try again in a moment!") { + if (problemJoiningPattern.matches(event.message)) { kickMessage = false showTime = true lastKickTime = SimpleTimeMark.now() From 2095a82bac5f06d6fba58f4b6ca79936813aed18 Mon Sep 17 00:00:00 2001 From: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Date: Mon, 28 Oct 2024 09:04:40 +1100 Subject: [PATCH 029/105] Backend: Use pre-processed methods for gui scaling operations (#2648) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../core/config/gui/GuiPositionEditor.kt | 21 ++++---- .../hannibal2/skyhanni/data/TitleManager.kt | 7 ++- .../skyhanni/features/chroma/ChromaShader.kt | 3 +- .../gui/customscoreboard/RenderBackground.kt | 7 ++- .../features/inventory/HarpFeatures.kt | 13 +++-- .../misc/RoundedRectangleOutlineShader.kt | 4 +- .../misc/compacttablist/TabListRenderer.kt | 5 +- .../misc/visualwords/VisualWordGui.kt | 5 +- .../hannibal2/skyhanni/utils/RenderUtils.kt | 50 ++++++++----------- .../skyhanni/utils/compat/GuiScreenUtils.kt | 12 +++-- .../utils/renderables/RenderableTooltips.kt | 17 +++---- 11 files changed, 67 insertions(+), 77 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/config/core/config/gui/GuiPositionEditor.kt b/src/main/java/at/hannibal2/skyhanni/config/core/config/gui/GuiPositionEditor.kt index 0adf1bed5e56..bd50b46e3fcb 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/core/config/gui/GuiPositionEditor.kt +++ b/src/main/java/at/hannibal2/skyhanni/config/core/config/gui/GuiPositionEditor.kt @@ -30,7 +30,6 @@ import at.hannibal2.skyhanni.utils.KeyboardManager import at.hannibal2.skyhanni.utils.NumberUtil.roundTo import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.compat.SkyhanniBaseScreen -import net.minecraft.client.Minecraft import net.minecraft.client.gui.inventory.GuiContainer import net.minecraft.client.renderer.GlStateManager import org.lwjgl.input.Keyboard @@ -115,8 +114,9 @@ class GuiPositionEditor( GlStateManager.pushMatrix() width = getScaledWidth() height = getScaledHeight() - val mouseX = Mouse.getX() * width / Minecraft.getMinecraft().displayWidth - val mouseY = height - Mouse.getY() * height / Minecraft.getMinecraft().displayHeight - 1 + + val (mouseX, mouseY) = GuiScreenUtils.mousePos + for ((index, position) in positions.withIndex()) { var elementWidth = position.getDummySize(true).x var elementHeight = position.getDummySize(true).y @@ -154,8 +154,8 @@ class GuiPositionEditor( override fun mouseClicked(originalX: Int, priginalY: Int, mouseButton: Int) { super.mouseClicked(originalX, priginalY, mouseButton) - val mouseX = Mouse.getX() * width / Minecraft.getMinecraft().displayWidth - val mouseY = height - Mouse.getY() * height / Minecraft.getMinecraft().displayHeight - 1 + val (mouseX, mouseY) = GuiScreenUtils.mousePos + for (i in positions.indices.reversed()) { val position = positions[i] val elementWidth = position.getDummySize().x @@ -222,8 +222,8 @@ class GuiPositionEditor( for (position in positions) { if (!position.clicked) continue - val mouseX = Mouse.getX() * width / Minecraft.getMinecraft().displayWidth - val mouseY = height - Mouse.getY() * height / Minecraft.getMinecraft().displayHeight - 1 + val (mouseX, mouseY) = GuiScreenUtils.mousePos + val elementWidth = position.getDummySize(true).x val elementHeight = position.getDummySize(true).y grabbedX += position.moveX(mouseX - grabbedX, elementWidth) @@ -236,13 +236,14 @@ class GuiPositionEditor( super.handleMouseInput() val mw = Mouse.getEventDWheel() if (mw == 0) return - val mx = Mouse.getEventX() * width / mc.displayWidth - val my = height - Mouse.getEventY() * height / mc.displayHeight - 1 + + val (mouseX, mouseY) = GuiScreenUtils.mousePos + val hovered = positions.firstOrNull { it.clicked } ?: positions.lastOrNull { val size = it.getDummySize() GuiRenderUtils.isPointInRect( - mx, my, + mouseX, mouseY, it.getAbsX() - border, it.getAbsY() - border, size.x + border * 2, size.y + border * 2, ) diff --git a/src/main/java/at/hannibal2/skyhanni/data/TitleManager.kt b/src/main/java/at/hannibal2/skyhanni/data/TitleManager.kt index 95dbe1577f56..2647768db5e9 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/TitleManager.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/TitleManager.kt @@ -5,9 +5,9 @@ import at.hannibal2.skyhanni.events.ProfileJoinEvent import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.ChatUtils import at.hannibal2.skyhanni.utils.SimpleTimeMark +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import io.github.notenoughupdates.moulconfig.internal.TextRenderUtils import net.minecraft.client.Minecraft -import net.minecraft.client.gui.ScaledResolution import net.minecraft.client.renderer.GlStateManager import net.minecraftforge.fml.common.eventhandler.SubscribeEvent import org.lwjgl.opengl.GL11 @@ -61,9 +61,8 @@ object TitleManager { fun onRenderOverlay(event: GuiRenderEvent.GuiOverlayRenderEvent) { if (endTime.isInPast()) return - val scaledResolution = ScaledResolution(Minecraft.getMinecraft()) - val width = scaledResolution.scaledWidth - val height = scaledResolution.scaledHeight + val width = GuiScreenUtils.scaledWindowWidth + val height = GuiScreenUtils.scaledWindowHeight GlStateManager.enableBlend() GlStateManager.tryBlendFuncSeparate(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA, 1, 0) diff --git a/src/main/java/at/hannibal2/skyhanni/features/chroma/ChromaShader.kt b/src/main/java/at/hannibal2/skyhanni/features/chroma/ChromaShader.kt index bb78592fa87c..0f34258fb010 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/chroma/ChromaShader.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/chroma/ChromaShader.kt @@ -3,6 +3,7 @@ package at.hannibal2.skyhanni.features.chroma import at.hannibal2.skyhanni.config.features.chroma.ChromaConfig.Direction import at.hannibal2.skyhanni.data.MinecraftData import at.hannibal2.skyhanni.mixins.transformers.AccessorMinecraft +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.shader.Shader import at.hannibal2.skyhanni.utils.shader.Uniform import net.minecraft.client.Minecraft @@ -17,7 +18,7 @@ abstract class ChromaShader(vertex: String, fragment: String) : Shader(vertex, f override fun registerUniforms() { registerUniform(Uniform.UniformType.FLOAT, "chromaSize") { - ChromaManager.config.chromaSize * (Minecraft.getMinecraft().displayWidth / 100f) + ChromaManager.config.chromaSize * (GuiScreenUtils.displayWidth / 100f) } registerUniform(Uniform.UniformType.FLOAT, "timeOffset") { var ticks = diff --git a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/RenderBackground.kt b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/RenderBackground.kt index 357b61a0c752..6a44d5861243 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/RenderBackground.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/RenderBackground.kt @@ -7,9 +7,8 @@ import at.hannibal2.skyhanni.data.GuiEditManager.getAbsY import at.hannibal2.skyhanni.features.gui.customscoreboard.CustomScoreboard.backgroundConfig import at.hannibal2.skyhanni.utils.ColorUtils.toChromaColor import at.hannibal2.skyhanni.utils.RenderUtils +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.renderables.Renderable -import net.minecraft.client.Minecraft -import net.minecraft.client.gui.ScaledResolution import net.minecraft.util.ResourceLocation object RenderBackground { @@ -74,8 +73,8 @@ object RenderBackground { val position = CustomScoreboard.config.position - val scaledWidth = ScaledResolution(Minecraft.getMinecraft()).scaledWidth - val scaledHeight = ScaledResolution(Minecraft.getMinecraft()).scaledHeight + val scaledWidth = GuiScreenUtils.scaledWindowWidth + val scaledHeight = GuiScreenUtils.scaledWindowHeight val elementWidth = (renderable.width * position.effectiveScale).toInt() val elementHeight = (renderable.height * position.effectiveScale).toInt() diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/HarpFeatures.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/HarpFeatures.kt index 05cdf94c32a9..604e3a7d0d15 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/HarpFeatures.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/HarpFeatures.kt @@ -20,9 +20,9 @@ import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.RegexUtils.anyMatches import at.hannibal2.skyhanni.utils.RegexUtils.matches import at.hannibal2.skyhanni.utils.SimpleTimeMark +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.repopatterns.RepoPattern import net.minecraft.client.Minecraft -import net.minecraft.client.gui.ScaledResolution import net.minecraft.client.gui.inventory.GuiChest import net.minecraft.client.player.inventory.ContainerLocalMenu import net.minecraft.item.Item @@ -37,7 +37,7 @@ object HarpFeatures { private val config get() = SkyHanniMod.feature.inventory.helper.harp private var lastClick = SimpleTimeMark.farPast() - private const val closeButtonSlot = 40 + private const val CLOSE_BUTTON_SLOT = 40 private val buttonColors = listOf('d', 'e', 'a', '2', '5', '9', 'b') @@ -118,10 +118,9 @@ object HarpFeatures { } // Copied from Minecraft Code to update the scale val minecraft = Minecraft.getMinecraft() - val scaledresolution = ScaledResolution(minecraft) - val i = scaledresolution.scaledWidth - val j = scaledresolution.scaledHeight - minecraft.currentScreen.setWorldAndResolution(minecraft, i, j) + val width = GuiScreenUtils.scaledWindowWidth + val height = GuiScreenUtils.scaledWindowHeight + minecraft.currentScreen.setWorldAndResolution(minecraft, width, height) } @SubscribeEvent @@ -170,7 +169,7 @@ object HarpFeatures { if (!config.quickRestart) return if (!isMenuGui(InventoryUtils.openInventoryName())) return - if (event.slot?.slotNumber != closeButtonSlot) return + if (event.slot?.slotNumber != CLOSE_BUTTON_SLOT) return if (openTime.passedSince() > 2.seconds) return event.container.inventory.filterNotNull().indexOfFirst { songSelectedPattern.anyMatches(it.getLore()) diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/RoundedRectangleOutlineShader.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/RoundedRectangleOutlineShader.kt index 2a5e131fa0da..ed43b348d7be 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/RoundedRectangleOutlineShader.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/RoundedRectangleOutlineShader.kt @@ -1,8 +1,8 @@ package at.hannibal2.skyhanni.features.misc +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.shader.Shader import at.hannibal2.skyhanni.utils.shader.Uniform -import net.minecraft.client.Minecraft object RoundedRectangleOutlineShader : Shader("rounded_rect_outline", "rounded_rect_outline") { @@ -14,7 +14,7 @@ object RoundedRectangleOutlineShader : Shader("rounded_rect_outline", "rounded_r var halfSize: FloatArray = floatArrayOf(0f, 0f) var centerPos: FloatArray = floatArrayOf(0f, 0f) set(value) { - field = floatArrayOf(value[0], Minecraft.getMinecraft().displayHeight - value[1]) + field = floatArrayOf(value[0], GuiScreenUtils.displayHeight - value[1]) } var borderThickness: Float = 5f var borderBlur: Float = 0.3f diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/compacttablist/TabListRenderer.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/compacttablist/TabListRenderer.kt index e95c02e8b22f..6fa91f7bf7f0 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/compacttablist/TabListRenderer.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/compacttablist/TabListRenderer.kt @@ -10,10 +10,10 @@ import at.hannibal2.skyhanni.utils.KeyboardManager.isActive import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.RegexUtils.matches import at.hannibal2.skyhanni.utils.TabListData +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.repopatterns.RepoPattern import net.minecraft.client.Minecraft import net.minecraft.client.gui.Gui -import net.minecraft.client.gui.ScaledResolution import net.minecraft.client.renderer.GlStateManager import net.minecraft.entity.player.EnumPlayerModelParts import net.minecraftforge.client.event.RenderGameOverlayEvent @@ -100,8 +100,7 @@ object TabListRenderer { } val minecraft = Minecraft.getMinecraft() - val scaledResolution = ScaledResolution(minecraft) - val screenWidth = scaledResolution.scaledWidth / 2 + val screenWidth = GuiScreenUtils.scaledWindowWidth / 2 val x = screenWidth - totalWidth / 2 val y = 10 diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/visualwords/VisualWordGui.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/visualwords/VisualWordGui.kt index 5fa8f6b78763..b4e12945c1da 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/visualwords/VisualWordGui.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/visualwords/VisualWordGui.kt @@ -14,6 +14,7 @@ import at.hannibal2.skyhanni.utils.OSUtils import at.hannibal2.skyhanni.utils.RegexUtils.matchMatcher import at.hannibal2.skyhanni.utils.SoundUtils import at.hannibal2.skyhanni.utils.StringUtils.convertToFormatted +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import com.google.gson.JsonObject import kotlinx.coroutines.launch import net.minecraft.client.Minecraft @@ -106,8 +107,8 @@ open class VisualWordGui : GuiScreen() { guiLeft = (width - sizeX) / 2 guiTop = (height - sizeY) / 2 - mouseX = Mouse.getX() * width / Minecraft.getMinecraft().displayWidth - mouseY = height - Mouse.getY() * height / Minecraft.getMinecraft().displayHeight - 1 + mouseX = GuiScreenUtils.mouseX + mouseY = GuiScreenUtils.mouseY GlStateManager.pushMatrix() drawRect(guiLeft, guiTop, guiLeft + sizeX, guiTop + sizeY, 0x50000000) diff --git a/src/main/java/at/hannibal2/skyhanni/utils/RenderUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/RenderUtils.kt index 7cf10426907a..be2904f87bd5 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/RenderUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/RenderUtils.kt @@ -40,7 +40,6 @@ import net.minecraft.item.ItemStack import net.minecraft.util.AxisAlignedBB import net.minecraft.util.MathHelper import net.minecraft.util.ResourceLocation -import org.lwjgl.input.Mouse import org.lwjgl.opengl.GL11 import java.awt.Color import java.nio.FloatBuffer @@ -96,15 +95,6 @@ object RenderUtils { highlight(color, x, y) } - fun getMouseX(): Int { - return Mouse.getX() * GuiScreenUtils.scaledWindowWidth / Minecraft.getMinecraft().displayWidth - } - - fun getMouseY(): Int { - val height = GuiScreenUtils.scaledWindowHeight - return height - Mouse.getY() * height / Minecraft.getMinecraft().displayHeight - 1 - } - fun highlight(color: Color, x: Int, y: Int) { GlStateManager.disableLighting() GlStateManager.disableDepth() @@ -514,8 +504,8 @@ object RenderUtils { fun Position.transform(): Pair { GlStateManager.translate(getAbsX().toFloat(), getAbsY().toFloat(), 0F) GlStateManager.scale(effectiveScale, effectiveScale, 1F) - val x = ((getMouseX() - getAbsX()) / effectiveScale).toInt() - val y = ((getMouseY() - getAbsY()) / effectiveScale).toInt() + val x = ((GuiScreenUtils.mouseX - getAbsX()) / effectiveScale).toInt() + val y = ((GuiScreenUtils.mouseY - getAbsY()) / effectiveScale).toInt() return x to y } @@ -1760,13 +1750,13 @@ object RenderUtils { return } - val scaledRes = ScaledResolution(Minecraft.getMinecraft()) - val widthIn = width * scaledRes.scaleFactor - val heightIn = height * scaledRes.scaleFactor - val xIn = x * scaledRes.scaleFactor - val yIn = y * scaledRes.scaleFactor + val scaleFactor = ScaledResolution(Minecraft.getMinecraft()).scaleFactor + val widthIn = width * scaleFactor + val heightIn = height * scaleFactor + val xIn = x * scaleFactor + val yIn = y * scaleFactor - RoundedTextureShader.scaleFactor = scaledRes.scaleFactor.toFloat() + RoundedTextureShader.scaleFactor = scaleFactor.toFloat() RoundedTextureShader.radius = radius.toFloat() RoundedTextureShader.smoothness = smoothness.toFloat() RoundedTextureShader.halfSize = floatArrayOf(widthIn / 2f, heightIn / 2f) @@ -1795,13 +1785,13 @@ object RenderUtils { * It is best kept at its default. */ fun drawRoundRect(x: Int, y: Int, width: Int, height: Int, color: Int, radius: Int = 10, smoothness: Int = 1) { - val scaledRes = ScaledResolution(Minecraft.getMinecraft()) - val widthIn = width * scaledRes.scaleFactor - val heightIn = height * scaledRes.scaleFactor - val xIn = x * scaledRes.scaleFactor - val yIn = y * scaledRes.scaleFactor + val scaleFactor = ScaledResolution(Minecraft.getMinecraft()).scaleFactor + val widthIn = width * scaleFactor + val heightIn = height * scaleFactor + val xIn = x * scaleFactor + val yIn = y * scaleFactor - RoundedRectangleShader.scaleFactor = scaledRes.scaleFactor.toFloat() + RoundedRectangleShader.scaleFactor = scaleFactor.toFloat() RoundedRectangleShader.radius = radius.toFloat() RoundedRectangleShader.smoothness = smoothness.toFloat() RoundedRectangleShader.halfSize = floatArrayOf(widthIn / 2f, heightIn / 2f) @@ -1841,15 +1831,15 @@ object RenderUtils { radius: Int = 10, blur: Float = 0.7f, ) { - val scaledRes = ScaledResolution(Minecraft.getMinecraft()) - val widthIn = width * scaledRes.scaleFactor - val heightIn = height * scaledRes.scaleFactor - val xIn = x * scaledRes.scaleFactor - val yIn = y * scaledRes.scaleFactor + val scaleFactor = ScaledResolution(Minecraft.getMinecraft()).scaleFactor + val widthIn = width * scaleFactor + val heightIn = height * scaleFactor + val xIn = x * scaleFactor + val yIn = y * scaleFactor val borderAdjustment = borderThickness / 2 - RoundedRectangleOutlineShader.scaleFactor = scaledRes.scaleFactor.toFloat() + RoundedRectangleOutlineShader.scaleFactor = scaleFactor.toFloat() RoundedRectangleOutlineShader.radius = radius.toFloat() RoundedRectangleOutlineShader.halfSize = floatArrayOf(widthIn / 2f, heightIn / 2f) RoundedRectangleOutlineShader.centerPos = floatArrayOf(xIn + (widthIn / 2f), yIn + (heightIn / 2f)) diff --git a/src/main/java/at/hannibal2/skyhanni/utils/compat/GuiScreenUtils.kt b/src/main/java/at/hannibal2/skyhanni/utils/compat/GuiScreenUtils.kt index 376ecec74b8f..d2f22dc5768f 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/compat/GuiScreenUtils.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/compat/GuiScreenUtils.kt @@ -5,7 +5,9 @@ import net.minecraft.client.gui.ScaledResolution import org.lwjgl.input.Mouse object GuiScreenUtils { + private val mc get() = Minecraft.getMinecraft() + val scaledWindowHeight get() = //#if MC < 1.16 @@ -30,7 +32,6 @@ object GuiScreenUtils { //$$ mc.window.width //#endif - val displayHeight get() = //#if MC < 1.16 @@ -39,11 +40,11 @@ object GuiScreenUtils { //$$ mc.window.height //#endif - val globalMouseX get() = Mouse.getX() - val globalMouseY get() = Mouse.getY() + private val globalMouseX get() = Mouse.getX() + private val globalMouseY get() = Mouse.getY() + + val mouseX get() = globalMouseX * scaledWindowWidth / displayWidth - val mouseX - get() = globalMouseX * scaledWindowWidth / displayWidth val mouseY: Int get() { val height = this.scaledWindowHeight @@ -56,4 +57,5 @@ object GuiScreenUtils { //#endif } + val mousePos: Pair get() = mouseX to mouseY } diff --git a/src/main/java/at/hannibal2/skyhanni/utils/renderables/RenderableTooltips.kt b/src/main/java/at/hannibal2/skyhanni/utils/renderables/RenderableTooltips.kt index b6c4225ba275..906371bf4300 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/renderables/RenderableTooltips.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/renderables/RenderableTooltips.kt @@ -4,9 +4,9 @@ import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.ItemUtils.getLore import at.hannibal2.skyhanni.utils.LorenzColor import at.hannibal2.skyhanni.utils.RenderUtils +import at.hannibal2.skyhanni.utils.compat.GuiScreenUtils import at.hannibal2.skyhanni.utils.renderables.RenderableUtils.renderXAligned import net.minecraft.client.Minecraft -import net.minecraft.client.gui.ScaledResolution import net.minecraft.client.renderer.GlStateManager import net.minecraft.client.renderer.RenderHelper import net.minecraft.item.ItemStack @@ -43,10 +43,9 @@ object RenderableTooltips { val tips = tooltip.tips if (tips.isEmpty()) return - val x = RenderUtils.getMouseX() + 12 - val y = RenderUtils.getMouseY() - if (tips.size > 1) 1 else -7 + val x = GuiScreenUtils.mouseX + 12 + val y = GuiScreenUtils.mouseY - if (tips.size > 1) 1 else -7 val borderColorStart = tooltip.getBorderColor() - val scaled = ScaledResolution(Minecraft.getMinecraft()) val isSpacedTitle = tooltip.isSpacedTitle() val tooltipTextWidth = tips.maxOf { it.width } @@ -54,19 +53,19 @@ object RenderableTooltips { val tooltipY = when { y < 16 -> 4 // Limit Top - y + tooltipHeight > scaled.scaledHeight -> { - if (tooltip.snapsToTopIfToLong && tooltipHeight + 8 > scaled.scaledHeight) + y + tooltipHeight > GuiScreenUtils.scaledWindowHeight -> { + if (tooltip.snapsToTopIfToLong && tooltipHeight + 8 > GuiScreenUtils.scaledWindowHeight) 4 // Snap to Top if to Long else - scaled.scaledHeight - tooltipHeight - 6 // Limit Bottom + GuiScreenUtils.scaledWindowHeight - tooltipHeight - 6 // Limit Bottom } else -> { y - 10 // normal } } - val tooltipX = if (x + tooltipTextWidth + 4 > scaled.scaledWidth) { - scaled.scaledWidth - tooltipTextWidth - 4 // Limit Right + val tooltipX = if (x + tooltipTextWidth + 4 > GuiScreenUtils.scaledWindowWidth) { + GuiScreenUtils.scaledWindowWidth - tooltipTextWidth - 4 // Limit Right } else { x // normal } From c65b18c7e95a7cefdeea3c0be9bb69d3195c6283 Mon Sep 17 00:00:00 2001 From: Empa <42304516+ItsEmpa@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:05:25 +0100 Subject: [PATCH 030/105] Improvement: Slayer Miniboss Mob Detection (#2081) Co-authored-by: ItsEmpa Co-authored-by: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../features/slayer/SlayerMiniBossFeatures.kt | 74 +++++++------------ .../skyhanni/features/slayer/SlayerType.kt | 48 ++++++++++-- 2 files changed, 69 insertions(+), 53 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerMiniBossFeatures.kt b/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerMiniBossFeatures.kt index 1dabaaba98bd..75f6ba9517cf 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerMiniBossFeatures.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerMiniBossFeatures.kt @@ -1,69 +1,44 @@ package at.hannibal2.skyhanni.features.slayer import at.hannibal2.skyhanni.SkyHanniMod -import at.hannibal2.skyhanni.events.EntityMaxHealthUpdateEvent +import at.hannibal2.skyhanni.data.SlayerAPI +import at.hannibal2.skyhanni.data.mob.Mob import at.hannibal2.skyhanni.events.LorenzRenderWorldEvent -import at.hannibal2.skyhanni.events.LorenzWorldChangeEvent -import at.hannibal2.skyhanni.features.combat.damageindicator.DamageIndicatorManager -import at.hannibal2.skyhanni.features.dungeon.DungeonAPI -import at.hannibal2.skyhanni.mixins.hooks.RenderLivingEntityHelper +import at.hannibal2.skyhanni.events.MobEvent import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule -import at.hannibal2.skyhanni.utils.CollectionUtils.editCopy -import at.hannibal2.skyhanni.utils.ColorUtils.withAlpha import at.hannibal2.skyhanni.utils.EntityUtils.canBeSeen -import at.hannibal2.skyhanni.utils.EntityUtils.hasMaxHealth import at.hannibal2.skyhanni.utils.LorenzColor -import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.RenderUtils.drawLineToEye import at.hannibal2.skyhanni.utils.getLorenzVec -import net.minecraft.entity.EntityCreature -import net.minecraft.entity.monster.EntityBlaze -import net.minecraft.entity.monster.EntityEnderman -import net.minecraft.entity.monster.EntitySpider -import net.minecraft.entity.monster.EntityZombie -import net.minecraft.entity.passive.EntityWolf import net.minecraftforge.fml.common.eventhandler.SubscribeEvent @SkyHanniModule object SlayerMiniBossFeatures { private val config get() = SkyHanniMod.feature.slayer - private var miniBosses = listOf() + private var miniBosses = mutableSetOf() @SubscribeEvent - fun onEntityHealthUpdate(event: EntityMaxHealthUpdateEvent) { - if (!isEnabled()) return - val entity = event.entity as? EntityCreature ?: return - if (DamageIndicatorManager.isBoss(entity)) return - - val maxHealth = event.maxHealth - for (bossType in SlayerMiniBossType.entries) { - if (!bossType.health.any { entity.hasMaxHealth(it, true, maxHealth) }) continue - if (bossType.clazz != entity.javaClass) continue - - miniBosses = miniBosses.editCopy { add(entity) } - RenderLivingEntityHelper.setEntityColorWithNoHurtTime( - entity, - LorenzColor.AQUA.toColor().withAlpha(127) - ) { config.slayerMinibossHighlight } - } + fun onMobSpawn(event: MobEvent.Spawn.SkyblockMob) { + val mob = event.mob + if (!SlayerMiniBossType.isMiniboss(mob.name)) return + miniBosses += mob + if (config.slayerMinibossHighlight) mob.highlight(LorenzColor.AQUA.toColor()) } @SubscribeEvent - fun onWorldChange(event: LorenzWorldChangeEvent) { - miniBosses = emptyList() + fun onMobDeSpawn(event: MobEvent.DeSpawn.SkyblockMob) { + miniBosses -= event.mob } @SubscribeEvent fun onWorldRender(event: LorenzRenderWorldEvent) { + if (!SlayerAPI.isInAnyArea) return if (!config.slayerMinibossLine) return for (mob in miniBosses) { - if (mob.health <= 0) continue - if (mob.isDead) continue - if (!mob.canBeSeen(10)) continue - + if (!mob.baseEntity.canBeSeen(10)) continue event.drawLineToEye( - mob.getLorenzVec().up(), + mob.baseEntity.getLorenzVec().up(), LorenzColor.AQUA.toColor(), config.slayerMinibossLineWidth, true, @@ -71,13 +46,20 @@ object SlayerMiniBossFeatures { } } - private fun isEnabled() = LorenzUtils.inSkyBlock && !DungeonAPI.inDungeon() && !LorenzUtils.inKuudraFight + enum class SlayerMiniBossType(vararg names: String) { + REVENANT("Revenant Sycophant", "Revenant Champion", "Deformed Revenant", "Atoned Champion", "Atoned Revenant"), + TARANTULA("Tarantula Vermin", "Tarantula Beast", "Mutant Tarantula"), + SVEN("Pack Enforcer", "Sven Follower", "Sven Alpha"), + VOIDLING("Voidling Devotee", "Voidling Radical", "Voidcrazed Maniac"), + INFERNAL("Flare Demon", "Kindleheart Demon", "Burningsoul Demon"), + ; - enum class SlayerMiniBossType(val clazz: Class, vararg val health: Int) { - REVENANT(EntityZombie::class.java, 24_000, 90_000, 360_000, 600_000, 2_400_000), - TARANTULA(EntitySpider::class.java, 54_000, 144_000, 576_000), - SVEN(EntityWolf::class.java, 45_000, 120_000, 480_000), - VOIDLING(EntityEnderman::class.java, 8_400_000, 17_500_000, 52_500_000), - INFERNAL(EntityBlaze::class.java, 12_000_000, 25_000_000, 75_000_000), + val names = names.toSet() + + companion object { + private val allNames = entries.flatMap { it.names }.toSet() + + fun isMiniboss(name: String) = name in allNames + } } } diff --git a/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerType.kt b/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerType.kt index 0a07e62fece0..9fff1bb06477 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerType.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/slayer/SlayerType.kt @@ -6,13 +6,47 @@ import net.minecraft.entity.monster.EntitySpider import net.minecraft.entity.monster.EntityZombie import net.minecraft.entity.passive.EntityWolf -enum class SlayerType(val displayName: String, val rngName: String, val clazz: Class<*>) { - REVENANT("Revenant Horror", "revenant", EntityZombie::class.java), - TARANTULA("Tarantula Broodfather", "tarantula", EntitySpider::class.java), - SVEN("Sven Packmaster", "sven", EntityWolf::class.java), - VOID("Voidgloom Seraph", "voidgloom", EntityEnderman::class.java), - INFERNO("Inferno Demonlord", "inferno", EntityBlaze::class.java), - VAMPIRE("Bloodfiend", "vampire", EntityZombie::class.java) // previously called "Riftstalker Bloodfiend" +enum class SlayerType( + val displayName: String, + val rngName: String, + val clazz: Class<*>, + val miniBossType: SlayerMiniBossFeatures.SlayerMiniBossType? = null, +) { + REVENANT( + "Revenant Horror", + "revenant", + EntityZombie::class.java, + SlayerMiniBossFeatures.SlayerMiniBossType.REVENANT, + ), + TARANTULA( + "Tarantula Broodfather", + "tarantula", + EntitySpider::class.java, + SlayerMiniBossFeatures.SlayerMiniBossType.TARANTULA, + ), + SVEN( + "Sven Packmaster", + "sven", + EntityWolf::class.java, + SlayerMiniBossFeatures.SlayerMiniBossType.SVEN, + ), + VOID( + "Voidgloom Seraph", + "voidgloom", + EntityEnderman::class.java, + SlayerMiniBossFeatures.SlayerMiniBossType.VOIDLING, + ), + INFERNO( + "Inferno Demonlord", + "inferno", + EntityBlaze::class.java, + SlayerMiniBossFeatures.SlayerMiniBossType.INFERNAL, + ), + VAMPIRE( + "Bloodfiend", + "vampire", + EntityZombie::class.java, + ) // previously called "Riftstalker Bloodfiend" ; companion object { From 6a7005e9859ce9f18c43d1d420c5257600914685 Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal002@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:08:08 +0100 Subject: [PATCH 031/105] Fixed holographic mob wrong health format in Rift's Crafting Room (#2846) --- .../features/rift/area/mirrorverse/CraftRoomHolographicMob.kt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/rift/area/mirrorverse/CraftRoomHolographicMob.kt b/src/main/java/at/hannibal2/skyhanni/features/rift/area/mirrorverse/CraftRoomHolographicMob.kt index ab5060be3a2b..a59f4b791178 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/rift/area/mirrorverse/CraftRoomHolographicMob.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/rift/area/mirrorverse/CraftRoomHolographicMob.kt @@ -11,6 +11,7 @@ import at.hannibal2.skyhanni.utils.EntityUtils import at.hannibal2.skyhanni.utils.HolographicEntities import at.hannibal2.skyhanni.utils.LocationUtils import at.hannibal2.skyhanni.utils.LocationUtils.isInside +import at.hannibal2.skyhanni.utils.NumberUtil.roundTo import at.hannibal2.skyhanni.utils.RenderUtils.drawString import at.hannibal2.skyhanni.utils.getLorenzVec import net.minecraft.client.entity.EntityOtherPlayerMP @@ -65,7 +66,7 @@ object CraftRoomHolographicMob { append("§a$mobName ") } if (config.showHealth) { - append("§c${theMob.health}♥") + append("§c${theMob.health.roundTo(1)}♥") } }.trim() From fc3ef51cd9d61c65b675f98c174779ea8b0dc75d Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal002@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:11:34 +0100 Subject: [PATCH 032/105] fixed typo in pattern group key (#2842) --- .../skyhanni/features/event/carnival/CarnivalGoal.kt | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/carnival/CarnivalGoal.kt b/src/main/java/at/hannibal2/skyhanni/features/event/carnival/CarnivalGoal.kt index 393979ebbf4c..d65e65ba16ac 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/carnival/CarnivalGoal.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/carnival/CarnivalGoal.kt @@ -24,7 +24,7 @@ import net.minecraft.item.ItemStack import net.minecraftforge.fml.common.eventhandler.SubscribeEvent import org.intellij.lang.annotations.Language -private val repoGroup = RepoPattern.group("carnvial.goals") +private val patternGroup = RepoPattern.group("event.carnival.goals") enum class CarnivalGoal( private val type: GoalType, @@ -126,8 +126,8 @@ enum class CarnivalGoal( private val patternKeyName = name.lowercase().replace("_", ".") - private val lorePattern by repoGroup.pattern("lore.$patternKeyName", loreLine) - private val chatPattern by repoGroup.pattern("chat.$patternKeyName", chatLine) + private val lorePattern by patternGroup.pattern("lore.$patternKeyName", loreLine) + private val chatPattern by patternGroup.pattern("chat.$patternKeyName", chatLine) private var isReached: Boolean get() { @@ -161,9 +161,9 @@ enum class CarnivalGoal( private val config get() = SkyHanniMod.feature.event.carnival private val storage get() = ProfileStorageData.profileSpecific?.carnival - private val inventoryPattern by repoGroup.pattern("inventory", "Carnival Goals") + private val inventoryPattern by patternGroup.pattern("inventory", "Carnival Goals") - private val completePattern by repoGroup.pattern("complete", "§a§lCOMPLETE") + private val completePattern by patternGroup.pattern("complete", "§a§lCOMPLETE") private var dirty = true From 45d20d1b77e0f5c5cdcab0687dc590b726fa913d Mon Sep 17 00:00:00 2001 From: J10a1n15 <45315647+j10a1n15@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:17:18 +0100 Subject: [PATCH 033/105] Backend + Fix: Improve active Perks Handling (#2838) Co-authored-by: Cal Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- detekt/baseline.xml | 2 +- .../config/features/dev/DebugConfig.java | 4 +- .../data/{MayorAPI.kt => ElectionAPI.kt} | 39 +++++----- .../skyhanni/data/{Mayors.kt => MayorData.kt} | 76 +++++++++---------- .../event/diana/DianaProfitTracker.kt | 2 +- .../event/diana/GriffinBurrowHelper.kt | 5 +- .../diana/MythologicalCreatureTracker.kt | 2 +- .../elements/ScoreboardElementMayor.kt | 20 +++-- .../features/inventory/MinisterInCalendar.kt | 16 ++-- versions/1.8.9/detekt/baseline.xml | 2 +- 10 files changed, 84 insertions(+), 84 deletions(-) rename src/main/java/at/hannibal2/skyhanni/data/{MayorAPI.kt => ElectionAPI.kt} (88%) rename src/main/java/at/hannibal2/skyhanni/data/{Mayors.kt => MayorData.kt} (81%) diff --git a/detekt/baseline.xml b/detekt/baseline.xml index 6665e039968c..fb620c66661c 100644 --- a/detekt/baseline.xml +++ b/detekt/baseline.xml @@ -30,9 +30,9 @@ CyclomaticComplexMethod:VampireSlayerFeatures.kt$VampireSlayerFeatures$private fun EntityOtherPlayerMP.process() CyclomaticComplexMethod:VisualWordGui.kt$VisualWordGui$override fun drawScreen(unusedX: Int, unusedY: Int, partialTicks: Float) InjectDispatcher:ClipboardUtils.kt$ClipboardUtils$IO + InjectDispatcher:ElectionAPI.kt$ElectionAPI$IO InjectDispatcher:GardenNextJacobContest.kt$GardenNextJacobContest$IO InjectDispatcher:HypixelBazaarFetcher.kt$HypixelBazaarFetcher$IO - InjectDispatcher:MayorAPI.kt$MayorAPI$IO LongMethod:CopyNearbyEntitiesCommand.kt$CopyNearbyEntitiesCommand$fun command(args: Array<String>) LongMethod:CropMoneyDisplay.kt$CropMoneyDisplay$private fun drawDisplay(): List<List<Any>> LongMethod:GhostCounter.kt$GhostCounter$private fun drawDisplay() diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java index 9f92436cfa3c..4607ab8df79c 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java +++ b/src/main/java/at/hannibal2/skyhanni/config/features/dev/DebugConfig.java @@ -1,7 +1,7 @@ package at.hannibal2.skyhanni.config.features.dev; import at.hannibal2.skyhanni.config.core.config.Position; -import at.hannibal2.skyhanni.data.Mayor; +import at.hannibal2.skyhanni.data.ElectionCandidate; import com.google.gson.annotations.Expose; import io.github.notenoughupdates.moulconfig.annotations.ConfigEditorBoolean; import io.github.notenoughupdates.moulconfig.annotations.ConfigEditorDropdown; @@ -145,7 +145,7 @@ public class DebugConfig { @Expose @ConfigOption(name = "Assume Mayor", desc = "Select a mayor to assume.") @ConfigEditorDropdown - public Property assumeMayor = Property.of(Mayor.DISABLED); + public Property assumeMayor = Property.of(ElectionCandidate.DISABLED); @Expose @ConfigOption(name = "Always April Fools", desc = "Always show April fools jokes.") diff --git a/src/main/java/at/hannibal2/skyhanni/data/MayorAPI.kt b/src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt similarity index 88% rename from src/main/java/at/hannibal2/skyhanni/data/MayorAPI.kt rename to src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt index 1cb023ecd3df..03a6a2e9ce59 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/MayorAPI.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt @@ -2,9 +2,8 @@ package at.hannibal2.skyhanni.data import at.hannibal2.skyhanni.SkyHanniMod import at.hannibal2.skyhanni.config.ConfigManager -import at.hannibal2.skyhanni.data.Mayor.Companion.addPerks -import at.hannibal2.skyhanni.data.Mayor.Companion.getMayorFromPerk -import at.hannibal2.skyhanni.data.Mayor.Companion.setAssumeMayorJson +import at.hannibal2.skyhanni.data.ElectionCandidate.Companion.getMayorFromPerk +import at.hannibal2.skyhanni.data.ElectionCandidate.Companion.setAssumeMayorJson import at.hannibal2.skyhanni.data.Perk.Companion.getPerkFromName import at.hannibal2.skyhanni.data.jsonobjects.other.MayorCandidate import at.hannibal2.skyhanni.data.jsonobjects.other.MayorElection @@ -43,11 +42,13 @@ import kotlin.time.Duration.Companion.milliseconds import kotlin.time.Duration.Companion.minutes @SkyHanniModule -object MayorAPI { +object ElectionAPI { private val group = RepoPattern.group("mayorapi") - // TODO: Add Regex-test + /** + * REGEX-TEST: Schedules an extra §bFishing Festival §7event during the year. + */ val foxyExtraEventPattern by group.pattern( "foxy.extraevent", "Schedules an extra §.(?.*) §.event during the year\\.", @@ -86,12 +87,12 @@ object MayorAPI { "§9Perkpocalypse Perks:", ) - var currentMayor: Mayor? = null + var currentMayor: ElectionCandidate? = null private set - var currentMinister: Mayor? = null + var currentMinister: ElectionCandidate? = null private set - private var lastMayor: Mayor? = null - var jerryExtraMayor: Pair = null to SimpleTimeMark.farPast() + private var lastMayor: ElectionCandidate? = null + var jerryExtraMayor: Pair = null to SimpleTimeMark.farPast() private set private var lastJerryExtraMayorReminder = SimpleTimeMark.farPast() @@ -111,11 +112,11 @@ object MayorAPI { * @param input: The name of the mayor * @return: The NotEnoughUpdates color of the mayor; If no mayor was found, it will return "§c" */ - fun mayorNameToColorCode(input: String): String = Mayor.getMayorFromName(input)?.color ?: "§c" + fun mayorNameToColorCode(input: String): String = ElectionCandidate.getMayorFromName(input)?.color ?: "§c" /** * @param input: The name of the mayor - * @return: The NotEnoughUpdates color of the mayor + the name of the mayor; If no mayor was found, it will return "§c[input]" + * @return: The NotEnoughUpdates color of the mayor with the name of the mayor; If no mayor was found, it will return "§c[input]" */ fun mayorNameWithColorCode(input: String) = mayorNameToColorCode(input) + input @@ -128,7 +129,8 @@ object MayorAPI { } if (!LorenzUtils.inSkyBlock) return - if (jerryExtraMayor.first != null && jerryExtraMayor.second.isInPast() && Mayor.JERRY.isActive()) { + if (!ElectionCandidate.JERRY.isActive()) return + if (jerryExtraMayor.first != null && jerryExtraMayor.second.isInPast()) { jerryExtraMayor = null to SimpleTimeMark.farPast() ChatUtils.clickableChat( "The Perkpocalypse Mayor has expired! Click here to update the new temporary Mayor.", @@ -136,7 +138,7 @@ object MayorAPI { ) } val misc = SkyHanniMod.feature.misc - if (Mayor.JERRY.isActive() && jerryExtraMayor.first == null && misc.unknownPerkpocalypseMayorWarning) { + if (jerryExtraMayor.first == null && misc.unknownPerkpocalypseMayorWarning) { if (lastJerryExtraMayorReminder.passedSince() < 5.minutes) return if (ReminderUtils.isBusy()) return lastJerryExtraMayorReminder = SimpleTimeMark.now() @@ -154,7 +156,7 @@ object MayorAPI { if (electionOverPattern.matches(event.message)) { lastMayor = currentMayor - currentMayor = Mayor.UNKNOWN + currentMayor = ElectionCandidate.UNKNOWN currentMinister = null } } @@ -211,7 +213,7 @@ object MayorAPI { private fun checkHypixelAPI(forceReload: Boolean = false) { if (!forceReload) { if (lastUpdate.passedSince() < 20.minutes) return - if (currentMayor == Mayor.UNKNOWN && lastUpdate.passedSince() < 1.minutes) return + if (currentMayor == ElectionCandidate.UNKNOWN && lastUpdate.passedSince() < 1.minutes) return } lastUpdate = SimpleTimeMark.now() @@ -241,10 +243,11 @@ object MayorAPI { @SubscribeEvent fun onConfigReload(event: ConfigLoadEvent) { - SkyHanniMod.feature.dev.debug.assumeMayor.onToggle { - val mayor = SkyHanniMod.feature.dev.debug.assumeMayor.get() + val config = SkyHanniMod.feature.dev.debug.assumeMayor + config.onToggle { + val mayor = config.get() - if (mayor == Mayor.DISABLED) { + if (mayor == ElectionCandidate.DISABLED) { checkHypixelAPI(forceReload = true) } else { mayor.addPerks(mayor.perks.toList()) diff --git a/src/main/java/at/hannibal2/skyhanni/data/Mayors.kt b/src/main/java/at/hannibal2/skyhanni/data/MayorData.kt similarity index 81% rename from src/main/java/at/hannibal2/skyhanni/data/Mayors.kt rename to src/main/java/at/hannibal2/skyhanni/data/MayorData.kt index 335648dc5116..3d1558987086 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/Mayors.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/MayorData.kt @@ -1,12 +1,13 @@ package at.hannibal2.skyhanni.data -import at.hannibal2.skyhanni.data.MayorAPI.currentMayor -import at.hannibal2.skyhanni.data.MayorAPI.foxyExtraEventPattern +import at.hannibal2.skyhanni.data.ElectionAPI.currentMayor +import at.hannibal2.skyhanni.data.ElectionAPI.foxyExtraEventPattern +import at.hannibal2.skyhanni.data.Perk.Companion.toPerk import at.hannibal2.skyhanni.data.jsonobjects.other.MayorPerk import at.hannibal2.skyhanni.test.command.ErrorManager import at.hannibal2.skyhanni.utils.RegexUtils.matchMatcher -enum class Mayor( +enum class ElectionCandidate( val mayorName: String, val color: String, vararg val perks: Perk, @@ -102,13 +103,17 @@ enum class Mayor( DISABLED("§cDisabled", "§7"), ; - val activePerks: MutableList = mutableListOf() + val activePerks get() = this.perks.filter { it.isActive } override fun toString() = mayorName - fun addAllPerks(): Mayor { - activePerks.addAll(perks) + fun addPerks(perks: List) { + this.perks.forEach { it.isActive = false } perks.forEach { it.isActive = true } + } + + fun addAllPerks(): ElectionCandidate { + this.perks.forEach { it.isActive = true } return this } @@ -116,13 +121,12 @@ enum class Mayor( companion object { - fun getMayorFromName(name: String): Mayor? = entries.firstOrNull { it.mayorName == name } + fun getMayorFromName(name: String): ElectionCandidate? = entries.firstOrNull { it.mayorName == name } - fun getMayorFromPerk(perk: Perk): Mayor? = entries.firstOrNull { it.perks.contains(perk) } + fun getMayorFromPerk(perk: Perk): ElectionCandidate? = entries.firstOrNull { it.perks.contains(perk) } - fun setAssumeMayorJson(name: String, perksJson: List): Mayor? { - val mayor = getMayorFromName(name) - if (mayor == null) { + fun setAssumeMayorJson(name: String, perksJson: List): ElectionCandidate? { + val mayor = getMayorFromName(name) ?: run { ErrorManager.logErrorStateWithData( "Unknown mayor found", "mayor name not in Mayor enum", @@ -133,38 +137,9 @@ enum class Mayor( return null } - val perks = perksJson.mapNotNull { perkJson -> - val perk = Perk.entries.firstOrNull { it.perkName == perkJson.renameIfFoxyExtraEventPerkFound() } - perk?.also { - it.description = perkJson.description - } - } - - mayor.addPerks(perks) + mayor.addPerks(perksJson.mapNotNull { it.toPerk() }) return mayor } - - fun Mayor.addPerks(perks: List) { - perks.forEach { it.isActive = false } - activePerks.forEach { it.isActive = false } - activePerks.clear() - for (perk in perks.filter { perks.contains(it) }) { - perk.isActive = true - activePerks.add(perk) - } - } - - private fun MayorPerk.renameIfFoxyExtraEventPerkFound(): String { - val foxyExtraEventPairs = mapOf( - "Spooky Festival" to "Extra Event (Spooky)", - "Mining Fiesta" to "Extra Event (Mining)", - "Fishing Festival" to "Extra Event (Fishing)", - ) - - return foxyExtraEventPattern.matchMatcher(this.description) { - foxyExtraEventPairs.entries.firstOrNull { it.key == group("event") }?.value - } ?: this.name - } } } @@ -235,10 +210,29 @@ enum class Perk(val perkName: String) { var isActive = false var description = "§cDescription failed to load from the API." + var minister = false override fun toString(): String = "$perkName: $description" companion object { fun getPerkFromName(name: String): Perk? = entries.firstOrNull { it.perkName == name } + + fun MayorPerk.toPerk(): Perk? = getPerkFromName(this.renameIfFoxyExtraEventPerkFound())?.let { + it.description = this.description + it.minister = this.minister + it + } + + private fun MayorPerk.renameIfFoxyExtraEventPerkFound(): String { + val foxyExtraEventPairs = mapOf( + "Spooky Festival" to "Extra Event (Spooky)", + "Mining Fiesta" to "Extra Event (Mining)", + "Fishing Festival" to "Extra Event (Fishing)", + ) + + return foxyExtraEventPattern.matchMatcher(this.description) { + foxyExtraEventPairs.entries.firstOrNull { it.key == group("event") }?.value + } ?: this.name + } } } diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/diana/DianaProfitTracker.kt b/src/main/java/at/hannibal2/skyhanni/features/event/diana/DianaProfitTracker.kt index cd9f48b62c25..c115f00dbaef 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/diana/DianaProfitTracker.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/diana/DianaProfitTracker.kt @@ -1,8 +1,8 @@ package at.hannibal2.skyhanni.features.event.diana import at.hannibal2.skyhanni.SkyHanniMod +import at.hannibal2.skyhanni.data.ElectionAPI.getElectionYear import at.hannibal2.skyhanni.data.ItemAddManager -import at.hannibal2.skyhanni.data.MayorAPI.getElectionYear import at.hannibal2.skyhanni.data.jsonobjects.repo.DianaDropsJson import at.hannibal2.skyhanni.events.GuiRenderEvent import at.hannibal2.skyhanni.events.ItemAddEvent diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/diana/GriffinBurrowHelper.kt b/src/main/java/at/hannibal2/skyhanni/features/event/diana/GriffinBurrowHelper.kt index 64b33c93418f..997ff7fd7367 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/diana/GriffinBurrowHelper.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/diana/GriffinBurrowHelper.kt @@ -3,10 +3,9 @@ package at.hannibal2.skyhanni.features.event.diana import at.hannibal2.skyhanni.SkyHanniMod import at.hannibal2.skyhanni.api.event.HandleEvent import at.hannibal2.skyhanni.config.ConfigUpdaterMigrator +import at.hannibal2.skyhanni.data.ElectionCandidate import at.hannibal2.skyhanni.data.EntityMovementData import at.hannibal2.skyhanni.data.IslandType -import at.hannibal2.skyhanni.data.Mayor -import at.hannibal2.skyhanni.data.MayorAPI.currentMayor import at.hannibal2.skyhanni.events.BlockClickEvent import at.hannibal2.skyhanni.events.BurrowDetectEvent import at.hannibal2.skyhanni.events.BurrowDugEvent @@ -402,7 +401,7 @@ object GriffinBurrowHelper { } if (!isEnabled()) { - if (currentMayor != Mayor.DIANA) { + if (!ElectionCandidate.DIANA.isActive()) { ChatUtils.chatAndOpenConfig( "§cSelect Diana as mayor overwrite!", SkyHanniMod.feature.dev.debug::assumeMayor, diff --git a/src/main/java/at/hannibal2/skyhanni/features/event/diana/MythologicalCreatureTracker.kt b/src/main/java/at/hannibal2/skyhanni/features/event/diana/MythologicalCreatureTracker.kt index 55e422caba5f..dbd46cd345aa 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/event/diana/MythologicalCreatureTracker.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/event/diana/MythologicalCreatureTracker.kt @@ -1,7 +1,7 @@ package at.hannibal2.skyhanni.features.event.diana import at.hannibal2.skyhanni.SkyHanniMod -import at.hannibal2.skyhanni.data.MayorAPI.getElectionYear +import at.hannibal2.skyhanni.data.ElectionAPI.getElectionYear import at.hannibal2.skyhanni.events.ConfigLoadEvent import at.hannibal2.skyhanni.events.GuiRenderEvent import at.hannibal2.skyhanni.events.LorenzChatEvent diff --git a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementMayor.kt b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementMayor.kt index 2d5deaaa4e20..46f3bb48f391 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementMayor.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/gui/customscoreboard/elements/ScoreboardElementMayor.kt @@ -1,6 +1,6 @@ package at.hannibal2.skyhanni.features.gui.customscoreboard.elements -import at.hannibal2.skyhanni.data.MayorAPI +import at.hannibal2.skyhanni.data.ElectionAPI import at.hannibal2.skyhanni.features.gui.customscoreboard.CustomScoreboard.mayorConfig import at.hannibal2.skyhanni.features.rift.RiftAPI import at.hannibal2.skyhanni.utils.TimeUtils.format @@ -9,15 +9,17 @@ import at.hannibal2.skyhanni.utils.TimeUtils.format // set 1s timer object ScoreboardElementMayor : ScoreboardElement() { override fun getDisplay() = buildList { - val currentMayorName = MayorAPI.currentMayor?.mayorName?.let { MayorAPI.mayorNameWithColorCode(it) } ?: return@buildList + val currentMayorName = ElectionAPI.currentMayor?.mayorName?.let { + ElectionAPI.mayorNameWithColorCode(it) + } ?: return@buildList val timeTillNextMayor = if (mayorConfig.showTimeTillNextMayor) { - "§7 (§e${MayorAPI.nextMayorTimestamp.timeUntil().format(maxUnits = 2)}§7)" + "§7 (§e${ElectionAPI.nextMayorTimestamp.timeUntil().format(maxUnits = 2)}§7)" } else "" add(currentMayorName + timeTillNextMayor) if (mayorConfig.showMayorPerks) { - MayorAPI.currentMayor?.activePerks?.forEach { perk -> + ElectionAPI.currentMayor?.activePerks?.forEach { perk -> add(" §7- §e${perk.perkName}") } } @@ -32,21 +34,23 @@ object ScoreboardElementMayor : ScoreboardElement() { override fun showIsland() = !RiftAPI.inRift() private fun addMinister() = buildList { - val ministerName = MayorAPI.currentMinister?.mayorName?.let { MayorAPI.mayorNameWithColorCode(it) } ?: return@buildList + val ministerName = ElectionAPI.currentMinister?.mayorName?.let { + ElectionAPI.mayorNameWithColorCode(it) + } ?: return@buildList add(ministerName) if (mayorConfig.showMayorPerks) { - MayorAPI.currentMinister?.activePerks?.forEach { perk -> + ElectionAPI.currentMinister?.activePerks?.forEach { perk -> add(" §7- §e${perk.perkName}") } } } private fun addJerryMayor() = buildList { - val jerryExtraMayor = MayorAPI.jerryExtraMayor + val jerryExtraMayor = ElectionAPI.jerryExtraMayor val extraMayor = jerryExtraMayor.first ?: return@buildList - val extraMayorName = MayorAPI.mayorNameWithColorCode(extraMayor.mayorName) + val extraMayorName = ElectionAPI.mayorNameWithColorCode(extraMayor.mayorName) val extraTimeTillNextMayor = if (mayorConfig.showTimeTillNextMayor) { " §7(§6${jerryExtraMayor.second.timeUntil().format(maxUnits = 2)}§7)" } else "" diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/MinisterInCalendar.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/MinisterInCalendar.kt index 892951c0f5df..054fed43340e 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/MinisterInCalendar.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/MinisterInCalendar.kt @@ -1,8 +1,8 @@ package at.hannibal2.skyhanni.features.inventory import at.hannibal2.skyhanni.SkyHanniMod -import at.hannibal2.skyhanni.data.Mayor -import at.hannibal2.skyhanni.data.MayorAPI +import at.hannibal2.skyhanni.data.ElectionAPI +import at.hannibal2.skyhanni.data.ElectionCandidate import at.hannibal2.skyhanni.events.InventoryCloseEvent import at.hannibal2.skyhanni.events.InventoryOpenEvent import at.hannibal2.skyhanni.events.render.gui.ReplaceItemEvent @@ -41,11 +41,11 @@ object MinisterInCalendar { @SubscribeEvent fun onInventoryOpen(event: InventoryOpenEvent) { if (!isEnabled()) return - if (!MayorAPI.calendarGuiPattern.matches(InventoryUtils.openInventoryName())) return - val minister = MayorAPI.currentMinister ?: return + if (!ElectionAPI.calendarGuiPattern.matches(InventoryUtils.openInventoryName())) return + val minister = ElectionAPI.currentMinister ?: return val itemStack = "${minister.name}_MAYOR_MONSTER".asInternalName().getItemStack() - val ministerColor = MayorAPI.mayorNameToColorCode(minister.mayorName) + val ministerColor = ElectionAPI.mayorNameToColorCode(minister.mayorName) ministerItemStack = changeItem(ministerColor, minister, itemStack) } @@ -53,7 +53,7 @@ object MinisterInCalendar { @SubscribeEvent fun onInventoryClose(event: InventoryCloseEvent) { if (!isEnabled()) return - if (!MayorAPI.calendarGuiPattern.matches(InventoryUtils.openInventoryName())) return + if (!ElectionAPI.calendarGuiPattern.matches(InventoryUtils.openInventoryName())) return ministerItemStack = null } @@ -61,13 +61,13 @@ object MinisterInCalendar { fun replaceItem(event: ReplaceItemEvent) { if (!isEnabled()) return if (event.inventory !is ContainerLocalMenu || event.slot != MINISTER_SLOT) return - if (!MayorAPI.calendarGuiPattern.matches(InventoryUtils.openInventoryName())) return + if (!ElectionAPI.calendarGuiPattern.matches(InventoryUtils.openInventoryName())) return event.replace(ministerItemStack ?: return) } private fun changeItem( ministerColor: String, - minister: Mayor, + minister: ElectionCandidate, item: ItemStack, ): ItemStack? { val ministerDisplayName = "${ministerColor}Minister ${minister.mayorName}" diff --git a/versions/1.8.9/detekt/baseline.xml b/versions/1.8.9/detekt/baseline.xml index 6665e039968c..fb620c66661c 100644 --- a/versions/1.8.9/detekt/baseline.xml +++ b/versions/1.8.9/detekt/baseline.xml @@ -30,9 +30,9 @@ CyclomaticComplexMethod:VampireSlayerFeatures.kt$VampireSlayerFeatures$private fun EntityOtherPlayerMP.process() CyclomaticComplexMethod:VisualWordGui.kt$VisualWordGui$override fun drawScreen(unusedX: Int, unusedY: Int, partialTicks: Float) InjectDispatcher:ClipboardUtils.kt$ClipboardUtils$IO + InjectDispatcher:ElectionAPI.kt$ElectionAPI$IO InjectDispatcher:GardenNextJacobContest.kt$GardenNextJacobContest$IO InjectDispatcher:HypixelBazaarFetcher.kt$HypixelBazaarFetcher$IO - InjectDispatcher:MayorAPI.kt$MayorAPI$IO LongMethod:CopyNearbyEntitiesCommand.kt$CopyNearbyEntitiesCommand$fun command(args: Array<String>) LongMethod:CropMoneyDisplay.kt$CropMoneyDisplay$private fun drawDisplay(): List<List<Any>> LongMethod:GhostCounter.kt$GhostCounter$private fun drawDisplay() From 50ee0e0c4e8daad88a225a84b675277229e516c6 Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal002@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:28:03 +0100 Subject: [PATCH 034/105] Improvement: Focus Mode Options (#2844) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../features/inventory/FocusModeConfig.java | 14 ++++++++++- .../skyhanni/features/inventory/FocusMode.kt | 25 ++++++++++++++++--- 2 files changed, 34 insertions(+), 5 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/inventory/FocusModeConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/inventory/FocusModeConfig.java index 3211354fec3d..7cf4e6016eb0 100644 --- a/src/main/java/at/hannibal2/skyhanni/config/features/inventory/FocusModeConfig.java +++ b/src/main/java/at/hannibal2/skyhanni/config/features/inventory/FocusModeConfig.java @@ -5,12 +5,14 @@ import io.github.notenoughupdates.moulconfig.annotations.ConfigEditorBoolean; import io.github.notenoughupdates.moulconfig.annotations.ConfigEditorKeybind; import io.github.notenoughupdates.moulconfig.annotations.ConfigOption; +import io.github.notenoughupdates.moulconfig.annotations.SearchTag; import org.lwjgl.input.Keyboard; public class FocusModeConfig { @Expose - @ConfigOption(name = "Enabled", desc = "In focus mode you only see the name of the item instead of the whole description.") + @ConfigOption(name = "Enabled", desc = "In focus mode you only see the name of the item instead of the whole description. §eSet a Toggle key below to use.") + @SearchTag("compact hide") @ConfigEditorBoolean @FeatureToggle public boolean enabled = false; @@ -19,4 +21,14 @@ public class FocusModeConfig { @ConfigOption(name = "Toggle Key", desc = "Key to toggle the focus mode on and off.") @ConfigEditorKeybind(defaultKey = Keyboard.KEY_NONE) public int toggleKey = Keyboard.KEY_NONE; + + @Expose + @ConfigOption(name = "Disable Hint", desc = "Disable the line in item tooltips that show how to enable or disable this feature via key press.") + @ConfigEditorBoolean + public boolean disableHint = false; + + @Expose + @ConfigOption(name = "Always Enabled", desc = "Ignore the keybind and enable this feature all the time.") + @ConfigEditorBoolean + public boolean alwaysEnabled = false; } diff --git a/src/main/java/at/hannibal2/skyhanni/features/inventory/FocusMode.kt b/src/main/java/at/hannibal2/skyhanni/features/inventory/FocusMode.kt index ad2ae077ee4e..427608d0be8b 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/inventory/FocusMode.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/inventory/FocusMode.kt @@ -5,6 +5,7 @@ import at.hannibal2.skyhanni.events.LorenzTickEvent import at.hannibal2.skyhanni.events.LorenzToolTipEvent import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule import at.hannibal2.skyhanni.utils.InventoryUtils +import at.hannibal2.skyhanni.utils.KeyboardManager import at.hannibal2.skyhanni.utils.KeyboardManager.isKeyClicked import at.hannibal2.skyhanni.utils.LorenzUtils import net.minecraftforge.fml.common.eventhandler.EventPriority @@ -15,20 +16,36 @@ object FocusMode { private val config get() = SkyHanniMod.feature.inventory.focusMode - private var toggle = true + private var active = false @SubscribeEvent(priority = EventPriority.LOWEST) fun onLorenzToolTip(event: LorenzToolTipEvent) { - if (!isEnabled() || !toggle) return + if (!isEnabled()) return if (event.toolTip.isEmpty()) return - event.toolTip = mutableListOf(event.toolTip.first()) + val keyName = KeyboardManager.getKeyName(config.toggleKey) + + val hint = !config.disableHint && !config.alwaysEnabled && keyName != "NONE" + if (active || config.alwaysEnabled) { + event.toolTip = buildList { + add(event.toolTip.first()) + if (hint) { + add("§7Focus Mode from SkyHanni active!") + add("Press $keyName to disable!") + } + }.toMutableList() + } else { + if (hint) { + event.toolTip.add(1, "§7Press $keyName to enable Focus Mode from SkyHanni!") + } + } } @SubscribeEvent fun onLorenzTick(event: LorenzTickEvent) { if (!isEnabled()) return + if (config.alwaysEnabled) return if (!config.toggleKey.isKeyClicked()) return - toggle = !toggle + active = !active } fun isEnabled() = LorenzUtils.inSkyBlock && InventoryUtils.inContainer() && config.enabled From 6d7049248706ebc6e6fc356638b3464caedea2d4 Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal00212@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:37:23 +0100 Subject: [PATCH 035/105] Version 0.28 Beta 9 --- docs/CHANGELOG.md | 25 +++++++++++++++++++++++++ root.gradle.kts | 2 +- 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/docs/CHANGELOG.md b/docs/CHANGELOG.md index f91b89c13179..c63451b5af53 100644 --- a/docs/CHANGELOG.md +++ b/docs/CHANGELOG.md @@ -61,6 +61,10 @@ #### Inventory Improvements + Added Pocket Sack-in-a-Sack support to Estimated Item Value. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2698) ++ Added more options to Focus Mode to avoid hiding the item lore unintentionally. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2844) + + Even when enabled in config, focus mode is now inactive on game start and needs to get enabled via toggle mode. + + Show a hint in the item lore how to enable/disable focus mode (with a config option to hide this hint). + + Option to enable focus mode all the time, ignoring the keybind. #### Chat and Command Improvements @@ -77,6 +81,7 @@ + Added Flare Expiration Sound. + Added Flare Expiration Flash Warning. + Added a setting to adjust the expiration warning time. ++ Improved Slayer Miniboss features. - Empa (https://github.com/hannibal002/SkyHanni/pull/2081) #### Mining Improvements @@ -103,6 +108,7 @@ + Added the date to the Custom Scoreboard Lobby code. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2802) + Added an option to display the profile type instead of the name in the Custom Scoreboard. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2810) ++ Improved performance when checking the Scoreboard. - Empa (https://github.com/hannibal002/SkyHanni/pull/2765) #### Misc Improvements @@ -139,6 +145,7 @@ + Fixed an issue with Estimated Item Value erroring when multiple mods affect the same item. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2787) + Fixed "Dungeon Potion level as stack size" not working in shop menus. - phoebe (https://github.com/hannibal002/SkyHanni/pull/2825) + Fixed being unable to use the "Close" button when "Change all clicks to shift clicks in brewing stands" is enabled. - phoebe (https://github.com/hannibal002/SkyHanni/pull/2824) ++ Fixed a rare error message when using Experimentation Table features. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2833) #### Combat Fixes @@ -199,16 +206,23 @@ + Fixed Fear Stat Display. - Fazfoxy (https://github.com/hannibal002/SkyHanni/pull/2766) + Fixed Carnival Goal display rarely showing outside the Hub Island. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2772) + Fixed the Great Spook features. - martimavocado (https://github.com/hannibal002/SkyHanni/pull/2804) ++ Fixed Primal Fear Notify incorrectly notifying when a Primal Fear is not ready to spawn. - Luna (https://github.com/hannibal002/SkyHanni/pull/2831) ++ Fixed typos in Primal Fear Solver. - Obsidian (https://github.com/hannibal002/SkyHanni/pull/2834) ++ Fixed issues where the Carnival Ticket claim feature would trigger even when a carnival isn't active. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2838) #### Rift Fixes + Fixed Mirrorverse features sometimes not working. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2773) ++ Fixed incorrect health format for holographic mobs in Rift's Crafting Room. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2846) #### Chat Fixes + Fixed item stash messages not being compacted correctly. - Daveed (https://github.com/hannibal002/SkyHanni/pull/2781) + Fixed own player messages not being reformatted by chat formatting. - !nea (https://github.com/hannibal002/SkyHanni/pull/2806) + Also fixed ranks losing their "+" colors. ++ Fixed compact stash messages. - Obsidian (https://github.com/hannibal002/SkyHanni/pull/2821) + + Fixed compact item stash messages not being detected correctly. + + Fixed the color of material messages. #### Misc Fixes @@ -217,6 +231,7 @@ + Fixed debug messages not sending when debug mode is enabled. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2793) + Fixed TPS display not working outside Skyblock. - Empa (https://github.com/hannibal002/SkyHanni/pull/2791) + Fixed the "Colored Class Level" tab list displaying "null". - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2814) ++ Fixed kick duration not showing with some kick messages. - Luna (https://github.com/hannibal002/SkyHanni/pull/2837) ### Technical Details @@ -249,6 +264,16 @@ + Added Shot support to the multi-version build. - !nea (https://github.com/hannibal002/SkyHanni/pull/2800) + This allows adding nullability annotations (and other simple annotations) to vanilla code. + Added an event handler check to SkyHanni Events. - CalMWolfs (https://github.com/hannibal002/SkyHanni/pull/2755) ++ Refactored and optimized the `NEUInternalName` class. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2841) + + Added caching for `fromItemNameOrNull` by introducing `itemNameCache` to improve efficiency on repeated calls. + + Renamed `asInternalName` to `toInternalName` for readability and consistency with Kotlin naming, marking `asInternalName` as deprecated for backward compatibility. + + Simplified coin name checks by replacing the `isCoins` method with a predefined set `coinNames`, enhancing readability and potentially reducing overhead. + + Renamed `map` to `internalNameMap` to better reflect its purpose. ++ Improved enchant detection and enchant parser error logging. - Vixid (https://github.com/hannibal002/SkyHanni/pull/2816) ++ Changed "Kick Duration" to use `RepoPatterns`. - Luna (https://github.com/hannibal002/SkyHanni/pull/2837) ++ Used pre-processed methods for GUI scaling operations. - CalMWolfs (https://github.com/hannibal002/SkyHanni/pull/2648) ++ Fixed a typo in the key of Carnival Repo Patterns. - hannibal2 (https://github.com/hannibal002/SkyHanni/pull/2842) ++ Improved the handling of active mayor perks, making it less annoying to work with. - j10a1n15 (https://github.com/hannibal002/SkyHanni/pull/2838) ## Version 0.27 diff --git a/root.gradle.kts b/root.gradle.kts index 11cd8a409819..477358b0dda4 100644 --- a/root.gradle.kts +++ b/root.gradle.kts @@ -14,7 +14,7 @@ plugins { allprojects { group = "at.hannibal2.skyhanni" - version = "0.28.Beta.8" + version = "0.28.Beta.9" repositories { mavenCentral() mavenLocal() From 740a046c467a2b313c9aa04b87aeeca6e7632e46 Mon Sep 17 00:00:00 2001 From: David Cole <40234707+DavidArthurCole@users.noreply.github.com> Date: Sun, 27 Oct 2024 23:23:21 -0400 Subject: [PATCH 036/105] malformed pattern (#2849) --- src/main/java/at/hannibal2/skyhanni/features/chat/ChatFilter.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/chat/ChatFilter.kt b/src/main/java/at/hannibal2/skyhanni/features/chat/ChatFilter.kt index c374a22794f0..18c94da97cdb 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/chat/ChatFilter.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/chat/ChatFilter.kt @@ -165,7 +165,7 @@ object ChatFilter { private val slayerDropPatterns = listOf( // Zombie // TODO merge patterns together. Just because old ones are designed poorly doesnt mean new ones need to be poor as well - "§b§lRARE DROP! §r§7\\(§r§f§r§7(.*)x §9Revenant Viscera§r§7\\) (.*)".toPattern(), + "§b§lRARE DROP! §r§7\\(§r§f§r§7(.*)x §r§f§r§9Revenant Viscera§r§7\\) (.*)".toPattern(), "§b§lRARE DROP! §r§7\\(§r§f§r§9Revenant Viscera§r§7\\) (.*)".toPattern(), "§b§lRARE DROP! §r§7\\(§r§f§r§7(.*)x §r§f§r§9Foul Flesh§r§7\\) (.*)".toPattern(), "§b§lRARE DROP! §r§7\\(§r§f§r§9Foul Flesh§r§7\\) (.*)".toPattern(), From 88e72841f33c3a675ffd08001229b72a5f85793a Mon Sep 17 00:00:00 2001 From: David Cole <40234707+DavidArthurCole@users.noreply.github.com> Date: Mon, 28 Oct 2024 12:36:21 -0400 Subject: [PATCH 037/105] Backend Improvement: Companionize Detekt Rule Regex (#2853) --- .../main/kotlin/formatting/CustomCommentSpacing.kt | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/detekt/src/main/kotlin/formatting/CustomCommentSpacing.kt b/detekt/src/main/kotlin/formatting/CustomCommentSpacing.kt index db9f2f8a75d4..bfb0b1a4b501 100644 --- a/detekt/src/main/kotlin/formatting/CustomCommentSpacing.kt +++ b/detekt/src/main/kotlin/formatting/CustomCommentSpacing.kt @@ -21,12 +21,6 @@ class CustomCommentSpacing(config: Config) : Rule(config) { override fun visitComment(comment: PsiComment) { if (comment.text.containsPreprocessingPattern()) return - - /** - * REGEX-TEST: // Test comment - * REGEX-TEST: /* Test comment */ - */ - val commentRegex = Regex("""^(?:\/{2}|\/\*)(?:\s.*|$)""", RegexOption.DOT_MATCHES_ALL) if (!commentRegex.matches(comment.text)) { report( CodeSmell( @@ -40,4 +34,12 @@ class CustomCommentSpacing(config: Config) : Rule(config) { // Fallback to super (ostensibly a no-check) super.visitComment(comment) } + + companion object { + /** + * REGEX-TEST: // Test comment + * REGEX-TEST: /* Test comment */ + */ + val commentRegex = Regex("""^(?:\/{2}|\/\*)(?:\s.*|$)""", RegexOption.DOT_MATCHES_ALL) + } } From 1a6f246e7c11b731ebca0780f62306fbb5aa141e Mon Sep 17 00:00:00 2001 From: Empa <42304516+ItsEmpa@users.noreply.github.com> Date: Mon, 28 Oct 2024 17:36:50 +0100 Subject: [PATCH 038/105] Backend: Fix Jitpack (#2852) Co-authored-by: Empa --- jitpack.yml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/jitpack.yml b/jitpack.yml index bbaedec93379..50590bedb86e 100644 --- a/jitpack.yml +++ b/jitpack.yml @@ -1,3 +1,4 @@ jdk: - - openjdk17 - + - openjdk21 +install: + - ./gradlew publishToMavenLocal From 2a8e5cf5912a540aeb7a3f2114be2630285ea14a Mon Sep 17 00:00:00 2001 From: J10a1n15 <45315647+j10a1n15@users.noreply.github.com> Date: Mon, 28 Oct 2024 17:37:38 +0100 Subject: [PATCH 039/105] Fix: Old Mayor Perks being active (#2851) --- src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt | 1 + src/main/java/at/hannibal2/skyhanni/data/MayorData.kt | 2 ++ 2 files changed, 3 insertions(+) diff --git a/src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt b/src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt index 03a6a2e9ce59..baedbd16cee5 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/ElectionAPI.kt @@ -231,6 +231,7 @@ object ElectionAPI { val currentMayorName = data.mayor.name if (lastMayor?.name != currentMayorName) { + Perk.resetPerks() currentMayor = setAssumeMayorJson(currentMayorName, data.mayor.perks) currentMinister = data.mayor.minister?.let { setAssumeMayorJson(it.name, listOf(it.perk)) } } diff --git a/src/main/java/at/hannibal2/skyhanni/data/MayorData.kt b/src/main/java/at/hannibal2/skyhanni/data/MayorData.kt index 3d1558987086..26246011f5f3 100644 --- a/src/main/java/at/hannibal2/skyhanni/data/MayorData.kt +++ b/src/main/java/at/hannibal2/skyhanni/data/MayorData.kt @@ -215,6 +215,8 @@ enum class Perk(val perkName: String) { override fun toString(): String = "$perkName: $description" companion object { + fun resetPerks() = entries.forEach { it.isActive = false } + fun getPerkFromName(name: String): Perk? = entries.firstOrNull { it.perkName == name } fun MayorPerk.toPerk(): Perk? = getPerkFromName(this.renameIfFoxyExtraEventPerkFound())?.let { From 55ed9131598f5f743b781cf95b39fa0a87a3177e Mon Sep 17 00:00:00 2001 From: hannibal2 <24389977+hannibal002@users.noreply.github.com> Date: Mon, 28 Oct 2024 19:28:51 +0100 Subject: [PATCH 040/105] Fix: Carnival Area (#2843) Co-authored-by: hannibal2 <24389977+hannibal00212@users.noreply.github.com> --- .../events/skyblock/AreaChangeEvents.kt | 2 +- .../skyhanni/features/misc/IslandAreas.kt | 21 ++++++++++++------- .../hannibal2/skyhanni/test/DebugCommand.kt | 5 ++++- .../test/graph/GraphEditorBugFinder.kt | 4 ++-- 4 files changed, 20 insertions(+), 12 deletions(-) diff --git a/src/main/java/at/hannibal2/skyhanni/events/skyblock/AreaChangeEvents.kt b/src/main/java/at/hannibal2/skyhanni/events/skyblock/AreaChangeEvents.kt index 340187030f2d..6683fa69ae26 100644 --- a/src/main/java/at/hannibal2/skyhanni/events/skyblock/AreaChangeEvents.kt +++ b/src/main/java/at/hannibal2/skyhanni/events/skyblock/AreaChangeEvents.kt @@ -4,4 +4,4 @@ import at.hannibal2.skyhanni.api.event.SkyHanniEvent // Detect area changes by looking at the scoreboard. class ScoreboardAreaChangeEvent(val area: String, val previousArea: String?) : SkyHanniEvent() -class GraphAreaChangeEvent(val area: String, val previousArea: String?) : SkyHanniEvent() +class GraphAreaChangeEvent(val area: String, val previousArea: String?, val onlyInternal: Boolean) : SkyHanniEvent() diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/IslandAreas.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/IslandAreas.kt index 6c0884fc3a90..2eeaef2f3ce8 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/IslandAreas.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/IslandAreas.kt @@ -53,7 +53,7 @@ object IslandAreas { display = null targetNode = null hasMoved = true - updateArea("no_area") + updateArea("no_area", onlyInternal = true) } fun nodeMoved() { @@ -162,10 +162,11 @@ object IslandAreas { val distance = difference.roundTo(0).toInt() val text = "$coloredName§7: §e$distance$suffix" + val isConfigVisible = node.getAreaTag(useConfig = true) != null if (!foundCurrentArea) { foundCurrentArea = true - val inAnArea = name != "no_area" + val inAnArea = name != "no_area" && isConfigVisible if (config.pathfinder.includeCurrentArea.get()) { if (inAnArea) { addSearchString("§eCurrent area: $coloredName") @@ -173,13 +174,14 @@ object IslandAreas { addSearchString("§7Not in an area.") } } - updateArea(name) + updateArea(name, onlyInternal = !isConfigVisible) addSearchString("§eAreas nearby:") continue } if (name == "no_area") continue + if (!isConfigVisible) continue foundAreas++ add( @@ -221,11 +223,11 @@ object IslandAreas { } } - private fun updateArea(name: String) { + private fun updateArea(name: String, onlyInternal: Boolean) { if (name != currentAreaName) { val oldArea = currentAreaName currentAreaName = name - GraphAreaChangeEvent(name, oldArea).post() + GraphAreaChangeEvent(name, oldArea, onlyInternal).post() } } @@ -233,6 +235,8 @@ object IslandAreas { fun onAreaChange(event: GraphAreaChangeEvent) { val name = event.area val inAnArea = name != "no_area" + // when this is a small area and small areas are disabled via config + if (event.onlyInternal) return if (inAnArea && config.enterTitle) { LorenzUtils.sendTitle("§aEntered $name!", 3.seconds) } @@ -247,7 +251,8 @@ object IslandAreas { if (name == currentAreaName) continue if (name == "no_area") continue val position = node.position - val color = node.getAreaTag()?.color?.getChatColor().orEmpty() + val areaTag = node.getAreaTag(useConfig = true) ?: continue + val color = areaTag.color.getChatColor() if (!position.canBeSeen(40.0)) return event.drawDynamicText(position, color + name, 1.5) } @@ -269,8 +274,8 @@ object IslandAreas { private val allAreas = listOf(GraphNodeTag.AREA, GraphNodeTag.SMALL_AREA) private val onlyLargeAreas = listOf(GraphNodeTag.AREA) - fun GraphNode.getAreaTag(ignoreConfig: Boolean = false): GraphNodeTag? = tags.firstOrNull { - it in (if (config.includeSmallAreas || ignoreConfig) allAreas else onlyLargeAreas) + fun GraphNode.getAreaTag(useConfig: Boolean = false): GraphNodeTag? = tags.firstOrNull { + it in (if (config.includeSmallAreas || !useConfig) allAreas else onlyLargeAreas) } private fun setTarget(node: GraphNode) { diff --git a/src/main/java/at/hannibal2/skyhanni/test/DebugCommand.kt b/src/main/java/at/hannibal2/skyhanni/test/DebugCommand.kt index d75b5abc6a57..5b1a48d069ae 100644 --- a/src/main/java/at/hannibal2/skyhanni/test/DebugCommand.kt +++ b/src/main/java/at/hannibal2/skyhanni/test/DebugCommand.kt @@ -7,6 +7,7 @@ import at.hannibal2.skyhanni.data.ProfileStorageData import at.hannibal2.skyhanni.data.repo.RepoManager import at.hannibal2.skyhanni.data.repo.RepoManager.Companion.hasDefaultSettings import at.hannibal2.skyhanni.events.DebugDataCollectEvent +import at.hannibal2.skyhanni.features.misc.IslandAreas import at.hannibal2.skyhanni.utils.ChatUtils import at.hannibal2.skyhanni.utils.LorenzUtils import at.hannibal2.skyhanni.utils.OSUtils @@ -127,7 +128,9 @@ object DebugCommand { event.addIrrelevant { add("on Hypixel SkyBlock") add("skyBlockIsland: ${LorenzUtils.skyBlockIsland}") - add("skyBlockArea: '${LorenzUtils.skyBlockArea}'") + add("skyBlockArea:") + add(" scoreboard: '${LorenzUtils.skyBlockArea}'") + add(" graph network: '${IslandAreas.currentAreaName}'") add("isOnAlphaServer: '${LorenzUtils.isOnAlphaServer}'") } } diff --git a/src/main/java/at/hannibal2/skyhanni/test/graph/GraphEditorBugFinder.kt b/src/main/java/at/hannibal2/skyhanni/test/graph/GraphEditorBugFinder.kt index ca65ae87f113..982fb12c50ab 100644 --- a/src/main/java/at/hannibal2/skyhanni/test/graph/GraphEditorBugFinder.kt +++ b/src/main/java/at/hannibal2/skyhanni/test/graph/GraphEditorBugFinder.kt @@ -43,7 +43,7 @@ object GraphEditorBugFinder { val nearestArea = mutableMapOf() for (node in nodes) { - val pathToNearestArea = GraphUtils.findFastestPath(node) { it.getAreaTag(ignoreConfig = true) != null }?.first + val pathToNearestArea = GraphUtils.findFastestPath(node) { it.getAreaTag() != null }?.first if (pathToNearestArea == null) { continue } @@ -56,7 +56,7 @@ object GraphEditorBugFinder { for (neighbour in node.neighbours.keys) { val neighbouringAreaNode = nearestArea[neighbour]?.name ?: continue if (neighbouringAreaNode == areaNode) continue - if ((null == node.getAreaTag(ignoreConfig = true))) { + if ((null == node.getAreaTag())) { bugs++ errorsInWorld[node] = "§cConflicting areas $areaNode and $neighbouringAreaNode" } From 3f4bdbab85ba6b54a54b99b23e176d52910c8d66 Mon Sep 17 00:00:00 2001 From: CalMWolfs <94038482+CalMWolfs@users.noreply.github.com> Date: Tue, 29 Oct 2024 13:30:22 +1100 Subject: [PATCH 041/105] remove println (#2857) --- .../skyhanni/features/fishing/trophy/GoldenFishTimer.kt | 1 - 1 file changed, 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/fishing/trophy/GoldenFishTimer.kt b/src/main/java/at/hannibal2/skyhanni/features/fishing/trophy/GoldenFishTimer.kt index dd023a7fadf3..50cbd54a947e 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/fishing/trophy/GoldenFishTimer.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/fishing/trophy/GoldenFishTimer.kt @@ -272,7 +272,6 @@ object GoldenFishTimer { if (!isActive()) return if (isGoldenFishActive()) return val entity = event.entity as? EntityArmorStand ?: return - entity.inventory.forEach { it?.getSkullTexture()?.let { texture -> println(texture) } } DelayedRun.runDelayed(1.seconds) { checkGoldenFish(entity) } } From 79adf7aa070fbfaa23241c9b5b8495628650ef68 Mon Sep 17 00:00:00 2001 From: Luna Date: Wed, 30 Oct 2024 00:07:17 +0100 Subject: [PATCH 042/105] Fix: Another kick message (#2861) --- .../hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt b/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt index 89f80fb734cd..86f860d81736 100644 --- a/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt +++ b/src/main/java/at/hannibal2/skyhanni/features/misc/SkyBlockKickDuration.kt @@ -31,10 +31,12 @@ object SkyBlockKickDuration { /** * REGEX-TEST: §cYou were kicked while joining that server! * REGEX-TEST: §cA kick occurred in your connection, so you were put in the SkyBlock lobby! + * REGEX-TEST: §cAn exception occurred in your connection, so you were put in the SkyBlock Lobby! */ + @Suppress("MaxLineLength") private val kickPattern by patternGroup.pattern( "kicked", - "§c(?:You were kicked while joining that server!|A kick occurred in your connection, so you were put in the SkyBlock lobby!)", + "§c(?:You were kicked while joining that server!|An? (?:kick|exception) occurred in your connection, so you were put in the SkyBlock [lL]obby!)", ) /** From 2f4eda4736bd368afd5037ff221e5447ea93113c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Linnea=20Gr=C3=A4f?= Date: Wed, 30 Oct 2024 04:41:40 +0100 Subject: [PATCH 043/105] Backend: getFormattedTextCompat method (#2811) Co-authored-by: Cal --- build.gradle.kts | 17 +++++- .../skyhanni/utils/compat/TextCompat.kt | 53 +++++++++++++++++++ .../hannibal2/skyhanni/utils/compat/World.kt | 23 +------- versions/1.21/buildpaths-test.txt | 2 + versions/1.21/buildpaths.txt | 1 + .../src/test/kotlin/TestLegacyColorFormat.kt | 22 ++++++++ .../org.junit.jupiter.api.extension.Extension | 0 versions/mapping-1.16.5-forge-1.12.2.txt | 2 +- 8 files changed, 97 insertions(+), 23 deletions(-) create mode 100644 src/main/java/at/hannibal2/skyhanni/utils/compat/TextCompat.kt create mode 100644 versions/1.21/buildpaths-test.txt create mode 100644 versions/1.21/buildpaths.txt create mode 100644 versions/1.21/src/test/kotlin/TestLegacyColorFormat.kt create mode 100644 versions/1.21/src/test/resources/META-INF/services/org.junit.jupiter.api.extension.Extension diff --git a/build.gradle.kts b/build.gradle.kts index cbd8eda3a2f7..15586f279067 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -25,7 +25,7 @@ import kotlin.io.path.outputStream plugins { idea java - id("com.github.johnrengelman.shadow") version "7.1.2" + id("com.gradleup.shadow") version "8.3.4" id("gg.essential.loom") id("dev.deftu.gradle.preprocess") kotlin("jvm") @@ -277,6 +277,21 @@ if (target == ProjectTarget.MAIN) { } } +fun includeBuildPaths(buildPathsFile: File, sourceSet: Provider) { + if (buildPathsFile.exists()) { + sourceSet.get().apply { + val buildPaths = buildPathsFile.readText().lineSequence() + .map { it.substringBefore("#").trim() } + .filter { it.isNotBlank() } + .toSet() + kotlin.include(buildPaths) + java.include(buildPaths) + } + } +} +includeBuildPaths(file("buildpaths.txt"), sourceSets.main) +includeBuildPaths(file("buildpaths-test.txt"), sourceSets.test) + tasks.withType { compilerOptions.jvmTarget.set(JvmTarget.fromTarget(target.minecraftVersion.formattedJavaLanguageVersion)) } diff --git a/src/main/java/at/hannibal2/skyhanni/utils/compat/TextCompat.kt b/src/main/java/at/hannibal2/skyhanni/utils/compat/TextCompat.kt new file mode 100644 index 000000000000..f34efe473223 --- /dev/null +++ b/src/main/java/at/hannibal2/skyhanni/utils/compat/TextCompat.kt @@ -0,0 +1,53 @@ +package at.hannibal2.skyhanni.utils.compat + +import net.minecraft.util.IChatComponent +//#if MC > 1.16 +//$$ import net.minecraft.ChatFormatting +//$$ import net.minecraft.network.chat.TextColor +//#endif +//#if MC > 1.20 +//$$ import net.minecraft.text.MutableText +//$$ import net.minecraft.text.PlainTextContent +//#endif + +fun IChatComponent.getDirectlyContainedText() = +//#if MC < 1.16 + this.unformattedTextForChat +//#elseif MC < 1.20 +//$$ this.contents +//#else +//$$ (this.content as? PlainTextContent)?.string().orEmpty() +//#endif + +fun IChatComponent.getFormattedTextCompat() = +//#if MC < 1.16 + this.formattedText +//#else +//$$run { +//$$ val sb = StringBuilder() +//$$ for (component in iterator()) { +//$$ sb.append(component.style.color?.toChatFormatting()?.toString() ?: "§r") +//$$ sb.append(component.getDirectlyContainedText()) +//$$ sb.append("§r") +//$$ } +//$$ sb.toString() +//$$} +//$$ +//$$private val textColorLUT = ChatFormatting.entries +//$$ .mapNotNull { formatting -> formatting.color?.let { it to formatting } } +//$$ .toMap() +//$$ +//$$fun TextColor.toChatFormatting(): ChatFormatting? { +//$$ return textColorLUT[this.value] +//$$} +//$$ +//$$fun Component.iterator(): Sequence { +//$$ return sequenceOf(this) + siblings.asSequence().flatMap { it.iterator() } // TODO: in theory we want to properly inherit styles here +//$$} +//#endif + +//#if MC > 1.20 +//$$fun MutableText.withColor(formatting: Formatting): Text { +//$$ return this.styled { it.withColor(formatting) } +//$$} +//#endif diff --git a/src/main/java/at/hannibal2/skyhanni/utils/compat/World.kt b/src/main/java/at/hannibal2/skyhanni/utils/compat/World.kt index 7916eb4e58b9..6402e44b42d6 100644 --- a/src/main/java/at/hannibal2/skyhanni/utils/compat/World.kt +++ b/src/main/java/at/hannibal2/skyhanni/utils/compat/World.kt @@ -6,7 +6,6 @@ import net.minecraft.entity.Entity import net.minecraft.entity.item.EntityArmorStand import net.minecraft.entity.player.EntityPlayer import net.minecraft.potion.Potion -import net.minecraft.util.IChatComponent fun WorldClient.getLoadedPlayers(): List = //#if MC < 1.14 @@ -15,18 +14,17 @@ fun WorldClient.getLoadedPlayers(): List = //$$ this.players() //#endif - fun Entity.getNameAsString(): String = this.name //#if MC >= 1.14 -//$$ .getString() +//$$ .string //#endif fun EntityArmorStand.getArmorOrFullInventory() = //#if MC < 1.12 this.inventory //#else -//$$ this.getArmorInventoryList() +//$$ this.armorInventoryList //#endif fun Minecraft.isOnMainThread() = @@ -36,21 +34,6 @@ fun Minecraft.isOnMainThread() = //$$ this.isSameThread //#endif -fun IChatComponent.getFormattedTextCompat() = -//#if MC < 1.16 - this.formattedText -//#else -//$$ run { -//$$ val sb = StringBuilder() -//$$ for (component in iterator()) { -//$$ sb.append(component.style.formattingCode) -//$$ sb.append(component.unformattedComponentText) -//$$ sb.append("§r") -//$$ } -//$$ sb.toString() -//$$ } -//#endif - object Effects { val invisibility = //#if MC <1.12 @@ -59,5 +42,3 @@ object Effects { //$$ net.minecraft.init.PotionTypes.INVISIBILITY //#endif } - - diff --git a/versions/1.21/buildpaths-test.txt b/versions/1.21/buildpaths-test.txt new file mode 100644 index 000000000000..6a660321af81 --- /dev/null +++ b/versions/1.21/buildpaths-test.txt @@ -0,0 +1,2 @@ +at/hannibal2/skyhanni/utils/compat/TextCompat.kt +TestLegacyColorFormat.kt diff --git a/versions/1.21/buildpaths.txt b/versions/1.21/buildpaths.txt new file mode 100644 index 000000000000..867bab8c01b9 --- /dev/null +++ b/versions/1.21/buildpaths.txt @@ -0,0 +1 @@ +at/hannibal2/skyhanni/utils/compat/TextCompat.kt diff --git a/versions/1.21/src/test/kotlin/TestLegacyColorFormat.kt b/versions/1.21/src/test/kotlin/TestLegacyColorFormat.kt new file mode 100644 index 000000000000..f1c2323efcf2 --- /dev/null +++ b/versions/1.21/src/test/kotlin/TestLegacyColorFormat.kt @@ -0,0 +1,22 @@ +import net.minecraft.text.Text +import net.minecraft.util.Formatting +import org.junit.jupiter.api.Assertions +import org.junit.jupiter.api.Test +import at.hannibal2.skyhanni.utils.compat.* + +class TestLegacyColorFormat { + @Test + fun testLegacyColorFormatString() { + val text = Text.literal("") + .append(Text.literal("[").withColor(Formatting.DARK_GRAY)) + .append(Text.literal("302").withColor(Formatting.BLUE)) + .append(Text.literal("] ").withColor(Formatting.DARK_GRAY)) + .append(Text.literal("♫ ").withColor(Formatting.GOLD)) + .append(Text.literal("[MVP").withColor(Formatting.AQUA)) + .append(Text.literal("+").withColor(Formatting.LIGHT_PURPLE)) + .append(Text.literal("] lrg89").withColor(Formatting.AQUA)) + .append(Text.literal(": test").withColor(Formatting.WHITE)) + Assertions.assertEquals("§r§r§8[§r§9302§r§8] §r§6♫ §r§b[MVP§r§d+§r§b] lrg89§r§f: test§r", text.getFormattedTextCompat()) + } + +} diff --git a/versions/1.21/src/test/resources/META-INF/services/org.junit.jupiter.api.extension.Extension b/versions/1.21/src/test/resources/META-INF/services/org.junit.jupiter.api.extension.Extension new file mode 100644 index 000000000000..e69de29bb2d1 diff --git a/versions/mapping-1.16.5-forge-1.12.2.txt b/versions/mapping-1.16.5-forge-1.12.2.txt index 71f6c71d249f..1293441ecf9f 100644 --- a/versions/mapping-1.16.5-forge-1.12.2.txt +++ b/versions/mapping-1.16.5-forge-1.12.2.txt @@ -1,4 +1,3 @@ - com.mojang.blaze3d.systems.RenderSystem net.minecraft.client.renderer.GlStateManager com.mojang.blaze3d.systems.RenderSystem color4f() color() com.mojang.blaze3d.systems.RenderSystem translatef() translate() @@ -146,6 +145,7 @@ net.minecraft.network.protocol.game.ServerboundPickItemPacket net.minecraft.netw net.minecraft.server.packs.resources.ResourceManager net.minecraft.client.resources.IResourceManager net.minecraft.world.effect.MobEffect net.minecraft.potion.Potion +net.minecraft.world.effect.MobEffects net.minecraft.init.PotionTypes net.minecraft.world.entity.Entity level getEntityWorld() net.minecraft.world.entity.Entity net.minecraft.entity.Entity From 1aca377197b41e0fb0b6469b8251265a76072dd8 Mon Sep 17 00:00:00 2001 From: Phoebe <77941535+catgirlseraid@users.noreply.github.com> Date: Wed, 30 Oct 2024 21:07:36 +1300 Subject: [PATCH 044/105] Improvement: Add most common labels to pr template (#2864) --- pull_request_template.md | 1 + 1 file changed, 1 insertion(+) diff --git a/pull_request_template.md b/pull_request_template.md index 02769a0f8470..625afe7357ab 100644 --- a/pull_request_template.md +++ b/pull_request_template.md @@ -1,6 +1,7 @@