Search in sources :

Example 31 with SlotTransaction

use of org.spongepowered.api.item.inventory.transaction.SlotTransaction in project SpongeCommon by SpongePowered.

the class DropItemWithHotkeyState method unwind.

@Override
public void unwind(InventoryPacketContext context) {
    final EntityPlayerMP player = context.getPacketPlayer();
    // final ItemStack usedStack = context.getItemUsed();
    // final ItemStackSnapshot usedSnapshot = ItemStackUtil.snapshotOf(usedStack);
    final Entity spongePlayer = EntityUtil.fromNative(player);
    try (CauseStackManager.StackFrame frame = Sponge.getCauseStackManager().pushCauseFrame()) {
        Sponge.getCauseStackManager().pushCause(spongePlayer);
        Sponge.getCauseStackManager().addContext(EventContextKeys.SPAWN_TYPE, InternalSpawnTypes.DROPPED_ITEM);
        context.getCapturedBlockSupplier().acceptAndClearIfNotEmpty(blocks -> TrackingUtil.processBlockCaptures(blocks, this, context));
        context.getCapturedItemsSupplier().acceptAndClearIfNotEmpty(items -> {
            final ArrayList<Entity> entities = new ArrayList<>();
            for (EntityItem item : items) {
                entities.add(EntityUtil.fromNative(item));
            }
            int usedButton = 0;
            if (context.getPacket() instanceof CPacketPlayerDigging) {
                final CPacketPlayerDigging packetIn = context.getPacket();
                usedButton = packetIn.getAction() == CPacketPlayerDigging.Action.DROP_ITEM ? PacketPhase.PACKET_BUTTON_PRIMARY_ID : 1;
            } else {
                final CPacketClickWindow packetIn = context.getPacket();
                usedButton = packetIn.getUsedButton();
            }
            Transaction<ItemStackSnapshot> cursorTrans = new Transaction<>(ItemStackSnapshot.NONE, ItemStackSnapshot.NONE);
            final IMixinContainer mixinContainer = ContainerUtil.toMixin(player.openContainer);
            List<SlotTransaction> slotTrans = mixinContainer.getCapturedTransactions();
            ClickInventoryEvent.Drop dropItemEvent = ((DropItemWithHotkeyState) this).createInventoryEvent(player, ContainerUtil.fromNative(player.openContainer), cursorTrans, Lists.newArrayList(slotTrans), entities, usedButton);
            SpongeImpl.postEvent(dropItemEvent);
            if (dropItemEvent.isCancelled() || PacketPhaseUtil.allTransactionsInvalid(dropItemEvent.getTransactions())) {
                ((IMixinEntityPlayerMP) player).restorePacketItem(EnumHand.MAIN_HAND);
                PacketPhaseUtil.handleSlotRestore(player, player.openContainer, dropItemEvent.getTransactions(), true);
            } else {
                processSpawnedEntities(player, dropItemEvent);
            }
            slotTrans.clear();
            mixinContainer.setCaptureInventory(false);
        });
        context.getCapturedEntityDropSupplier().acceptIfNotEmpty(itemMapping -> {
        });
        final IMixinContainer mixinContainer = ContainerUtil.toMixin(player.openContainer);
        mixinContainer.setCaptureInventory(false);
        mixinContainer.getCapturedTransactions().clear();
    }
}
Also used : CPacketPlayerDigging(net.minecraft.network.play.client.CPacketPlayerDigging) Entity(org.spongepowered.api.entity.Entity) CPacketClickWindow(net.minecraft.network.play.client.CPacketClickWindow) StackFrame(org.spongepowered.api.event.CauseStackManager.StackFrame) ArrayList(java.util.ArrayList) ClickInventoryEvent(org.spongepowered.api.event.item.inventory.ClickInventoryEvent) IMixinEntityPlayerMP(org.spongepowered.common.interfaces.entity.player.IMixinEntityPlayerMP) SlotTransaction(org.spongepowered.api.item.inventory.transaction.SlotTransaction) IMixinContainer(org.spongepowered.common.interfaces.IMixinContainer) SlotTransaction(org.spongepowered.api.item.inventory.transaction.SlotTransaction) Transaction(org.spongepowered.api.data.Transaction) CauseStackManager(org.spongepowered.api.event.CauseStackManager) ItemStackSnapshot(org.spongepowered.api.item.inventory.ItemStackSnapshot) EntityPlayerMP(net.minecraft.entity.player.EntityPlayerMP) IMixinEntityPlayerMP(org.spongepowered.common.interfaces.entity.player.IMixinEntityPlayerMP) EntityItem(net.minecraft.entity.item.EntityItem)

Example 32 with SlotTransaction

use of org.spongepowered.api.item.inventory.transaction.SlotTransaction in project SpongeCommon by SpongePowered.

