diff options
Diffstat (limited to 'src/main/kotlin/moe/nea/firmament/util')
-rw-r--r-- | src/main/kotlin/moe/nea/firmament/util/SBData.kt | 57 | ||||
-rw-r--r-- | src/main/kotlin/moe/nea/firmament/util/data/ProfileSpecificDataHolder.kt | 11 |
2 files changed, 51 insertions, 17 deletions
diff --git a/src/main/kotlin/moe/nea/firmament/util/SBData.kt b/src/main/kotlin/moe/nea/firmament/util/SBData.kt index f2f1d1d..1d97dfa 100644 --- a/src/main/kotlin/moe/nea/firmament/util/SBData.kt +++ b/src/main/kotlin/moe/nea/firmament/util/SBData.kt @@ -18,49 +18,81 @@ package moe.nea.firmament.util +import java.util.UUID import kotlinx.serialization.SerializationException import kotlinx.serialization.decodeFromString import kotlin.time.Duration import kotlin.time.Duration.Companion.seconds +import net.minecraft.network.packet.c2s.play.CommandExecutionC2SPacket import moe.nea.firmament.Firmament +import moe.nea.firmament.events.ClientChatLineReceivedEvent +import moe.nea.firmament.events.OutgoingPacketEvent import moe.nea.firmament.events.ServerChatLineReceivedEvent import moe.nea.firmament.events.SkyblockServerUpdateEvent import moe.nea.firmament.events.WorldReadyEvent object SBData { - val profileRegex = "(?:Your profile was changed to: |You are playing on profile: )(.+)".toRegex() - var profileCuteName: String? = null + private val profileRegex = "Profile ID: ([a-z0-9\\-]+)".toRegex() + var profileId: UUID? = null private var lastLocrawSent = Timer() + private val anyLocrawSent = Timer() private val locrawRoundtripTime: Duration = 5.seconds + private var hasReceivedProfile = false + private var hasSentLocraw = false var locraw: Locraw? = null - val skyblockLocation get() = locraw?.skyblockLocation - + val skyblockLocation: String? get() = locraw?.skyblockLocation + val hasValidLocraw get() = locraw?.server !in listOf("limbo", null) fun init() { + OutgoingPacketEvent.subscribe { event -> + if (event.packet is CommandExecutionC2SPacket && event.packet.command == "locraw") { + anyLocrawSent.markNow() + } + } ServerChatLineReceivedEvent.subscribe { event -> val profileMatch = profileRegex.matchEntire(event.unformattedString) if (profileMatch != null) { - profileCuteName = profileMatch.groupValues[1] + try { + profileId = UUID.fromString(profileMatch.groupValues[1]) + hasReceivedProfile = true + if (!hasValidLocraw && !hasSentLocraw && anyLocrawSent.timePassed() > locrawRoundtripTime) { + sendLocraw() + } + } catch (e: IllegalArgumentException) { + profileId = null + e.printStackTrace() + } } if (event.unformattedString.startsWith("{")) { - if (tryReceiveLocraw(event.unformattedString) && lastLocrawSent.timePassed() < locrawRoundtripTime) { - lastLocrawSent.markFarPast() - event.cancel() + if (tryReceiveLocraw(event.unformattedString)) { + if (!hasValidLocraw && !hasSentLocraw && hasReceivedProfile) { + sendLocraw() + } } } } + ClientChatLineReceivedEvent.subscribe { event -> + if (event.unformattedString.startsWith("{") && tryReceiveLocraw(event.unformattedString) && lastLocrawSent.timePassed() < locrawRoundtripTime) { + lastLocrawSent.markFarPast() + event.cancel() + } + } WorldReadyEvent.subscribe { - sendLocraw() locraw = null + hasSentLocraw = false + hasReceivedProfile = false } } - private fun tryReceiveLocraw(unformattedString: String): Boolean = try { + private fun tryReceiveLocraw(unformattedString: String, update: Boolean = true): Boolean = try { val lastLocraw = locraw - locraw = Firmament.json.decodeFromString<Locraw>(unformattedString) - SkyblockServerUpdateEvent.publish(SkyblockServerUpdateEvent(lastLocraw, locraw)) + val n = Firmament.json.decodeFromString<Locraw>(unformattedString) + if (update) { + locraw = n + SkyblockServerUpdateEvent.publish(SkyblockServerUpdateEvent(lastLocraw, locraw)) + } true } catch (e: SerializationException) { e.printStackTrace() @@ -71,6 +103,7 @@ object SBData { } fun sendLocraw() { + hasSentLocraw = true lastLocrawSent.markNow() val nh = MC.player?.networkHandler ?: return nh.sendChatCommand("locraw") diff --git a/src/main/kotlin/moe/nea/firmament/util/data/ProfileSpecificDataHolder.kt b/src/main/kotlin/moe/nea/firmament/util/data/ProfileSpecificDataHolder.kt index 7111344..06523c3 100644 --- a/src/main/kotlin/moe/nea/firmament/util/data/ProfileSpecificDataHolder.kt +++ b/src/main/kotlin/moe/nea/firmament/util/data/ProfileSpecificDataHolder.kt @@ -19,6 +19,7 @@ package moe.nea.firmament.util.data import java.nio.file.Path +import java.util.UUID import kotlinx.serialization.KSerializer import kotlin.io.path.createDirectories import kotlin.io.path.deleteExisting @@ -37,10 +38,10 @@ abstract class ProfileSpecificDataHolder<S>( private val configDefault: () -> S ) : IDataHolder<S?> { - var allConfigs: MutableMap<String, S> + var allConfigs: MutableMap<UUID, S> override val data: S? - get() = SBData.profileCuteName?.let { + get() = SBData.profileId?.let { allConfigs.computeIfAbsent(it) { configDefault() } } @@ -52,7 +53,7 @@ abstract class ProfileSpecificDataHolder<S>( private val configDirectory: Path get() = Firmament.CONFIG_DIR.resolve("profiles").resolve(configName) - private fun readValues(): MutableMap<String, S> { + private fun readValues(): MutableMap<UUID, S> { if (!configDirectory.exists()) { configDirectory.createDirectories() } @@ -61,7 +62,7 @@ abstract class ProfileSpecificDataHolder<S>( .filter { it.extension == "json" } .mapNotNull { try { - it.nameWithoutExtension to Firmament.json.decodeFromString(dataSerializer, it.readText()) + UUID.fromString(it.nameWithoutExtension) to Firmament.json.decodeFromString(dataSerializer, it.readText()) } catch (e: Exception) { /* Expecting IOException and SerializationException, but Kotlin doesn't allow multi catches*/ IDataHolder.badLoads.add(configName) Firmament.logger.error( @@ -79,7 +80,7 @@ abstract class ProfileSpecificDataHolder<S>( } val c = allConfigs configDirectory.listDirectoryEntries().forEach { - if (it.nameWithoutExtension !in c) { + if (it.nameWithoutExtension !in c.mapKeys { it.toString() }) { it.deleteExisting() } } |