From 4218db100d79aa4a899566977c58a70cc85fa58d Mon Sep 17 00:00:00 2001 From: raoulvdberge Date: Tue, 9 May 2017 01:52:29 +0200 Subject: [PATCH] Fixed #1205 - "Portable Grid" --- .../raoulvdberge/refinedstorage/RSConfig.java | 15 + .../raoulvdberge/refinedstorage/RSUtils.java | 2 +- .../network/grid/ItemGridHandlerPortable.java | 156 +++++++++ .../item/NetworkItemWirelessFluidGrid.java | 5 +- .../network/item/NetworkItemWirelessGrid.java | 5 +- .../storage/StorageCacheItemPortable.java | 90 +++++ .../storage/StorageDiskItemPortable.java | 107 ++++++ .../container/ContainerGrid.java | 28 +- .../refinedstorage/gui/GuiHandler.java | 41 ++- .../refinedstorage/gui/grid/GuiGrid.java | 16 +- .../gui/grid/stack/GridStackItem.java | 9 +- .../refinedstorage/item/ItemNetworkItem.java | 6 - .../refinedstorage/item/ItemPortableGrid.java | 36 ++ .../item/ItemWirelessCraftingMonitor.java | 9 +- .../item/ItemWirelessFluidGrid.java | 28 +- .../refinedstorage/item/ItemWirelessGrid.java | 30 +- .../network/MessageGridItemDelta.java | 16 +- .../network/MessageGridItemUpdate.java | 51 +-- ...te.java => MessageGridSettingsUpdate.java} | 18 +- .../refinedstorage/proxy/ProxyCommon.java | 13 +- .../tile/grid/PortableGrid.java | 316 ++++++++++++++++++ .../tile/grid/WirelessFluidGrid.java | 2 + .../tile/grid/WirelessGrid.java | 16 +- .../assets/refinedstorage/lang/en_us.lang | 5 +- .../textures/gui/portable_grid.png | Bin 0 -> 2224 bytes 25 files changed, 876 insertions(+), 144 deletions(-) create mode 100644 src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/grid/ItemGridHandlerPortable.java create mode 100644 src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageCacheItemPortable.java create mode 100644 src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageDiskItemPortable.java rename src/main/java/com/raoulvdberge/refinedstorage/network/{MessageWirelessGridSettingsUpdate.java => MessageGridSettingsUpdate.java} (76%) mode change 100755 => 100644 create mode 100644 src/main/java/com/raoulvdberge/refinedstorage/tile/grid/PortableGrid.java create mode 100644 src/main/resources/assets/refinedstorage/textures/gui/portable_grid.png diff --git a/src/main/java/com/raoulvdberge/refinedstorage/RSConfig.java b/src/main/java/com/raoulvdberge/refinedstorage/RSConfig.java index 9f72c17b8..ea311c314 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/RSConfig.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/RSConfig.java @@ -72,6 +72,13 @@ public final class RSConfig { public int wirelessGridInsertUsage; //endregion + //region Portable Grid + public boolean portableGridUsesEnergy; + public int portableGridOpenUsage; + public int portableGridExtractUsage; + public int portableGridInsertUsage; + //endregion + //region Wireless Fluid Grid public boolean wirelessFluidGridUsesEnergy; public int wirelessFluidGridOpenUsage; @@ -102,6 +109,7 @@ public final class RSConfig { private static final String GRID = "grid"; private static final String WIRELESS_TRANSMITTER = "wirelessTransmitter"; private static final String WIRELESS_GRID = "wirelessGrid"; + private static final String PORTABLE_GRID = "portableGrid"; private static final String WIRELESS_FLUID_GRID = "wirelessFluidGrid"; private static final String WIRELESS_CRAFTING_MONITOR = "wirelessCraftingMonitor"; private static final String UPGRADES = "upgrades"; @@ -185,6 +193,13 @@ public final class RSConfig { wirelessGridExtractUsage = config.getInt("extract", WIRELESS_GRID, 3, 0, Integer.MAX_VALUE, "The energy used by the Wireless Grid to extract items"); //endregion + //region Portable Grid + portableGridUsesEnergy = config.getBoolean("usesEnergy", PORTABLE_GRID, true, "Whether the Portable Grid uses energy"); + portableGridOpenUsage = config.getInt("open", PORTABLE_GRID, 30, 0, Integer.MAX_VALUE, "The energy used by the Portable Grid to open"); + portableGridInsertUsage = config.getInt("insert", PORTABLE_GRID, 3, 0, Integer.MAX_VALUE, "The energy used by the Portable Grid to insert items"); + portableGridExtractUsage = config.getInt("extract", PORTABLE_GRID, 3, 0, Integer.MAX_VALUE, "The energy used by the Portable Grid to extract items"); + //endregion + //region Wireless Grid wirelessFluidGridUsesEnergy = config.getBoolean("usesEnergy", WIRELESS_FLUID_GRID, true, "Whether the Fluid Wireless Grid uses energy"); wirelessFluidGridOpenUsage = config.getInt("open", WIRELESS_FLUID_GRID, 30, 0, Integer.MAX_VALUE, "The energy used by the Fluid Wireless Grid to open"); diff --git a/src/main/java/com/raoulvdberge/refinedstorage/RSUtils.java b/src/main/java/com/raoulvdberge/refinedstorage/RSUtils.java index aceba2a51..9bf951ee7 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/RSUtils.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/RSUtils.java @@ -129,7 +129,7 @@ public final class RSUtils { writeItemStack(buf, stack, null, false); } - public static void writeItemStack(ByteBuf buf, ItemStack stack, INetworkMaster network, boolean displayCraftText) { + public static void writeItemStack(ByteBuf buf, ItemStack stack, @Nullable INetworkMaster network, boolean displayCraftText) { buf.writeInt(Item.getIdFromItem(stack.getItem())); buf.writeInt(stack.getCount()); buf.writeInt(stack.getItemDamage()); diff --git a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/grid/ItemGridHandlerPortable.java b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/grid/ItemGridHandlerPortable.java new file mode 100644 index 000000000..8fac86d00 --- /dev/null +++ b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/grid/ItemGridHandlerPortable.java @@ -0,0 +1,156 @@ +package com.raoulvdberge.refinedstorage.apiimpl.network.grid; + +import com.raoulvdberge.refinedstorage.RS; +import com.raoulvdberge.refinedstorage.RSUtils; +import com.raoulvdberge.refinedstorage.api.network.grid.IItemGridHandler; +import com.raoulvdberge.refinedstorage.api.util.IComparer; +import com.raoulvdberge.refinedstorage.apiimpl.API; +import com.raoulvdberge.refinedstorage.tile.grid.PortableGrid; +import net.minecraft.entity.player.EntityPlayerMP; +import net.minecraft.item.ItemStack; +import net.minecraft.util.EnumFacing; +import net.minecraftforge.items.CapabilityItemHandler; +import net.minecraftforge.items.IItemHandler; +import net.minecraftforge.items.ItemHandlerHelper; + +import javax.annotation.Nullable; + +public class ItemGridHandlerPortable implements IItemGridHandler { + private PortableGrid portableGrid; + + public ItemGridHandlerPortable(PortableGrid portableGrid) { + this.portableGrid = portableGrid; + } + + @Override + public void onExtract(EntityPlayerMP player, int hash, int flags) { + if (portableGrid.getStorage() == null || !portableGrid.isActive()) { + return; + } + + ItemStack item = portableGrid.getCache().getList().get(hash); + + if (item == null) { + return; + } + + int itemSize = item.getCount(); + int maxItemSize = item.getItem().getItemStackLimit(item); + + boolean single = (flags & EXTRACT_SINGLE) == EXTRACT_SINGLE; + + ItemStack held = player.inventory.getItemStack(); + + if (single) { + if (!held.isEmpty() && (!API.instance().getComparer().isEqualNoQuantity(item, held) || held.getCount() + 1 > held.getMaxStackSize())) { + return; + } + } else if (!player.inventory.getItemStack().isEmpty()) { + return; + } + + int size = 64; + + if ((flags & EXTRACT_HALF) == EXTRACT_HALF && itemSize > 1) { + size = itemSize / 2; + + if (size > maxItemSize / 2) { + size = maxItemSize / 2; + } + } else if (single) { + size = 1; + } else if ((flags & EXTRACT_SHIFT) == EXTRACT_SHIFT) { + // NO OP, the quantity already set (64) is needed for shift + } + + size = Math.min(size, maxItemSize); + + ItemStack took = portableGrid.getStorage().extract(item, size, IComparer.COMPARE_DAMAGE | IComparer.COMPARE_NBT, true); + + if (took != null) { + if ((flags & EXTRACT_SHIFT) == EXTRACT_SHIFT) { + IItemHandler playerInventory = player.getCapability(CapabilityItemHandler.ITEM_HANDLER_CAPABILITY, EnumFacing.UP); + + if (ItemHandlerHelper.insertItem(playerInventory, took, true).isEmpty()) { + took = portableGrid.getStorage().extract(item, size, IComparer.COMPARE_DAMAGE | IComparer.COMPARE_NBT, false); + + ItemHandlerHelper.insertItem(playerInventory, took, false); + } + } else { + took = portableGrid.getStorage().extract(item, size, IComparer.COMPARE_DAMAGE | IComparer.COMPARE_NBT, false); + + if (single && !held.isEmpty()) { + held.grow(1); + } else { + player.inventory.setItemStack(took); + } + + player.updateHeldItem(); + } + + portableGrid.drainEnergy(RS.INSTANCE.config.portableGridExtractUsage); + } + } + + @Nullable + @Override + public ItemStack onInsert(EntityPlayerMP player, ItemStack stack) { + if (portableGrid.getStorage() == null || !portableGrid.isActive()) { + return stack; + } + + ItemStack remainder = portableGrid.getStorage().insert(stack, stack.getCount(), false); + + portableGrid.drainEnergy(RS.INSTANCE.config.portableGridInsertUsage); + + return remainder; + } + + @Override + public void onInsertHeldItem(EntityPlayerMP player, boolean single) { + if (player.inventory.getItemStack().isEmpty() || portableGrid.getStorage() == null || !portableGrid.isActive()) { + return; + } + + ItemStack stack = player.inventory.getItemStack(); + int size = single ? 1 : stack.getCount(); + + if (single) { + if (portableGrid.getStorage().insert(stack, size, true) == null) { + portableGrid.getStorage().insert(stack, size, false); + + stack.shrink(size); + + if (stack.getCount() == 0) { + player.inventory.setItemStack(ItemStack.EMPTY); + } + } + } else { + player.inventory.setItemStack(RSUtils.transformNullToEmpty(portableGrid.getStorage().insert(stack, size, false))); + } + + player.updateHeldItem(); + + portableGrid.drainEnergy(RS.INSTANCE.config.portableGridInsertUsage); + } + + @Override + public ItemStack onShiftClick(EntityPlayerMP player, ItemStack stack) { + return RSUtils.transformNullToEmpty(onInsert(player, stack)); + } + + @Override + public void onCraftingPreviewRequested(EntityPlayerMP player, int hash, int quantity, boolean noPreview) { + // NO OP + } + + @Override + public void onCraftingRequested(EntityPlayerMP player, ItemStack stack, int quantity) { + // NO OP + } + + @Override + public void onCraftingCancelRequested(EntityPlayerMP player, int id) { + // NO OP + } +} diff --git a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessFluidGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessFluidGrid.java index f78f7ea1d..9b499788e 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessFluidGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessFluidGrid.java @@ -8,6 +8,7 @@ import com.raoulvdberge.refinedstorage.api.network.item.INetworkItem; import com.raoulvdberge.refinedstorage.api.network.item.INetworkItemHandler; import com.raoulvdberge.refinedstorage.api.network.security.Permission; import com.raoulvdberge.refinedstorage.item.ItemWirelessFluidGrid; +import com.raoulvdberge.refinedstorage.tile.grid.WirelessFluidGrid; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.item.ItemStack; @@ -17,8 +18,6 @@ import net.minecraftforge.energy.CapabilityEnergy; import net.minecraftforge.energy.IEnergyStorage; public class NetworkItemWirelessFluidGrid implements INetworkItem { - public static final int GRID_TYPE = 1; - private INetworkItemHandler handler; private EntityPlayer player; private ItemStack stack; @@ -46,7 +45,7 @@ public class NetworkItemWirelessFluidGrid implements INetworkItem { return false; } - player.openGui(RS.INSTANCE, RSGui.WIRELESS_GRID, player.getEntityWorld(), hand.ordinal(), controllerWorld.provider.getDimension(), GRID_TYPE); + player.openGui(RS.INSTANCE, RSGui.WIRELESS_GRID, player.getEntityWorld(), hand.ordinal(), controllerWorld.provider.getDimension(), WirelessFluidGrid.GRID_TYPE); network.sendFluidStorageToClient((EntityPlayerMP) player); diff --git a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessGrid.java index 9792f408e..b5d0a71c4 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/network/item/NetworkItemWirelessGrid.java @@ -8,6 +8,7 @@ import com.raoulvdberge.refinedstorage.api.network.item.INetworkItem; import com.raoulvdberge.refinedstorage.api.network.item.INetworkItemHandler; import com.raoulvdberge.refinedstorage.api.network.security.Permission; import com.raoulvdberge.refinedstorage.item.ItemWirelessGrid; +import com.raoulvdberge.refinedstorage.tile.grid.WirelessGrid; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.item.ItemStack; @@ -17,8 +18,6 @@ import net.minecraftforge.energy.CapabilityEnergy; import net.minecraftforge.energy.IEnergyStorage; public class NetworkItemWirelessGrid implements INetworkItem { - public static final int GRID_TYPE = 0; - private INetworkItemHandler handler; private EntityPlayer player; private ItemStack stack; @@ -46,7 +45,7 @@ public class NetworkItemWirelessGrid implements INetworkItem { return false; } - player.openGui(RS.INSTANCE, RSGui.WIRELESS_GRID, player.getEntityWorld(), hand.ordinal(), controllerWorld.provider.getDimension(), GRID_TYPE); + player.openGui(RS.INSTANCE, RSGui.WIRELESS_GRID, player.getEntityWorld(), hand.ordinal(), controllerWorld.provider.getDimension(), WirelessGrid.GRID_TYPE); network.sendItemStorageToClient((EntityPlayerMP) player); diff --git a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageCacheItemPortable.java b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageCacheItemPortable.java new file mode 100644 index 000000000..17389fd5f --- /dev/null +++ b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageCacheItemPortable.java @@ -0,0 +1,90 @@ +package com.raoulvdberge.refinedstorage.apiimpl.storage; + +import com.raoulvdberge.refinedstorage.RS; +import com.raoulvdberge.refinedstorage.RSUtils; +import com.raoulvdberge.refinedstorage.api.storage.IStorage; +import com.raoulvdberge.refinedstorage.api.storage.IStorageCache; +import com.raoulvdberge.refinedstorage.api.util.IStackList; +import com.raoulvdberge.refinedstorage.apiimpl.API; +import com.raoulvdberge.refinedstorage.network.MessageGridItemDelta; +import com.raoulvdberge.refinedstorage.network.MessageGridItemUpdate; +import com.raoulvdberge.refinedstorage.tile.grid.PortableGrid; +import io.netty.buffer.ByteBuf; +import net.minecraft.entity.player.EntityPlayerMP; +import net.minecraft.item.ItemStack; + +import javax.annotation.Nonnull; +import java.util.Collections; +import java.util.List; +import java.util.function.Consumer; + +public class StorageCacheItemPortable implements IStorageCache { + private PortableGrid portableGrid; + private IStackList list = API.instance().createItemStackList(); + + public StorageCacheItemPortable(PortableGrid portableGrid) { + this.portableGrid = portableGrid; + } + + @Override + public void invalidate() { + list.clear(); + + if (portableGrid.getStorage() != null) { + portableGrid.getStorage().getStacks().forEach(list::add); + } + + RS.INSTANCE.network.sendTo(new MessageGridItemUpdate((buf) -> { + buf.writeInt(list.getStacks().size()); + + for (ItemStack stack : list.getStacks()) { + RSUtils.writeItemStack(buf, stack, null, false); + + buf.writeInt(API.instance().getItemStackHashCode(stack)); + buf.writeBoolean(false); + buf.writeBoolean(false); + } + }, false), (EntityPlayerMP) portableGrid.getPlayer()); + } + + @Override + public void add(@Nonnull ItemStack stack, int size, boolean rebuilding) { + list.add(stack, size); + + if (!rebuilding) { + RS.INSTANCE.network.sendTo(new MessageGridItemDelta(getSendHandler(stack), size), (EntityPlayerMP) portableGrid.getPlayer()); + } + } + + @Override + public void remove(@Nonnull ItemStack stack, int size) { + if (list.remove(stack, size)) { + RS.INSTANCE.network.sendTo(new MessageGridItemDelta(getSendHandler(stack), -size), (EntityPlayerMP) portableGrid.getPlayer()); + } + } + + private Consumer getSendHandler(@Nonnull ItemStack stack) { + return buf -> { + RSUtils.writeItemStack(buf, stack, null, false); + + buf.writeInt(API.instance().getItemStackHashCode(stack)); + buf.writeBoolean(false); + buf.writeBoolean(false); + }; + } + + @Override + public void sort() { + // NO OP + } + + @Override + public IStackList getList() { + return list; + } + + @Override + public List> getStorages() { + return Collections.emptyList(); + } +} diff --git a/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageDiskItemPortable.java b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageDiskItemPortable.java new file mode 100644 index 000000000..42ca4cf3c --- /dev/null +++ b/src/main/java/com/raoulvdberge/refinedstorage/apiimpl/storage/StorageDiskItemPortable.java @@ -0,0 +1,107 @@ +package com.raoulvdberge.refinedstorage.apiimpl.storage; + +import com.raoulvdberge.refinedstorage.api.storage.AccessType; +import com.raoulvdberge.refinedstorage.api.storage.IStorageDisk; +import com.raoulvdberge.refinedstorage.api.storage.StorageDiskType; +import com.raoulvdberge.refinedstorage.tile.grid.PortableGrid; +import net.minecraft.item.ItemStack; + +import javax.annotation.Nonnull; +import javax.annotation.Nullable; +import java.util.Collection; +import java.util.function.Supplier; + +public class StorageDiskItemPortable implements IStorageDisk { + private IStorageDisk parent; + private PortableGrid portableGrid; + + public StorageDiskItemPortable(IStorageDisk parent, PortableGrid portableGrid) { + this.parent = parent; + this.portableGrid = portableGrid; + } + + @Override + public int getCapacity() { + return parent.getCapacity(); + } + + @Override + public boolean isValid(ItemStack stack) { + return parent.isValid(stack); + } + + @Override + public void onPassContainerContext(Runnable listener, Supplier voidExcess, Supplier accessType) { + parent.onPassContainerContext(listener, voidExcess, accessType); + } + + @Override + public void readFromNBT() { + parent.readFromNBT(); + } + + @Override + public void writeToNBT() { + parent.writeToNBT(); + } + + @Override + public StorageDiskType getType() { + return parent.getType(); + } + + @Override + public Collection getStacks() { + return parent.getStacks(); + } + + @Nullable + @Override + public ItemStack insert(@Nonnull ItemStack stack, int size, boolean simulate) { + int storedPre = parent.getStored(); + + ItemStack remainder = parent.insert(stack, size, simulate); + + if (!simulate) { + int inserted = parent.getCacheDelta(storedPre, size, remainder); + + if (inserted > 0) { + portableGrid.getCache().add(stack, inserted, false); + } + } + + return remainder; + } + + @Nullable + @Override + public ItemStack extract(@Nonnull ItemStack stack, int size, int flags, boolean simulate) { + ItemStack extracted = parent.extract(stack, size, flags, simulate); + + if (!simulate && extracted != null) { + portableGrid.getCache().remove(extracted, extracted.getCount()); + } + + return extracted; + } + + @Override + public int getStored() { + return parent.getStored(); + } + + @Override + public int getPriority() { + return parent.getPriority(); + } + + @Override + public AccessType getAccessType() { + return parent.getAccessType(); + } + + @Override + public int getCacheDelta(int storedPreInsertion, int size, @Nullable ItemStack remainder) { + return parent.getCacheDelta(storedPreInsertion, size, remainder); + } +} diff --git a/src/main/java/com/raoulvdberge/refinedstorage/container/ContainerGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/container/ContainerGrid.java index f87981eea..9ff2de192 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/container/ContainerGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/container/ContainerGrid.java @@ -3,11 +3,13 @@ package com.raoulvdberge.refinedstorage.container; import com.raoulvdberge.refinedstorage.RSItems; import com.raoulvdberge.refinedstorage.api.network.grid.IFluidGridHandler; import com.raoulvdberge.refinedstorage.api.network.grid.IItemGridHandler; +import com.raoulvdberge.refinedstorage.api.storage.IStorageDiskProvider; import com.raoulvdberge.refinedstorage.apiimpl.network.node.NetworkNodeGrid; import com.raoulvdberge.refinedstorage.block.GridType; import com.raoulvdberge.refinedstorage.container.slot.*; import com.raoulvdberge.refinedstorage.gui.grid.IGridDisplay; import com.raoulvdberge.refinedstorage.tile.grid.IGrid; +import com.raoulvdberge.refinedstorage.tile.grid.PortableGrid; import com.raoulvdberge.refinedstorage.tile.grid.TileGrid; import com.raoulvdberge.refinedstorage.tile.grid.WirelessGrid; import net.minecraft.entity.player.EntityPlayer; @@ -45,8 +47,14 @@ public class ContainerGrid extends ContainerBase { int headerAndSlots = getTabDelta() + display.getHeader() + (display.getVisibleRows() * 18); if (grid.getType() != GridType.FLUID) { + int yStart = 6; + + if (grid instanceof PortableGrid) { + yStart = 38; + } + for (int i = 0; i < 4; ++i) { - addSlotToContainer(new SlotItemHandler(grid.getFilter(), i, 204, 6 + (18 * i) + getTabDelta())); + addSlotToContainer(new SlotItemHandler(grid.getFilter(), i, 204, yStart + (18 * i) + getTabDelta())); } } @@ -55,6 +63,10 @@ public class ContainerGrid extends ContainerBase { addSlotToContainer(new SlotOutput(((NetworkNodeGrid) grid).getPatterns(), 1, 152, headerAndSlots + 40)); } + if (grid instanceof PortableGrid) { + addSlotToContainer(new SlotItemHandler(((PortableGrid) grid).getDisk(), 0, 204, 6 + getTabDelta())); + } + addPlayerInventory(8, display.getYPlayerInventory()); if (grid.getType() == GridType.CRAFTING) { @@ -162,7 +174,7 @@ public class ContainerGrid extends ContainerBase { return ItemStack.EMPTY; } - } else if (grid.getType() == GridType.PATTERN && stack.getItem() == RSItems.PATTERN) { + } else if ((grid.getType() == GridType.PATTERN && stack.getItem() == RSItems.PATTERN) || (grid instanceof PortableGrid && stack.getItem() instanceof IStorageDiskProvider)) { int startIndex = 4; int endIndex = startIndex + 1; @@ -177,6 +189,16 @@ public class ContainerGrid extends ContainerBase { detectAndSendChanges(); + // For some reason it doesn't detect when moving the disk from disk inventory to player inventory... + if (grid instanceof PortableGrid && slotIndex == 4) { + ((PortableGrid) grid).getDisk().setStackInSlot(0, ItemStack.EMPTY); + } + + return ItemStack.EMPTY; + } + + // When we shift click a storage disk in a portable grid and our inventory is full, the disk can't go in the storage! + if (grid instanceof PortableGrid) { return ItemStack.EMPTY; } } @@ -205,6 +227,6 @@ public class ContainerGrid extends ContainerBase { @Override protected boolean isHeldItemDisabled() { - return grid instanceof WirelessGrid; + return grid instanceof WirelessGrid || grid instanceof PortableGrid; } } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/gui/GuiHandler.java b/src/main/java/com/raoulvdberge/refinedstorage/gui/GuiHandler.java index 3ce1e34a6..54c084d7e 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/gui/GuiHandler.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/gui/GuiHandler.java @@ -1,8 +1,6 @@ package com.raoulvdberge.refinedstorage.gui; import com.raoulvdberge.refinedstorage.RSGui; -import com.raoulvdberge.refinedstorage.apiimpl.network.item.NetworkItemWirelessFluidGrid; -import com.raoulvdberge.refinedstorage.apiimpl.network.item.NetworkItemWirelessGrid; import com.raoulvdberge.refinedstorage.apiimpl.network.node.IGuiReaderWriter; import com.raoulvdberge.refinedstorage.container.*; import com.raoulvdberge.refinedstorage.gui.grid.GridDisplayDummy; @@ -12,10 +10,7 @@ import com.raoulvdberge.refinedstorage.integration.mcmp.RSMCMPAddon; import com.raoulvdberge.refinedstorage.tile.*; import com.raoulvdberge.refinedstorage.tile.craftingmonitor.TileCraftingMonitor; import com.raoulvdberge.refinedstorage.tile.craftingmonitor.WirelessCraftingMonitor; -import com.raoulvdberge.refinedstorage.tile.grid.IGrid; -import com.raoulvdberge.refinedstorage.tile.grid.TileGrid; -import com.raoulvdberge.refinedstorage.tile.grid.WirelessFluidGrid; -import com.raoulvdberge.refinedstorage.tile.grid.WirelessGrid; +import com.raoulvdberge.refinedstorage.tile.grid.*; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.inventory.Container; import net.minecraft.item.ItemStack; @@ -84,11 +79,11 @@ public class GuiHandler implements IGuiHandler { @Override public Object getServerGuiElement(int ID, EntityPlayer player, World world, int x, int y, int z) { if (ID == RSGui.WIRELESS_GRID) { - return getWirelessGridContainer(player, x, y, z); + return getGridContainer(player, x, y, z); } else if (ID == RSGui.FILTER) { return getFilterContainer(player, x); } else if (ID == RSGui.WIRELESS_CRAFTING_MONITOR) { - return getWirelessCraftingMonitorContainer(player, x, y); + return getCraftingMonitorContainer(player, x, y); } return getContainer(ID, player, IntegrationMCMP.isLoaded() ? RSMCMPAddon.unwrapTile(world, new BlockPos(x, y, z)) : world.getTileEntity(new BlockPos(x, y, z))); @@ -107,7 +102,7 @@ public class GuiHandler implements IGuiHandler { gui.inventorySlots = new ContainerGrid(grid, gui, null, player); return gui; case RSGui.WIRELESS_GRID: - return getWirelessGridGui(player, x, y, z); + return getGridGui(player, x, y, z); case RSGui.DISK_DRIVE: return new GuiStorage((ContainerDiskDrive) getContainer(ID, player, tile), ((TileDiskDrive) tile).getNode(), "gui/disk_drive.png"); case RSGui.IMPORTER: @@ -149,7 +144,7 @@ public class GuiHandler implements IGuiHandler { case RSGui.DISK_MANIPULATOR: return new GuiDiskManipulator((ContainerDiskManipulator) getContainer(ID, player, tile)); case RSGui.WIRELESS_CRAFTING_MONITOR: - return getWirelessCraftingMonitorGui(player, x, y); + return getCraftingMonitorGui(player, x, y); case RSGui.READER_WRITER: return new GuiReaderWriter((ContainerReaderWriter) getContainer(ID, player, tile), (IGuiReaderWriter) ((TileNode) tile).getNode()); case RSGui.SECURITY_MANAGER: @@ -161,43 +156,45 @@ public class GuiHandler implements IGuiHandler { } } - private IGrid getWirelessGrid(EntityPlayer player, int hand, int controllerDimension, int type) { + private IGrid getGrid(EntityPlayer player, int hand, int controllerDimension, int type) { ItemStack stack = player.getHeldItem(EnumHand.values()[hand]); switch (type) { - case NetworkItemWirelessGrid.GRID_TYPE: + case WirelessGrid.GRID_TYPE: return new WirelessGrid(controllerDimension, stack); - case NetworkItemWirelessFluidGrid.GRID_TYPE: + case WirelessFluidGrid.GRID_TYPE: return new WirelessFluidGrid(controllerDimension, stack); + case PortableGrid.GRID_TYPE: + return new PortableGrid(player, stack); default: return null; } } - private GuiGrid getWirelessGridGui(EntityPlayer player, int hand, int controllerDimension, int type) { - IGrid grid = getWirelessGrid(player, hand, controllerDimension, type); + private GuiGrid getGridGui(EntityPlayer player, int hand, int controllerDimension, int type) { + IGrid grid = getGrid(player, hand, controllerDimension, type); GuiGrid gui = new GuiGrid(null, grid); gui.inventorySlots = new ContainerGrid(grid, gui, null, player); return gui; } - private ContainerGrid getWirelessGridContainer(EntityPlayer player, int hand, int controllerDimension, int type) { - return new ContainerGrid(getWirelessGrid(player, hand, controllerDimension, type), new GridDisplayDummy(), null, player); + private ContainerGrid getGridContainer(EntityPlayer player, int hand, int controllerDimension, int type) { + return new ContainerGrid(getGrid(player, hand, controllerDimension, type), new GridDisplayDummy(), null, player); } - private WirelessCraftingMonitor getWirelessCraftingMonitor(EntityPlayer player, int hand, int controllerDimension) { + private WirelessCraftingMonitor getCraftingMonitor(EntityPlayer player, int hand, int controllerDimension) { return new WirelessCraftingMonitor(controllerDimension, player.getHeldItem(EnumHand.values()[hand])); } - private GuiCraftingMonitor getWirelessCraftingMonitorGui(EntityPlayer player, int hand, int controllerDimension) { - WirelessCraftingMonitor craftingMonitor = getWirelessCraftingMonitor(player, hand, controllerDimension); + private GuiCraftingMonitor getCraftingMonitorGui(EntityPlayer player, int hand, int controllerDimension) { + WirelessCraftingMonitor craftingMonitor = getCraftingMonitor(player, hand, controllerDimension); return new GuiCraftingMonitor(new ContainerCraftingMonitor(craftingMonitor, null, player), craftingMonitor); } - private ContainerCraftingMonitor getWirelessCraftingMonitorContainer(EntityPlayer player, int hand, int controllerDimension) { - return new ContainerCraftingMonitor(getWirelessCraftingMonitor(player, hand, controllerDimension), null, player); + private ContainerCraftingMonitor getCraftingMonitorContainer(EntityPlayer player, int hand, int controllerDimension) { + return new ContainerCraftingMonitor(getCraftingMonitor(player, hand, controllerDimension), null, player); } private ContainerFilter getFilterContainer(EntityPlayer player, int hand) { diff --git a/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/GuiGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/GuiGrid.java index 17f5fc746..5f5e9dd1f 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/GuiGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/GuiGrid.java @@ -26,6 +26,7 @@ import com.raoulvdberge.refinedstorage.item.filter.FilterTab; import com.raoulvdberge.refinedstorage.network.*; import com.raoulvdberge.refinedstorage.tile.data.TileDataManager; import com.raoulvdberge.refinedstorage.tile.grid.IGrid; +import com.raoulvdberge.refinedstorage.tile.grid.PortableGrid; import com.raoulvdberge.refinedstorage.tile.grid.TileGrid; import net.minecraft.client.audio.PositionedSoundRecord; import net.minecraft.client.gui.GuiButton; @@ -146,7 +147,7 @@ public class GuiGrid extends GuiBase implements IGridDisplay { oredictPattern = addCheckBox(x + 64, y + getTabDelta() + getHeader() + (getVisibleRows() * 18) + 46, t("misc.refinedstorage:oredict"), TileGrid.OREDICT_PATTERN.getValue()); } - if (grid.getType() != GridType.FLUID) { + if (grid.getType() != GridType.FLUID && grid.getViewType() != -1) { addSideButton(new SideButtonGridViewType(this, grid)); } @@ -379,6 +380,8 @@ public class GuiGrid extends GuiBase implements IGridDisplay { bindTexture("gui/crafting_grid.png"); } else if (grid.getType() == GridType.PATTERN) { bindTexture("gui/pattern_grid.png"); + } else if (grid instanceof PortableGrid) { + bindTexture("gui/portable_grid.png"); } else { bindTexture("gui/grid.png"); } @@ -388,7 +391,7 @@ public class GuiGrid extends GuiBase implements IGridDisplay { drawTexture(x, yy, 0, 0, screenWidth - (grid.getType() != GridType.FLUID ? 34 : 0), getHeader()); if (grid.getType() != GridType.FLUID) { - drawTexture(x + screenWidth - 34 + 4, y + getTabDelta(), 197, 0, 30, 82); + drawTexture(x + screenWidth - 34 + 4, y + getTabDelta(), 197, 0, 30, grid instanceof PortableGrid ? 114 : 82); } int rows = getVisibleRows(); @@ -677,4 +680,13 @@ public class GuiGrid extends GuiBase implements IGridDisplay { oredictPattern.setIsChecked(checked); } } + + @Override + public void onGuiClosed() { + super.onGuiClosed(); + + ITEMS.clear(); + FLUIDS.clear(); + STACKS.clear(); + } } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/stack/GridStackItem.java b/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/stack/GridStackItem.java index e5b5a2748..d369ba347 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/stack/GridStackItem.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/gui/grid/stack/GridStackItem.java @@ -20,13 +20,12 @@ public class GridStackItem implements IGridStack { private ItemStack stack; private boolean craftable; private boolean displayCraftText; - private String[] oreIds; + private String[] oreIds = null; public GridStackItem(ByteBuf buf) { - stack = RSUtils.readItemStack(buf); - hash = buf.readInt(); - craftable = buf.readBoolean(); - oreIds = null; + this.stack = RSUtils.readItemStack(buf); + this.hash = buf.readInt(); + this.craftable = buf.readBoolean(); setDisplayCraftText(buf.readBoolean()); } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemNetworkItem.java b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemNetworkItem.java index 2b2d8a625..1a774b258 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemNetworkItem.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemNetworkItem.java @@ -79,8 +79,6 @@ public abstract class ItemNetworkItem extends ItemEnergyItem implements INetwork tag.setInteger(NBT_CONTROLLER_Z, pos.getZ()); tag.setInteger(NBT_DIMENSION_ID, player.dimension); - initDefaults(tag); - stack.setTagCompound(tag); return EnumActionResult.SUCCESS; @@ -89,10 +87,6 @@ public abstract class ItemNetworkItem extends ItemEnergyItem implements INetwork return EnumActionResult.PASS; } - protected void initDefaults(NBTTagCompound tag) { - // NO OP - } - public static int getDimensionId(ItemStack stack) { return stack.getTagCompound().getInteger(NBT_DIMENSION_ID); } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemPortableGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemPortableGrid.java index 729420510..53c51121c 100644 --- a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemPortableGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemPortableGrid.java @@ -1,7 +1,43 @@ package com.raoulvdberge.refinedstorage.item; +import com.raoulvdberge.refinedstorage.RS; +import com.raoulvdberge.refinedstorage.RSGui; +import com.raoulvdberge.refinedstorage.tile.grid.PortableGrid; +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.item.ItemStack; +import net.minecraft.util.ActionResult; +import net.minecraft.util.EnumActionResult; +import net.minecraft.util.EnumHand; +import net.minecraft.world.World; + public class ItemPortableGrid extends ItemEnergyItem { public ItemPortableGrid() { super("portable_grid"); } + + @Override + public ActionResult onItemRightClick(World world, EntityPlayer player, EnumHand hand) { + ItemStack stack = player.getHeldItem(hand); + + if (!world.isRemote) { + player.openGui(RS.INSTANCE, RSGui.WIRELESS_GRID, player.getEntityWorld(), hand.ordinal(), 0, PortableGrid.GRID_TYPE); + } + + return ActionResult.newResult(EnumActionResult.SUCCESS, stack); + } + + @Override + public boolean shouldCauseReequipAnimation(ItemStack oldStack, ItemStack newStack, boolean slotChanged) { + if (oldStack.getItem() == newStack.getItem()) { + if (ItemWirelessGrid.getSortingDirection(oldStack) == ItemWirelessGrid.getSortingDirection(newStack) && + ItemWirelessGrid.getSortingType(oldStack) == ItemWirelessGrid.getSortingType(newStack) && + ItemWirelessGrid.getSearchBoxMode(oldStack) == ItemWirelessGrid.getSearchBoxMode(newStack) && + ItemWirelessGrid.getTabSelected(oldStack) == ItemWirelessGrid.getTabSelected(newStack) && + ItemWirelessGrid.getSize(oldStack) == ItemWirelessGrid.getSize(newStack)) { + return false; + } + } + + return super.shouldCauseReequipAnimation(oldStack, newStack, slotChanged); + } } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessCraftingMonitor.java b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessCraftingMonitor.java index 1c28500ff..b1d56ed0c 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessCraftingMonitor.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessCraftingMonitor.java @@ -16,13 +16,6 @@ public class ItemWirelessCraftingMonitor extends ItemNetworkItem { super("wireless_crafting_monitor"); } - @Override - public void initDefaults(NBTTagCompound tag) { - super.initDefaults(tag); - - tag.setBoolean(NBT_VIEW_AUTOMATED, true); - } - @Override @Nonnull public INetworkItem provide(INetworkItemHandler handler, EntityPlayer player, ItemStack stack) { @@ -38,6 +31,6 @@ public class ItemWirelessCraftingMonitor extends ItemNetworkItem { } public static boolean canViewAutomated(ItemStack stack) { - return stack.hasTagCompound() && stack.getTagCompound().hasKey(NBT_VIEW_AUTOMATED) && stack.getTagCompound().getBoolean(NBT_VIEW_AUTOMATED); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NBT_VIEW_AUTOMATED)) ? stack.getTagCompound().getBoolean(NBT_VIEW_AUTOMATED) : true; } } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessFluidGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessFluidGrid.java index cc3ef830c..929317ad5 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessFluidGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessFluidGrid.java @@ -6,7 +6,6 @@ import com.raoulvdberge.refinedstorage.apiimpl.network.item.NetworkItemWirelessF import com.raoulvdberge.refinedstorage.apiimpl.network.node.NetworkNodeGrid; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.item.ItemStack; -import net.minecraft.nbt.NBTTagCompound; import javax.annotation.Nonnull; @@ -15,25 +14,6 @@ public class ItemWirelessFluidGrid extends ItemNetworkItem { super("wireless_fluid_grid"); } - @Override - public void initDefaults(NBTTagCompound tag) { - super.initDefaults(tag); - - tag.setInteger(NetworkNodeGrid.NBT_SORTING_DIRECTION, NetworkNodeGrid.SORTING_DIRECTION_DESCENDING); - tag.setInteger(NetworkNodeGrid.NBT_SORTING_TYPE, NetworkNodeGrid.SORTING_TYPE_QUANTITY); - tag.setInteger(NetworkNodeGrid.NBT_SEARCH_BOX_MODE, NetworkNodeGrid.SEARCH_BOX_MODE_NORMAL); - tag.setInteger(NetworkNodeGrid.NBT_SIZE, NetworkNodeGrid.SIZE_STRETCH); - } - - @Override - public boolean isValid(ItemStack stack) { - return super.isValid(stack) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_DIRECTION) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_TYPE) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SEARCH_BOX_MODE) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SIZE); - } - @Override @Nonnull public INetworkItem provide(INetworkItemHandler handler, EntityPlayer player, ItemStack stack) { @@ -41,18 +21,18 @@ public class ItemWirelessFluidGrid extends ItemNetworkItem { } public static int getSortingType(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_TYPE); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_TYPE)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_TYPE) : NetworkNodeGrid.SORTING_TYPE_QUANTITY; } public static int getSortingDirection(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_DIRECTION); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_DIRECTION)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_DIRECTION) : NetworkNodeGrid.SORTING_DIRECTION_DESCENDING; } public static int getSearchBoxMode(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SEARCH_BOX_MODE); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SEARCH_BOX_MODE)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SEARCH_BOX_MODE) : NetworkNodeGrid.SEARCH_BOX_MODE_NORMAL; } public static int getSize(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SIZE); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SIZE)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SIZE) : NetworkNodeGrid.SIZE_STRETCH; } } diff --git a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessGrid.java index 15dc5ab99..d95d885af 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/item/ItemWirelessGrid.java @@ -6,7 +6,6 @@ import com.raoulvdberge.refinedstorage.apiimpl.network.item.NetworkItemWirelessG import com.raoulvdberge.refinedstorage.apiimpl.network.node.NetworkNodeGrid; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.item.ItemStack; -import net.minecraft.nbt.NBTTagCompound; import javax.annotation.Nonnull; @@ -15,27 +14,6 @@ public class ItemWirelessGrid extends ItemNetworkItem { super("wireless_grid"); } - @Override - public void initDefaults(NBTTagCompound tag) { - super.initDefaults(tag); - - tag.setInteger(NetworkNodeGrid.NBT_VIEW_TYPE, NetworkNodeGrid.VIEW_TYPE_NORMAL); - tag.setInteger(NetworkNodeGrid.NBT_SORTING_DIRECTION, NetworkNodeGrid.SORTING_DIRECTION_DESCENDING); - tag.setInteger(NetworkNodeGrid.NBT_SORTING_TYPE, NetworkNodeGrid.SORTING_TYPE_QUANTITY); - tag.setInteger(NetworkNodeGrid.NBT_SEARCH_BOX_MODE, NetworkNodeGrid.SEARCH_BOX_MODE_NORMAL); - tag.setInteger(NetworkNodeGrid.NBT_SIZE, NetworkNodeGrid.SIZE_STRETCH); - tag.setInteger(NetworkNodeGrid.NBT_TAB_SELECTED, -1); - } - - @Override - public boolean isValid(ItemStack stack) { - return super.isValid(stack) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_VIEW_TYPE) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_DIRECTION) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_TYPE) - && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SEARCH_BOX_MODE); - } - @Override @Nonnull public INetworkItem provide(INetworkItemHandler handler, EntityPlayer player, ItemStack stack) { @@ -43,19 +21,19 @@ public class ItemWirelessGrid extends ItemNetworkItem { } public static int getViewType(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_VIEW_TYPE); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_VIEW_TYPE)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_VIEW_TYPE) : NetworkNodeGrid.VIEW_TYPE_NORMAL; } public static int getSortingType(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_TYPE); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_TYPE)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_TYPE) : NetworkNodeGrid.SORTING_TYPE_QUANTITY; } public static int getSortingDirection(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_DIRECTION); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SORTING_DIRECTION)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SORTING_DIRECTION) : NetworkNodeGrid.SORTING_DIRECTION_DESCENDING; } public static int getSearchBoxMode(ItemStack stack) { - return stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SEARCH_BOX_MODE); + return (stack.hasTagCompound() && stack.getTagCompound().hasKey(NetworkNodeGrid.NBT_SEARCH_BOX_MODE)) ? stack.getTagCompound().getInteger(NetworkNodeGrid.NBT_SEARCH_BOX_MODE) : NetworkNodeGrid.SEARCH_BOX_MODE_NORMAL; } public static int getTabSelected(ItemStack stack) { diff --git a/src/main/java/com/raoulvdberge/refinedstorage/network/MessageGridItemDelta.java b/src/main/java/com/raoulvdberge/refinedstorage/network/MessageGridItemDelta.java index 6795a1d26..8198672d9 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/network/MessageGridItemDelta.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/network/MessageGridItemDelta.java @@ -11,9 +11,11 @@ import net.minecraftforge.fml.common.network.simpleimpl.IMessage; import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler; import net.minecraftforge.fml.common.network.simpleimpl.MessageContext; +import java.util.function.Consumer; + public class MessageGridItemDelta implements IMessage, IMessageHandler { - private INetworkMaster network; - private ItemStack stack; + // @todo: we can remove sendHandler if we improve the network == null condition in RSUtils.writeItemStack + private Consumer sendHandler; private int delta; private GridStackItem clientStack; @@ -22,8 +24,12 @@ public class MessageGridItemDelta implements IMessage, IMessageHandler RSUtils.writeItemStack(buf, stack, network, false); + this.delta = delta; + } + + public MessageGridItemDelta(Consumer sendHandler, int delta) { + this.sendHandler = sendHandler; this.delta = delta; } @@ -35,7 +41,7 @@ public class MessageGridItemDelta implements IMessage, IMessageHandler { - private INetworkMaster network; + private Consumer sendHandler; private boolean canCraft; private List stacks = new ArrayList<>(); @@ -25,7 +26,33 @@ public class MessageGridItemUpdate implements IMessage, IMessageHandler { + int size = network.getItemStorageCache().getList().getStacks().size(); + + for (ICraftingPattern pattern : network.getCraftingManager().getPatterns()) { + size += pattern.getOutputs().stream().filter(Objects::nonNull).count(); + } + + buf.writeInt(size); + + for (ItemStack stack : network.getItemStorageCache().getList().getStacks()) { + RSUtils.writeItemStack(buf, stack, network, false); + } + + for (ICraftingPattern pattern : network.getCraftingManager().getPatterns()) { + for (ItemStack output : pattern.getOutputs()) { + if (output != null) { + RSUtils.writeItemStack(buf, output, network, true); + } + } + } + }; + + this.canCraft = canCraft; + } + + public MessageGridItemUpdate(Consumer sendHandler, boolean canCraft) { + this.sendHandler = sendHandler; this.canCraft = canCraft; } @@ -44,25 +71,7 @@ public class MessageGridItemUpdate implements IMessage, IMessageHandler implements IMessage { +public class MessageGridSettingsUpdate extends MessageHandlerPlayerToServer implements IMessage { private int viewType; private int sortingDirection; private int sortingType; @@ -17,10 +19,10 @@ public class MessageWirelessGridSettingsUpdate extends MessageHandlerPlayerToSer private int size; private int tabSelected; - public MessageWirelessGridSettingsUpdate() { + public MessageGridSettingsUpdate() { } - public MessageWirelessGridSettingsUpdate(int viewType, int sortingDirection, int sortingType, int searchBoxMode, int size, int tabSelected) { + public MessageGridSettingsUpdate(int viewType, int sortingDirection, int sortingType, int searchBoxMode, int size, int tabSelected) { this.viewType = viewType; this.sortingDirection = sortingDirection; this.sortingType = sortingType; @@ -50,12 +52,16 @@ public class MessageWirelessGridSettingsUpdate extends MessageHandlerPlayerToSer } @Override - public void handle(MessageWirelessGridSettingsUpdate message, EntityPlayerMP player) { + public void handle(MessageGridSettingsUpdate message, EntityPlayerMP player) { if (player.openContainer instanceof ContainerGrid) { IGrid grid = ((ContainerGrid) player.openContainer).getGrid(); - if (grid instanceof WirelessGrid) { - ItemStack stack = ((WirelessGrid) grid).getStack(); + if (grid instanceof WirelessGrid || grid instanceof PortableGrid) { + ItemStack stack = grid instanceof WirelessGrid ? ((WirelessGrid) grid).getStack() : ((PortableGrid) grid).getStack(); + + if (!stack.hasTagCompound()) { + stack.setTagCompound(new NBTTagCompound()); + } if (NetworkNodeGrid.isValidViewType(message.viewType)) { stack.getTagCompound().setInteger(NetworkNodeGrid.NBT_VIEW_TYPE, message.viewType); diff --git a/src/main/java/com/raoulvdberge/refinedstorage/proxy/ProxyCommon.java b/src/main/java/com/raoulvdberge/refinedstorage/proxy/ProxyCommon.java index 416389d5a..e5fe6402f 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/proxy/ProxyCommon.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/proxy/ProxyCommon.java @@ -100,7 +100,7 @@ public class ProxyCommon { RS.INSTANCE.network.registerMessage(MessageGridItemPull.class, MessageGridItemPull.class, id++, Side.SERVER); RS.INSTANCE.network.registerMessage(MessageGridCraftingClear.class, MessageGridCraftingClear.class, id++, Side.SERVER); RS.INSTANCE.network.registerMessage(MessageGridCraftingTransfer.class, MessageGridCraftingTransfer.class, id++, Side.SERVER); - RS.INSTANCE.network.registerMessage(MessageWirelessGridSettingsUpdate.class, MessageWirelessGridSettingsUpdate.class, id++, Side.SERVER); + RS.INSTANCE.network.registerMessage(MessageGridSettingsUpdate.class, MessageGridSettingsUpdate.class, id++, Side.SERVER); RS.INSTANCE.network.registerMessage(MessageGridCraftingStart.class, MessageGridCraftingStart.class, id++, Side.SERVER); RS.INSTANCE.network.registerMessage(MessageGridPatternCreate.class, MessageGridPatternCreate.class, id++, Side.SERVER); RS.INSTANCE.network.registerMessage(MessageCraftingMonitorCancel.class, MessageCraftingMonitorCancel.class, id++, Side.SERVER); @@ -375,6 +375,17 @@ public class ProxyCommon { 'A', new ItemStack(RSItems.PROCESSOR, 1, ItemProcessor.TYPE_ADVANCED) ); + // Portable Grid + GameRegistry.addRecipe(new ItemStack(RSItems.PORTABLE_GRID), + "EHE", + "ECE", + "EAE", + 'E', new ItemStack(RSItems.QUARTZ_ENRICHED_IRON), + 'H', new ItemStack(Blocks.CHEST), + 'C', new ItemStack(RSBlocks.CONTROLLER, 1, ControllerType.NORMAL.getId()), + 'A', new ItemStack(RSItems.PROCESSOR, 1, ItemProcessor.TYPE_ADVANCED) + ); + // Wireless Fluid Grid GameRegistry.addRecipe(new ItemStack(RSItems.WIRELESS_FLUID_GRID, 1, ItemWirelessFluidGrid.TYPE_NORMAL), "EPE", diff --git a/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/PortableGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/PortableGrid.java new file mode 100644 index 000000000..5a5889d56 --- /dev/null +++ b/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/PortableGrid.java @@ -0,0 +1,316 @@ +package com.raoulvdberge.refinedstorage.tile.grid; + +import com.raoulvdberge.refinedstorage.RS; +import com.raoulvdberge.refinedstorage.RSUtils; +import com.raoulvdberge.refinedstorage.api.network.INetworkMaster; +import com.raoulvdberge.refinedstorage.api.network.grid.IItemGridHandler; +import com.raoulvdberge.refinedstorage.api.storage.AccessType; +import com.raoulvdberge.refinedstorage.api.storage.IStorageDisk; +import com.raoulvdberge.refinedstorage.api.storage.IStorageDiskProvider; +import com.raoulvdberge.refinedstorage.api.storage.StorageDiskType; +import com.raoulvdberge.refinedstorage.apiimpl.network.grid.ItemGridHandlerPortable; +import com.raoulvdberge.refinedstorage.apiimpl.network.node.diskdrive.NetworkNodeDiskDrive; +import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageCacheItemPortable; +import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageDiskItemPortable; +import com.raoulvdberge.refinedstorage.block.GridType; +import com.raoulvdberge.refinedstorage.gui.grid.GuiGrid; +import com.raoulvdberge.refinedstorage.inventory.ItemHandlerBase; +import com.raoulvdberge.refinedstorage.inventory.ItemHandlerFilter; +import com.raoulvdberge.refinedstorage.item.ItemPortableGrid; +import com.raoulvdberge.refinedstorage.item.ItemWirelessGrid; +import com.raoulvdberge.refinedstorage.item.filter.Filter; +import com.raoulvdberge.refinedstorage.item.filter.FilterTab; +import com.raoulvdberge.refinedstorage.network.MessageGridSettingsUpdate; +import com.raoulvdberge.refinedstorage.tile.data.TileDataParameter; +import net.minecraft.client.Minecraft; +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.inventory.InventoryCraftResult; +import net.minecraft.inventory.InventoryCrafting; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; +import net.minecraftforge.energy.CapabilityEnergy; +import net.minecraftforge.fml.common.FMLCommonHandler; +import net.minecraftforge.fml.relauncher.Side; + +import javax.annotation.Nullable; +import java.util.ArrayList; +import java.util.List; + +public class PortableGrid implements IGrid { + public static final int GRID_TYPE = 2; + + @Nullable + private IStorageDisk storage; + private StorageCacheItemPortable cache = new StorageCacheItemPortable(this); + private ItemGridHandlerPortable handler = new ItemGridHandlerPortable(this); + + private EntityPlayer player; + private ItemStack stack; + + private int sortingType; + private int sortingDirection; + private int searchBoxMode; + private int tabSelected; + private int size; + + private List filters = new ArrayList<>(); + private List tabs = new ArrayList<>(); + private ItemHandlerFilter filter = new ItemHandlerFilter(filters, tabs, null) { + @Override + protected void onContentsChanged(int slot) { + super.onContentsChanged(slot); + + if (!stack.hasTagCompound()) { + stack.setTagCompound(new NBTTagCompound()); + } + + RSUtils.writeItems(this, slot, stack.getTagCompound()); + } + }; + private ItemHandlerBase disk = new ItemHandlerBase(1, s -> NetworkNodeDiskDrive.VALIDATOR_STORAGE_DISK.test(s) && ((IStorageDiskProvider) s.getItem()).create(s).getType() == StorageDiskType.ITEMS) { + @Override + protected void onContentsChanged(int slot) { + super.onContentsChanged(slot); + + if (FMLCommonHandler.instance().getEffectiveSide() == Side.SERVER) { + if (getStackInSlot(slot).isEmpty()) { + storage = null; + } else { + IStorageDiskProvider provider = (IStorageDiskProvider) getStackInSlot(slot).getItem(); + + storage = new StorageDiskItemPortable(provider.create(getStackInSlot(slot)), PortableGrid.this); + storage.readFromNBT(); + storage.onPassContainerContext(() -> { + }, () -> false, () -> AccessType.INSERT_EXTRACT); + } + + cache.invalidate(); + + RSUtils.writeItems(this, 4, stack.getTagCompound()); + } + } + }; + + public PortableGrid(EntityPlayer player, ItemStack stack) { + this.player = player; + this.stack = stack; + + // Only extract when we can + if (isActive()) { + drainEnergy(RS.INSTANCE.config.portableGridOpenUsage); + } + + this.sortingType = ItemWirelessGrid.getSortingType(stack); + this.sortingDirection = ItemWirelessGrid.getSortingDirection(stack); + this.searchBoxMode = ItemWirelessGrid.getSearchBoxMode(stack); + this.tabSelected = ItemWirelessGrid.getTabSelected(stack); + this.size = ItemWirelessGrid.getSize(stack); + + if (!stack.hasTagCompound()) { + stack.setTagCompound(new NBTTagCompound()); + } + + for (int i = 0; i < 4; ++i) { + RSUtils.readItems(filter, i, stack.getTagCompound()); + } + + RSUtils.readItems(disk, 4, stack.getTagCompound()); + } + + public void drainEnergy(int energy) { + if (RS.INSTANCE.config.portableGridUsesEnergy) { + stack.getCapability(CapabilityEnergy.ENERGY, null).extractEnergy(energy, false); + } + } + + public ItemStack getStack() { + return stack; + } + + public StorageCacheItemPortable getCache() { + return cache; + } + + @Nullable + public IStorageDisk getStorage() { + return storage; + } + + public ItemHandlerBase getDisk() { + return disk; + } + + public EntityPlayer getPlayer() { + return player; + } + + @Override + public GridType getType() { + return GridType.NORMAL; + } + + @Nullable + @Override + public INetworkMaster getNetwork() { + return null; + } + + @Nullable + @Override + public IItemGridHandler getItemHandler() { + return handler; + } + + @Override + public String getGuiTitle() { + return "gui.refinedstorage:portable_grid"; + } + + @Override + public int getViewType() { + return -1; + } + + @Override + public int getSortingType() { + return sortingType; + } + + @Override + public int getSortingDirection() { + return sortingDirection; + } + + @Override + public int getSearchBoxMode() { + return searchBoxMode; + } + + @Override + public int getTabSelected() { + return tabSelected; + } + + @Override + public int getSize() { + return size; + } + + @Override + public void onViewTypeChanged(int type) { + // NO OP + } + + @Override + public void onSortingTypeChanged(int type) { + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), type, getSearchBoxMode(), getSize(), getTabSelected())); + + this.sortingType = type; + + GuiGrid.markForSorting(); + } + + @Override + public void onSortingDirectionChanged(int direction) { + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), direction, getSortingType(), getSearchBoxMode(), getSize(), getTabSelected())); + + this.sortingDirection = direction; + + GuiGrid.markForSorting(); + } + + @Override + public void onSearchBoxModeChanged(int searchBoxMode) { + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), searchBoxMode, getSize(), getTabSelected())); + + this.searchBoxMode = searchBoxMode; + } + + @Override + public void onSizeChanged(int size) { + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), getSearchBoxMode(), size, getTabSelected())); + + this.size = size; + + if (Minecraft.getMinecraft().currentScreen != null) { + Minecraft.getMinecraft().currentScreen.initGui(); + } + } + + @Override + public void onTabSelectionChanged(int tab) { + this.tabSelected = tab == tabSelected ? -1 : tab; + + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), getSearchBoxMode(), getSize(), tabSelected)); + + GuiGrid.markForSorting(); + } + + @Override + public List getFilters() { + return filters; + } + + @Override + public List getTabs() { + return tabs; + } + + @Override + public ItemHandlerBase getFilter() { + return filter; + } + + @Override + public TileDataParameter getRedstoneModeConfig() { + return null; + } + + @Override + public InventoryCrafting getCraftingMatrix() { + return null; + } + + @Override + public InventoryCraftResult getCraftingResult() { + return null; + } + + @Override + public void onCraftingMatrixChanged() { + // NO OP + } + + @Override + public void onCrafted(EntityPlayer player) { + // NO OP + } + + @Override + public void onCraftedShift(EntityPlayer player) { + // NO OP + } + + @Override + public void onRecipeTransfer(EntityPlayer player, ItemStack[][] recipe) { + // NO OP + } + + @Override + public void onClosed(EntityPlayer player) { + if (!player.world.isRemote && storage != null) { + storage.writeToNBT(); + + RSUtils.writeItems(disk, 4, stack.getTagCompound()); + } + } + + @Override + public boolean isActive() { + if (RS.INSTANCE.config.portableGridUsesEnergy && stack.getItemDamage() != ItemPortableGrid.TYPE_CREATIVE && stack.getCapability(CapabilityEnergy.ENERGY, null).getEnergyStored() <= RS.INSTANCE.config.portableGridOpenUsage) { + return false; + } + + return true; + } +} diff --git a/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessFluidGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessFluidGrid.java index b99eb5ff1..c0983dab6 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessFluidGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessFluidGrid.java @@ -26,6 +26,8 @@ import java.util.Collections; import java.util.List; public class WirelessFluidGrid implements IGrid { + public static final int GRID_TYPE = 1; + private ItemStack stack; private int controllerDimension; diff --git a/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessGrid.java b/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessGrid.java index 0e1d9ed8d..68487fe77 100755 --- a/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessGrid.java +++ b/src/main/java/com/raoulvdberge/refinedstorage/tile/grid/WirelessGrid.java @@ -10,7 +10,7 @@ import com.raoulvdberge.refinedstorage.inventory.ItemHandlerFilter; import com.raoulvdberge.refinedstorage.item.ItemWirelessGrid; import com.raoulvdberge.refinedstorage.item.filter.Filter; import com.raoulvdberge.refinedstorage.item.filter.FilterTab; -import com.raoulvdberge.refinedstorage.network.MessageWirelessGridSettingsUpdate; +import com.raoulvdberge.refinedstorage.network.MessageGridSettingsUpdate; import com.raoulvdberge.refinedstorage.tile.data.TileDataParameter; import net.minecraft.client.Minecraft; import net.minecraft.entity.player.EntityPlayer; @@ -28,6 +28,8 @@ import java.util.ArrayList; import java.util.List; public class WirelessGrid implements IGrid { + public static final int GRID_TYPE = 0; + private ItemStack stack; private int controllerDimension; @@ -135,7 +137,7 @@ public class WirelessGrid implements IGrid { @Override public void onViewTypeChanged(int type) { - RS.INSTANCE.network.sendToServer(new MessageWirelessGridSettingsUpdate(type, getSortingDirection(), getSortingType(), getSearchBoxMode(), getSize(), getTabSelected())); + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(type, getSortingDirection(), getSortingType(), getSearchBoxMode(), getSize(), getTabSelected())); this.viewType = type; @@ -144,7 +146,7 @@ public class WirelessGrid implements IGrid { @Override public void onSortingTypeChanged(int type) { - RS.INSTANCE.network.sendToServer(new MessageWirelessGridSettingsUpdate(getViewType(), getSortingDirection(), type, getSearchBoxMode(), getSize(), getTabSelected())); + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), type, getSearchBoxMode(), getSize(), getTabSelected())); this.sortingType = type; @@ -153,7 +155,7 @@ public class WirelessGrid implements IGrid { @Override public void onSortingDirectionChanged(int direction) { - RS.INSTANCE.network.sendToServer(new MessageWirelessGridSettingsUpdate(getViewType(), direction, getSortingType(), getSearchBoxMode(), getSize(), getTabSelected())); + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), direction, getSortingType(), getSearchBoxMode(), getSize(), getTabSelected())); this.sortingDirection = direction; @@ -162,14 +164,14 @@ public class WirelessGrid implements IGrid { @Override public void onSearchBoxModeChanged(int searchBoxMode) { - RS.INSTANCE.network.sendToServer(new MessageWirelessGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), searchBoxMode, getSize(), getTabSelected())); + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), searchBoxMode, getSize(), getTabSelected())); this.searchBoxMode = searchBoxMode; } @Override public void onSizeChanged(int size) { - RS.INSTANCE.network.sendToServer(new MessageWirelessGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), getSearchBoxMode(), size, getTabSelected())); + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), getSearchBoxMode(), size, getTabSelected())); this.size = size; @@ -182,7 +184,7 @@ public class WirelessGrid implements IGrid { public void onTabSelectionChanged(int tab) { this.tabSelected = tab == tabSelected ? -1 : tab; - RS.INSTANCE.network.sendToServer(new MessageWirelessGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), getSearchBoxMode(), getSize(), tabSelected)); + RS.INSTANCE.network.sendToServer(new MessageGridSettingsUpdate(getViewType(), getSortingDirection(), getSortingType(), getSearchBoxMode(), getSize(), tabSelected)); GuiGrid.markForSorting(); } diff --git a/src/main/resources/assets/refinedstorage/lang/en_us.lang b/src/main/resources/assets/refinedstorage/lang/en_us.lang index cfe904155..90c59c260 100755 --- a/src/main/resources/assets/refinedstorage/lang/en_us.lang +++ b/src/main/resources/assets/refinedstorage/lang/en_us.lang @@ -75,6 +75,7 @@ gui.refinedstorage:security_manager.permission.4.tooltip=Adding or removing devi gui.refinedstorage:security_manager.permission.5=Security gui.refinedstorage:security_manager.permission.5.tooltip=Ability to change security options gui.refinedstorage:storage_monitor=Storage Monitor +gui.refinedstorage:portable_grid=Portable Grid misc.refinedstorage:energy_stored=%d / %d RS misc.refinedstorage:energy_usage=Usage: %d RS/t @@ -283,4 +284,6 @@ item.refinedstorage:wrench.mode.0=Rotation item.refinedstorage:wrench.mode.1=Configuration item.refinedstorage:wrench.mode.2=Dismantling item.refinedstorage:security_card.name=Security Card -item.refinedstorage:security_card.owner=Bound to: %s \ No newline at end of file +item.refinedstorage:security_card.owner=Bound to: %s +item.refinedstorage:portable_grid.0.name=Portable Grid +item.refinedstorage:portable_grid.1.name=Creative Portable Grid diff --git a/src/main/resources/assets/refinedstorage/textures/gui/portable_grid.png b/src/main/resources/assets/refinedstorage/textures/gui/portable_grid.png new file mode 100644 index 0000000000000000000000000000000000000000..e05f603efffcf77c363797ead53e8891c4c1b0b7 GIT binary patch literal 2224 zcmeAS@N?(olHy`uVBq!ia0y~yU<5K58911MRQ8&P5D>38$lZxy-8q?;Kn_c~qpu?a z!^VE@KZ&di49pAxJ|V6^adUI?(9qEC?(Sp9j{X1tA1E>kMnhnPgh10{aTQRmDGBlm z1}6TI3>bpHv#SE5owL9rvY3H^?=T269?xHq0u+=iag8Vm&QB{TPb^AhC`ioAE78kK zEm1JhGte_Ma%RbX11w-TJY5_^D&pSGY0O(}Ai%nF$>0C}=Z=18a_(si$``IMwtBg; zd*SZl6@f9A-j%)PJM*@2pWelfT6fp}wlnDe`O0~XiK!rnC2Ppi?kfP-Gc-fIUF49 zGk94P7#KNT=wIbvc~NctT!U%d-{=h-UwD_*%xkb`V?4|9;&1S?RcH3>3@Z8gC2oBy z!(8J}e>0~pI=%d(Ktsb9*PmQd!b2=4H$>iHjqzbA$-KnH$Mmi^_O$Ze09kwMeXzLVr6@B%!Qr&mt}+ zkf9>e{aE@otq&^cY_N%AW?cI%_mNiW^vXSn9XE@&aam|wwtg^m{u>V2DJvQ7{#1Ux zpZU^r#b25^EIjf|mB+jr+Uk;Kobzay$0&bM#Et37cM*_v-xqUSxTDMwVeym^Y{wGs z*RmyQA0qjI{#PxP)O2{>!;+WxcJ&gy>8yXU+%?vH44Zo8=_%O{r+&^8j1pY1RC#3w z(3K9|&m0+m1~ins49h(h8Z@25fdOL0gX>J&Y!-jK=k?0y6JLdDLB9LUn<1XDZd?~E zl^e}J@AG<96nWrH>|>P#v2w=8#v-PEN(Y{ziQ2UzsQUp5iigiIp5}%c6w}P9`@pEY;-*xYaaRsAo)h+yAS&@XHH` R)~*IsBA%{(F6*2UngGJ(+28;G literal 0 HcmV?d00001