Update quantum battery item

This commit is contained in:
DBotThePony 2024-08-10 10:37:47 +07:00
parent ed8717964d
commit 23f02036b9
Signed by: DBot
GPG Key ID: DCC23B5715498507
2 changed files with 42 additions and 51 deletions

View File

@ -3,7 +3,8 @@ package ru.dbotthepony.mc.otm.item
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap
import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet import it.unimi.dsi.fastutil.objects.ObjectOpenHashSet
import net.minecraft.ChatFormatting import net.minecraft.ChatFormatting
import net.minecraft.core.Direction import net.minecraft.core.HolderLookup
import net.minecraft.core.HolderLookup.Provider
import net.minecraft.core.registries.BuiltInRegistries import net.minecraft.core.registries.BuiltInRegistries
import net.minecraft.nbt.CompoundTag import net.minecraft.nbt.CompoundTag
import net.minecraft.network.FriendlyByteBuf import net.minecraft.network.FriendlyByteBuf
@ -15,16 +16,12 @@ import net.minecraft.world.item.Item
import net.minecraft.world.item.ItemStack import net.minecraft.world.item.ItemStack
import net.minecraft.world.item.Rarity import net.minecraft.world.item.Rarity
import net.minecraft.world.item.TooltipFlag import net.minecraft.world.item.TooltipFlag
import net.minecraft.world.level.Level
import net.minecraft.world.level.saveddata.SavedData import net.minecraft.world.level.saveddata.SavedData
import net.minecraftforge.client.event.ClientPlayerNetworkEvent import net.neoforged.neoforge.capabilities.Capabilities
import net.minecraftforge.common.capabilities.Capability import net.neoforged.neoforge.capabilities.RegisterCapabilitiesEvent
import net.minecraftforge.common.capabilities.ForgeCapabilities import net.neoforged.neoforge.client.event.ClientPlayerNetworkEvent
import net.minecraftforge.common.capabilities.ICapabilityProvider import net.neoforged.neoforge.event.tick.ServerTickEvent
import net.minecraftforge.common.util.LazyOptional import net.neoforged.neoforge.network.PacketDistributor
import net.minecraftforge.event.TickEvent
import net.minecraftforge.event.TickEvent.ServerTickEvent
import net.minecraftforge.registries.ForgeRegistries
import net.neoforged.neoforge.network.handling.IPayloadContext import net.neoforged.neoforge.network.handling.IPayloadContext
import ru.dbotthepony.mc.otm.OverdriveThatMatters import ru.dbotthepony.mc.otm.OverdriveThatMatters
import ru.dbotthepony.mc.otm.capability.FlowDirection import ru.dbotthepony.mc.otm.capability.FlowDirection
@ -38,8 +35,6 @@ import ru.dbotthepony.mc.otm.config.EnergyBalanceValues
import ru.dbotthepony.mc.otm.core.ResourceLocation import ru.dbotthepony.mc.otm.core.ResourceLocation
import ru.dbotthepony.mc.otm.core.TranslatableComponent import ru.dbotthepony.mc.otm.core.TranslatableComponent
import ru.dbotthepony.mc.otm.core.collect.filter import ru.dbotthepony.mc.otm.core.collect.filter
import ru.dbotthepony.mc.otm.core.getID
import ru.dbotthepony.mc.otm.core.getValue
import ru.dbotthepony.mc.otm.core.isNotEmpty import ru.dbotthepony.mc.otm.core.isNotEmpty
import ru.dbotthepony.mc.otm.core.math.Decimal import ru.dbotthepony.mc.otm.core.math.Decimal
import ru.dbotthepony.mc.otm.core.math.getDecimal import ru.dbotthepony.mc.otm.core.math.getDecimal
@ -48,16 +43,14 @@ import ru.dbotthepony.mc.otm.core.math.set
import ru.dbotthepony.mc.otm.core.math.writeDecimal import ru.dbotthepony.mc.otm.core.math.writeDecimal
import ru.dbotthepony.mc.otm.core.nbt.getUUIDSafe import ru.dbotthepony.mc.otm.core.nbt.getUUIDSafe
import ru.dbotthepony.mc.otm.core.nbt.set import ru.dbotthepony.mc.otm.core.nbt.set
import ru.dbotthepony.mc.otm.core.orThrow
import ru.dbotthepony.mc.otm.core.tagNotNull
import ru.dbotthepony.mc.otm.core.util.formatPower import ru.dbotthepony.mc.otm.core.util.formatPower
import ru.dbotthepony.mc.otm.isClientThread import ru.dbotthepony.mc.otm.isClientThread
import ru.dbotthepony.mc.otm.isServerThread import ru.dbotthepony.mc.otm.isServerThread
import ru.dbotthepony.mc.otm.lazyPerServer import ru.dbotthepony.mc.otm.lazyPerServer
import ru.dbotthepony.mc.otm.network.MatteryPacket import ru.dbotthepony.mc.otm.registry.CapabilitiesRegisterListener
import ru.dbotthepony.mc.otm.registry.MDataComponentTypes
import java.util.* import java.util.*
import java.util.function.Function import java.util.function.Function
import java.util.function.Supplier
import kotlin.collections.MutableList import kotlin.collections.MutableList
import kotlin.collections.component1 import kotlin.collections.component1
import kotlin.collections.component2 import kotlin.collections.component2
@ -65,7 +58,7 @@ import kotlin.collections.forEach
import kotlin.collections.iterator import kotlin.collections.iterator
import kotlin.collections.set import kotlin.collections.set
class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanceValues?) : Item(Properties().stacksTo(1).rarity(if (balanceValues == null) Rarity.EPIC else Rarity.UNCOMMON)), IQuantumLinked { class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanceValues?) : Item(Properties().stacksTo(1).rarity(if (balanceValues == null) Rarity.EPIC else Rarity.UNCOMMON)), IQuantumLinked, CapabilitiesRegisterListener {
val isCreative = balanceValues == null val isCreative = balanceValues == null
interface IValues { interface IValues {
@ -99,7 +92,7 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
} }
class Data() : SavedData() { class Data() : SavedData() {
constructor(nbt: CompoundTag) : this() { constructor(nbt: CompoundTag, registry: Provider) : this() {
load(nbt) load(nbt)
} }
@ -136,7 +129,7 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
return values(UUID.randomUUID()) return values(UUID.randomUUID())
} }
override fun save(nbt: CompoundTag): CompoundTag { override fun save(nbt: CompoundTag, registry: HolderLookup.Provider): CompoundTag {
for ((key, values) in data) { for ((key, values) in data) {
nbt[key.toString()] = values.serialize() nbt[key.toString()] = values.serialize()
} }
@ -160,9 +153,7 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
it.overworld().dataStorage.computeIfAbsent(SavedData.Factory(::Data, ::Data, DataFixTypes.SAVED_DATA_MAP_DATA), "otm_$savedataID") it.overworld().dataStorage.computeIfAbsent(SavedData.Factory(::Data, ::Data, DataFixTypes.SAVED_DATA_MAP_DATA), "otm_$savedataID")
} }
private inner class Power(private val stack: ItemStack) : IMatteryEnergyStorage, ICapabilityProvider { private inner class Power(private val stack: ItemStack) : IMatteryEnergyStorage {
private val resolver = LazyOptional.of { this }
override val energyFlow: FlowDirection override val energyFlow: FlowDirection
get() = FlowDirection.BI_DIRECTIONAL get() = FlowDirection.BI_DIRECTIONAL
@ -170,23 +161,15 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
fun updateValues() { fun updateValues() {
if (!values.isServer && isServerThread()) { if (!values.isServer && isServerThread()) {
values = serverData.values(stack.tag?.getUUIDSafe("uuid") ?: UUID.randomUUID().also { stack.tagNotNull["uuid"] = it }) values = serverData.values(stack[MDataComponentTypes.QUANTUM_LINK_ID] ?: UUID.randomUUID().also { stack[MDataComponentTypes.QUANTUM_LINK_ID] = it })
} else if (isClientThread()) { } else if (isClientThread()) {
val id = stack.tag?.getUUIDSafe("uuid") ?: return val id = stack[MDataComponentTypes.QUANTUM_LINK_ID] ?: return
if (values.uuid != id) if (values.uuid != id)
values = clientData.computeIfAbsent(id, Function { UnboundValues(it) }) values = clientData.computeIfAbsent(id, Function { UnboundValues(it) })
} }
} }
override fun <T : Any?> getCapability(cap: Capability<T>, side: Direction?): LazyOptional<T> {
if (cap == ForgeCapabilities.ENERGY || cap == MatteryCapability.ENERGY) {
return resolver.cast()
}
return LazyOptional.empty()
}
override fun extractEnergy(howMuch: Decimal, simulate: Boolean): Decimal { override fun extractEnergy(howMuch: Decimal, simulate: Boolean): Decimal {
if (!howMuch.isPositive) if (!howMuch.isPositive)
return Decimal.ZERO return Decimal.ZERO
@ -296,14 +279,20 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
return p_150901_.matteryEnergy?.getBarColor() ?: super.getBarColor(p_150901_) return p_150901_.matteryEnergy?.getBarColor() ?: super.getBarColor(p_150901_)
} }
override fun initCapabilities(stack: ItemStack, nbt: CompoundTag?): ICapabilityProvider { override fun registerCapabilities(event: RegisterCapabilitiesEvent) {
return Power(stack) event.registerItem(Capabilities.EnergyStorage.ITEM, { o, _ -> Power(o) }, this)
event.registerItem(MatteryCapability.ITEM_ENERGY, { o, _ -> Power(o) }, this)
} }
override fun appendHoverText(itemStack: ItemStack, level: Level?, components: MutableList<Component>, flags: TooltipFlag) { override fun appendHoverText(
super.appendHoverText(itemStack, level, components, flags) itemStack: ItemStack,
context: TooltipContext,
components: MutableList<Component>,
flags: TooltipFlag
) {
super.appendHoverText(itemStack, context, components, flags)
val power = itemStack.getCapability(MatteryCapability.ENERGY).orThrow() as Power val power = itemStack.getCapability(MatteryCapability.ITEM_ENERGY) as Power
power.updateValues() power.updateValues()
components.add(TranslatableComponent("otm.item.quantum_description").withStyle(ChatFormatting.DARK_GRAY)) components.add(TranslatableComponent("otm.item.quantum_description").withStyle(ChatFormatting.DARK_GRAY))
@ -328,12 +317,12 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
companion object { companion object {
fun clientDisconnect(event: ClientPlayerNetworkEvent.LoggingOut) { fun clientDisconnect(event: ClientPlayerNetworkEvent.LoggingOut) {
ForgeRegistries.ITEMS.values.forEach { if (it is QuantumBatteryItem) it.clientData.clear() } BuiltInRegistries.ITEM.forEach { if (it is QuantumBatteryItem) it.clientData.clear() }
} }
fun readPacket(buff: FriendlyByteBuf): ChargePacket { fun readPacket(buff: FriendlyByteBuf): ChargePacket {
return ChargePacket( return ChargePacket(
ForgeRegistries.ITEMS.getValue(buff.readInt()) as QuantumBatteryItem, BuiltInRegistries.ITEM.byId(buff.readInt()) as QuantumBatteryItem,
buff.readUUID(), buff.readUUID(),
buff.readDecimal(), buff.readDecimal(),
buff.readDecimal(), buff.readDecimal(),
@ -341,17 +330,16 @@ class QuantumBatteryItem(val savedataID: String, val balanceValues: EnergyBalanc
) )
} }
fun tick(event: ServerTickEvent) { fun tick(event: ServerTickEvent.Post) {
if (event.phase == TickEvent.Phase.END) { for (ply in event.server.playerList.players) {
for (ply in event.server.playerList.players) { val networkedChannels = ObjectOpenHashSet<UUID>(0)
val networkedChannels = ObjectOpenHashSet<UUID>(0)
for (item in ply.trackedItems().filter { it.isNotEmpty && it.item is QuantumBatteryItem }) { for (item in ply.trackedItems().filter { it.isNotEmpty && it.item is QuantumBatteryItem }) {
val power = item.getCapability(MatteryCapability.ENERGY).orThrow() as Power val power = item.getCapability(MatteryCapability.ITEM_ENERGY) as Power
power.updateValues() power.updateValues()
if (power.values.isServer && networkedChannels.add(power.values.uuid)) {
GenericNetworkChannel.send(ply, ChargePacket(item.item as QuantumBatteryItem, power.values.uuid, power.batteryLevel, power.passed, power.received)) if (power.values.isServer && networkedChannels.add(power.values.uuid)) {
} PacketDistributor.sendToPlayer(ply, ChargePacket(item.item as QuantumBatteryItem, power.values.uuid, power.batteryLevel, power.passed, power.received))
} }
} }
} }

View File

@ -41,6 +41,8 @@ object MDataComponentTypes {
} }
} }
private fun uuid() = DataComponentType.builder<UUID>().persistent(UUIDUtil.CODEC).networkSynchronized(UUIDUtil.STREAM_CODEC).build()
val BATTERY_LEVEL: DataComponentType<Decimal> by registry.register("battery_level") { DecimalComponent() } val BATTERY_LEVEL: DataComponentType<Decimal> by registry.register("battery_level") { DecimalComponent() }
val MAX_BATTERY_LEVEL: DataComponentType<Decimal> by registry.register("max_battery_level") { DecimalComponent() } val MAX_BATTERY_LEVEL: DataComponentType<Decimal> by registry.register("max_battery_level") { DecimalComponent() }
val MAX_BATTERY_INPUT: DataComponentType<Decimal> by registry.register("max_battery_input") { DecimalComponent() } val MAX_BATTERY_INPUT: DataComponentType<Decimal> by registry.register("max_battery_input") { DecimalComponent() }
@ -48,8 +50,9 @@ object MDataComponentTypes {
val MATTER_LEVEL: DataComponentType<Decimal> by registry.register("matter_level") { DecimalComponent() } val MATTER_LEVEL: DataComponentType<Decimal> by registry.register("matter_level") { DecimalComponent() }
val EXOPACK_SLOT_COUNT: DataComponentType<Int> by registry.register("exopack_slot_count") { DataComponentType.builder<Int>().persistent(Codec.INT).networkSynchronized(StreamCodecs.INT).build() } val EXOPACK_SLOT_COUNT: DataComponentType<Int> by registry.register("exopack_slot_count") { DataComponentType.builder<Int>().persistent(Codec.INT).networkSynchronized(StreamCodecs.INT).build() }
val EXOPACK_UPGRADE_UUID: DataComponentType<UUID> by registry.register("exopack_upgrade_uuid") { DataComponentType.builder<UUID>().persistent(UUIDUtil.CODEC).networkSynchronized(UUIDUtil.STREAM_CODEC).build() } val EXOPACK_UPGRADE_ID: DataComponentType<UUID> by registry.register("exopack_upgrade_id") { uuid() }
val CONDENSATION_DRIVE_UUID: DataComponentType<UUID> by registry.register("condensation_drive_uuid") { DataComponentType.builder<UUID>().persistent(UUIDUtil.CODEC).networkSynchronized(UUIDUtil.STREAM_CODEC).build() } val QUANTUM_LINK_ID: DataComponentType<UUID> by registry.register("quantum_link_id") { uuid() }
val CONDENSATION_DRIVE_UUID: DataComponentType<UUID> by registry.register("condensation_drive_uuid") { uuid() }
val PATTERNS: DataComponentType<List<PatternState>> by registry.register("patterns") { DataComponentType.builder<List<PatternState>>().persistent(Codec.list(PatternState.CODEC)).build() } val PATTERNS: DataComponentType<List<PatternState>> by registry.register("patterns") { DataComponentType.builder<List<PatternState>>().persistent(Codec.list(PatternState.CODEC)).build() }
val ITEM_FILTER: DataComponentType<ItemFilter> by registry.register("item_filter") { DataComponentType.builder<ItemFilter>().persistent(ItemFilter.CODEC).build() } val ITEM_FILTER: DataComponentType<ItemFilter> by registry.register("item_filter") { DataComponentType.builder<ItemFilter>().persistent(ItemFilter.CODEC).build() }