the class PacketPhaseUtil method validateCapturedTransactions.

public static void validateCapturedTransactions(int slotId, Container openContainer, List<SlotTransaction> capturedTransactions) {
    if (capturedTransactions.size() == 0 && slotId >= 0 && slotId < openContainer.inventorySlots.size()) {
        final Slot slot = openContainer.getSlot(slotId);
        if (slot != null) {
            ItemStackSnapshot snapshot = slot.getHasStack() ? ((org.spongepowered.api.item.inventory.ItemStack) slot.getStack()).createSnapshot() : ItemStackSnapshot.NONE;
            final SlotTransaction slotTransaction = new SlotTransaction(ContainerUtil.getSlot(openContainer, slotId), snapshot, snapshot);
            capturedTransactions.add(slotTransaction);
        }
    }
}
Also used : Slot(net.minecraft.inventory.Slot) SPacketSetSlot(net.minecraft.network.play.server.SPacketSetSlot) ItemStackSnapshot(org.spongepowered.api.item.inventory.ItemStackSnapshot) SlotTransaction(org.spongepowered.api.item.inventory.transaction.SlotTransaction)

Example 33 with SlotTransaction

use of org.spongepowered.api.item.inventory.transaction.SlotTransaction in project SpongeCommon by SpongePowered.

the class PacketPhaseUtil method handleSlotRestore.

public static void handleSlotRestore(EntityPlayer player, @Nullable Container openContainer, List<SlotTransaction> slotTransactions, boolean eventCancelled) {
    for (SlotTransaction slotTransaction : slotTransactions) {
        if ((!slotTransaction.getCustom().isPresent() && slotTransaction.isValid()) && !eventCancelled) {
            continue;
        }
        final SlotAdapter slot = (SlotAdapter) slotTransaction.getSlot();
        ItemStackSnapshot snapshot = eventCancelled || !slotTransaction.isValid() ? slotTransaction.getOriginal() : slotTransaction.getCustom().get();
        final ItemStack originalStack = ItemStackUtil.fromSnapshotToNative(snapshot);
        if (openContainer == null) {
            slot.set(((org.spongepowered.api.item.inventory.ItemStack) originalStack));
        } else {
            final int slotNumber = slot.slotNumber;
            final Slot nmsSlot = openContainer.getSlot(slotNumber);
            if (nmsSlot != null) {
                nmsSlot.putStack(originalStack);
            }
        }
    }
    if (openContainer != null) {
        openContainer.detectAndSendChanges();
        // we must also validate the player still has the same container open after the event has been processed
        if (eventCancelled && player.openContainer == openContainer && player instanceof EntityPlayerMP) {
            ((EntityPlayerMP) player).sendContainerToPlayer(openContainer);
        }
    }
}
Also used : ItemStackSnapshot(org.spongepowered.api.item.inventory.ItemStackSnapshot) Slot(net.minecraft.inventory.Slot) SPacketSetSlot(net.minecraft.network.play.server.SPacketSetSlot) SlotAdapter(org.spongepowered.common.item.inventory.adapter.impl.slots.SlotAdapter) EntityPlayerMP(net.minecraft.entity.player.EntityPlayerMP) ItemStack(net.minecraft.item.ItemStack) SlotTransaction(org.spongepowered.api.item.inventory.transaction.SlotTransaction)

Example 34 with SlotTransaction

use of org.spongepowered.api.item.inventory.transaction.SlotTransaction in project SpongeCommon by SpongePowered.

the class SpongeCommonEventFactory method callInventoryPickupEvent.

public static boolean callInventoryPickupEvent(IInventory inventory, ItemStack[] prevInventory) {
    Inventory spongeInventory = InventoryUtil.toInventory(inventory, null);
    List<SlotTransaction> trans = generateTransactions(spongeInventory, inventory, prevInventory);
    if (trans.isEmpty()) {
        return true;
    }
    ChangeInventoryEvent.Pickup event = SpongeEventFactory.createChangeInventoryEventPickup(Sponge.getCauseStackManager().getCurrentCause(), spongeInventory, trans);
    SpongeImpl.postEvent(event);
    applyTransactions(event);
    return !event.isCancelled();
}
Also used : ChangeInventoryEvent(org.spongepowered.api.event.item.inventory.ChangeInventoryEvent) SlotTransaction(org.spongepowered.api.item.inventory.transaction.SlotTransaction) IMixinInventory(org.spongepowered.common.interfaces.IMixinInventory) OrderedInventory(org.spongepowered.api.item.inventory.type.OrderedInventory) CraftingInventory(org.spongepowered.api.item.inventory.crafting.CraftingInventory) CarriedInventory(org.spongepowered.api.item.inventory.type.CarriedInventory) Inventory(org.spongepowered.api.item.inventory.Inventory) CustomInventory(org.spongepowered.common.item.inventory.custom.CustomInventory) IInventory(net.minecraft.inventory.IInventory)

