Remove LibBlockAttributes ItemStackCollections use
This commit is contained in:
parent
d782d43e1b
commit
7e71a1e03d
|
@ -1,6 +1,6 @@
|
|||
package net.shadowfacts.phycon.block.terminal
|
||||
|
||||
import alexiil.mc.lib.attributes.item.ItemStackCollections
|
||||
import it.unimi.dsi.fastutil.objects.Object2IntOpenHashMap
|
||||
import net.fabricmc.fabric.api.transfer.v1.item.ItemVariant
|
||||
import net.fabricmc.fabric.api.transfer.v1.storage.Storage
|
||||
import net.fabricmc.fabric.api.transfer.v1.transaction.Transaction
|
||||
|
@ -52,8 +52,7 @@ abstract class AbstractTerminalBlockEntity(type: BlockEntityType<*>, pos: BlockP
|
|||
override val pendingInsertions = mutableListOf<PendingInsertion>()
|
||||
override val dispatchStackTimeout = INSERTION_TIMEOUT
|
||||
|
||||
// TODO: need a ItemVariant -> Int/Long map
|
||||
val cachedNetItems = ItemStackCollections.intMap()
|
||||
val cachedNetItems = Object2IntOpenHashMap<ItemVariant>()
|
||||
private var requestInventoryTimestamp: Long? = null
|
||||
|
||||
// todo: multiple players could have the terminal open simultaneously
|
||||
|
@ -142,7 +141,7 @@ abstract class AbstractTerminalBlockEntity(type: BlockEntityType<*>, pos: BlockP
|
|||
val transaction = Transaction.openOuter()
|
||||
for (view in inventory.iterator(transaction)) {
|
||||
val amount = view.amount.toInt()
|
||||
cachedNetItems.mergeInt(view.resource.toStack(), amount, IntBinaryOperator { a, b -> a + b })
|
||||
cachedNetItems.mergeInt(view.resource, amount, IntBinaryOperator { a, b -> a + b })
|
||||
}
|
||||
transaction.close()
|
||||
}
|
||||
|
|
|
@ -1,24 +1,20 @@
|
|||
package net.shadowfacts.phycon.block.terminal
|
||||
|
||||
import net.fabricmc.fabric.api.transfer.v1.item.ItemVariant
|
||||
import net.minecraft.screen.slot.Slot
|
||||
import net.minecraft.screen.slot.SlotActionType
|
||||
import net.minecraft.entity.player.PlayerEntity
|
||||
import net.minecraft.entity.player.PlayerInventory
|
||||
import net.minecraft.item.ItemStack
|
||||
import net.minecraft.network.PacketByteBuf
|
||||
import net.minecraft.screen.ScreenHandler
|
||||
import net.minecraft.screen.ScreenHandlerType
|
||||
import net.minecraft.server.network.ServerPlayerEntity
|
||||
import net.minecraft.util.Identifier
|
||||
import net.minecraft.util.registry.Registry
|
||||
import net.shadowfacts.phycon.DefaultPlugin
|
||||
import net.shadowfacts.phycon.PhysicalConnectivity
|
||||
import net.shadowfacts.phycon.init.PhyBlocks
|
||||
import net.shadowfacts.phycon.init.PhyScreens
|
||||
import net.shadowfacts.phycon.networking.S2CTerminalUpdateDisplayedItems
|
||||
import net.shadowfacts.phycon.util.SortMode
|
||||
import net.shadowfacts.phycon.util.TerminalSettings
|
||||
import net.shadowfacts.phycon.util.copyWithCount
|
||||
import net.shadowfacts.phycon.util.name
|
||||
import java.lang.ref.WeakReference
|
||||
import kotlin.math.ceil
|
||||
import kotlin.math.max
|
||||
|
@ -49,7 +45,7 @@ abstract class AbstractTerminalScreenHandler<T : AbstractTerminalBlockEntity>(
|
|||
field = value
|
||||
if (terminal.world!!.isClient) {
|
||||
itemsForDisplay = value.map {
|
||||
it.stack.copyWithCount(it.amount)
|
||||
it.variant.toStack(it.amount)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -106,6 +102,8 @@ abstract class AbstractTerminalScreenHandler<T : AbstractTerminalBlockEntity>(
|
|||
return@filter true
|
||||
}
|
||||
}
|
||||
// TODO: this is happening on the logical server, won't work with localization
|
||||
// should filtering happen on the client?
|
||||
it.key.name.string.contains(searchQuery, true)
|
||||
}
|
||||
|
||||
|
@ -273,5 +271,5 @@ abstract class AbstractTerminalScreenHandler<T : AbstractTerminalBlockEntity>(
|
|||
fun isBufferSlot(id: Int) = id in bufferSlotsStart until playerSlotsStart
|
||||
fun isPlayerSlot(id: Int) = id >= playerSlotsStart
|
||||
|
||||
data class Entry(val stack: ItemStack, val amount: Int)
|
||||
data class Entry(val variant: ItemVariant, val amount: Int)
|
||||
}
|
||||
|
|
|
@ -1,7 +1,9 @@
|
|||
package net.shadowfacts.phycon.block.terminal
|
||||
|
||||
import alexiil.mc.lib.attributes.item.ItemStackCollections
|
||||
import it.unimi.dsi.fastutil.ints.IntBinaryOperator
|
||||
import it.unimi.dsi.fastutil.objects.Object2IntArrayMap
|
||||
import net.fabricmc.fabric.api.screenhandler.v1.ExtendedScreenHandlerFactory
|
||||
import net.fabricmc.fabric.api.transfer.v1.item.ItemVariant
|
||||
import net.minecraft.block.BlockState
|
||||
import net.minecraft.entity.player.PlayerEntity
|
||||
import net.minecraft.entity.player.PlayerInventory
|
||||
|
@ -20,7 +22,6 @@ import net.shadowfacts.phycon.util.equalsIgnoringAmount
|
|||
import net.shadowfacts.phycon.util.fromTag
|
||||
import net.shadowfacts.phycon.util.toTag
|
||||
import java.util.LinkedList
|
||||
import kotlin.math.min
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
|
@ -52,20 +53,23 @@ class CraftingTerminalBlockEntity(pos: BlockPos, state: BlockState) :
|
|||
}
|
||||
|
||||
fun requestItemsForCrafting(maxAmount: Int) {
|
||||
val amounts = ItemStackCollections.map<IntArray>()
|
||||
// use an array map because we have at most 9 items
|
||||
// values are bitfields of which slots contain the item
|
||||
val stackToSlotsMap = Object2IntArrayMap<ItemVariant>()
|
||||
|
||||
val or = IntBinaryOperator { a, b -> a or b }
|
||||
for (i in 0 until craftingInv.size()) {
|
||||
val craftingInvStack = craftingInv.getStack(i)
|
||||
if (craftingInvStack.isEmpty) continue
|
||||
if (craftingInvStack.count >= craftingInvStack.maxCount) continue
|
||||
|
||||
if (craftingInvStack !in amounts) amounts[craftingInvStack] = IntArray(9) { 0 }
|
||||
amounts[craftingInvStack]!![i] = min(maxAmount, craftingInvStack.maxCount - craftingInvStack.count)
|
||||
stackToSlotsMap.mergeInt(ItemVariant.of(craftingInvStack), 1 shl i, or)
|
||||
}
|
||||
|
||||
for ((stack, amountPerSlot) in amounts) {
|
||||
val total = amountPerSlot.sum()
|
||||
val request = CraftingStackLocateRequest(stack, total, counter, amountPerSlot)
|
||||
for ((variant, slots) in stackToSlotsMap) {
|
||||
val total = slots.countOneBits()
|
||||
val stack = variant.toStack()
|
||||
val request = CraftingStackLocateRequest(stack, total, counter, slots)
|
||||
pendingRequests.add(request)
|
||||
sendPacket(LocateStackPacket(stack, ipAddress))
|
||||
}
|
||||
|
@ -90,19 +94,19 @@ class CraftingTerminalBlockEntity(pos: BlockPos, state: BlockState) :
|
|||
if (currentStack.count >= currentStack.maxCount) continue
|
||||
if (!currentStack.equalsIgnoringAmount(remaining)) continue
|
||||
|
||||
val toInsert =
|
||||
minOf(remaining.count, currentStack.maxCount - currentStack.count, craftingReq.amountPerSlot[i])
|
||||
currentStack.count += toInsert
|
||||
remaining.count -= toInsert
|
||||
craftingReq.amountPerSlot[i] -= toInsert
|
||||
craftingReq.received += toInsert
|
||||
currentStack.count += 1
|
||||
remaining.count -= 1
|
||||
|
||||
craftingReq.slots = craftingReq.slots and (1 shl i).inv()
|
||||
craftingReq.received += 1
|
||||
|
||||
if (remaining.isEmpty) {
|
||||
break
|
||||
}
|
||||
}
|
||||
|
||||
if (craftingReq.amountPerSlot.sum() == 0 || craftingReq.received >= craftingReq.totalResultAmount) {
|
||||
// if slots == 0, there are no more slots needing items for this request
|
||||
if (craftingReq.slots == 0 || craftingReq.received >= craftingReq.totalResultAmount) {
|
||||
completedCraftingStackRequests.remove(craftingReq)
|
||||
}
|
||||
|
||||
|
@ -132,7 +136,10 @@ class CraftingTerminalBlockEntity(pos: BlockPos, state: BlockState) :
|
|||
stack: ItemStack,
|
||||
amount: Int,
|
||||
timestamp: Long,
|
||||
val amountPerSlot: IntArray,
|
||||
/**
|
||||
* Values are bitfields of which slots in the crafting inventory this request is for.
|
||||
*/
|
||||
var slots: Int,
|
||||
) : StackLocateRequest(stack, amount, timestamp) {
|
||||
var received: Int = 0
|
||||
}
|
||||
|
|
|
@ -10,9 +10,7 @@ import net.minecraft.network.PacketByteBuf
|
|||
import net.shadowfacts.phycon.PhysicalConnectivityClient
|
||||
import net.shadowfacts.phycon.block.terminal.AbstractTerminalBlockEntity
|
||||
import net.shadowfacts.phycon.block.terminal.AbstractTerminalScreenHandler
|
||||
import net.shadowfacts.phycon.util.TerminalSettings
|
||||
import net.shadowfacts.phycon.util.readItemStackWithoutCount
|
||||
import net.shadowfacts.phycon.util.writeItemStackWithoutCount
|
||||
import net.shadowfacts.phycon.util.*
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
|
@ -35,7 +33,7 @@ object S2CTerminalUpdateDisplayedItems : ClientReceiver {
|
|||
|
||||
buf.writeVarInt(entries.size)
|
||||
for (e in entries) {
|
||||
buf.writeItemStackWithoutCount(e.stack)
|
||||
buf.writeItemVariant(e.variant)
|
||||
buf.writeVarInt(e.amount)
|
||||
}
|
||||
|
||||
|
@ -58,7 +56,7 @@ object S2CTerminalUpdateDisplayedItems : ClientReceiver {
|
|||
val entryCount = buf.readVarInt()
|
||||
val entries = ArrayList<AbstractTerminalScreenHandler.Entry>(entryCount)
|
||||
for (i in 0 until entryCount) {
|
||||
entries.add(AbstractTerminalScreenHandler.Entry(buf.readItemStackWithoutCount(), buf.readVarInt()))
|
||||
entries.add(AbstractTerminalScreenHandler.Entry(buf.readItemVariant(), buf.readVarInt()))
|
||||
}
|
||||
val query = buf.readString()
|
||||
PhysicalConnectivityClient.terminalSettings.fromTag(buf.readNbt()!!)
|
||||
|
|
|
@ -1,10 +0,0 @@
|
|||
package net.shadowfacts.phycon.util
|
||||
|
||||
import net.minecraft.item.ItemStack
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
fun ItemStack.copyWithCount(count: Int): ItemStack {
|
||||
return copy().also { it.count = count }
|
||||
}
|
|
@ -6,6 +6,10 @@ import net.minecraft.item.ItemStack
|
|||
* @author shadowfacts
|
||||
*/
|
||||
|
||||
fun ItemStack.copyWithCount(count: Int): ItemStack {
|
||||
return copy().also { it.count = count }
|
||||
}
|
||||
|
||||
fun ItemStack.equalsIgnoringAmount(other: ItemStack): Boolean {
|
||||
if (this.isEmpty) return other.isEmpty
|
||||
if (other.isEmpty) return false
|
||||
|
|
|
@ -0,0 +1,18 @@
|
|||
package net.shadowfacts.phycon.util
|
||||
|
||||
import net.fabricmc.fabric.api.transfer.v1.item.ItemVariant
|
||||
import net.minecraft.item.ItemStack
|
||||
import net.minecraft.text.Text
|
||||
|
||||
/**
|
||||
* @author shadowfacts
|
||||
*/
|
||||
|
||||
val ItemVariant.name: Text
|
||||
get() {
|
||||
// don't use toStack because that copies the NBT
|
||||
// we assume that items don't mutate NBT in getName
|
||||
val stack = ItemStack(this.item, 1)
|
||||
stack.nbt = this.nbt
|
||||
return item.getName(stack)
|
||||
}
|
|
@ -1,5 +1,6 @@
|
|||
package net.shadowfacts.phycon.util
|
||||
|
||||
import net.fabricmc.fabric.api.transfer.v1.item.ItemVariant
|
||||
import net.minecraft.item.Item
|
||||
import net.minecraft.item.ItemStack
|
||||
import net.minecraft.nbt.NbtCompound
|
||||
|
@ -35,3 +36,11 @@ fun PacketByteBuf.readItemStackWithoutCount(): ItemStack {
|
|||
stack
|
||||
}
|
||||
}
|
||||
|
||||
fun PacketByteBuf.writeItemVariant(variant: ItemVariant) {
|
||||
variant.toPacket(this)
|
||||
}
|
||||
|
||||
fun PacketByteBuf.readItemVariant(): ItemVariant {
|
||||
return ItemVariant.fromPacket(this)
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue