aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/main/java/at/hannibal2/skyhanni/config/features/fishing/BarnTimerConfig.java25
-rw-r--r--src/main/java/at/hannibal2/skyhanni/features/fishing/FishingTimer.kt222
2 files changed, 182 insertions, 65 deletions
diff --git a/src/main/java/at/hannibal2/skyhanni/config/features/fishing/BarnTimerConfig.java b/src/main/java/at/hannibal2/skyhanni/config/features/fishing/BarnTimerConfig.java
index 42e36fe50..d62d066e5 100644
--- a/src/main/java/at/hannibal2/skyhanni/config/features/fishing/BarnTimerConfig.java
+++ b/src/main/java/at/hannibal2/skyhanni/config/features/fishing/BarnTimerConfig.java
@@ -8,17 +8,18 @@ import io.github.notenoughupdates.moulconfig.annotations.ConfigEditorKeybind;
import io.github.notenoughupdates.moulconfig.annotations.ConfigEditorSlider;
import io.github.notenoughupdates.moulconfig.annotations.ConfigLink;
import io.github.notenoughupdates.moulconfig.annotations.ConfigOption;
+import io.github.notenoughupdates.moulconfig.observer.Property;
import org.lwjgl.input.Keyboard;
public class BarnTimerConfig {
@Expose
@ConfigOption(
name = "Barn Fishing Timer",
- desc = "Show the time and amount of sea creatures while fishing on the barn via hub."
+ desc = "Show the time and amount of own sea creatures nearby while barn fishing."
)
@ConfigEditorBoolean
@FeatureToggle
- public boolean enabled = true;
+ public Property<Boolean> enabled = Property.of(true);
@Expose
@ConfigOption(
@@ -26,7 +27,7 @@ public class BarnTimerConfig {
desc = "Show the Barn Fishing Timer in the Crystal Hollows."
)
@ConfigEditorBoolean
- public boolean crystalHollows = true;
+ public Property<Boolean> crystalHollows = Property.of(true);
@Expose
@ConfigOption(
@@ -34,7 +35,7 @@ public class BarnTimerConfig {
desc = "Show the Barn Fishing Timer in the Crimson Isle."
)
@ConfigEditorBoolean
- public boolean crimsonIsle = true;
+ public Property<Boolean> crimsonIsle = Property.of(true);
@Expose
@ConfigOption(
@@ -42,7 +43,7 @@ public class BarnTimerConfig {
desc = "Show the Barn Fishing Timer on the Jerry's Workshop island."
)
@ConfigEditorBoolean
- public boolean winterIsland = true;
+ public Property<Boolean> winterIsland = Property.of(true);
@Expose
@ConfigOption(
@@ -50,12 +51,12 @@ public class BarnTimerConfig {
desc = "Show the Barn Fishing Timer on all the different islands that Stranded players can visit."
)
@ConfigEditorBoolean
- public boolean forStranded = true;
+ public Property<Boolean> forStranded = Property.of(true);
@Expose
@ConfigOption(
name = "Worm Cap Alert",
- desc = "Alerts you with title and sound if you hit the Worm Sea Creature limit of 60."
+ desc = "Alerts you with title and sound if you hit the Worm Sea Creature limit of 20."
)
@ConfigEditorBoolean
public boolean wormLimitAlert = true;
@@ -75,6 +76,16 @@ public class BarnTimerConfig {
public int alertTime = 330;
@Expose
+ @ConfigOption(name = "Fishing Cap Alert", desc = "Gives a warning when you reach a certain amount of mobs.")
+ @ConfigEditorBoolean
+ public boolean fishingCapAlert = true;
+
+ @Expose
+ @ConfigOption(name = "Fishing Cap Amount", desc = "Amount of mobs at which to trigger the Fishing Cap Alert.")
+ @ConfigEditorSlider(minValue = 10, maxValue = 60, minStep = 1)
+ public int fishingCapAmount = 30;
+
+ @Expose
@ConfigLink(owner = BarnTimerConfig.class, field = "enabled")
public Position pos = new Position(10, 10, false, true);
}
diff --git a/src/main/java/at/hannibal2/skyhanni/features/fishing/FishingTimer.kt b/src/main/java/at/hannibal2/skyhanni/features/fishing/FishingTimer.kt
index 26470fd9e..74cf9294d 100644
--- a/src/main/java/at/hannibal2/skyhanni/features/fishing/FishingTimer.kt
+++ b/src/main/java/at/hannibal2/skyhanni/features/fishing/FishingTimer.kt
@@ -3,25 +3,32 @@ package at.hannibal2.skyhanni.features.fishing
import at.hannibal2.skyhanni.SkyHanniMod
import at.hannibal2.skyhanni.config.ConfigUpdaterMigrator
import at.hannibal2.skyhanni.data.IslandType
+import at.hannibal2.skyhanni.data.mob.Mob
import at.hannibal2.skyhanni.events.GuiRenderEvent
+import at.hannibal2.skyhanni.events.LorenzKeyPressEvent
import at.hannibal2.skyhanni.events.LorenzTickEvent
+import at.hannibal2.skyhanni.events.LorenzWorldChangeEvent
+import at.hannibal2.skyhanni.events.MobEvent
+import at.hannibal2.skyhanni.events.SeaCreatureFishEvent
+import at.hannibal2.skyhanni.events.SecondPassedEvent
import at.hannibal2.skyhanni.skyhannimodule.SkyHanniModule
-import at.hannibal2.skyhanni.utils.EntityUtils
-import at.hannibal2.skyhanni.utils.KeyboardManager.isKeyHeld
-import at.hannibal2.skyhanni.utils.LocationUtils
+import at.hannibal2.skyhanni.utils.KeyboardManager.isKeyClicked
+import at.hannibal2.skyhanni.utils.LocationUtils.distanceTo
+import at.hannibal2.skyhanni.utils.LocationUtils.distanceToPlayer
import at.hannibal2.skyhanni.utils.LorenzUtils
import at.hannibal2.skyhanni.utils.LorenzUtils.isInIsland
import at.hannibal2.skyhanni.utils.LorenzVec
+import at.hannibal2.skyhanni.utils.RecalculatingValue
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.TimeLimitedSet
import at.hannibal2.skyhanni.utils.TimeUnit
import at.hannibal2.skyhanni.utils.TimeUtils.format
+import at.hannibal2.skyhanni.utils.getLorenzVec
import net.minecraft.client.Minecraft
-import net.minecraft.entity.item.EntityArmorStand
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent
-import kotlin.time.Duration.Companion.milliseconds
import kotlin.time.Duration.Companion.seconds
@SkyHanniModule
@@ -29,100 +36,199 @@ object FishingTimer {
private val config get() = SkyHanniMod.feature.fishing.barnTimer
private val barnLocation = LorenzVec(108, 89, -252)
+ private val mobDespawnTime = mutableMapOf<Mob, SimpleTimeMark>()
+
+ private var lastSeaCreatureFished = SimpleTimeMark.farPast()
+ private var display: String? = null
+ private var lastNameFished: String? = null
+
+ private var babyMagmaSlugsToFind = 0
+ private var lastMagmaSlugLocation: LorenzVec? = null
+ private var lastMagmaSlugTime = SimpleTimeMark.farPast()
+ private var recentBabyMagmaSlugs = TimeLimitedSet<Mob>(2.seconds)
+
+ private var mobsToFind = 0
+
+ private val recentMobs = TimeLimitedSet<Mob>(2.seconds)
+ private val currentCap by RecalculatingValue(1.seconds) {
+ when (LorenzUtils.skyBlockIsland) {
+ IslandType.CRYSTAL_HOLLOWS -> 20
+ IslandType.CRIMSON_ISLE -> 5
+ else -> config.fishingCapAmount
+ }
+ }
private var rightLocation = false
private var currentCount = 0
private var startTime = SimpleTimeMark.farPast()
- private var inHollows = false
@SubscribeEvent
- fun onTick(event: LorenzTickEvent) {
- if (!LorenzUtils.inSkyBlock) return
- if (!config.enabled) return
-
- if (event.repeatSeconds(3)) {
- rightLocation = isRightLocation()
+ fun onSecondPassed(event: SecondPassedEvent) {
+ if (!isEnabled()) return
+ updateLocation()
+ if (startTime.passedSince().inWholeSeconds - config.alertTime in 0..3) {
+ playSound()
+ }
+ if (config.wormLimitAlert && IslandType.CRYSTAL_HOLLOWS.isInIsland()) {
+ if (currentCount >= 20) {
+ playSound()
+ LorenzUtils.sendTitle("§cWORM CAP FULL!!!", 2.seconds)
+ }
+ } else if (config.fishingCapAlert && currentCount >= currentCap) {
+ playSound()
}
+ }
- if (!rightLocation) return
+ private fun playSound() = SoundUtils.repeatSound(250, 4, SoundUtils.plingSound)
- if (event.isMod(5)) checkMobs()
- if (event.isMod(7)) tryPlaySound()
- if (config.manualResetTimer.isKeyHeld() && Minecraft.getMinecraft().currentScreen == null) {
- startTime = SimpleTimeMark.now()
+ @SubscribeEvent
+ fun onMobSpawn(event: MobEvent.Spawn.SkyblockMob) {
+ if (!isEnabled()) return
+ val mob = event.mob
+ if (babyMagmaSlugsToFind != 0 && mob.name == "Baby Magma Slug") {
+ recentBabyMagmaSlugs += mob
+ handleBabySlugs()
+ return
}
+ if (mob.name !in SeaCreatureManager.allFishingMobs) return
+ recentMobs += mob
+ handle()
}
- private fun tryPlaySound() {
- if (currentCount == 0) return
-
- val passedSince = startTime.passedSince()
- val barnTimerAlertTime = (config.alertTime * 1_000).milliseconds
- if (passedSince in barnTimerAlertTime..(barnTimerAlertTime + 3.seconds)) {
- SoundUtils.playBeepSound()
+ @SubscribeEvent
+ fun onMobDeSpawn(event: MobEvent.DeSpawn.SkyblockMob) {
+ if (!isEnabled()) return
+ val mob = event.mob
+ if (mob in mobDespawnTime) {
+ mobDespawnTime -= mob
+ if (mob.name == "Magma Slug") {
+ lastMagmaSlugLocation = mob.baseEntity.getLorenzVec()
+ babyMagmaSlugsToFind += 3
+ lastMagmaSlugTime = SimpleTimeMark.now()
+ handleBabySlugs()
+ }
}
+ recentMobs -= mob
+ updateInfo()
}
- private fun checkMobs() {
- val newCount = countMobs()
+ @SubscribeEvent
+ fun onSeaCreatureFish(event: SeaCreatureFishEvent) {
+ if (!isEnabled()) return
+ if (!rightLocation) return
+ lastSeaCreatureFished = SimpleTimeMark.now()
+ lastNameFished = event.seaCreature.name
+ mobsToFind = if (event.doubleHook) 2 else 1
+ handle()
+ }
- if (currentCount == 0 && newCount > 0) {
- startTime = SimpleTimeMark.now()
+ private fun handle() {
+ if (lastSeaCreatureFished.passedSince() > 2.seconds) return
+ val name = lastNameFished ?: return
+ val mobs = recentMobs.filter { it.name == name && it !in mobDespawnTime }
+ .sortedBy { it.baseEntity.distanceToPlayer() }
+ .take(mobsToFind).ifEmpty { return }
+ mobsToFind -= mobs.size
+ mobs.forEach { mobDespawnTime[it] = SimpleTimeMark.now() }
+ if (mobsToFind == 0) {
+ recentMobs.clear()
+ lastNameFished = null
}
+ updateInfo()
+ }
- currentCount = newCount
- if (newCount == 0) {
- startTime = SimpleTimeMark.farPast()
+ private fun handleBabySlugs() {
+ if (lastMagmaSlugTime.passedSince() > 2.seconds) return
+ if (babyMagmaSlugsToFind == 0) return
+ val location = lastMagmaSlugLocation ?: return
+ val slugs = recentBabyMagmaSlugs.filter { it !in mobDespawnTime }
+ .sortedBy { it.baseEntity.distanceTo(location) }
+ .take(babyMagmaSlugsToFind).ifEmpty { return }
+ babyMagmaSlugsToFind -= slugs.size
+ slugs.forEach { mobDespawnTime[it] = SimpleTimeMark.now() }
+ if (babyMagmaSlugsToFind == 0) {
+ recentBabyMagmaSlugs.clear()
+ lastMagmaSlugLocation = null
}
+ updateInfo()
+ }
- if (inHollows && newCount >= 60 && config.wormLimitAlert) {
- SoundUtils.playBeepSound()
- LorenzUtils.sendTitle("§cWORM CAP FULL!!!", 2.seconds)
+ @SubscribeEvent
+ fun onKeyPress(event: LorenzKeyPressEvent) {
+ if (!isEnabled()) return
+ if (Minecraft.getMinecraft().currentScreen != null) return
+ if (config.manualResetTimer.isKeyClicked()) {
+ mobDespawnTime.replaceAll { _, _ ->
+ SimpleTimeMark.now()
+ }
}
}
- private fun countMobs() =
- EntityUtils.getEntities<EntityArmorStand>().map { entity -> FishingAPI.seaCreatureCount(entity) }.sum()
-
- private fun isRightLocation(): Boolean {
- inHollows = false
-
- if (config.forStranded && LorenzUtils.isStrandedProfile) return true
-
- if (config.crystalHollows && IslandType.CRYSTAL_HOLLOWS.isInIsland()) {
- inHollows = true
- return true
+ private fun updateInfo() {
+ currentCount = mobDespawnTime.entries.sumOf {
+ 1 + it.key.extraEntities.size
}
+ startTime = mobDespawnTime.maxByOrNull { it.value.passedSince() }?.value ?: SimpleTimeMark.farPast()
+ display = createDisplay()
+ }
- if (config.crimsonIsle && IslandType.CRIMSON_ISLE.isInIsland()) return true
-
- if (config.winterIsland && IslandType.WINTER.isInIsland()) return true
-
- if (!IslandType.THE_FARMING_ISLANDS.isInIsland()) {
- return LocationUtils.playerLocation().distance(barnLocation) < 50
+ private fun updateLocation() {
+ rightLocation = when (LorenzUtils.skyBlockIsland) {
+ IslandType.CRYSTAL_HOLLOWS -> config.crystalHollows.get()
+ IslandType.CRIMSON_ISLE -> config.crimsonIsle.get()
+ IslandType.WINTER -> config.winterIsland.get()
+ IslandType.HUB -> barnLocation.distanceToPlayer() < 50
+ IslandType.PRIVATE_ISLAND -> config.forStranded.get() && LorenzUtils.isStrandedProfile
+ else -> false
}
+ }
- return false
+ @SubscribeEvent
+ fun onTick(event: LorenzTickEvent) {
+ if (!isEnabled()) return
+ if (!rightLocation) return
+ if (currentCount == 0) return
+ if (!FishingAPI.isFishing()) return
+
+ display = createDisplay()
}
@SubscribeEvent
fun onRenderOverlay(event: GuiRenderEvent.GuiOverlayRenderEvent) {
- if (!LorenzUtils.inSkyBlock) return
- if (!config.enabled) return
+ if (!isEnabled()) return
if (!rightLocation) return
if (currentCount == 0) return
if (!FishingAPI.isFishing()) return
+ val text = display ?: return
+ config.pos.renderString(text, posLabel = "BarnTimer")
+ }
+
+ private fun createDisplay(): String {
val passedSince = startTime.passedSince()
- val barnTimerAlertTime = (config.alertTime * 1_000).milliseconds
- val color = if (passedSince > barnTimerAlertTime) "§c" else "§e"
+ val timeColor = if (passedSince > config.alertTime.seconds) "§c" else "§e"
val timeFormat = passedSince.format(TimeUnit.MINUTE)
+ val countColor = if (config.fishingCapAlert && currentCount >= currentCap) "§c" else "§e"
val name = StringUtils.pluralize(currentCount, "sea creature")
- val text = "$color$timeFormat §8(§e$currentCount §b$name§8)"
+ return "$timeColor$timeFormat §8($countColor$currentCount §b$name§8)"
+ }
- config.pos.renderString(text, posLabel = "BarnTimer")
+ @SubscribeEvent
+ fun onWorldChange(event: LorenzWorldChangeEvent) {
+ mobDespawnTime.clear()
+ recentMobs.clear()
+ babyMagmaSlugsToFind = 0
+ display = null
+ lastMagmaSlugLocation = null
+ lastMagmaSlugTime = SimpleTimeMark.farPast()
+ recentBabyMagmaSlugs.clear()
+ mobsToFind = 0
+ currentCount = 0
+ startTime = SimpleTimeMark.farPast()
}
+ private fun isEnabled() = LorenzUtils.inSkyBlock && config.enabled.get()
+
@SubscribeEvent
fun onConfigFix(event: ConfigUpdaterMigrator.ConfigFixEvent) {
event.move(3, "fishing.barnTimer", "fishing.barnTimer.enabled")