Example 35 with SlotTransaction

use of org.spongepowered.api.item.inventory.transaction.SlotTransaction in project SpongeCommon by SpongePowered.

the class SpongeCommonEventFactory method callCraftEventPost.

public static CraftItemEvent.Craft callCraftEventPost(EntityPlayer player, CraftingInventory inventory, ItemStackSnapshot result, @Nullable CraftingRecipe recipe, Container container, List<SlotTransaction> transactions) {
    // Get previous cursor if captured
    ItemStack previousCursor = ((IMixinContainer) container).getPreviousCursor();
    if (previousCursor == null) {
        // or get the current one
        previousCursor = player.inventory.getItemStack();
    }
    Transaction<ItemStackSnapshot> cursorTransaction = new Transaction<>(ItemStackUtil.snapshotOf(previousCursor), ItemStackUtil.snapshotOf(player.inventory.getItemStack()));
    CraftItemEvent.Craft event = SpongeEventFactory.createCraftItemEventCraft(Sponge.getCauseStackManager().getCurrentCause(), result, inventory, cursorTransaction, Optional.ofNullable(recipe), ((org.spongepowered.api.item.inventory.Container) container), transactions);
    SpongeImpl.postEvent(event);
    ((IMixinContainer) container).setCaptureInventory(false);
    // handle slot-transactions
    PacketPhaseUtil.handleSlotRestore(player, container, new ArrayList<>(transactions), event.isCancelled());
    if (event.isCancelled() || !event.getCursorTransaction().isValid() || event.getCursorTransaction().getCustom().isPresent()) {
        // handle cursor-transaction
        ItemStackSnapshot newCursor = event.isCancelled() || event.getCursorTransaction().isValid() ? event.getCursorTransaction().getOriginal() : event.getCursorTransaction().getFinal();
        player.inventory.setItemStack(ItemStackUtil.fromSnapshotToNative(newCursor));
        if (player instanceof EntityPlayerMP) {
            ((EntityPlayerMP) player).connection.sendPacket(new SPacketSetSlot(-1, -1, player.inventory.getItemStack()));
        }
    }
    transactions.clear();
    ((IMixinContainer) container).setCaptureInventory(true);
    return event;
}
Also used : IMixinContainer(org.spongepowered.common.interfaces.IMixinContainer) Container(net.minecraft.inventory.Container) IMixinContainer(org.spongepowered.common.interfaces.IMixinContainer) SlotTransaction(org.spongepowered.api.item.inventory.transaction.SlotTransaction) Transaction(org.spongepowered.api.data.Transaction) CraftItemEvent(org.spongepowered.api.event.item.inventory.CraftItemEvent) ItemStackSnapshot(org.spongepowered.api.item.inventory.ItemStackSnapshot) EntityPlayerMP(net.minecraft.entity.player.EntityPlayerMP) IMixinEntityPlayerMP(org.spongepowered.common.interfaces.entity.player.IMixinEntityPlayerMP) SPacketSetSlot(net.minecraft.network.play.server.SPacketSetSlot) ItemStack(net.minecraft.item.ItemStack)

Aggregations

SlotTransaction (org.spongepowered.api.item.inventory.transaction.SlotTransaction)50 ItemStackSnapshot (org.spongepowered.api.item.inventory.ItemStackSnapshot)30 ArrayList (java.util.ArrayList)20 ItemStack (org.spongepowered.api.item.inventory.ItemStack)16 Inventory (org.spongepowered.api.item.inventory.Inventory)14 CraftingInventory (org.spongepowered.api.item.inventory.crafting.CraftingInventory)14 Entity (org.spongepowered.api.entity.Entity)13 Transaction (org.spongepowered.api.data.Transaction)11 ChangeInventoryEvent (org.spongepowered.api.event.item.inventory.ChangeInventoryEvent)11 ClickInventoryEvent (org.spongepowered.api.event.item.inventory.ClickInventoryEvent)11 Slot (org.spongepowered.api.item.inventory.Slot)11 Slot (net.minecraft.inventory.Slot)9 SPacketSetSlot (net.minecraft.network.play.server.SPacketSetSlot)9 AbstractSlot (org.lanternpowered.server.inventory.AbstractSlot)9 SpawnEntityEvent (org.spongepowered.api.event.entity.SpawnEntityEvent)9 IMixinContainer (org.spongepowered.common.interfaces.IMixinContainer)9 Nullable (javax.annotation.Nullable)8 ItemStack (net.minecraft.item.ItemStack)8 CauseStack (org.lanternpowered.server.event.CauseStack)8 List (java.util.List)7