From bd11e117413a6f062ed23749eaf3b69bc9e4a762 Mon Sep 17 00:00:00 2001 From: lc-1337 <62835225+lc-1337@users.noreply.github.com> Date: Thu, 11 Dec 2025 17:09:06 +0200 Subject: [PATCH] Universal GUI (#872) Co-authored-by: Kogepan229 Co-authored-by: Kogepan229 <73163994+Kogepan229@users.noreply.github.com> Co-authored-by: Martin Robertz --- repositories.gradle | 1 + .../appeng/api/features/ILevelViewable.java | 34 + .../api/features/IWirelessTermHandler.java | 8 + .../api/features/IWirelessTermRegistry.java | 2 + .../appeng/api/features/LevelItemInfo.java | 20 + .../java/appeng/api/features/LevelState.java | 11 + .../implementations/guiobjects/IGuiItem.java | 10 +- .../guiobjects/IPortableCell.java | 11 +- .../implementations/items/IStorageCell.java | 16 +- .../implementations/tiles/ICellWorkbench.java | 24 + .../api/networking/crafting/ICraftingCPU.java | 2 +- .../networking/crafting/ICraftingGrid.java | 6 +- .../crafting/ICraftingProviderHelper.java | 6 +- .../crafting/ICraftingRequester.java | 11 +- .../api/networking/storage/IBaseMonitor.java | 4 +- .../api/networking/storage/IStorageGrid.java | 2 +- .../appeng/api/parts/ICraftingTerminal.java | 12 + .../appeng/api/parts/IInterfaceTerminal.java | 13 + .../java/appeng/api/parts/ILevelEmitter.java | 21 + .../appeng/api/parts/IPatternTerminal.java | 99 +++ .../appeng/api/parts/IPatternTerminalEx.java | 12 + .../java/appeng/api/parts/IStorageBus.java | 40 + .../api/storage/ICellCacheRegistry.java | 4 + .../appeng/api/storage/ICellInventory.java | 22 +- .../api/storage/ICellInventoryHandler.java | 6 +- .../api/storage/ICellWorkbenchItem.java | 16 +- .../appeng/api/storage/ITerminalHost.java | 6 + .../appeng/api/storage/MEMonitorHandler.java | 22 +- .../appeng/api/storage/StorageChannel.java | 22 + .../java/appeng/api/storage/StorageName.java | 19 + .../appeng/api/storage/data/IAEStack.java | 20 + .../appeng/api/storage/data/IDisplayRepo.java | 10 +- src/main/java/appeng/client/ActionKey.java | 4 +- src/main/java/appeng/client/ClientHelper.java | 5 + .../java/appeng/client/gui/AEBaseGui.java | 355 ++++----- .../java/appeng/client/gui/AEBaseMEGui.java | 124 --- src/main/java/appeng/client/gui/GuiSub.java | 45 ++ src/main/java/appeng/client/gui/IGuiSub.java | 7 + .../client/gui/implementations/GuiAmount.java | 32 +- .../client/gui/implementations/GuiBusIO.java | 116 +++ .../implementations/GuiCellRestriction.java | 9 +- .../gui/implementations/GuiCellWorkbench.java | 35 +- .../gui/implementations/GuiCraftAmount.java | 69 +- .../gui/implementations/GuiCraftConfirm.java | 94 +-- .../gui/implementations/GuiCraftingCPU.java | 168 ++-- .../implementations/GuiCraftingStatus.java | 84 +- .../gui/implementations/GuiInterface.java | 4 + .../implementations/GuiInterfaceTerminal.java | 38 +- .../gui/implementations/GuiLevelEmitter.java | 20 +- .../gui/implementations/GuiMEMonitorable.java | 338 +++++--- .../implementations/GuiMEPortableCell.java | 2 +- .../gui/implementations/GuiNetworkStatus.java | 72 +- .../implementations/GuiOptimizePatterns.java | 44 +- .../gui/implementations/GuiOreFilter.java | 17 +- .../GuiPatternItemRenamer.java | 69 +- .../gui/implementations/GuiPatternMulti.java | 31 +- .../gui/implementations/GuiPatternTerm.java | 183 ++++- .../gui/implementations/GuiPatternTermEx.java | 199 ++--- .../GuiPatternValueAmount.java | 70 +- .../gui/implementations/GuiPriority.java | 61 -- .../gui/implementations/GuiRenamer.java | 4 +- .../gui/implementations/GuiStorageBus.java | 73 +- .../gui/implementations/GuiUpgradeable.java | 77 +- .../gui/implementations/GuiWirelessTerm.java | 27 - .../gui/slots/VirtualMEMonitorableSlot.java | 27 + .../gui/slots/VirtualMEPatternSlot.java | 29 + .../gui/slots/VirtualMEPhantomSlot.java | 105 +++ .../client/gui/slots/VirtualMEPinSlot.java | 62 ++ .../client/gui/slots/VirtualMESlot.java | 145 ++++ .../client/gui/slots/VirtualMESlotSingle.java | 26 + .../java/appeng/client/me/InternalSlotME.java | 51 -- src/main/java/appeng/client/me/ItemRepo.java | 131 ++-- src/main/java/appeng/client/me/PinSlotME.java | 23 - .../appeng/client/me/SlotDisconnected.java | 83 -- src/main/java/appeng/client/me/SlotME.java | 98 --- .../appeng/container/AEBaseContainer.java | 459 +++++------ .../appeng/container/ContainerSubGui.java | 50 ++ .../java/appeng/container/PrimaryGui.java | 39 + .../implementations/ContainerBusIO.java | 40 + .../ContainerCellRestriction.java | 8 +- .../ContainerCellWorkbench.java | 104 +-- .../implementations/ContainerChest.java | 2 +- .../implementations/ContainerCondenser.java | 2 +- .../implementations/ContainerCraftAmount.java | 33 +- .../ContainerCraftConfirm.java | 68 +- .../ContainerCraftingStatus.java | 46 +- .../ContainerCraftingTerm.java | 12 +- .../implementations/ContainerDrive.java | 2 +- .../implementations/ContainerGrinder.java | 2 +- .../ContainerInterfaceTerminal.java | 9 +- .../ContainerLevelEmitter.java | 84 +- .../ContainerMEMonitorable.java | 724 +++++++++++++++--- .../ContainerMEPortableCell.java | 66 +- .../ContainerNetworkStatus.java | 2 +- .../implementations/ContainerNetworkTool.java | 2 +- .../ContainerOptimizePatterns.java | 44 +- .../implementations/ContainerOreFilter.java | 8 +- .../ContainerPatternItemRenamer.java | 25 +- .../ContainerPatternMulti.java | 4 +- .../implementations/ContainerPatternTerm.java | 486 +++++++----- .../ContainerPatternTermEx.java | 412 +--------- .../ContainerPatternValueAmount.java | 80 +- .../implementations/ContainerPriority.java | 4 +- .../implementations/ContainerQNB.java | 2 +- .../implementations/ContainerQuartzKnife.java | 2 +- .../implementations/ContainerRenamer.java | 8 +- .../implementations/ContainerSecurity.java | 4 +- .../implementations/ContainerSkyChest.java | 2 +- .../ContainerSpatialIOPort.java | 2 +- .../implementations/ContainerStorageBus.java | 136 ++-- .../implementations/ContainerUpgradeable.java | 27 +- .../ContainerVibrationChamber.java | 2 +- .../implementations/ContainerWireless.java | 2 +- .../ContainerWirelessTerm.java | 47 -- .../interfaces/IContainerSubGui.java | 19 + .../interfaces/IVirtualSlotHolder.java | 10 + .../interfaces/IVirtualSlotSource.java | 9 + .../appeng/container/slot/SlotDisabled.java | 1 + src/main/java/appeng/core/CommonHelper.java | 4 + src/main/java/appeng/core/Registration.java | 3 +- .../features/registries/CellRegistry.java | 10 +- .../features/registries/WirelessRegistry.java | 25 +- .../registries/entries/BasicCellHandler.java | 5 +- .../entries/CreativeCellHandler.java | 9 +- .../registries/entries/VoidCellHandler.java | 4 +- .../core/sync/AppEngPacketHandlerBase.java | 8 +- src/main/java/appeng/core/sync/GuiBridge.java | 170 ++-- .../core/sync/packets/PacketCraftRequest.java | 3 + .../packets/PacketCraftingItemInterface.java | 51 +- .../sync/packets/PacketInventoryAction.java | 50 +- .../sync/packets/PacketMEInventoryUpdate.java | 13 +- .../sync/packets/PacketMonitorableAction.java | 69 ++ .../packets/PacketPatternItemRenamer.java | 86 --- .../sync/packets/PacketPatternMultiSet.java | 27 +- .../sync/packets/PacketPatternValueSet.java | 66 +- .../core/sync/packets/PacketPinsUpdate.java | 15 +- .../core/sync/packets/PacketSwitchGuis.java | 44 +- .../core/sync/packets/PacketValueConfig.java | 15 +- .../core/sync/packets/PacketVirtualSlot.java | 95 +++ .../appeng/crafting/MECraftingInventory.java | 7 +- .../helpers/ICustomButtonDataObject.java | 28 + .../appeng/helpers/ICustomButtonProvider.java | 26 + .../appeng/helpers/ICustomButtonSource.java | 6 + .../java/appeng/helpers/IPinsHandler.java | 12 +- .../helpers/IPrimaryGuiIconProvider.java | 9 + .../java/appeng/helpers/InventoryAction.java | 7 - .../appeng/helpers/MonitorableAction.java | 20 + .../appeng/helpers/MultiCraftingTracker.java | 12 +- .../java/appeng/helpers/PatternHelper.java | 3 + .../helpers/WirelessTerminalGuiObject.java | 232 +++--- .../java/appeng/integration/modules/NEI.java | 5 +- .../modules/NEIHelpers/NEISearchField.java | 16 +- src/main/java/appeng/items/AEBaseCell.java | 411 ++++++++++ .../java/appeng/items/AEBaseInfiniteCell.java | 118 +++ .../java/appeng/items/AEBasePortableCell.java | 180 +++++ .../appeng/items/contents/CellConfig.java | 4 +- .../items/contents/CellConfigLegacy.java | 102 +++ .../contents/CellConfigLegacyWrapper.java | 65 ++ .../java/appeng/items/contents/PinList.java | 28 + .../appeng/items/contents/PinsHandler.java | 57 +- .../appeng/items/contents/PinsHolder.java | 58 +- .../items/contents/PortableCellViewer.java | 17 +- .../WirelessCraftingTerminalGuiObject.java | 55 ++ .../WirelessInterfaceTerminalGuiObject.java | 137 ++++ .../WirelessPatternTerminalGuiObject.java | 173 +++++ .../appeng/items/misc/ItemEncodedPattern.java | 7 +- .../storage/ItemAdvancedStorageCell.java | 1 + .../items/storage/ItemBasicStorageCell.java | 393 +--------- .../storage/ItemCreativeStorageCell.java | 33 +- .../items/storage/ItemExtremeStorageCell.java | 7 - .../appeng/items/storage/ItemViewCell.java | 30 +- .../items/storage/ItemVoidStorageCell.java | 26 +- .../appeng/items/tools/ToolNetworkTool.java | 3 +- .../appeng/items/tools/ToolPriorityCard.java | 3 +- .../tools/powered/ToolColorApplicator.java | 24 +- .../items/tools/powered/ToolMassCannon.java | 26 +- .../items/tools/powered/ToolPortableCell.java | 171 +---- .../tools/powered/ToolWirelessTerminal.java | 8 + .../tools/quartz/ToolQuartzCuttingKnife.java | 3 +- .../appeng/me/cache/CraftingGridCache.java | 48 +- .../appeng/me/cache/GridStorageCache.java | 6 +- .../java/appeng/me/cache/NetworkMonitor.java | 34 +- .../implementations/CraftingCPUCluster.java | 23 +- .../java/appeng/me/storage/CellInventory.java | 304 ++++---- .../me/storage/CellInventoryHandler.java | 52 +- .../me/storage/CreativeCellInventory.java | 165 +++- .../appeng/me/storage/FluidCellInventory.java | 33 + .../me/storage/FluidCellInventoryHandler.java | 56 ++ .../appeng/me/storage/ItemCellInventory.java | 33 + .../me/storage/ItemCellInventoryHandler.java | 48 ++ .../me/storage/MEMonitorIInventory.java | 18 +- .../me/storage/MEMonitorPassThrough.java | 18 +- .../appeng/me/storage/VoidCellInventory.java | 216 +++--- .../parts/automation/PartBaseExportBus.java | 311 ++++++++ .../parts/automation/PartBaseImportBus.java | 178 +++++ .../parts/automation/PartExportBus.java | 386 ++-------- .../parts/automation/PartFormationPlane.java | 8 +- .../parts/automation/PartImportBus.java | 241 ++---- .../parts/automation/PartLevelEmitter.java | 102 +-- .../parts/automation/PartSharedItemBus.java | 134 ++-- .../java/appeng/parts/misc/PartInterface.java | 12 +- .../appeng/parts/misc/PartStorageBus.java | 190 +++-- .../appeng/parts/p2p/PartP2PInterface.java | 10 +- .../parts/reporting/AbstractPartTerminal.java | 7 +- .../parts/reporting/PartCraftingTerminal.java | 9 +- .../reporting/PartInterfaceTerminal.java | 3 +- .../parts/reporting/PartPatternTerminal.java | 154 ++-- .../reporting/PartPatternTerminalEx.java | 239 ++---- .../appeng/parts/reporting/PartTerminal.java | 6 + .../tile/inventory/IAEStackInventory.java | 109 +++ .../tile/inventory/IIAEStackInventory.java | 10 + .../appeng/tile/misc/TileCellWorkbench.java | 91 ++- .../java/appeng/tile/misc/TileInterface.java | 12 +- .../java/appeng/tile/misc/TileSecurity.java | 6 + .../java/appeng/tile/storage/TileChest.java | 23 +- .../java/appeng/tile/storage/TileDrive.java | 41 +- src/main/java/appeng/util/FluidUtils.java | 95 +++ src/main/java/appeng/util/ItemSorters.java | 20 +- src/main/java/appeng/util/Platform.java | 81 +- .../java/appeng/util/item/AEFluidStack.java | 62 ++ .../java/appeng/util/item/AEItemStack.java | 37 + src/main/java/appeng/util/item/AEStack.java | 62 ++ src/main/java/appeng/util/item/FluidList.java | 7 +- .../java/appeng/util/item/IAEStackList.java | 6 +- .../appliedenergistics2/lang/en_US.lang | 7 +- 225 files changed, 8182 insertions(+), 5684 deletions(-) create mode 100644 src/main/java/appeng/api/features/ILevelViewable.java create mode 100644 src/main/java/appeng/api/features/LevelItemInfo.java create mode 100644 src/main/java/appeng/api/features/LevelState.java create mode 100644 src/main/java/appeng/api/implementations/tiles/ICellWorkbench.java create mode 100644 src/main/java/appeng/api/parts/ICraftingTerminal.java create mode 100644 src/main/java/appeng/api/parts/IInterfaceTerminal.java create mode 100644 src/main/java/appeng/api/parts/ILevelEmitter.java create mode 100644 src/main/java/appeng/api/parts/IPatternTerminal.java create mode 100644 src/main/java/appeng/api/parts/IPatternTerminalEx.java create mode 100644 src/main/java/appeng/api/parts/IStorageBus.java create mode 100644 src/main/java/appeng/api/storage/StorageName.java delete mode 100644 src/main/java/appeng/client/gui/AEBaseMEGui.java create mode 100644 src/main/java/appeng/client/gui/GuiSub.java create mode 100644 src/main/java/appeng/client/gui/IGuiSub.java create mode 100644 src/main/java/appeng/client/gui/implementations/GuiBusIO.java delete mode 100644 src/main/java/appeng/client/gui/implementations/GuiWirelessTerm.java create mode 100644 src/main/java/appeng/client/gui/slots/VirtualMEMonitorableSlot.java create mode 100644 src/main/java/appeng/client/gui/slots/VirtualMEPatternSlot.java create mode 100644 src/main/java/appeng/client/gui/slots/VirtualMEPhantomSlot.java create mode 100644 src/main/java/appeng/client/gui/slots/VirtualMEPinSlot.java create mode 100644 src/main/java/appeng/client/gui/slots/VirtualMESlot.java create mode 100644 src/main/java/appeng/client/gui/slots/VirtualMESlotSingle.java delete mode 100644 src/main/java/appeng/client/me/InternalSlotME.java delete mode 100644 src/main/java/appeng/client/me/PinSlotME.java delete mode 100644 src/main/java/appeng/client/me/SlotDisconnected.java delete mode 100644 src/main/java/appeng/client/me/SlotME.java create mode 100644 src/main/java/appeng/container/ContainerSubGui.java create mode 100644 src/main/java/appeng/container/PrimaryGui.java create mode 100644 src/main/java/appeng/container/implementations/ContainerBusIO.java delete mode 100644 src/main/java/appeng/container/implementations/ContainerWirelessTerm.java create mode 100644 src/main/java/appeng/container/interfaces/IContainerSubGui.java create mode 100644 src/main/java/appeng/container/interfaces/IVirtualSlotHolder.java create mode 100644 src/main/java/appeng/container/interfaces/IVirtualSlotSource.java create mode 100644 src/main/java/appeng/core/sync/packets/PacketMonitorableAction.java delete mode 100644 src/main/java/appeng/core/sync/packets/PacketPatternItemRenamer.java create mode 100644 src/main/java/appeng/core/sync/packets/PacketVirtualSlot.java create mode 100644 src/main/java/appeng/helpers/ICustomButtonDataObject.java create mode 100644 src/main/java/appeng/helpers/ICustomButtonProvider.java create mode 100644 src/main/java/appeng/helpers/ICustomButtonSource.java create mode 100644 src/main/java/appeng/helpers/IPrimaryGuiIconProvider.java create mode 100644 src/main/java/appeng/helpers/MonitorableAction.java create mode 100644 src/main/java/appeng/items/AEBaseCell.java create mode 100644 src/main/java/appeng/items/AEBaseInfiniteCell.java create mode 100644 src/main/java/appeng/items/AEBasePortableCell.java create mode 100644 src/main/java/appeng/items/contents/CellConfigLegacy.java create mode 100644 src/main/java/appeng/items/contents/CellConfigLegacyWrapper.java create mode 100644 src/main/java/appeng/items/contents/PinList.java create mode 100644 src/main/java/appeng/items/contents/WirelessCraftingTerminalGuiObject.java create mode 100644 src/main/java/appeng/items/contents/WirelessInterfaceTerminalGuiObject.java create mode 100644 src/main/java/appeng/items/contents/WirelessPatternTerminalGuiObject.java create mode 100644 src/main/java/appeng/me/storage/FluidCellInventory.java create mode 100644 src/main/java/appeng/me/storage/FluidCellInventoryHandler.java create mode 100644 src/main/java/appeng/me/storage/ItemCellInventory.java create mode 100644 src/main/java/appeng/me/storage/ItemCellInventoryHandler.java create mode 100644 src/main/java/appeng/parts/automation/PartBaseExportBus.java create mode 100644 src/main/java/appeng/parts/automation/PartBaseImportBus.java create mode 100644 src/main/java/appeng/tile/inventory/IAEStackInventory.java create mode 100644 src/main/java/appeng/tile/inventory/IIAEStackInventory.java create mode 100644 src/main/java/appeng/util/FluidUtils.java diff --git a/repositories.gradle b/repositories.gradle index 98d4fb9a5..5f33d7150 100644 --- a/repositories.gradle +++ b/repositories.gradle @@ -1,6 +1,7 @@ // Add any additional repositories for your dependencies here repositories { + mavenLocal() maven { name 'MM repo' url 'https://maven.k-4u.nl/' diff --git a/src/main/java/appeng/api/features/ILevelViewable.java b/src/main/java/appeng/api/features/ILevelViewable.java new file mode 100644 index 000000000..e1ab84c98 --- /dev/null +++ b/src/main/java/appeng/api/features/ILevelViewable.java @@ -0,0 +1,34 @@ +package appeng.api.features; + +import net.minecraft.tileentity.TileEntity; +import net.minecraftforge.common.util.ForgeDirection; + +import appeng.api.networking.IGridHost; +import appeng.api.util.DimensionalCoord; +import appeng.helpers.ICustomNameObject; + +public interface ILevelViewable extends IGridHost, ICustomNameObject { + + DimensionalCoord getLocation(); + + TileEntity getTile(); + + ForgeDirection getSide(); + + /** + * Number of rows to expect. This is used with {@link #rowSize()} to determine how to render the slots. + */ + default int rows() { + return 1; + }; + + /** + * Number of slots per row. + */ + default int rowSize() { + return 1; + }; + + LevelItemInfo[] getLevelItemInfoList(); + +} diff --git a/src/main/java/appeng/api/features/IWirelessTermHandler.java b/src/main/java/appeng/api/features/IWirelessTermHandler.java index b6807ea64..7b5ecf5cd 100644 --- a/src/main/java/appeng/api/features/IWirelessTermHandler.java +++ b/src/main/java/appeng/api/features/IWirelessTermHandler.java @@ -47,6 +47,14 @@ public interface IWirelessTermHandler extends INetworkEncodable { */ boolean hasPower(EntityPlayer player, double amount, ItemStack is); + default boolean hasInfinityPower(ItemStack is) { + return false; + } + + default boolean hasInfinityRange(ItemStack is) { + return false; + } + /** * Return the config manager for the wireless terminal. * diff --git a/src/main/java/appeng/api/features/IWirelessTermRegistry.java b/src/main/java/appeng/api/features/IWirelessTermRegistry.java index f9aec79cd..c7c7dba9d 100644 --- a/src/main/java/appeng/api/features/IWirelessTermRegistry.java +++ b/src/main/java/appeng/api/features/IWirelessTermRegistry.java @@ -45,4 +45,6 @@ public interface IWirelessTermRegistry { * opens the wireless terminal gui, the wireless terminal item, must be in the active slot on the tool bar. */ void openWirelessTerminalGui(ItemStack item, World w, EntityPlayer player); + + boolean performCheck(final ItemStack item, final EntityPlayer player); } diff --git a/src/main/java/appeng/api/features/LevelItemInfo.java b/src/main/java/appeng/api/features/LevelItemInfo.java new file mode 100644 index 000000000..b53034591 --- /dev/null +++ b/src/main/java/appeng/api/features/LevelItemInfo.java @@ -0,0 +1,20 @@ +package appeng.api.features; + +import javax.annotation.Nonnull; + +import appeng.api.storage.data.IAEStack; + +public class LevelItemInfo { + + public IAEStack stack; + public long quantity; + public long batchSize; + public LevelState state; + + public LevelItemInfo(@Nonnull IAEStack stack, long quantity, long batchSize, LevelState state) { + this.stack = stack; + this.quantity = quantity; + this.batchSize = batchSize; + this.state = state; + } +} diff --git a/src/main/java/appeng/api/features/LevelState.java b/src/main/java/appeng/api/features/LevelState.java new file mode 100644 index 000000000..6741985b7 --- /dev/null +++ b/src/main/java/appeng/api/features/LevelState.java @@ -0,0 +1,11 @@ +package appeng.api.features; + +public enum LevelState { + None, + Idle, + Craft, + Export, + Error, + NotFound, + CantCraft +} diff --git a/src/main/java/appeng/api/implementations/guiobjects/IGuiItem.java b/src/main/java/appeng/api/implementations/guiobjects/IGuiItem.java index 210745fe6..b6f2a92d1 100644 --- a/src/main/java/appeng/api/implementations/guiobjects/IGuiItem.java +++ b/src/main/java/appeng/api/implementations/guiobjects/IGuiItem.java @@ -13,6 +13,7 @@ package appeng.api.implementations.guiobjects; +import net.minecraft.entity.player.EntityPlayer; import net.minecraft.item.ItemStack; import net.minecraft.world.World; @@ -21,5 +22,12 @@ import net.minecraft.world.World; */ public interface IGuiItem { - IGuiItemObject getGuiObject(ItemStack is, World world, int x, int y, int z); + @Deprecated + default IGuiItemObject getGuiObject(ItemStack is, World world, int x, int y, int z) { + return getGuiObject(is, world, null, x, y, z); + } + + default IGuiItemObject getGuiObject(ItemStack is, World world, EntityPlayer player, int x, int y, int z) { + return null; + } } diff --git a/src/main/java/appeng/api/implementations/guiobjects/IPortableCell.java b/src/main/java/appeng/api/implementations/guiobjects/IPortableCell.java index 72c7f6aac..385ab3cbe 100644 --- a/src/main/java/appeng/api/implementations/guiobjects/IPortableCell.java +++ b/src/main/java/appeng/api/implementations/guiobjects/IPortableCell.java @@ -14,12 +14,17 @@ package appeng.api.implementations.guiobjects; import appeng.api.networking.energy.IEnergySource; -import appeng.api.storage.IMEMonitor; import appeng.api.storage.ITerminalHost; -import appeng.api.storage.data.IAEItemStack; +import appeng.container.interfaces.IInventorySlotAware; +import appeng.core.localization.GuiText; /** * Obtained via {@link IGuiItem} getGuiObject */ -public interface IPortableCell extends ITerminalHost, IMEMonitor, IEnergySource, IGuiItemObject { +public interface IPortableCell extends ITerminalHost, IEnergySource, IGuiItemObject, IInventorySlotAware { + + @Override + default GuiText getName() { + return GuiText.PortableCell; + } } diff --git a/src/main/java/appeng/api/implementations/items/IStorageCell.java b/src/main/java/appeng/api/implementations/items/IStorageCell.java index cb36eabc6..47c0c402d 100644 --- a/src/main/java/appeng/api/implementations/items/IStorageCell.java +++ b/src/main/java/appeng/api/implementations/items/IStorageCell.java @@ -18,7 +18,9 @@ import javax.annotation.Nullable; import net.minecraft.item.ItemStack; import appeng.api.storage.ICellWorkbenchItem; +import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; /** * Any item which implements this can be treated as an IMEInventory via Util.getCell / Util.isCell It automatically @@ -69,15 +71,21 @@ public interface IStorageCell extends ICellWorkbenchItem { */ int getTotalTypes(ItemStack cellItem); + @Deprecated + default boolean isBlackListed(ItemStack cellItem, IAEItemStack requestedAddition) { + return this.isBlackListed(requestedAddition); + } + /** * Allows you to fine tune which items are allowed on a given cell, if you don't care, just return false; As the * handler for this type of cell is still the default cells, the normal AE black list is also applied. * - * @param cellItem item * @param requestedAddition requested addition * @return true to preventAdditionOfItem */ - boolean isBlackListed(ItemStack cellItem, IAEItemStack requestedAddition); + default boolean isBlackListed(IAEStack requestedAddition) { + return false; + } /** * Allows you to specify if this storage cell can be stored inside other storage cells, only set this for special @@ -111,4 +119,8 @@ public interface IStorageCell extends ICellWorkbenchItem { * @return drain in ae/t this storage cell will use. */ double getIdleDrain(); + + default StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } } diff --git a/src/main/java/appeng/api/implementations/tiles/ICellWorkbench.java b/src/main/java/appeng/api/implementations/tiles/ICellWorkbench.java new file mode 100644 index 000000000..7e43536e0 --- /dev/null +++ b/src/main/java/appeng/api/implementations/tiles/ICellWorkbench.java @@ -0,0 +1,24 @@ +package appeng.api.implementations.tiles; + +import net.minecraft.inventory.IInventory; + +import appeng.api.implementations.IUpgradeableHost; +import appeng.api.storage.ICellWorkbenchItem; +import appeng.api.storage.StorageChannel; +import appeng.helpers.ICellRestriction; +import appeng.helpers.IOreFilterable; +import appeng.tile.inventory.IAEAppEngInventory; +import appeng.tile.inventory.IIAEStackInventory; +import appeng.util.IConfigManagerHost; + +public interface ICellWorkbench extends IUpgradeableHost, IAEAppEngInventory, IConfigManagerHost, IOreFilterable, + ICellRestriction, IIAEStackInventory { + + ICellWorkbenchItem getCell(); + + boolean isSame(ICellWorkbench cellWorkbench); + + IInventory getCellUpgradeInventory(); + + StorageChannel getStorageChannel(); +} diff --git a/src/main/java/appeng/api/networking/crafting/ICraftingCPU.java b/src/main/java/appeng/api/networking/crafting/ICraftingCPU.java index 9cd101611..0089a22e4 100644 --- a/src/main/java/appeng/api/networking/crafting/ICraftingCPU.java +++ b/src/main/java/appeng/api/networking/crafting/ICraftingCPU.java @@ -24,7 +24,7 @@ import appeng.api.util.CraftCancelListener; import appeng.api.util.CraftCompleteListener; import appeng.api.util.CraftUpdateListener; -public interface ICraftingCPU extends IBaseMonitor { +public interface ICraftingCPU extends IBaseMonitor { /** * @return true if the CPU currently has a job. diff --git a/src/main/java/appeng/api/networking/crafting/ICraftingGrid.java b/src/main/java/appeng/api/networking/crafting/ICraftingGrid.java index 0b027a18f..3da3bca15 100644 --- a/src/main/java/appeng/api/networking/crafting/ICraftingGrid.java +++ b/src/main/java/appeng/api/networking/crafting/ICraftingGrid.java @@ -52,6 +52,10 @@ public interface ICraftingGrid extends IGridCache { @Deprecated ImmutableMap> getCraftingPatterns(); + @Deprecated + Future beginCraftingJob(World world, IGrid grid, BaseActionSource actionSrc, IAEItemStack craftWhat, + ICraftingCallback callback); + /** * Begin calculating a crafting job. * @@ -63,7 +67,7 @@ public interface ICraftingGrid extends IGridCache { * @return a future which will at an undetermined point in the future get you the {@link ICraftingJob} do not wait * on this, your be waiting forever. */ - Future beginCraftingJob(World world, IGrid grid, BaseActionSource actionSrc, IAEItemStack craftWhat, + Future beginCraftingJob(World world, IGrid grid, BaseActionSource actionSrc, IAEStack craftWhat, ICraftingCallback callback); /** diff --git a/src/main/java/appeng/api/networking/crafting/ICraftingProviderHelper.java b/src/main/java/appeng/api/networking/crafting/ICraftingProviderHelper.java index 850c84980..d3756ee5a 100644 --- a/src/main/java/appeng/api/networking/crafting/ICraftingProviderHelper.java +++ b/src/main/java/appeng/api/networking/crafting/ICraftingProviderHelper.java @@ -14,6 +14,7 @@ package appeng.api.networking.crafting; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; /** * Passed to a ICraftingProvider as a interface to manipulate the available crafting jobs. @@ -25,8 +26,11 @@ public interface ICraftingProviderHelper { */ void addCraftingOption(ICraftingMedium medium, ICraftingPatternDetails api); + @Deprecated + void setEmitable(IAEItemStack what); + /** * Set an item can Emitable */ - void setEmitable(IAEItemStack what); + void setEmitable(IAEStack what); } diff --git a/src/main/java/appeng/api/networking/crafting/ICraftingRequester.java b/src/main/java/appeng/api/networking/crafting/ICraftingRequester.java index d50892891..e38abe7d2 100644 --- a/src/main/java/appeng/api/networking/crafting/ICraftingRequester.java +++ b/src/main/java/appeng/api/networking/crafting/ICraftingRequester.java @@ -18,6 +18,7 @@ import com.google.common.collect.ImmutableSet; import appeng.api.config.Actionable; import appeng.api.networking.security.IActionHost; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; public interface ICraftingRequester extends IActionHost { @@ -37,7 +38,15 @@ public interface ICraftingRequester extends IActionHost { * @param mode action mode * @return unwanted item */ - IAEItemStack injectCraftedItems(ICraftingLink link, IAEItemStack items, Actionable mode); + + default IAEStack injectCraftedItems(ICraftingLink link, IAEStack items, Actionable mode) { + return null; + } + + @Deprecated + default IAEItemStack injectCraftedItems(ICraftingLink link, IAEItemStack items, Actionable mode) { + return (IAEItemStack) injectCraftedItems(link, (IAEStack) items, mode); + } /** * called when the job changes from in progress, to either complete, or canceled. diff --git a/src/main/java/appeng/api/networking/storage/IBaseMonitor.java b/src/main/java/appeng/api/networking/storage/IBaseMonitor.java index b2da7fc54..4b4909c20 100644 --- a/src/main/java/appeng/api/networking/storage/IBaseMonitor.java +++ b/src/main/java/appeng/api/networking/storage/IBaseMonitor.java @@ -21,10 +21,10 @@ public interface IBaseMonitor { /** * add a new Listener to the monitor, be sure to properly remove yourself when your done. */ - void addListener(IMEMonitorHandlerReceiver l, Object verificationToken); + void addListener(IMEMonitorHandlerReceiver l, Object verificationToken); /** * remove a Listener to the monitor. */ - void removeListener(IMEMonitorHandlerReceiver l); + void removeListener(IMEMonitorHandlerReceiver l); } diff --git a/src/main/java/appeng/api/networking/storage/IStorageGrid.java b/src/main/java/appeng/api/networking/storage/IStorageGrid.java index cb6dc7d11..5e695b840 100644 --- a/src/main/java/appeng/api/networking/storage/IStorageGrid.java +++ b/src/main/java/appeng/api/networking/storage/IStorageGrid.java @@ -37,7 +37,7 @@ public interface IStorageGrid extends IGridCache, IStorageMonitorable { * * @param input injected items */ - void postAlterationOfStoredItems(StorageChannel chan, Iterable input, BaseActionSource src); + void postAlterationOfStoredItems(StorageChannel chan, Iterable> input, BaseActionSource src); /** * Used to add a cell provider to the storage system diff --git a/src/main/java/appeng/api/parts/ICraftingTerminal.java b/src/main/java/appeng/api/parts/ICraftingTerminal.java new file mode 100644 index 000000000..7ee62dbd2 --- /dev/null +++ b/src/main/java/appeng/api/parts/ICraftingTerminal.java @@ -0,0 +1,12 @@ +package appeng.api.parts; + +import appeng.api.implementations.tiles.ISegmentedInventory; +import appeng.api.implementations.tiles.IViewCellStorage; +import appeng.api.storage.ITerminalHost; +import appeng.api.storage.ITerminalPins; +import appeng.tile.inventory.IAEAppEngInventory; +import appeng.util.IConfigManagerHost; + +public interface ICraftingTerminal extends ITerminalHost, IConfigManagerHost, IViewCellStorage, IAEAppEngInventory, + ITerminalPins, ISegmentedInventory { +} diff --git a/src/main/java/appeng/api/parts/IInterfaceTerminal.java b/src/main/java/appeng/api/parts/IInterfaceTerminal.java new file mode 100644 index 000000000..2bba9bc3d --- /dev/null +++ b/src/main/java/appeng/api/parts/IInterfaceTerminal.java @@ -0,0 +1,13 @@ +package appeng.api.parts; + +import appeng.api.networking.security.IActionHost; +import appeng.core.localization.GuiText; + +public interface IInterfaceTerminal extends IActionHost { + + boolean needsUpdate(); + + default GuiText getName() { + return GuiText.InterfaceTerminal; + } +} diff --git a/src/main/java/appeng/api/parts/ILevelEmitter.java b/src/main/java/appeng/api/parts/ILevelEmitter.java new file mode 100644 index 000000000..4a8808493 --- /dev/null +++ b/src/main/java/appeng/api/parts/ILevelEmitter.java @@ -0,0 +1,21 @@ +package appeng.api.parts; + +import appeng.api.features.ILevelViewable; +import appeng.api.implementations.IUpgradeableHost; +import appeng.api.networking.crafting.ICraftingProvider; +import appeng.api.networking.crafting.ICraftingWatcherHost; +import appeng.api.networking.energy.IEnergyWatcherHost; +import appeng.api.networking.storage.IStackWatcherHost; +import appeng.api.networking.ticking.IGridTickable; +import appeng.api.storage.IMEMonitorHandlerReceiver; +import appeng.api.storage.data.IAEStack; +import appeng.tile.inventory.IIAEStackInventory; + +public interface ILevelEmitter + extends IEnergyWatcherHost, IStackWatcherHost, ICraftingWatcherHost, IMEMonitorHandlerReceiver>, + ICraftingProvider, IGridTickable, IUpgradeableHost, IIAEStackInventory, ILevelViewable { + + void setReportingValue(final long v); + + long getReportingValue(); +} diff --git a/src/main/java/appeng/api/parts/IPatternTerminal.java b/src/main/java/appeng/api/parts/IPatternTerminal.java new file mode 100644 index 000000000..d59dcbb77 --- /dev/null +++ b/src/main/java/appeng/api/parts/IPatternTerminal.java @@ -0,0 +1,99 @@ +package appeng.api.parts; + +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.world.World; + +import appeng.api.implementations.ICraftingPatternItem; +import appeng.api.implementations.tiles.IViewCellStorage; +import appeng.api.networking.crafting.ICraftingPatternDetails; +import appeng.api.networking.security.IActionHost; +import appeng.api.storage.ITerminalHost; +import appeng.api.storage.ITerminalPins; +import appeng.api.storage.data.IAEStack; +import appeng.helpers.PatternHelper; +import appeng.helpers.UltimatePatternHelper; +import appeng.items.misc.ItemEncodedPattern; +import appeng.tile.inventory.IAEAppEngInventory; +import appeng.tile.inventory.IAEStackInventory; +import appeng.tile.inventory.IIAEStackInventory; +import appeng.util.IConfigManagerHost; + +public interface IPatternTerminal extends IIAEStackInventory, ITerminalHost, IConfigManagerHost, IViewCellStorage, + IAEAppEngInventory, ITerminalPins, IActionHost { + + boolean isCraftingRecipe(); + + void setCraftingRecipe(final boolean craftingMode); + + boolean isSubstitution(); + + boolean canBeSubstitution(); + + void setSubstitution(boolean canSubstitute); + + void setCanBeSubstitution(boolean beSubstitute); + + IInventory getInventoryByName(final String name); + + void exPatternTerminalCall(IAEStack[] in, IAEStack[] out); + + default void loadPatternFromItem(final ItemStack stack, World world, IAEStackInventory crafting, + IAEStackInventory output) { + if (stack != null && stack.getItem() instanceof ICraftingPatternItem pattern) { + final NBTTagCompound encodedValue = stack.getTagCompound(); + + if (encodedValue != null) { + final ICraftingPatternDetails details = pattern.getPatternForItem(stack, world); + final boolean substitute = encodedValue.getBoolean("substitute"); + final boolean beSubstitute = encodedValue.getBoolean("beSubstitute"); + final boolean isCrafting = encodedValue.getBoolean("crafting"); + final IAEStack[] inItems; + final IAEStack[] outItems; + + if (details == null) { + if (stack.getItem() instanceof ItemEncodedPattern) { + inItems = PatternHelper.loadIAEItemStackFromNBT(encodedValue.getTagList("in", 10), true, null); + outItems = PatternHelper + .loadIAEItemStackFromNBT(encodedValue.getTagList("out", 10), true, null); + } else { + inItems = UltimatePatternHelper + .loadIAEStackFromNBT(encodedValue.getTagList("in", 10), true, null); + outItems = UltimatePatternHelper + .loadIAEStackFromNBT(encodedValue.getTagList("out", 10), true, null); + } + } else { + inItems = details.getAEInputs(); + outItems = details.getAEOutputs(); + } + + this.setCraftingRecipe(isCrafting); + this.setSubstitution(substitute); + this.setCanBeSubstitution(beSubstitute); + + exPatternTerminalCall(inItems, outItems); + + for (int x = 0; x < crafting.getSizeInventory(); x++) { + crafting.putAEStackInSlot(x, null); + } + + for (int x = 0; x < output.getSizeInventory(); x++) { + output.putAEStackInSlot(x, null); + } + + for (int x = 0; x < crafting.getSizeInventory() && x < inItems.length; x++) { + if (inItems[x] != null) { + crafting.putAEStackInSlot(x, inItems[x]); + } + } + + for (int x = 0; x < output.getSizeInventory() && x < outItems.length; x++) { + if (outItems[x] != null) { + output.putAEStackInSlot(x, outItems[x]); + } + } + } + } + } +} diff --git a/src/main/java/appeng/api/parts/IPatternTerminalEx.java b/src/main/java/appeng/api/parts/IPatternTerminalEx.java new file mode 100644 index 000000000..1ad1ca3cc --- /dev/null +++ b/src/main/java/appeng/api/parts/IPatternTerminalEx.java @@ -0,0 +1,12 @@ +package appeng.api.parts; + +public interface IPatternTerminalEx extends IPatternTerminal { + + boolean isInverted(); + + void setInverted(boolean inverted); + + int getActivePage(); + + void setActivePage(int activePage); +} diff --git a/src/main/java/appeng/api/parts/IStorageBus.java b/src/main/java/appeng/api/parts/IStorageBus.java new file mode 100644 index 000000000..f68dc132f --- /dev/null +++ b/src/main/java/appeng/api/parts/IStorageBus.java @@ -0,0 +1,40 @@ +package appeng.api.parts; + +import appeng.api.AEApi; +import appeng.api.implementations.IUpgradeableHost; +import appeng.api.networking.ticking.IGridTickable; +import appeng.api.storage.ICellContainer; +import appeng.api.storage.IMEMonitorHandlerReceiver; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEStack; +import appeng.api.storage.data.IItemList; +import appeng.helpers.IOreFilterable; +import appeng.helpers.IPrimaryGuiIconProvider; +import appeng.helpers.IPriorityHost; +import appeng.integration.IntegrationType; +import appeng.me.storage.MEInventoryHandler; +import appeng.tile.inventory.IIAEStackInventory; +import appeng.transformer.annotations.Integration.Interface; +import appeng.util.IConfigManagerHost; +import buildcraft.api.transport.IPipeConnection; + +@Interface(iname = IntegrationType.BuildCraftTransport, iface = "buildcraft.api.transport.IPipeConnection") +public interface IStorageBus + extends IGridTickable, ICellContainer, IMEMonitorHandlerReceiver>, IPipeConnection, IPriorityHost, + IOreFilterable, IConfigManagerHost, IUpgradeableHost, IIAEStackInventory, IPrimaryGuiIconProvider { + + boolean needSyncGUI(); + + void setNeedSyncGUI(boolean needSyncGUI); + + MEInventoryHandler getInternalHandler(); + + StorageChannel getStorageChannel(); + + default IItemList getItemList() { + return switch (getStorageChannel()) { + case ITEMS -> AEApi.instance().storage().createItemList(); + case FLUIDS -> AEApi.instance().storage().createFluidList(); + }; + } +} diff --git a/src/main/java/appeng/api/storage/ICellCacheRegistry.java b/src/main/java/appeng/api/storage/ICellCacheRegistry.java index 23d83d094..46682bb8a 100644 --- a/src/main/java/appeng/api/storage/ICellCacheRegistry.java +++ b/src/main/java/appeng/api/storage/ICellCacheRegistry.java @@ -22,6 +22,10 @@ public interface ICellCacheRegistry { int getCellStatus(); + default StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } + TYPE getCellType(); enum TYPE { diff --git a/src/main/java/appeng/api/storage/ICellInventory.java b/src/main/java/appeng/api/storage/ICellInventory.java index 7ffec6085..066e85580 100644 --- a/src/main/java/appeng/api/storage/ICellInventory.java +++ b/src/main/java/appeng/api/storage/ICellInventory.java @@ -17,9 +17,12 @@ import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import appeng.api.config.FuzzyMode; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.items.contents.CellConfigLegacy; +import appeng.items.contents.CellConfigLegacyWrapper; +import appeng.tile.inventory.IAEStackInventory; -public interface ICellInventory extends IMEInventory { +public interface ICellInventory> extends IMEInventory { /** * @return the item stack of this storage cell. @@ -38,8 +41,19 @@ public interface ICellInventory extends IMEInventory { /** * @return access configured list + * @deprecated Use {@link ICellInventory#getConfigAEInventory()} */ - IInventory getConfigInventory(); + @Deprecated + default IInventory getConfigInventory() { + return new CellConfigLegacy(this.getConfigAEInventory(), this.getChannel()); + } + + /** + * @return access configured list + */ + default IAEStackInventory getConfigAEInventory() { + return new CellConfigLegacyWrapper(this.getConfigInventory()); + } /** * @return access installed upgrades. @@ -99,7 +113,7 @@ public interface ICellInventory extends IMEInventory { /** * @return how many more items can be stored with Distribution card. */ - long getRemainingItemsCountDist(IAEItemStack l); + long getRemainingItemsCountDist(StackType l); /** * @return how many items can be added without consuming another byte. diff --git a/src/main/java/appeng/api/storage/ICellInventoryHandler.java b/src/main/java/appeng/api/storage/ICellInventoryHandler.java index 860e444a7..20b9c92fa 100644 --- a/src/main/java/appeng/api/storage/ICellInventoryHandler.java +++ b/src/main/java/appeng/api/storage/ICellInventoryHandler.java @@ -14,14 +14,14 @@ package appeng.api.storage; import appeng.api.config.IncludeExclude; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; -public interface ICellInventoryHandler extends IMEInventoryHandler { +public interface ICellInventoryHandler> extends IMEInventoryHandler { /** * @return get access to the Cell Inventory. */ - ICellInventory getCellInv(); + ICellInventory getCellInv(); boolean isPreformatted(); diff --git a/src/main/java/appeng/api/storage/ICellWorkbenchItem.java b/src/main/java/appeng/api/storage/ICellWorkbenchItem.java index 95f475846..54d534585 100644 --- a/src/main/java/appeng/api/storage/ICellWorkbenchItem.java +++ b/src/main/java/appeng/api/storage/ICellWorkbenchItem.java @@ -17,6 +17,9 @@ import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import appeng.api.config.FuzzyMode; +import appeng.items.contents.CellConfigLegacy; +import appeng.items.contents.CellConfigLegacyWrapper; +import appeng.tile.inventory.IAEStackInventory; public interface ICellWorkbenchItem { @@ -36,6 +39,11 @@ public interface ICellWorkbenchItem { */ IInventory getUpgradesInventory(ItemStack is); + @Deprecated + default IInventory getConfigInventory(ItemStack is) { + return new CellConfigLegacy(this.getConfigAEInventory(is), this.getStorageChannel()); + } + /** * Used to extract, or mirror the contents of the work bench onto the cell. *

@@ -43,7 +51,9 @@ public interface ICellWorkbenchItem { *

* onInventoryChange will be called when saving is needed. */ - IInventory getConfigInventory(ItemStack is); + default IAEStackInventory getConfigAEInventory(ItemStack is) { + return new CellConfigLegacyWrapper(this.getConfigInventory(is)); + } /** * @return the current fuzzy status. @@ -68,4 +78,8 @@ public interface ICellWorkbenchItem { * @param filter new ore dictionary filter */ default void setOreFilter(ItemStack is, String filter) {} + + default StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } } diff --git a/src/main/java/appeng/api/storage/ITerminalHost.java b/src/main/java/appeng/api/storage/ITerminalHost.java index e18c7a453..543498375 100644 --- a/src/main/java/appeng/api/storage/ITerminalHost.java +++ b/src/main/java/appeng/api/storage/ITerminalHost.java @@ -14,6 +14,12 @@ package appeng.api.storage; import appeng.api.util.IConfigurableObject; +import appeng.core.localization.GuiText; public interface ITerminalHost extends IStorageMonitorable, IConfigurableObject { + + default GuiText getName() { + return GuiText.Terminal; + } + } diff --git a/src/main/java/appeng/api/storage/MEMonitorHandler.java b/src/main/java/appeng/api/storage/MEMonitorHandler.java index a34ff3f3c..9624c1a76 100644 --- a/src/main/java/appeng/api/storage/MEMonitorHandler.java +++ b/src/main/java/appeng/api/storage/MEMonitorHandler.java @@ -34,11 +34,11 @@ import appeng.util.IterationCounter; * * @param */ -public class MEMonitorHandler implements IMEMonitor { +public class MEMonitorHandler> implements IMEMonitor { private final IMEInventoryHandler internalHandler; private final IItemList cachedList; - private final HashMap, Object> listeners = new HashMap<>(); + private final HashMap listeners = new HashMap<>(); protected boolean hasChanged = true; @@ -53,12 +53,12 @@ public class MEMonitorHandler implements IMEMonitor< } @Override - public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { + public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { this.listeners.put(l, verificationToken); } @Override - public void removeListener(final IMEMonitorHandlerReceiver l) { + public void removeListener(final IMEMonitorHandlerReceiver l) { this.listeners.remove(l); } @@ -74,7 +74,7 @@ public class MEMonitorHandler implements IMEMonitor< return this.internalHandler; } - private StackType monitorDifference(final IAEStack original, final StackType leftOvers, final boolean extraction, + private StackType monitorDifference(final IAEStack original, final StackType leftOvers, final boolean extraction, final BaseActionSource src) { final StackType diff = (StackType) original.copy(); @@ -91,16 +91,16 @@ public class MEMonitorHandler implements IMEMonitor< return leftOvers; } - protected void postChangesToListeners(final Iterable changes, final BaseActionSource src) { + protected void postChangesToListeners(final Iterable> changes, final BaseActionSource src) { this.notifyListenersOfChange(changes, src); } - protected void notifyListenersOfChange(final Iterable diff, final BaseActionSource src) { + protected void notifyListenersOfChange(final Iterable> diff, final BaseActionSource src) { this.hasChanged = true; // need to update the cache. - final Iterator, Object>> i = this.getListeners(); + final Iterator> i = this.getListeners(); while (i.hasNext()) { - final Entry, Object> o = i.next(); - final IMEMonitorHandlerReceiver receiver = o.getKey(); + final Entry o = i.next(); + final IMEMonitorHandlerReceiver receiver = o.getKey(); if (receiver.isValid(o.getValue())) { receiver.postChange(this, diff, src); } else { @@ -109,7 +109,7 @@ public class MEMonitorHandler implements IMEMonitor< } } - protected Iterator, Object>> getListeners() { + protected Iterator> getListeners() { return this.listeners.entrySet().iterator(); } diff --git a/src/main/java/appeng/api/storage/StorageChannel.java b/src/main/java/appeng/api/storage/StorageChannel.java index a920d8141..0cbaa82e3 100644 --- a/src/main/java/appeng/api/storage/StorageChannel.java +++ b/src/main/java/appeng/api/storage/StorageChannel.java @@ -13,6 +13,9 @@ package appeng.api.storage; +import java.lang.reflect.ParameterizedType; +import java.lang.reflect.Type; + import appeng.api.AEApi; import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; @@ -44,4 +47,23 @@ public enum StorageChannel { return AEApi.instance().storage().createFluidList(); } } + + public IItemList createPrimitiveList() { + if (this == ITEMS) { + return AEApi.instance().storage().createPrimitiveItemList(); + } else { + return AEApi.instance().storage().createFluidList(); + } + } + + public static StorageChannel getStorageChannelByParametrizedClass(Class theClass) { + if (theClass.getGenericSuperclass() instanceof ParameterizedType parameterizedType) { + final Type type = parameterizedType.getActualTypeArguments()[0]; + + if (type == IAEItemStack.class) return StorageChannel.ITEMS; + else if (type == IAEFluidStack.class) return StorageChannel.FLUIDS; + } + + return null; + } } diff --git a/src/main/java/appeng/api/storage/StorageName.java b/src/main/java/appeng/api/storage/StorageName.java new file mode 100644 index 000000000..c21546e98 --- /dev/null +++ b/src/main/java/appeng/api/storage/StorageName.java @@ -0,0 +1,19 @@ +package appeng.api.storage; + +public enum StorageName { + + NONE(""), + CRAFTING_INPUT("crafting"), + CRAFTING_OUTPUT("output"), + CRAFTING_PATTERN("pattern"); + + private final String name; + + StorageName(String name) { + this.name = name; + } + + public String getName() { + return this.name; + } +} diff --git a/src/main/java/appeng/api/storage/data/IAEStack.java b/src/main/java/appeng/api/storage/data/IAEStack.java index be4103a1f..b356487a5 100644 --- a/src/main/java/appeng/api/storage/data/IAEStack.java +++ b/src/main/java/appeng/api/storage/data/IAEStack.java @@ -15,10 +15,16 @@ package appeng.api.storage.data; import java.io.IOException; +import javax.annotation.Nullable; + +import net.minecraft.client.Minecraft; +import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import appeng.api.config.FuzzyMode; import appeng.api.storage.StorageChannel; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; import io.netty.buffer.ByteBuf; public interface IAEStack { @@ -240,7 +246,21 @@ public interface IAEStack { String getDisplayName(); + String getModId(); + void setTagCompound(NBTTagCompound tag); boolean hasTagCompound(); + + @Nullable + ItemStack getItemStackForNEI(); + + @SideOnly(Side.CLIENT) + void drawInGui(Minecraft mc, int x, int y); + + @SideOnly(Side.CLIENT) + void drawOverlayInGui(Minecraft mc, int x, int y, boolean showAmount, boolean showAmountAlways, + boolean showCraftableText, boolean showCraftableIcon); + + int getPowerMultiplier(); } diff --git a/src/main/java/appeng/api/storage/data/IDisplayRepo.java b/src/main/java/appeng/api/storage/data/IDisplayRepo.java index 70b3001d3..1502b7b57 100644 --- a/src/main/java/appeng/api/storage/data/IDisplayRepo.java +++ b/src/main/java/appeng/api/storage/data/IDisplayRepo.java @@ -11,12 +11,18 @@ import appeng.helpers.IPinsHandler; */ public interface IDisplayRepo extends IPinsHandler { + @Deprecated void postUpdate(final IAEItemStack stack); + void postUpdate(final IAEStack stack); + void setViewCell(final ItemStack[] filters); + @Deprecated IAEItemStack getReferenceItem(int idx); + IAEStack getReferenceStack(int idx); + ItemStack getItem(int idx); void updateView(); @@ -40,8 +46,4 @@ public interface IDisplayRepo extends IPinsHandler { boolean isPaused(); void setPaused(boolean paused); - - default IItemList getAvailableItems() { - throw new UnsupportedOperationException("This method is not implemented for this IDisplayRepo."); - } } diff --git a/src/main/java/appeng/client/ActionKey.java b/src/main/java/appeng/client/ActionKey.java index fa51efeee..75ad5f20f 100644 --- a/src/main/java/appeng/client/ActionKey.java +++ b/src/main/java/appeng/client/ActionKey.java @@ -6,7 +6,9 @@ public enum ActionKey { TOGGLE_FOCUS(Keyboard.KEY_NONE), - SEARCH_CONNECTED_INVENTORIES(Keyboard.KEY_NONE); + SEARCH_CONNECTED_INVENTORIES(Keyboard.KEY_NONE), + + CONTROL_OPERATION(Keyboard.KEY_LCONTROL); private final int defaultKey; diff --git a/src/main/java/appeng/client/ClientHelper.java b/src/main/java/appeng/client/ClientHelper.java index c67610901..6d83ebc43 100644 --- a/src/main/java/appeng/client/ClientHelper.java +++ b/src/main/java/appeng/client/ClientHelper.java @@ -435,6 +435,11 @@ public class ClientHelper extends ServerHelper { return this.bindings.get(key).isPressed(); } + @Override + public int getKeybind(ActionKey key) { + return this.bindings.get(key).getKeyCode(); + } + @Override public boolean isActionKey(ActionKey key, int pressedKeyCode) { return isActiveAndMatches(this.bindings.get(key), pressedKeyCode); diff --git a/src/main/java/appeng/client/gui/AEBaseGui.java b/src/main/java/appeng/client/gui/AEBaseGui.java index 8381ce219..071844c31 100644 --- a/src/main/java/appeng/client/gui/AEBaseGui.java +++ b/src/main/java/appeng/client/gui/AEBaseGui.java @@ -16,11 +16,13 @@ import java.text.ParseException; import java.util.ArrayList; import java.util.Collection; import java.util.HashSet; -import java.util.LinkedList; import java.util.List; import java.util.Set; import java.util.concurrent.TimeUnit; +import javax.annotation.Nonnull; +import javax.annotation.Nullable; + import net.minecraft.client.Minecraft; import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.gui.GuiButton; @@ -45,12 +47,15 @@ import com.google.common.base.Joiner; import com.google.common.base.Stopwatch; import appeng.api.events.GuiScrollEvent; +import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.client.ActionKey; +import appeng.client.ClientHelper; +import appeng.client.gui.slots.VirtualMEPhantomSlot; +import appeng.client.gui.slots.VirtualMESlot; import appeng.client.gui.widgets.GuiScrollbar; import appeng.client.gui.widgets.ITooltip; -import appeng.client.me.InternalSlotME; -import appeng.client.me.SlotDisconnected; -import appeng.client.me.SlotME; import appeng.client.render.AppEngRenderItem; import appeng.client.render.TranslatedRenderItem; import appeng.container.AEBaseContainer; @@ -62,7 +67,6 @@ import appeng.container.slot.OptionalSlotRestrictedInput; import appeng.container.slot.SlotCraftingTerm; import appeng.container.slot.SlotDisabled; import appeng.container.slot.SlotFake; -import appeng.container.slot.SlotFakeCraftingMatrix; import appeng.container.slot.SlotInaccessible; import appeng.container.slot.SlotOutput; import appeng.container.slot.SlotPatternTerm; @@ -75,17 +79,17 @@ import appeng.core.localization.GuiText; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketInventoryAction; import appeng.core.sync.packets.PacketSwapSlots; +import appeng.helpers.ICustomButtonProvider; import appeng.helpers.InventoryAction; import appeng.integration.IntegrationRegistry; import appeng.integration.IntegrationType; import appeng.integration.abstraction.INEI; import appeng.util.Platform; -import appeng.util.item.AEItemStack; import codechicken.lib.gui.GuiDraw; import codechicken.nei.guihook.GuiContainerManager; import cpw.mods.fml.common.Loader; -public abstract class AEBaseGui extends GuiContainer { +public abstract class AEBaseGui extends GuiContainer implements IGuiTooltipHandler { private static class AEGuiTooltip { @@ -131,7 +135,6 @@ public abstract class AEBaseGui extends GuiContainer { } private static boolean switchingGuis; - private final List meSlots = new LinkedList<>(); // drag y protected final Set drag_click = new HashSet<>(); public static final AppEngRenderItem aeRenderItem = new AppEngRenderItem(); @@ -143,12 +146,18 @@ public abstract class AEBaseGui extends GuiContainer { private ItemStack dbl_whichItem; private Slot bl_clicked; private boolean subGui; + private static int controlKey; + + private final List virtualSlots = new ArrayList<>(); + private final List draggedSlots = new ArrayList<>(); + private VirtualMESlot hoveredVirtualSlot = null; public AEBaseGui(final Container container) { super(container); this.subGui = switchingGuis; switchingGuis = false; aeRenderItem.parent = this; + controlKey = ClientHelper.proxy.getKeybind(ActionKey.CONTROL_OPERATION); } protected static String join(final Collection toolTip, final String delimiter) { @@ -174,12 +183,11 @@ public abstract class AEBaseGui extends GuiContainer { public void initGui() { super.initGui(); - final List slots = this.getInventorySlots(); - slots.removeIf(SlotME.class::isInstance); + this.virtualSlots.clear(); + } - for (final InternalSlotME me : this.meSlots) { - slots.add(new SlotME(me)); - } + protected void registerVirtualSlots(VirtualMESlot slot) { + virtualSlots.add(slot); } @SuppressWarnings("unchecked") @@ -315,6 +323,9 @@ public abstract class AEBaseGui extends GuiContainer { this.currentToolTip.shift(ox, oy); this.drawFG(ox, oy, x, y); this.currentToolTip.shift(0, 0); + + this.hoveredVirtualSlot = null; + this.drawVirtualSlots(this.virtualSlots, x, y); } public abstract void drawFG(int offsetX, int offsetY, int mouseX, int mouseY); @@ -360,6 +371,10 @@ public abstract class AEBaseGui extends GuiContainer { @Override protected void mouseClicked(final int xCoord, final int yCoord, final int btn) { this.drag_click.clear(); + this.draggedSlots.clear(); + + final VirtualMESlot slot = getVirtualMESlotUnderMouse(); + if (slot != null && this.handleVirtualSlotClick(slot, btn)) return; if (btn == 1) { for (final Object o : this.buttonList) { @@ -378,8 +393,49 @@ public abstract class AEBaseGui extends GuiContainer { super.mouseClicked(xCoord, yCoord, btn); } + protected boolean handleVirtualSlotClick(final VirtualMESlot slot, final int mouseButton) { + if (slot instanceof VirtualMEPhantomSlot vSlot) { + this.handlePhantomSlotInteraction(vSlot, mouseButton); + + // Prevent double dragging + if (this.mc.thePlayer.inventory.getItemStack() != null + && !this.draggedSlots.contains(this.hoveredVirtualSlot)) { + this.draggedSlots.add(this.hoveredVirtualSlot); + } + } + + return false; + } + + protected void handleDragVirtualSlot(VirtualMESlot slot, int mouseButton) { + if (slot instanceof VirtualMEPhantomSlot patternSlot) { + this.handlePhantomSlotInteraction(patternSlot, mouseButton); + } + } + + protected void handlePhantomSlotInteraction(VirtualMEPhantomSlot slot, int mouseButton) { + slot.handleMouseClicked(true, true, isCtrlKeyDown(), mouseButton); + } + @Override protected void mouseClickMove(final int x, final int y, final int c, final long d) { + // Hold left or right mouse button + if (c == 0 || c == 1) { + // Update hovered slot + for (VirtualMESlot slot : virtualSlots) { + if (slot.isHovered(x - this.guiLeft + 1, y - this.guiTop + 1)) { + this.hoveredVirtualSlot = slot; + break; + } + } + + if (this.mc.thePlayer.inventory.getItemStack() != null && this.hoveredVirtualSlot != null + && !this.draggedSlots.contains(this.hoveredVirtualSlot)) { + this.draggedSlots.add(this.hoveredVirtualSlot); + this.handleDragVirtualSlot(this.hoveredVirtualSlot, c); + } + } + final Slot slot = this.getSlot(x, y); final ItemStack itemstack = this.mc.thePlayer.inventory.getItemStack(); @@ -398,36 +454,6 @@ public abstract class AEBaseGui extends GuiContainer { NetworkHandler.instance.sendToServer(p); } } - } else if (slot instanceof SlotDisconnected) { - this.drag_click.add(slot); - if (this.drag_click.size() > 1) { - if (itemstack != null) { - for (final Slot dr : this.drag_click) { - if (slot.getStack() == null) { - InventoryAction action = InventoryAction.SPLIT_OR_PLACE_SINGLE; - final PacketInventoryAction p = new PacketInventoryAction( - action, - dr.getSlotIndex(), - ((SlotDisconnected) slot).getSlot().getId()); - NetworkHandler.instance.sendToServer(p); - } - } - } else if (isShiftKeyDown()) { - for (final Slot dr : this.drag_click) { - InventoryAction action = null; - if (slot.getStack() != null) { - action = InventoryAction.SHIFT_CLICK; - } - if (action != null) { - final PacketInventoryAction p = new PacketInventoryAction( - action, - dr.getSlotIndex(), - ((SlotDisconnected) slot).getSlot().getId()); - NetworkHandler.instance.sendToServer(p); - } - } - } - } } else { super.mouseClickMove(x, y, c, d); } @@ -437,39 +463,18 @@ public abstract class AEBaseGui extends GuiContainer { protected void handleMouseClick(final Slot slot, final int slotIdx, final int ctrlDown, final int mouseButton) { final EntityPlayer player = Minecraft.getMinecraft().thePlayer; - if (mouseButton == 3) { - if (slot instanceof OptionalSlotFake || slot instanceof SlotFakeCraftingMatrix) { - if (slot.getHasStack()) { - InventoryAction action = InventoryAction.SET_PATTERN_VALUE; - if (isCtrlKeyDown()) { - action = InventoryAction.RENAME_PATTERN_ITEM; - } - - IAEItemStack stack = AEItemStack.create(slot.getStack()); - - ((AEBaseContainer) this.inventorySlots).setTargetStack(stack); - final PacketInventoryAction p = new PacketInventoryAction(action, slotIdx, 0); - NetworkHandler.instance.sendToServer(p); - - return; - } - } - - } else { - - if (slot instanceof SlotFake) { - final InventoryAction action = ctrlDown == 1 ? InventoryAction.SPLIT_OR_PLACE_SINGLE - : InventoryAction.PICKUP_OR_SET_DOWN; - - if (this.drag_click.size() > 1) { - return; - } - - final PacketInventoryAction p = new PacketInventoryAction(action, slotIdx, 0); - NetworkHandler.instance.sendToServer(p); + if (slot instanceof SlotFake) { + final InventoryAction action = ctrlDown == 1 ? InventoryAction.SPLIT_OR_PLACE_SINGLE + : InventoryAction.PICKUP_OR_SET_DOWN; + if (this.drag_click.size() > 1) { return; } + + final PacketInventoryAction p = new PacketInventoryAction(action, slotIdx, 0); + NetworkHandler.instance.sendToServer(p); + + return; } if (slot instanceof SlotPatternTerm) { @@ -503,118 +508,19 @@ public abstract class AEBaseGui extends GuiContainer { if (Keyboard.isKeyDown(Keyboard.KEY_SPACE)) { if (this.enableSpaceClicking() && !(slot instanceof SlotPatternTerm)) { - IAEItemStack stack = null; - if (slot instanceof SlotME) { - stack = ((SlotME) slot).getAEStack(); - } - int slotNum = this.getInventorySlots().size(); - if (!(slot instanceof SlotME) && slot != null) { + if (slot != null) { slotNum = slot.slotNumber; } - ((AEBaseContainer) this.inventorySlots).setTargetStack(stack); + ((AEBaseContainer) this.inventorySlots).setTargetStack(null); final PacketInventoryAction p = new PacketInventoryAction(InventoryAction.MOVE_REGION, slotNum, 0); NetworkHandler.instance.sendToServer(p); return; } } - if (slot instanceof SlotDisconnected) { - if (this.drag_click.size() > 1) { - return; - } - - InventoryAction action = null; - - switch (mouseButton) { - case 0 -> // pickup / set-down. - { - ItemStack heldStack = player.inventory.getItemStack(); - if (slot.getStack() == null && heldStack != null) action = InventoryAction.SPLIT_OR_PLACE_SINGLE; - else if (slot.getStack() != null && (heldStack == null || heldStack.stackSize <= 1)) - action = InventoryAction.PICKUP_OR_SET_DOWN; - } - case 1 -> action = ctrlDown == 1 ? InventoryAction.PICKUP_SINGLE : InventoryAction.SHIFT_CLICK; - case 3 -> { // creative dupe: - if (player.capabilities.isCreativeMode) { - action = InventoryAction.CREATIVE_DUPLICATE; - } - } // drop item: - default -> {} - } - - if (action != null) { - final PacketInventoryAction p = new PacketInventoryAction( - action, - slot.getSlotIndex(), - ((SlotDisconnected) slot).getSlot().getId()); - NetworkHandler.instance.sendToServer(p); - } - - return; - } - - if (slot instanceof SlotME sme) { - InventoryAction action = null; - IAEItemStack stack = null; - - switch (mouseButton) { - case 0 -> { // pickup / set-down. - action = ctrlDown == 1 ? InventoryAction.SPLIT_OR_PLACE_SINGLE : InventoryAction.PICKUP_OR_SET_DOWN; - if (sme.isPin() && player.inventory.getItemStack() != null) { - final PacketInventoryAction p = new PacketInventoryAction( - InventoryAction.SET_PIN, - sme.getPinIndex(), - 0); - NetworkHandler.instance.sendToServer(p); - return; - } - - stack = sme.getAEStack(); - if (stack != null && action == InventoryAction.PICKUP_OR_SET_DOWN - && stack.getStackSize() == 0 - && player.inventory.getItemStack() == null) { - action = InventoryAction.AUTO_CRAFT; - } - } - case 1 -> { - if (sme.isPin() && ctrlDown == 1) { // clear pin - final PacketInventoryAction p = new PacketInventoryAction( - InventoryAction.SET_PIN, - sme.getPinIndex(), - -1); - NetworkHandler.instance.sendToServer(p); - return; - } - - action = ctrlDown == 1 ? InventoryAction.PICKUP_SINGLE : InventoryAction.SHIFT_CLICK; - stack = ((SlotME) slot).getAEStack(); - } - case 3 -> { // creative dupe: - stack = ((SlotME) slot).getAEStack(); - if (stack != null && stack.isCraftable()) { - action = InventoryAction.AUTO_CRAFT; - } else if (player.capabilities.isCreativeMode) { - final IAEItemStack slotItem = ((SlotME) slot).getAEStack(); - if (slotItem != null) { - action = InventoryAction.CREATIVE_DUPLICATE; - } - } - } // drop item: - default -> {} - } - - if (action != null) { - ((AEBaseContainer) this.inventorySlots).setTargetStack(stack); - final PacketInventoryAction p = new PacketInventoryAction(action, this.getInventorySlots().size(), 0); - NetworkHandler.instance.sendToServer(p); - } - - return; - } - if (!this.disableShiftClick && isShiftKeyDown()) { this.disableShiftClick = true; @@ -751,24 +657,7 @@ public abstract class AEBaseGui extends GuiContainer { * @return If the event was handled */ protected boolean mouseWheelEvent(final int x, final int y, final int wheel) { - if (!isShiftKeyDown()) { - return false; - } - final Slot slot = this.getSlot(x, y); - if (slot instanceof SlotME) { - final IAEItemStack item = ((SlotME) slot).getAEStack(); - if (item != null) { - ((AEBaseContainer) this.inventorySlots).setTargetStack(item); - final InventoryAction direction = wheel > 0 ? InventoryAction.ROLL_DOWN : InventoryAction.ROLL_UP; - final int times = Math.abs(wheel); - final int inventorySize = this.getInventorySlots().size(); - for (int h = 0; h < times; h++) { - final PacketInventoryAction p = new PacketInventoryAction(direction, inventorySize, 0); - NetworkHandler.instance.sendToServer(p); - } - } - } - return true; + return false; } protected boolean enableSpaceClicking() { @@ -814,10 +703,7 @@ public abstract class AEBaseGui extends GuiContainer { } private void drawSlot(final Slot s) { - if (s instanceof SlotME || s instanceof SlotFake) { - if (s instanceof SlotME sme && sme.isPin() && !sme.getHasStack()) { - drawTextureOnSlot(s, sme.getPinIcon(), sme.getOpacityOfIcon()); - } + if (s instanceof SlotFake) { IAEItemStack stack = Platform.getAEStackInSlot(s); if (s instanceof SlotFake && stack != null && stack.getStackSize() == 1) { this.safeDrawSlot(s); @@ -862,8 +748,7 @@ public abstract class AEBaseGui extends GuiContainer { || s instanceof AppEngCraftingSlot || s instanceof SlotDisabled || s instanceof SlotInaccessible - || s instanceof SlotRestrictedInput - || s instanceof SlotDisconnected; + || s instanceof SlotRestrictedInput; if (isValid && s instanceof SlotRestrictedInput) { try { isValid = ((SlotRestrictedInput) s).isValid(is, this.mc.theWorld); @@ -1033,10 +918,6 @@ public abstract class AEBaseGui extends GuiContainer { this.scrollBar = myScrollBar; } - protected List getMeSlots() { - return this.meSlots; - } - public static final synchronized boolean isSwitchingGuis() { return switchingGuis; } @@ -1114,4 +995,74 @@ public abstract class AEBaseGui extends GuiContainer { public int getYSize() { return ySize; } + + public static boolean isCtrlKeyDown() { + return Keyboard.isKeyDown(controlKey); + } + + private void drawVirtualSlots(@Nonnull List slots, int mouseX, int mouseY) { + final int x = mouseX - this.guiLeft + 1; + final int y = mouseY - this.guiTop + 1; + GL11.glPushAttrib(GL11.GL_ENABLE_BIT | GL11.GL_COLOR_BUFFER_BIT | GL11.GL_LIGHTING_BIT); + RenderHelper.enableGUIStandardItemLighting(); + GL11.glEnable(GL11.GL_DEPTH_TEST); + + for (VirtualMESlot slot : slots) { + boolean isHovered = slot.drawStackAndOverlay(this.mc, x, y); + if (isHovered) { + this.hoveredVirtualSlot = slot; + } + } + GL11.glPopAttrib(); + } + + public @Nullable VirtualMESlot getVirtualMESlotUnderMouse() { + return this.hoveredVirtualSlot; + } + + public void initCustomButtons(int xOffset, int yOffset) { + if (inventorySlots instanceof AEBaseContainer abc && abc.getTarget() instanceof ICustomButtonProvider icbp) + icbp.initCustomButtons( + this.guiLeft, + this.guiTop, + this.xSize, + this.ySize, + xOffset, + yOffset, + this.buttonList); + } + + public boolean actionPerformedCustomButtons(final GuiButton btn) { + if (inventorySlots instanceof AEBaseContainer abc && abc.getTarget() instanceof ICustomButtonProvider icbp) + return icbp.actionPerformedCustomButtons(btn); + return false; + } + + @Override + public List handleItemTooltip(final ItemStack stack, final int mouseX, final int mouseY, + final List currentToolTip) { + VirtualMESlot hoveredSlot = this.getVirtualMESlotUnderMouse(); + if (hoveredSlot == null) return currentToolTip; + + if (hoveredSlot.getAEStack() instanceof IAEFluidStack afs) { + if (currentToolTip.isEmpty()) { + currentToolTip.add(afs.getDisplayName()); + } else { + currentToolTip.set(0, afs.getDisplayName()); + } + } + + return currentToolTip; + } + + @Override + public ItemStack getHoveredStack() { + VirtualMESlot hoveredSlot = this.getVirtualMESlotUnderMouse(); + if (hoveredSlot == null) return null; + + IAEStack hoveredAEStack = hoveredSlot.getAEStack(); + if (hoveredAEStack == null) return null; + + return hoveredAEStack.getItemStackForNEI(); + } } diff --git a/src/main/java/appeng/client/gui/AEBaseMEGui.java b/src/main/java/appeng/client/gui/AEBaseMEGui.java deleted file mode 100644 index 34c44bb6f..000000000 --- a/src/main/java/appeng/client/gui/AEBaseMEGui.java +++ /dev/null @@ -1,124 +0,0 @@ -/* - * This file is part of Applied Energistics 2. Copyright (c) 2013 - 2014, AlgorithmX2, All rights reserved. Applied - * Energistics 2 is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General - * Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any - * later version. Applied Energistics 2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; - * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General - * Public License for more details. You should have received a copy of the GNU Lesser General Public License along with - * Applied Energistics 2. If not, see . - */ - -package appeng.client.gui; - -import java.text.NumberFormat; -import java.util.List; -import java.util.Locale; - -import net.minecraft.inventory.Container; -import net.minecraft.inventory.Slot; -import net.minecraft.item.ItemStack; - -import appeng.api.config.TerminalFontSize; -import appeng.api.storage.data.IAEItemStack; -import appeng.client.me.SlotME; -import appeng.container.slot.SlotFake; -import appeng.core.AEConfig; -import appeng.core.localization.ButtonToolTips; -import appeng.util.Platform; - -public abstract class AEBaseMEGui extends AEBaseGui implements IGuiTooltipHandler { - - public AEBaseMEGui(final Container container) { - super(container); - } - - @Override - public List handleItemTooltip(final ItemStack stack, final int mouseX, final int mouseY, - final List currentToolTip) { - if (stack != null) { - final Slot s = this.getSlot(mouseX, mouseY); - final boolean isSlotME = s instanceof SlotME; - if (isSlotME || s instanceof SlotFake) { - final int BigNumber = AEConfig.instance.getTerminalFontSize() == TerminalFontSize.SMALL ? 9999 : 999; - - IAEItemStack myStack = null; - - try { - myStack = Platform.getAEStackInSlot(s); - } catch (final Throwable ignore) {} - - if (myStack != null) { - if (myStack.getStackSize() > BigNumber || (myStack.getStackSize() > 1 && stack.isItemDamaged())) { - final String local = isSlotME ? ButtonToolTips.ItemsStored.getLocal() - : ButtonToolTips.ItemCount.getLocal(); - final String formattedAmount = NumberFormat.getNumberInstance(Locale.US) - .format(myStack.getStackSize()); - final String format = String.format(local, formattedAmount); - - currentToolTip.add("\u00a77" + format); - } - - if (myStack.getCountRequestable() > 0) { - final String local = ButtonToolTips.ItemsRequestable.getLocal(); - final String formattedAmount = NumberFormat.getNumberInstance(Locale.US) - .format(myStack.getCountRequestable()); - final String format = String.format(local, formattedAmount); - - currentToolTip.add("\u00a77" + format); - } - } else if (stack.stackSize > BigNumber || (stack.stackSize > 1 && stack.isItemDamaged())) { - final String local = ButtonToolTips.ItemsStored.getLocal(); - final String formattedAmount = NumberFormat.getNumberInstance(Locale.US).format(stack.stackSize); - final String format = String.format(local, formattedAmount); - - currentToolTip.add("\u00a77" + format); - } - } - } - return currentToolTip; - } - - // Vanilla version... - // protected void drawItemStackTooltip(ItemStack stack, int x, int y) - @Override - public void renderToolTip(final ItemStack stack, final int x, final int y) { - final Slot s = this.getSlot(x, y); - if ((s instanceof SlotME || s instanceof SlotFake) && stack != null) { - final int BigNumber = AEConfig.instance.getTerminalFontSize() == TerminalFontSize.SMALL ? 9999 : 999; - - IAEItemStack myStack = null; - - try { - myStack = Platform.getAEStackInSlot(s); - } catch (final Throwable ignore) {} - - if (myStack != null) { - @SuppressWarnings("unchecked") - final List currentToolTip = stack - .getTooltip(this.mc.thePlayer, this.mc.gameSettings.advancedItemTooltips); - - if (myStack.getStackSize() > BigNumber || (myStack.getStackSize() > 1 && stack.isItemDamaged())) { - currentToolTip.add( - "Items Stored: " - + NumberFormat.getNumberInstance(Locale.US).format(myStack.getStackSize())); - } - - if (myStack.getCountRequestable() > 0) { - currentToolTip.add( - "Items Requestable: " - + NumberFormat.getNumberInstance(Locale.US).format(myStack.getCountRequestable())); - } - - this.drawTooltip(x, y, currentToolTip.toArray(new String[0])); - } else if (stack.stackSize > BigNumber) { - final List var4 = stack - .getTooltip(this.mc.thePlayer, this.mc.gameSettings.advancedItemTooltips); - var4.add("Items Stored: " + NumberFormat.getNumberInstance(Locale.US).format(stack.stackSize)); - this.drawTooltip(x, y, var4.toArray(new String[0])); - return; - } - } - super.renderToolTip(stack, x, y); - // super.drawItemStackTooltip( stack, x, y ); - } -} diff --git a/src/main/java/appeng/client/gui/GuiSub.java b/src/main/java/appeng/client/gui/GuiSub.java new file mode 100644 index 000000000..44de1d515 --- /dev/null +++ b/src/main/java/appeng/client/gui/GuiSub.java @@ -0,0 +1,45 @@ +package appeng.client.gui; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.inventory.Container; + +import appeng.client.gui.widgets.GuiTabButton; +import appeng.container.interfaces.IContainerSubGui; +import appeng.core.sync.network.NetworkHandler; +import appeng.core.sync.packets.PacketSwitchGuis; + +public abstract class GuiSub extends AEBaseGui implements IGuiSub { + + protected final IContainerSubGui container; + protected GuiTabButton originalGuiBtn; + + public GuiSub(Container container) { + super(container); + this.container = (IContainerSubGui) container; + this.container.setGuiLink(this); + } + + @Override + public void initGui() { + super.initGui(); + if (container.getPrimaryGuiIcon() != null) initPrimaryGuiButton(); + } + + public void initPrimaryGuiButton() { + this.buttonList.add( + this.originalGuiBtn = new GuiTabButton( + this.guiLeft + this.xSize - 22, + this.guiTop, + container.getPrimaryGuiIcon(), + container.getPrimaryGuiIcon().getDisplayName(), + itemRender)); + } + + @Override + protected void actionPerformed(final GuiButton btn) { + super.actionPerformed(btn); + if (btn == this.originalGuiBtn) { + NetworkHandler.instance.sendToServer(new PacketSwitchGuis()); + } + } +} diff --git a/src/main/java/appeng/client/gui/IGuiSub.java b/src/main/java/appeng/client/gui/IGuiSub.java new file mode 100644 index 000000000..3133e1421 --- /dev/null +++ b/src/main/java/appeng/client/gui/IGuiSub.java @@ -0,0 +1,7 @@ +package appeng.client.gui; + +public interface IGuiSub { + + void initPrimaryGuiButton(); + +} diff --git a/src/main/java/appeng/client/gui/implementations/GuiAmount.java b/src/main/java/appeng/client/gui/implementations/GuiAmount.java index e7a5ab6a0..8332f03f4 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiAmount.java +++ b/src/main/java/appeng/client/gui/implementations/GuiAmount.java @@ -2,27 +2,20 @@ package appeng.client.gui.implementations; import net.minecraft.client.gui.GuiButton; import net.minecraft.inventory.Container; -import net.minecraft.item.ItemStack; import org.lwjgl.input.Keyboard; -import appeng.client.gui.AEBaseGui; -import appeng.client.gui.widgets.GuiTabButton; +import appeng.client.gui.GuiSub; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; import appeng.core.AEConfig; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; -import appeng.core.sync.network.NetworkHandler; -import appeng.core.sync.packets.PacketSwitchGuis; import appeng.helpers.Reflected; import appeng.util.calculators.ArithHelper; import appeng.util.calculators.Calculator; -public abstract class GuiAmount extends AEBaseGui { +public abstract class GuiAmount extends GuiSub { protected MEGuiTextField amountTextField; - protected GuiTabButton originalGuiBtn; protected GuiButton nextBtn; @@ -35,9 +28,6 @@ public abstract class GuiAmount extends AEBaseGui { protected GuiButton minus100; protected GuiButton minus1000; - protected GuiBridge originalGui; - protected ItemStack myIcon; - @Reflected public GuiAmount(final Container container) { super(container); @@ -66,19 +56,6 @@ public abstract class GuiAmount extends AEBaseGui { this.buttonList.add( this.nextBtn = new GuiButton(0, this.guiLeft + 128, this.guiTop + 51, 38, 20, GuiText.Next.getLocal())); - final Object target = ((AEBaseContainer) this.inventorySlots).getTarget(); - - this.setOriginGUI(target); - if (this.originalGui != null && myIcon != null) { - this.buttonList.add( - this.originalGuiBtn = new GuiTabButton( - this.guiLeft + 154, - this.guiTop, - this.myIcon, - this.myIcon.getDisplayName(), - itemRender)); - } - this.amountTextField = new MEGuiTextField(61, 12); this.amountTextField.x = this.guiLeft + 60; this.amountTextField.y = this.guiTop + 55; @@ -86,8 +63,6 @@ public abstract class GuiAmount extends AEBaseGui { this.amountTextField.setFocused(true); } - protected abstract void setOriginGUI(Object target); - protected int getButtonQtyByIndex(int index) { return AEConfig.instance.craftItemsByStackAmounts(index); } @@ -118,9 +93,6 @@ public abstract class GuiAmount extends AEBaseGui { @Override protected void actionPerformed(final GuiButton btn) { super.actionPerformed(btn); - if (btn == this.originalGuiBtn) { - NetworkHandler.instance.sendToServer(new PacketSwitchGuis(this.originalGui)); - } final boolean isPlus = btn == this.plus1 || btn == this.plus10 || btn == this.plus100 || btn == this.plus1000; final boolean isMinus = btn == this.minus1 || btn == this.minus10 diff --git a/src/main/java/appeng/client/gui/implementations/GuiBusIO.java b/src/main/java/appeng/client/gui/implementations/GuiBusIO.java new file mode 100644 index 000000000..9ec98c3fe --- /dev/null +++ b/src/main/java/appeng/client/gui/implementations/GuiBusIO.java @@ -0,0 +1,116 @@ +package appeng.client.gui.implementations; + +import net.minecraft.entity.player.InventoryPlayer; + +import org.lwjgl.opengl.GL11; + +import appeng.api.config.Upgrades; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; +import appeng.client.gui.slots.VirtualMEPhantomSlot; +import appeng.container.implementations.ContainerBusIO; +import appeng.parts.automation.PartSharedItemBus; +import appeng.tile.inventory.IAEStackInventory; + +public class GuiBusIO extends GuiUpgradeable { + + protected VirtualMEPhantomSlot[] virtualSlots; + private final PartSharedItemBus bus; + + public GuiBusIO(final InventoryPlayer inventoryPlayer, final PartSharedItemBus te) { + super(new ContainerBusIO(inventoryPlayer, te)); + this.bus = te; + } + + @Override + public void initGui() { + super.initGui(); + this.initVirtualSlots(); + } + + private void initVirtualSlots() { + this.virtualSlots = new VirtualMEPhantomSlot[9]; + final IAEStackInventory inputInv = this.bus.getAEInventoryByName(StorageName.NONE); + for (int y = 0; y < 3; y++) { + for (int x = 0; x < 3; x++) { + VirtualMEPhantomSlot slot = new VirtualMEPhantomSlot( + 62 + 18 * x, + 22 + 18 * (y % (3)), + inputInv, + x + y * 3); + this.virtualSlots[x + y * 3] = slot; + this.registerVirtualSlots(slot); + } + } + } + + @Override + public void drawBG(int offsetX, int offsetY, int mouseX, int mouseY) { + super.drawBG(offsetX, offsetY, mouseX, mouseY); + + final int capacity = this.cvb.getUpgradeable().getInstalledUpgrades(Upgrades.CAPACITY); + if (capacity < 1) { + GL11.glPushAttrib(GL11.GL_ALL_ATTRIB_BITS); + GL11.glColor4f(1.0F, 1.0F, 1.0F, 0.4F); + GL11.glEnable(GL11.GL_BLEND); + } + + this.drawTexturedModalRect(offsetX + 61, offsetY + 39, 79, 39, 18, 18); + this.drawTexturedModalRect(offsetX + 79, offsetY + 21, 79, 39, 18, 18); + this.drawTexturedModalRect(offsetX + 97, offsetY + 39, 79, 39, 18, 18); + this.drawTexturedModalRect(offsetX + 79, offsetY + 57, 79, 39, 18, 18); + + if (capacity < 1) { + GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F); + GL11.glPopAttrib(); + } + + if (capacity < 2) { + GL11.glPushAttrib(GL11.GL_ALL_ATTRIB_BITS); + GL11.glColor4f(1.0F, 1.0F, 1.0F, 0.4F); + GL11.glEnable(GL11.GL_BLEND); + } + + this.drawTexturedModalRect(offsetX + 61, offsetY + 21, 79, 39, 18, 18); + this.drawTexturedModalRect(offsetX + 61, offsetY + 57, 79, 39, 18, 18); + this.drawTexturedModalRect(offsetX + 97, offsetY + 21, 79, 39, 18, 18); + this.drawTexturedModalRect(offsetX + 97, offsetY + 57, 79, 39, 18, 18); + + if (capacity < 2) { + GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F); + GL11.glPopAttrib(); + } + + } + + @Override + protected void handleButtonVisibility() { + super.handleButtonVisibility(); + + final int capacity = this.cvb.getUpgradeable().getInstalledUpgrades(Upgrades.CAPACITY); + final boolean firstTier = capacity > 0; + final boolean secondTier = capacity > 1; + + this.virtualSlots[1].setHidden(!firstTier); + this.virtualSlots[3].setHidden(!firstTier); + this.virtualSlots[5].setHidden(!firstTier); + this.virtualSlots[7].setHidden(!firstTier); + + this.virtualSlots[0].setHidden(!secondTier); + this.virtualSlots[2].setHidden(!secondTier); + this.virtualSlots[6].setHidden(!secondTier); + this.virtualSlots[8].setHidden(!secondTier); + + } + + @Override + protected String getBackground() { + return "guis/bus.png"; + } + + @Override + protected void handlePhantomSlotInteraction(VirtualMEPhantomSlot slot, int mouseButton) { + StorageChannel channel = StorageChannel.getStorageChannelByParametrizedClass(this.bus.getClass()); + slot.handleMouseClicked(channel == StorageChannel.ITEMS, channel == StorageChannel.FLUIDS, false); + } +} diff --git a/src/main/java/appeng/client/gui/implementations/GuiCellRestriction.java b/src/main/java/appeng/client/gui/implementations/GuiCellRestriction.java index 297b0665e..325b3123c 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiCellRestriction.java +++ b/src/main/java/appeng/client/gui/implementations/GuiCellRestriction.java @@ -6,14 +6,13 @@ import net.minecraft.entity.player.InventoryPlayer; import org.lwjgl.input.Keyboard; -import appeng.client.gui.AEBaseGui; +import appeng.client.gui.GuiSub; import appeng.client.gui.widgets.MEGuiTextField; import appeng.container.implementations.ContainerCellRestriction; import appeng.container.implementations.ContainerCellRestriction.CellData; import appeng.core.AELog; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; @@ -21,7 +20,7 @@ import appeng.helpers.ICellRestriction; import appeng.util.calculators.ArithHelper; import appeng.util.calculators.Calculator; -public class GuiCellRestriction extends AEBaseGui { +public class GuiCellRestriction extends GuiSub { private MEGuiTextField amountField; private MEGuiTextField typesField; @@ -29,7 +28,7 @@ public class GuiCellRestriction extends AEBaseGui { public GuiCellRestriction(InventoryPlayer ip, ICellRestriction obj) { super(new ContainerCellRestriction(ip, obj)); - this.xSize = 256; + this.xSize = 204; this.amountField = new MEGuiTextField(85, 12); this.typesField = new MEGuiTextField(30, 12); @@ -144,7 +143,7 @@ public class GuiCellRestriction extends AEBaseGui { } catch (IOException e) { AELog.debug(e); } - NetworkHandler.instance.sendToServer(new PacketSwitchGuis(GuiBridge.GUI_CELL_WORKBENCH)); + NetworkHandler.instance.sendToServer(new PacketSwitchGuis()); } else if (!(this.amountField.textboxKeyTyped(character, key) || this.typesField.textboxKeyTyped(character, key))) { super.keyTyped(character, key); diff --git a/src/main/java/appeng/client/gui/implementations/GuiCellWorkbench.java b/src/main/java/appeng/client/gui/implementations/GuiCellWorkbench.java index 94c27437d..e929e6d81 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiCellWorkbench.java +++ b/src/main/java/appeng/client/gui/implementations/GuiCellWorkbench.java @@ -25,6 +25,9 @@ import appeng.api.config.FuzzyMode; import appeng.api.config.Settings; import appeng.api.config.Upgrades; import appeng.api.implementations.items.IUpgradeModule; +import appeng.api.implementations.tiles.ICellWorkbench; +import appeng.api.storage.StorageChannel; +import appeng.client.gui.slots.VirtualMEPhantomSlot; import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.GuiToggleButton; import appeng.container.implementations.ContainerCellWorkbench; @@ -33,7 +36,7 @@ import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; -import appeng.tile.misc.TileCellWorkbench; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.Platform; public class GuiCellWorkbench extends GuiUpgradeable { @@ -44,8 +47,9 @@ public class GuiCellWorkbench extends GuiUpgradeable { private GuiImgButton partition; private GuiToggleButton copyMode; protected GuiImgButton cellRestriction; + private VirtualMEPhantomSlot[] configSlots; - public GuiCellWorkbench(final InventoryPlayer inventoryPlayer, final TileCellWorkbench te) { + public GuiCellWorkbench(final InventoryPlayer inventoryPlayer, final ICellWorkbench te) { super(new ContainerCellWorkbench(inventoryPlayer, te)); this.workbench = (ContainerCellWorkbench) this.inventorySlots; this.ySize = 251; @@ -84,6 +88,8 @@ public class GuiCellWorkbench extends GuiUpgradeable { this.buttonList.add(this.copyMode); this.buttonList.add(this.oreFilter); this.buttonList.add(this.cellRestriction); + + initVirtualSlots(); } @Override @@ -163,6 +169,25 @@ public class GuiCellWorkbench extends GuiUpgradeable { } } + private void initVirtualSlots() { + this.configSlots = new VirtualMEPhantomSlot[63]; + final IAEStackInventory inputInv = this.workbench.getConfig(); + final int xo = 8; + final int yo = -133; + + for (int y = 0; y < 7; y++) { + for (int x = 0; x < 9; x++) { + VirtualMEPhantomSlot slot = new VirtualMEPhantomSlot( + xo + x * 18, + yo + y * 18 + 9 * 18, + inputInv, + x + y * 9); + this.configSlots[x + y * 9] = slot; + this.registerVirtualSlots(slot); + } + } + } + @Override protected void handleButtonVisibility() { this.copyMode.setState(this.workbench.getCopyMode() == CopyMode.CLEAR_ON_REMOVE); @@ -224,4 +249,10 @@ public class GuiCellWorkbench extends GuiUpgradeable { } } catch (final IOException ignored) {} } + + @Override + protected void handlePhantomSlotInteraction(VirtualMEPhantomSlot slot, int mouseButton) { + StorageChannel channel = workbench.getStorageChannel(); + slot.handleMouseClicked(channel == StorageChannel.ITEMS, channel == StorageChannel.FLUIDS, false); + } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiCraftAmount.java b/src/main/java/appeng/client/gui/implementations/GuiCraftAmount.java index bf89da3c8..a91a429f1 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiCraftAmount.java +++ b/src/main/java/appeng/client/gui/implementations/GuiCraftAmount.java @@ -12,38 +12,36 @@ package appeng.client.gui.implementations; import net.minecraft.client.gui.GuiButton; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.item.ItemStack; import org.lwjgl.input.Mouse; -import appeng.api.AEApi; import appeng.api.config.CraftingMode; import appeng.api.config.Settings; -import appeng.api.definitions.IDefinitions; -import appeng.api.definitions.IParts; import appeng.api.storage.ITerminalHost; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.client.gui.slots.VirtualMESlotSingle; import appeng.client.gui.widgets.GuiImgButton; import appeng.container.implementations.ContainerCraftAmount; +import appeng.container.interfaces.IVirtualSlotHolder; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketCraftRequest; import appeng.helpers.Reflected; -import appeng.helpers.WirelessTerminalGuiObject; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; -import appeng.parts.reporting.PartTerminal; import appeng.util.Platform; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; -public class GuiCraftAmount extends GuiAmount { +public class GuiCraftAmount extends GuiAmount implements IVirtualSlotHolder { private GuiImgButton craftingMode; + private final VirtualMESlotSingle slot; @Reflected public GuiCraftAmount(final InventoryPlayer inventoryPlayer, final ITerminalHost te) { super(new ContainerCraftAmount(inventoryPlayer, te)); + + this.slot = new VirtualMESlotSingle(34, 53, 0, null); } @Override @@ -59,49 +57,7 @@ public class GuiCraftAmount extends GuiAmount { CraftingMode.STANDARD)); ((ContainerCraftAmount) this.inventorySlots).setAmountField(this.amountTextField); - } - - @Override - protected void setOriginGUI(Object target) { - - final IDefinitions definitions = AEApi.instance().definitions(); - final IParts parts = definitions.parts(); - - if (target instanceof WirelessTerminalGuiObject) { - for (final ItemStack wirelessTerminalStack : definitions.items().wirelessTerminal().maybeStack(1).asSet()) { - myIcon = wirelessTerminalStack; - } - - this.originalGui = GuiBridge.GUI_WIRELESS_TERM; - } - - if (target instanceof PartTerminal) { - for (final ItemStack stack : parts.terminal().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_ME; - } - - if (target instanceof PartCraftingTerminal) { - for (final ItemStack stack : parts.craftingTerminal().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_CRAFTING_TERMINAL; - } - - if (target instanceof PartPatternTerminal) { - for (final ItemStack stack : parts.patternTerminal().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - if (target instanceof PartPatternTerminalEx) { - for (final ItemStack stack : parts.patternTerminalEx().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } + this.registerVirtualSlots(this.slot); } @Override @@ -168,4 +124,9 @@ public class GuiCraftAmount extends GuiAmount { protected String getBackground() { return "guis/craftAmt.png"; } + + @Override + public void receiveSlotStacks(StorageName _invName, Int2ObjectMap> slotStacks) { + this.slot.setAEStack(slotStacks.get(0)); + } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiCraftConfirm.java b/src/main/java/appeng/client/gui/implementations/GuiCraftConfirm.java index ef74050a5..3a18125e8 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiCraftConfirm.java +++ b/src/main/java/appeng/client/gui/implementations/GuiCraftConfirm.java @@ -12,6 +12,7 @@ package appeng.client.gui.implementations; import static appeng.api.config.Settings.CRAFTING_SORT_BY; import static appeng.api.config.Settings.SORT_DIRECTION; +import static appeng.util.Platform.stackConvert; import java.text.NumberFormat; import java.util.ArrayList; @@ -38,8 +39,9 @@ import appeng.api.config.SortDir; import appeng.api.config.TerminalStyle; import appeng.api.storage.ITerminalHost; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; -import appeng.client.gui.AEBaseGui; +import appeng.client.gui.GuiSub; import appeng.client.gui.IGuiTooltipHandler; import appeng.client.gui.widgets.GuiAeButton; import appeng.client.gui.widgets.GuiCraftingCPUTable; @@ -58,24 +60,18 @@ import appeng.core.AELog; import appeng.core.localization.ButtonToolTips; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; import appeng.crafting.v2.CraftingJobV2; -import appeng.helpers.WirelessTerminalGuiObject; import appeng.integration.modules.NEI; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; -import appeng.parts.reporting.PartTerminal; import appeng.util.ColorPickHelper; import appeng.util.Platform; import appeng.util.ReadableNumberConverter; import appeng.util.RoundHelper; import appeng.util.item.AEItemStack; -public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolder, IGuiTooltipHandler { +public class GuiCraftConfirm extends GuiSub implements ICraftingCPUTableHolder, IGuiTooltipHandler { public static final int TREE_VIEW_TEXTURE_WIDTH = 238; public static final int TREE_VIEW_TEXTURE_HEIGHT = 238; @@ -151,7 +147,6 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde private CraftingSortOrder sortMode = CraftingSortOrder.NAME; private SortDir sortDir = SortDir.ASCENDING; - private GuiBridge OriginalGui; private GuiButton cancel; private GuiButton start; private GuiButton startWithFollow; @@ -167,7 +162,7 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde private MEGuiTextField searchField; private int tooltip = -1; private ItemStack hoveredStack; - private ArrayList goToData = new ArrayList<>(); + private final ArrayList goToData = new ArrayList<>(); private int searchGotoIndex = -1; private IAEItemStack needHighlight; @@ -186,26 +181,6 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde this, ((ContainerCraftConfirm) inventorySlots).cpuTable, c -> this.ccc.cpuCraftingSameItem(c) && this.ccc.cpuMatches(c)); - - if (te instanceof WirelessTerminalGuiObject) { - this.OriginalGui = GuiBridge.GUI_WIRELESS_TERM; - } - - if (te instanceof PartTerminal) { - this.OriginalGui = GuiBridge.GUI_ME; - } - - if (te instanceof PartCraftingTerminal) { - this.OriginalGui = GuiBridge.GUI_CRAFTING_TERMINAL; - } - - if (te instanceof PartPatternTerminal) { - this.OriginalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - if (te instanceof PartPatternTerminalEx) { - this.OriginalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } } @Override @@ -812,32 +787,30 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde } } - public void postUpdate(final List list, final byte ref) { - switch (ref) { - case 0 -> { - for (final IAEItemStack l : list) { - this.handleInput(this.storage, l); + public void postUpdate(final List> list, final byte ref) { + for (final IAEStack l : list) { + IAEItemStack stack = stackConvert(l); + switch (ref) { + case 0 -> { + this.handleInput(this.storage, stack); } - } - case 1 -> { - for (final IAEItemStack l : list) { - this.handleInput(this.pending, l); + case 1 -> { + this.handleInput(this.pending, stack); } - } - case 2 -> { - for (final IAEItemStack l : list) { - this.handleInput(this.missing, l); + case 2 -> { + this.handleInput(this.missing, stack); } } } - for (final IAEItemStack l : list) { - final long amt = this.getTotal(l); + for (final IAEStack l : list) { + IAEItemStack stack = stackConvert(l); + final long amt = this.getTotal(stack); if (amt <= 0) { - this.deleteVisualStack(l); + this.deleteVisualStack(stack); } else { - final IAEItemStack is = this.findVisualStack(l); + final IAEItemStack is = this.findVisualStack(stack); is.setStackSize(amt); } } @@ -880,7 +853,7 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde return ((AEItemStack) i1).getDisplayName().compareToIgnoreCase(((AEItemStack) i2).getDisplayName()) * sortDir.sortHint; if (sortMode == CraftingSortOrder.MOD) { - int v = ((AEItemStack) i1).getModID().compareToIgnoreCase(((AEItemStack) i2).getModID()); + int v = ((AEItemStack) i1).getModId().compareToIgnoreCase(((AEItemStack) i2).getModId()); return (v == 0 ? ((AEItemStack) i1).getDisplayName().compareToIgnoreCase(((AEItemStack) i2).getDisplayName()) : v) * sortDir.sortHint; @@ -995,7 +968,7 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde cpuTable.cycleCPU(backwards); } else if (btn == this.cancel) { this.addMissingItemsToBookMark(); - switchToOriginalGUI(); + NetworkHandler.instance.sendToServer(new PacketSwitchGuis()); } else if (btn == this.switchDisplayMode) { this.displayMode = this.displayMode.next(); recalculateScreenSize(); @@ -1060,13 +1033,6 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde } } - public void switchToOriginalGUI() { - // null if terminal is not a native AE2 terminal - if (this.OriginalGui != null) { - NetworkHandler.instance.sendToServer(new PacketSwitchGuis(this.OriginalGui)); - } - } - public ItemStack getHoveredStack() { return hoveredStack; } @@ -1121,16 +1087,17 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde missing.add(iaeItemStack.getItemStack()); } - final IAEItemStack outputStack = ((ContainerCraftConfirm) this.inventorySlots).getItemToCraft(); + final ItemStack outputStack = this.getItemStackForBookMark(); - if (outputStack != null) { - NEI.instance.addToBookmark(outputStack.getItemStack(), missing); - } else { - NEI.instance.addToBookmark(null, missing); - } + NEI.instance.addToBookmark(outputStack, missing); } } + private ItemStack getItemStackForBookMark() { + final IAEStack outputStack = ((ContainerCraftConfirm) this.inventorySlots).getItemToCraft(); + return outputStack.getItemStackForNEI(); + } + public IItemList getStorage() { return this.storage; } @@ -1142,4 +1109,7 @@ public class GuiCraftConfirm extends AEBaseGui implements ICraftingCPUTableHolde public IItemList getMissing() { return this.missing; } + + @Override + public void initPrimaryGuiButton() {} } diff --git a/src/main/java/appeng/client/gui/implementations/GuiCraftingCPU.java b/src/main/java/appeng/client/gui/implementations/GuiCraftingCPU.java index fa55208a5..b381992c0 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiCraftingCPU.java +++ b/src/main/java/appeng/client/gui/implementations/GuiCraftingCPU.java @@ -13,6 +13,7 @@ package appeng.client.gui.implementations; import java.io.IOException; import java.text.NumberFormat; import java.util.ArrayList; +import java.util.Collections; import java.util.HashMap; import java.util.Iterator; import java.util.LinkedList; @@ -21,12 +22,14 @@ import java.util.Map; import java.util.concurrent.TimeUnit; import net.minecraft.client.gui.GuiButton; +import net.minecraft.client.renderer.RenderHelper; import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import org.apache.commons.lang3.time.DurationFormatUtils; import org.lwjgl.opengl.GL11; +import org.lwjgl.opengl.GL12; import com.google.common.base.Joiner; @@ -38,6 +41,7 @@ import appeng.api.config.SortOrder; import appeng.api.config.ViewItems; import appeng.api.config.YesNo; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.api.util.NamedDimensionalCoord; import appeng.client.gui.AEBaseGui; @@ -103,11 +107,9 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti private final ContainerCraftingCPU craftingCpu; - protected IItemList storage = AEApi.instance().storage().createItemList(); - protected IItemList active = AEApi.instance().storage().createItemList(); - protected IItemList pending = AEApi.instance().storage().createItemList(); - - private IAEItemStack hoveredAEStack = null; + protected IItemList> storage = AEApi.instance().storage().createAEStackList(); + protected IItemList> active = AEApi.instance().storage().createAEStackList(); + protected IItemList> pending = AEApi.instance().storage().createAEStackList(); protected int rows = DISPLAYED_ROWS; @@ -177,23 +179,23 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } } - protected List visual = new ArrayList<>(); + protected List> visual = new ArrayList<>(); private GuiButton cancel; private GuiAeButton suspend; - protected List visualHiddenStored = new ArrayList<>(); + protected List> visualHiddenStored = new ArrayList<>(); protected GuiImgButton toggleHideStored; protected boolean hideStored; private int tooltip = -1; private final RemainingOperations remainingOperations = new RemainingOperations(); - private ItemStack hoveredStack; - private ItemStack hoveredNbtStack; + private IAEStack hoveredStack; + private NBTTagCompound hoveredStackNbt; private GuiAeButton findNext; private GuiAeButton findPrev; private GuiImgButton changeAllow; private MEGuiTextField searchField; - private ArrayList goToData = new ArrayList<>(); + private final ArrayList goToData = new ArrayList<>(); private int searchGotoIndex = -1; - private IAEItemStack needHighlight; + private IAEStack needHighlight; public GuiCraftingCPU(final InventoryPlayer inventoryPlayer, final Object te) { this(new ContainerCraftingCPU(inventoryPlayer, te)); @@ -211,9 +213,9 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } public void clearItems() { - this.storage = AEApi.instance().storage().createItemList(); - this.active = AEApi.instance().storage().createItemList(); - this.pending = AEApi.instance().storage().createItemList(); + this.storage = AEApi.instance().storage().createAEStackList(); + this.active = AEApi.instance().storage().createAEStackList(); + this.pending = AEApi.instance().storage().createAEStackList(); this.visual = new ArrayList<>(); this.visualHiddenStored = new ArrayList<>(); } @@ -255,17 +257,12 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } - public IAEItemStack getHoveredAEStack() { - return hoveredAEStack; - } - @Override protected void mouseClicked(final int xCoord, final int yCoord, final int btn) { - if (isShiftKeyDown() && this.hoveredNbtStack != null) { - NBTTagCompound data = Platform.openNbtData(this.hoveredNbtStack); + if (isShiftKeyDown() && this.hoveredStackNbt != null) { // when using the highlight feature in the crafting GUI we want to show all the interfaces // that currently received items so the player can see if the items are processed properly - List ndcl = NamedDimensionalCoord.readAsListFromNBTNamed(data); + List ndcl = NamedDimensionalCoord.readAsListFromNBTNamed(hoveredStackNbt); Map ndcm = new HashMap<>(); for (NamedDimensionalCoord ndc : ndcl) { ndcm.put( @@ -278,14 +275,15 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti ndcm, ((Localization) () -> "tile.appliedenergistics2.BlockInterface.name").getLocal()); mc.thePlayer.closeScreen(); - } else if (hoveredAEStack != null && btn == 2) { - ((AEBaseContainer) inventorySlots).setTargetStack(hoveredAEStack); + } else if (this.hoveredStack != null && btn == 2) { + ((AEBaseContainer) inventorySlots).setTargetStack(this.hoveredStack); final PacketInventoryAction p = new PacketInventoryAction( InventoryAction.AUTO_CRAFT, inventorySlots.inventorySlots.size(), - hoveredAEStack.getStackSize()); + this.hoveredStack.getStackSize()); NetworkHandler.instance.sendToServer(p); } + super.mouseClicked(xCoord, yCoord, btn); this.searchField.mouseClicked(xCoord, yCoord, btn); } @@ -412,8 +410,8 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti if (this.searchField.getText().isEmpty()) return; String s = this.searchField.getText().toLowerCase(); int visCount = 0; - for (IAEItemStack aeis : hideStored ? this.visualHiddenStored : this.visual) { - if (aeis != null && Platform.getItemDisplayName(aeis).toLowerCase().contains(s)) { + for (IAEStack stack : hideStored ? this.visualHiddenStored : this.visual) { + if (stack != null && stack.getDisplayName().toLowerCase().contains(s)) { goToData.add(visCount); } visCount++; @@ -435,14 +433,14 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti searchGotoIndex--; } - List visualTemp; + List> visualTemp; if (this.hideStored) { visualTemp = this.visualHiddenStored; } else { visualTemp = this.visual; } - IAEItemStack aeis = visualTemp.get(goToData.get(searchGotoIndex)); + IAEStack aeis = visualTemp.get(goToData.get(searchGotoIndex)); this.getScrollBar().setCurrentScroll(goToData.get(searchGotoIndex) / 3 - this.rows / 2); needHighlight = aeis.copy(); } @@ -470,7 +468,7 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti .formatDuration(elapsedInMilliseconds, GuiText.ETAFormat.getLocal()); // If title is empty, don't show that ' - ' - if (title.length() == 0) { + if (title.isEmpty()) { title = elapsedTimeText; } else { title += " - " + elapsedTimeText; @@ -501,21 +499,21 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti final int offY = 23; final ReadableNumberConverter converter = ReadableNumberConverter.INSTANCE; - List visualTemp; + List> visualTemp; if (this.hideStored) { visualTemp = this.visualHiddenStored; } else { visualTemp = this.visual; } for (int z = viewStart; z < Math.min(viewEnd, visualTemp.size()); z++) { - final IAEItemStack refStack = visualTemp.get(z); // repo.getReferenceItem( z ); + final IAEStack refStack = visualTemp.get(z); // repo.getReferenceItem( z ); if (refStack != null) { GL11.glPushMatrix(); GL11.glScaled(0.5, 0.5, 0.5); - final IAEItemStack stored = this.storage.findPrecise(refStack); - final IAEItemStack activeStack = this.active.findPrecise(refStack); - final IAEItemStack pendingStack = this.pending.findPrecise(refStack); + final IAEStack stored = this.storage.findPrecise(refStack); + final IAEStack activeStack = this.active.findPrecise(refStack); + final IAEStack pendingStack = this.pending.findPrecise(refStack); int lines = 0; @@ -577,7 +575,7 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti GuiColors.CraftingCPUAmount.getColor()); if (this.tooltip == z - viewStart) { - hoveredAEStack = refStack; + this.hoveredStack = refStack; lineList.add( GuiText.Crafting.getLocal() + ": " + NumberFormat.getInstance().format(activeStack.getStackSize())); @@ -609,23 +607,28 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti final int posX = x * (1 + SECTION_LENGTH) + ITEMSTACK_LEFT_OFFSET + SECTION_LENGTH - 19; final int posY = y * offY + ITEMSTACK_TOP_OFFSET; - final ItemStack is = refStack.copy().getItemStack(); + final IAEStack is = refStack.copy(); if (this.tooltip == z - viewStart) { dspToolTip = Platform.getItemDisplayName(is); - if (lineList.size() > 0) { - addItemTooltip(refStack, lineList); + if (!lineList.isEmpty()) { + addItemTooltip(refStack, lineList, refStack.equals(this.hoveredStack)); dspToolTip = dspToolTip + '\n' + Joiner.on("\n").join(lineList); } toolPosX = x * (1 + SECTION_LENGTH) + ITEMSTACK_LEFT_OFFSET + SECTION_LENGTH - 8; toolPosY = y * offY + ITEMSTACK_TOP_OFFSET; - hoveredStack = is; + this.hoveredStack = is; } - this.drawItem(posX, posY, is); + GL11.glPushAttrib(GL11.GL_ENABLE_BIT | GL11.GL_COLOR_BUFFER_BIT | GL11.GL_LIGHTING_BIT); + RenderHelper.enableGUIStandardItemLighting(); + GL11.glEnable(GL12.GL_RESCALE_NORMAL); + GL11.glEnable(GL11.GL_DEPTH_TEST); + is.drawInGui(this.mc, posX, posY); + GL11.glPopAttrib(); if (!this.searchField.getText().isEmpty() && goToData.contains(z)) { final int startX = x * (1 + SECTION_LENGTH) + ITEMSTACK_LEFT_OFFSET; @@ -648,28 +651,27 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } } - if (this.tooltip >= 0 && dspToolTip.length() > 0) { + if (this.tooltip >= 0 && !dspToolTip.isEmpty()) { this.drawTooltip(toolPosX, toolPosY + 10, dspToolTip); } } @SuppressWarnings("unchecked") - protected void addItemTooltip(IAEItemStack refStack, List lineList) { + protected void addItemTooltip(IAEStack refStack, List lineList, boolean stackChanged) { if (isShiftKeyDown()) { - final ItemStack is = refStack.copy().getItemStack(); - final List l = is.getTooltip(this.mc.thePlayer, this.mc.gameSettings.advancedItemTooltips); + final List l = refStack instanceof IAEItemStack ais + ? ais.getItemStack().getTooltip(this.mc.thePlayer, this.mc.gameSettings.advancedItemTooltips) + : Collections.EMPTY_LIST; if (!l.isEmpty()) l.remove(0); lineList.addAll(l); - if (this.hoveredNbtStack == null || this.hoveredNbtStack.getItem() != is.getItem()) { - this.hoveredNbtStack = is; + if (this.hoveredStackNbt == null || stackChanged) { try { NetworkHandler.instance.sendToServer(new PacketCraftingItemInterface(refStack.copy())); } catch (Exception ignored) {} } else { - NBTTagCompound data = Platform.openNbtData(this.hoveredNbtStack); - List blocks = NamedDimensionalCoord.readAsListFromNBTNamed(data); + List blocks = NamedDimensionalCoord.readAsListFromNBTNamed(this.hoveredStackNbt); - ScheduledReason sr = ScheduledReason.values()[data.getInteger("ScheduledReason")]; + ScheduledReason sr = ScheduledReason.values()[this.hoveredStackNbt.getInteger("ScheduledReason")]; if (sr != ScheduledReason.UNDEFINED) lineList.add(sr.getLocal()); if (blocks.isEmpty()) return; @@ -686,7 +688,7 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti lineList.add(GuiText.HoldShiftClick_HIGHLIGHT_INTERFACE.getLocal()); } } else { - this.hoveredNbtStack = null; + this.hoveredStackNbt = null; lineList.add(GuiText.HoldShiftForTooltip.getLocal()); } } @@ -711,40 +713,36 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } } - public void postUpdate(IAEItemStack is) { - this.hoveredNbtStack = is.getItemStack(); + public void postUpdateTooltip(NBTTagCompound nbt) { + this.hoveredStackNbt = nbt; } public void postUpdate(int remainingOperations) { this.remainingOperations.setRemainingOperations(remainingOperations); } - public void postUpdate(final List list, final byte ref) { - switch (ref) { - case 0 -> { - for (final IAEItemStack l : list) { - this.handleInput(this.storage, l); + public void postUpdate(final List> list, final byte ref) { + for (final IAEStack stack : list) { + switch (ref) { + case 0 -> { + this.handleInput(this.storage, stack); } - } - case 1 -> { - for (final IAEItemStack l : list) { - this.handleInput(this.active, l); + case 1 -> { + this.handleInput(this.active, stack); } - } - case 2 -> { - for (final IAEItemStack l : list) { - this.handleInput(this.pending, l); + case 2 -> { + this.handleInput(this.pending, stack); } } } - for (final IAEItemStack l : list) { - final long amt = this.getTotal(l); + for (final IAEStack stack : list) { + final long amt = this.getTotal(stack); if (amt <= 0) { - this.deleteVisualStack(l); + this.deleteVisualStack(stack); } else { - final IAEItemStack is = this.findVisualStack(l); + final IAEStack is = this.findVisualStack(stack); is.setStackSize(amt); } } @@ -754,8 +752,8 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti this.setScrollBar(); } - private void handleInput(final IItemList s, final IAEItemStack l) { - IAEItemStack a = s.findPrecise(l); + private void handleInput(final IItemList> s, final IAEStack l) { + IAEStack a = s.findPrecise(l); if (l.getStackSize() <= 0) { if (a != null) { @@ -773,10 +771,10 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } } - private long getTotal(final IAEItemStack is) { - final IAEItemStack a = this.storage.findPrecise(is); - final IAEItemStack b = this.active.findPrecise(is); - final IAEItemStack c = this.pending.findPrecise(is); + private long getTotal(final IAEStack is) { + final IAEStack a = this.storage.findPrecise(is); + final IAEStack b = this.active.findPrecise(is); + final IAEStack c = this.pending.findPrecise(is); long total = 0; @@ -795,11 +793,11 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti return total; } - private void deleteVisualStack(final IAEItemStack l) { - final Iterator i = this.visual.iterator(); + private void deleteVisualStack(final IAEStack l) { + final Iterator> i = this.visual.iterator(); while (i.hasNext()) { - final IAEItemStack o = i.next(); + final IAEStack o = i.next(); if (o.equals(l)) { i.remove(); return; @@ -807,14 +805,14 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti } } - private IAEItemStack findVisualStack(final IAEItemStack l) { - for (final IAEItemStack o : this.visual) { + private IAEStack findVisualStack(final IAEStack l) { + for (final IAEStack o : this.visual) { if (o.equals(l)) { return o; } } - final IAEItemStack stack = l.copy(); + final IAEStack stack = l.copy(); this.visual.add(stack); return stack; @@ -837,15 +835,15 @@ public class GuiCraftingCPU extends AEBaseGui implements ISortSource, IGuiToolti @Override public ItemStack getHoveredStack() { - return hoveredStack; + return hoveredStack != null ? this.hoveredStack.getItemStackForNEI() : null; } private void hideStoredSorting() { this.visualHiddenStored = new ArrayList<>(); - for (final IAEItemStack refStack : this.visual) { + for (final IAEStack refStack : this.visual) { if (refStack != null) { - final IAEItemStack activeStack = this.active.findPrecise(refStack); - final IAEItemStack pendingStack = this.pending.findPrecise(refStack); + final IAEStack activeStack = this.active.findPrecise(refStack); + final IAEStack pendingStack = this.pending.findPrecise(refStack); if ((activeStack != null && activeStack.getStackSize() > 0) || (pendingStack != null && pendingStack.getStackSize() > 0)) { this.visualHiddenStored.add(refStack); diff --git a/src/main/java/appeng/client/gui/implementations/GuiCraftingStatus.java b/src/main/java/appeng/client/gui/implementations/GuiCraftingStatus.java index 5e195562e..40998e6eb 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiCraftingStatus.java +++ b/src/main/java/appeng/client/gui/implementations/GuiCraftingStatus.java @@ -19,19 +19,16 @@ import java.util.List; import net.minecraft.client.gui.GuiButton; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagList; import org.lwjgl.input.Mouse; -import appeng.api.AEApi; import appeng.api.config.Settings; import appeng.api.config.TerminalStyle; -import appeng.api.definitions.IDefinitions; -import appeng.api.definitions.IParts; import appeng.api.storage.ITerminalHost; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.client.gui.IGuiSub; import appeng.client.gui.widgets.GuiAeButton; import appeng.client.gui.widgets.GuiCraftingCPUTable; import appeng.client.gui.widgets.GuiImgButton; @@ -42,17 +39,11 @@ import appeng.core.AEConfig; import appeng.core.AELog; import appeng.core.localization.ButtonToolTips; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; -import appeng.helpers.WirelessTerminalGuiObject; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; -import appeng.parts.reporting.PartTerminal; -public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTableHolder { +public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTableHolder, IGuiSub { private final ContainerCraftingStatus status; private GuiButton selectCPU; @@ -60,8 +51,6 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab private final GuiCraftingCPUTable cpuTable; protected GuiTabButton originalGuiBtn; - private GuiBridge originalGui; - protected ItemStack myIcon = null; private boolean tallMode; private GuiImgButton switchTallMode; private List playersFollowingCurrentCraft = new ArrayList<>(); @@ -70,49 +59,11 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab super(new ContainerCraftingStatus(inventoryPlayer, te)); this.status = (ContainerCraftingStatus) this.inventorySlots; + this.status.setGuiLink(this); this.tallMode = AEConfig.instance.getConfigManager().getSetting(Settings.TERMINAL_STYLE) == TerminalStyle.TALL; recalculateScreenSize(); - final Object target = this.status.getTarget(); - final IDefinitions definitions = AEApi.instance().definitions(); - final IParts parts = definitions.parts(); - cpuTable = new GuiCraftingCPUTable(this, this.status.getCPUTable(), c -> false); - - if (target instanceof WirelessTerminalGuiObject) { - for (final ItemStack wirelessTerminalStack : definitions.items().wirelessTerminal().maybeStack(1).asSet()) { - this.myIcon = wirelessTerminalStack; - } - - this.originalGui = GuiBridge.GUI_WIRELESS_TERM; - } - - if (target instanceof PartTerminal) { - for (final ItemStack stack : parts.terminal().maybeStack(1).asSet()) { - this.myIcon = stack; - } - this.originalGui = GuiBridge.GUI_ME; - } - - if (target instanceof PartCraftingTerminal) { - for (final ItemStack stack : parts.craftingTerminal().maybeStack(1).asSet()) { - this.myIcon = stack; - } - this.originalGui = GuiBridge.GUI_CRAFTING_TERMINAL; - } - - if (target instanceof PartPatternTerminal) { - for (final ItemStack stack : parts.patternTerminal().maybeStack(1).asSet()) { - this.myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - if (target instanceof PartPatternTerminalEx) { - for (final ItemStack stack : parts.patternTerminalEx().maybeStack(1).asSet()) { - this.myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } } @Override @@ -137,7 +88,7 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab AELog.debug(e); } } else if (btn == this.originalGuiBtn) { - NetworkHandler.instance.sendToServer(new PacketSwitchGuis(this.originalGui)); + NetworkHandler.instance.sendToServer(new PacketSwitchGuis()); } else if (btn == this.switchTallMode) { tallMode = !tallMode; AEConfig.instance.getConfigManager() @@ -156,6 +107,8 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab super.initGui(); this.setScrollBar(); + if (status.getPrimaryGuiIcon() != null) initPrimaryGuiButton(); + this.selectCPU = new GuiButton( 0, this.guiLeft + 8, @@ -175,16 +128,6 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab ButtonToolTips.ToFollow.getLocal()); this.buttonList.add(this.follow); - if (this.myIcon != null) { - this.buttonList.add( - this.originalGuiBtn = new GuiTabButton( - this.guiLeft + 213, - this.guiTop - 4, - this.myIcon, - this.myIcon.getDisplayName(), - itemRender)); - this.originalGuiBtn.setHideEdge(13); - } this.switchTallMode = new GuiImgButton( this.guiLeft - 18, this.guiTop + this.ySize - 18, @@ -324,7 +267,7 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab } @Override - public void postUpdate(List list, byte ref) { + public void postUpdate(List> list, byte ref) { super.postUpdate(list, ref); setScrollBar(); } @@ -336,4 +279,15 @@ public class GuiCraftingStatus extends GuiCraftingCPU implements ICraftingCPUTab this.playersFollowingCurrentCraft.add(tagList.getStringTagAt(index)); } } + + public void initPrimaryGuiButton() { + this.buttonList.add( + this.originalGuiBtn = new GuiTabButton( + this.guiLeft + this.xSize - 25, + this.guiTop - 4, + status.getPrimaryGuiIcon(), + status.getPrimaryGuiIcon().getDisplayName(), + itemRender)); + this.originalGuiBtn.setHideEdge(13); + } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiInterface.java b/src/main/java/appeng/client/gui/implementations/GuiInterface.java index feb833398..a22025b68 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiInterface.java +++ b/src/main/java/appeng/client/gui/implementations/GuiInterface.java @@ -141,6 +141,8 @@ public class GuiInterface extends GuiUpgradeable { FuzzyMode.IGNORE_ALL); this.fuzzyMode.visible = this.bc.getInstalledUpgrades(Upgrades.FUZZY) > 0; this.buttonList.add(fuzzyMode); + + initCustomButtons(this.guiLeft - 18, offset); } @Override @@ -206,6 +208,8 @@ public class GuiInterface extends GuiUpgradeable { protected void actionPerformed(final GuiButton btn) { super.actionPerformed(btn); + if (actionPerformedCustomButtons(btn)) return; + final boolean backwards = Mouse.isButtonDown(1); if (btn == this.priority) { diff --git a/src/main/java/appeng/client/gui/implementations/GuiInterfaceTerminal.java b/src/main/java/appeng/client/gui/implementations/GuiInterfaceTerminal.java index f58be0b67..37d890d8d 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiInterfaceTerminal.java +++ b/src/main/java/appeng/client/gui/implementations/GuiInterfaceTerminal.java @@ -50,6 +50,8 @@ import appeng.api.config.StringOrder; import appeng.api.config.TerminalStyle; import appeng.api.config.YesNo; import appeng.api.implementations.ICraftingPatternItem; +import appeng.api.parts.IInterfaceTerminal; +import appeng.api.storage.data.IAEStack; import appeng.api.util.NamedDimensionalCoord; import appeng.client.gui.AEBaseGui; import appeng.client.gui.IGuiTooltipHandler; @@ -78,7 +80,6 @@ import appeng.integration.IntegrationType; import appeng.integration.modules.NEI; import appeng.items.misc.ItemEncodedPattern; import appeng.me.cluster.implementations.CraftingCPUCluster; -import appeng.parts.reporting.PartInterfaceTerminal; import appeng.tile.inventory.AppEngInternalInventory; import appeng.util.Platform; import appeng.util.item.AEItemStack; @@ -148,7 +149,7 @@ public class GuiInterfaceTerminal extends AEBaseGui private static final float STEP_Z = 10.0f; private static final float MAGIC_RENDER_ITEM_Z = 50.0f; - public GuiInterfaceTerminal(final InventoryPlayer inventoryPlayer, final PartInterfaceTerminal te) { + public GuiInterfaceTerminal(final InventoryPlayer inventoryPlayer, final IInterfaceTerminal te) { this(new ContainerInterfaceTerminal(inventoryPlayer, te)); } @@ -234,28 +235,34 @@ public class GuiInterfaceTerminal extends AEBaseGui searchFieldNames.x = guiLeft + Math.max(32, VIEW_LEFT) + 99; searchFieldNames.y = guiTop + 38; + int offset = guiTop + 8; terminalStyleBox.xPosition = guiLeft - 18; - terminalStyleBox.yPosition = guiTop + 8; + terminalStyleBox.yPosition = offset; + offset += 18; searchStringSave.xPosition = guiLeft - 18; - searchStringSave.yPosition = terminalStyleBox.yPosition + 18; + searchStringSave.yPosition = offset; + offset += 18; guiButtonSectionOrder.xPosition = guiLeft - 18; - guiButtonSectionOrder.yPosition = searchStringSave.yPosition + 18; + guiButtonSectionOrder.yPosition = offset; + offset += 18; guiButtonBrokenRecipes.xPosition = guiLeft - 18; - guiButtonBrokenRecipes.yPosition = guiButtonSectionOrder.yPosition + 18; + guiButtonBrokenRecipes.yPosition = offset; + offset += 18; guiButtonHideFull.xPosition = guiLeft - 18; - guiButtonHideFull.yPosition = guiButtonBrokenRecipes.yPosition + 18; + guiButtonHideFull.yPosition = offset; + offset += 18; guiButtonAssemblersOnly.xPosition = guiLeft - 18; - guiButtonAssemblersOnly.yPosition = guiButtonHideFull.yPosition + 18; + guiButtonAssemblersOnly.yPosition = offset; + offset += 18; guiButtonUseSubstitute.xPosition = guiLeft - 18; - guiButtonUseSubstitute.yPosition = guiButtonAssemblersOnly.yPosition + 18; - - offsetY = guiButtonUseSubstitute.yPosition; // last button pos for ae2fc + guiButtonUseSubstitute.yPosition = offset; + offset += 18; setSearchString(); @@ -269,6 +276,8 @@ public class GuiInterfaceTerminal extends AEBaseGui buttonList.add(searchStringSave); buttonList.add(terminalStyleBox); buttonList.add(guiButtonUseSubstitute); + + initCustomButtons(this.guiLeft - 18, offset); } protected void repositionSlots() { @@ -345,6 +354,7 @@ public class GuiInterfaceTerminal extends AEBaseGui @Override protected void actionPerformed(final GuiButton btn) { + if (actionPerformedCustomButtons(btn)) return; if (btn == guiButtonAssemblersOnly) { onlyMolecularAssemblers = !onlyMolecularAssemblers; masterList.markDirty(); @@ -943,10 +953,10 @@ public class GuiInterfaceTerminal extends AEBaseGui for (int i = 0; i < tags.tagCount(); i++) { final NBTTagCompound tag = tags.getCompoundTagAt(i); - final ItemStack parsedItemStack = ItemStack.loadItemStackFromNBT(tag); + final IAEStack aes = Platform.readStackNBT(tag, true); - if (parsedItemStack != null) { - if (itemFilter.test(parsedItemStack)) { + if (aes != null) { + if (itemFilter.test(aes.getItemStackForNEI())) { return true; } } else if (containsInvalidDisplayName && !tag.hasNoTags()) { diff --git a/src/main/java/appeng/client/gui/implementations/GuiLevelEmitter.java b/src/main/java/appeng/client/gui/implementations/GuiLevelEmitter.java index b3b1babb8..a11250b79 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiLevelEmitter.java +++ b/src/main/java/appeng/client/gui/implementations/GuiLevelEmitter.java @@ -24,6 +24,9 @@ import appeng.api.config.RedstoneMode; import appeng.api.config.Settings; import appeng.api.config.Upgrades; import appeng.api.config.YesNo; +import appeng.api.parts.ILevelEmitter; +import appeng.api.storage.StorageName; +import appeng.client.gui.slots.VirtualMEPhantomSlot; import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.MEGuiTextField; import appeng.container.implementations.ContainerLevelEmitter; @@ -33,7 +36,6 @@ import appeng.core.localization.GuiText; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketConfigButton; import appeng.core.sync.packets.PacketValueConfig; -import appeng.parts.automation.PartLevelEmitter; import appeng.util.calculators.ArithHelper; import appeng.util.calculators.Calculator; @@ -56,7 +58,9 @@ public class GuiLevelEmitter extends GuiUpgradeable { private GuiImgButton levelMode; private GuiImgButton craftingMode; - public GuiLevelEmitter(final InventoryPlayer inventoryPlayer, final PartLevelEmitter te) { + private VirtualMEPhantomSlot config; + + public GuiLevelEmitter(final InventoryPlayer inventoryPlayer, final ILevelEmitter te) { super(new ContainerLevelEmitter(inventoryPlayer, te)); } @@ -70,6 +74,13 @@ public class GuiLevelEmitter extends GuiUpgradeable { this.amountTextField.setFocused(true); ((ContainerLevelEmitter) this.inventorySlots).setTextField(this.amountTextField); this.validateText(); + + this.config = new VirtualMEPhantomSlot( + 17, + 42, + ((ContainerLevelEmitter) inventorySlots).getLvlEmitter().getAEInventoryByName(StorageName.NONE), + 0); + this.registerVirtualSlots(this.config); } @Override @@ -250,6 +261,11 @@ public class GuiLevelEmitter extends GuiUpgradeable { super.mouseClicked(xCoord, yCoord, btn); } + @Override + protected void handlePhantomSlotInteraction(VirtualMEPhantomSlot slot, int mouseButton) { + slot.handleMouseClicked(true, true, isCtrlKeyDown()); + } + @Override protected void keyTyped(final char character, final int key) { if (!this.checkHotbarKeys(key)) { diff --git a/src/main/java/appeng/client/gui/implementations/GuiMEMonitorable.java b/src/main/java/appeng/client/gui/implementations/GuiMEMonitorable.java index 0b6dc0981..d0c7edfa3 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiMEMonitorable.java +++ b/src/main/java/appeng/client/gui/implementations/GuiMEMonitorable.java @@ -11,48 +11,55 @@ package appeng.client.gui.implementations; import java.io.IOException; +import java.text.NumberFormat; import java.util.List; +import java.util.Locale; +import javax.annotation.Nullable; + +import net.minecraft.client.Minecraft; import net.minecraft.client.gui.GuiButton; +import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.inventory.Slot; import net.minecraft.item.ItemStack; +import net.minecraft.util.EnumChatFormatting; import net.minecraftforge.client.event.GuiScreenEvent.InitGuiEvent; import net.minecraftforge.common.MinecraftForge; import org.lwjgl.input.Keyboard; import org.lwjgl.input.Mouse; -import appeng.api.AEApi; import appeng.api.config.CraftingStatus; import appeng.api.config.PinsState; import appeng.api.config.SearchBoxFocusPriority; import appeng.api.config.SearchBoxMode; import appeng.api.config.Settings; +import appeng.api.config.TerminalFontSize; import appeng.api.config.TerminalStyle; import appeng.api.config.YesNo; -import appeng.api.implementations.guiobjects.IPortableCell; -import appeng.api.implementations.tiles.IMEChest; import appeng.api.implementations.tiles.IViewCellStorage; import appeng.api.storage.ITerminalHost; import appeng.api.storage.ITerminalPins; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IDisplayRepo; -import appeng.api.storage.data.IItemList; import appeng.api.util.IConfigManager; import appeng.api.util.IConfigurableObject; import appeng.client.ActionKey; -import appeng.client.gui.AEBaseMEGui; +import appeng.client.gui.AEBaseGui; +import appeng.client.gui.slots.VirtualMEMonitorableSlot; +import appeng.client.gui.slots.VirtualMEPatternSlot; +import appeng.client.gui.slots.VirtualMEPinSlot; +import appeng.client.gui.slots.VirtualMESlot; import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.GuiScrollbar; import appeng.client.gui.widgets.GuiTabButton; import appeng.client.gui.widgets.IDropToFillTextField; import appeng.client.gui.widgets.ISortSource; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.client.me.InternalSlotME; import appeng.client.me.ItemRepo; -import appeng.client.me.PinSlotME; -import appeng.client.me.SlotME; +import appeng.container.AEBaseContainer; import appeng.container.implementations.ContainerMEMonitorable; import appeng.container.slot.AppEngSlot; import appeng.container.slot.SlotCraftingMatrix; @@ -67,22 +74,21 @@ import appeng.core.localization.GuiText; import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketInventoryAction; +import appeng.core.sync.packets.PacketMonitorableAction; import appeng.core.sync.packets.PacketPinsUpdate; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; import appeng.helpers.IPinsHandler; import appeng.helpers.InventoryAction; -import appeng.helpers.WirelessTerminalGuiObject; +import appeng.helpers.MonitorableAction; import appeng.integration.IntegrationRegistry; import appeng.integration.IntegrationType; import appeng.integration.modules.NEI; import appeng.items.storage.ItemViewCell; -import appeng.parts.reporting.AbstractPartTerminal; -import appeng.tile.misc.TileSecurity; import appeng.util.IConfigManagerHost; import appeng.util.Platform; -public class GuiMEMonitorable extends AEBaseMEGui +public class GuiMEMonitorable extends AEBaseGui implements ISortSource, IConfigManagerHost, IDropToFillTextField, IPinsHandler { public static int craftingGridOffsetX; @@ -90,7 +96,8 @@ public class GuiMEMonitorable extends AEBaseMEGui private static String memoryText = ""; private final IDisplayRepo repo; - private final int offsetX = 9; + protected int offsetRepoX = 9; + protected int offsetRepoY = 18; private final int MAGIC_HEIGHT_NUMBER = 114 + 1; private final int lowerTextureOffset = 0; private final IConfigManager configSrc; @@ -99,12 +106,12 @@ public class GuiMEMonitorable extends AEBaseMEGui private final ContainerMEMonitorable monitorableContainer; private GuiTabButton craftingStatusBtn; private GuiImgButton craftingStatusImgBtn; - private final MEGuiTextField searchField; + protected final MEGuiTextField searchField; private GuiText myName; private int perRow = 9; private int reservedSpace = 0; private boolean customSortOrder = true; - private int rows = 0; + protected int rows = 0; private int standardSize; private GuiImgButton ViewBox; private GuiImgButton SortByBox; @@ -122,6 +129,11 @@ public class GuiMEMonitorable extends AEBaseMEGui public final boolean hasPinHost; private boolean enableShiftPause = true; + protected VirtualMEPinSlot[] pinSlots = null; + protected VirtualMEMonitorableSlot[] monitorableSlots = null; + + private final ITerminalHost host; + public GuiMEMonitorable(final InventoryPlayer inventoryPlayer, final ITerminalHost te) { this(inventoryPlayer, te, new ContainerMEMonitorable(inventoryPlayer, te)); } @@ -134,6 +146,7 @@ public class GuiMEMonitorable extends AEBaseMEGui final GuiScrollbar scrollbar = new GuiScrollbar(); this.setScrollBar(scrollbar); this.repo = new ItemRepo(scrollbar, this); + this.host = te; this.xSize = 195; this.ySize = 204; @@ -148,17 +161,7 @@ public class GuiMEMonitorable extends AEBaseMEGui this.viewCell = te instanceof IViewCellStorage; - if (te instanceof TileSecurity) { - this.myName = GuiText.Security; - } else if (te instanceof WirelessTerminalGuiObject) { - this.myName = GuiText.WirelessTerminal; - } else if (te instanceof IPortableCell) { - this.myName = GuiText.PortableCell; - } else if (te instanceof IMEChest) { - this.myName = GuiText.Chest; - } else if (te instanceof AbstractPartTerminal) { - this.myName = GuiText.Terminal; - } + this.myName = te.getName(); hasPinHost = te instanceof ITerminalPins; @@ -176,8 +179,8 @@ public class GuiMEMonitorable extends AEBaseMEGui NEI.searchField.putFormatter(this.searchField); } - public void postUpdate(final List list) { - for (final IAEItemStack is : list) { + public void postUpdate(final List> list) { + for (final IAEStack is : list) { this.repo.postUpdate(is); } @@ -186,7 +189,7 @@ public class GuiMEMonitorable extends AEBaseMEGui } private void setScrollBar() { - this.getScrollBar().setTop(18).setLeft(175).setHeight(this.rows * 18 - 2); + this.getScrollBar().setTop(this.offsetRepoY).setLeft(166 + this.offsetRepoX).setHeight(this.rows * 18 - 2); this.getScrollBar().setRange( 0, (this.repo.size() + pinsState.ordinal() * 9 + this.perRow - 1) / this.perRow - this.rows, @@ -195,6 +198,7 @@ public class GuiMEMonitorable extends AEBaseMEGui @Override protected void actionPerformed(final GuiButton btn) { + if (actionPerformedCustomButtons(btn)) return; if (btn == this.craftingStatusBtn || btn == this.craftingStatusImgBtn) { NetworkHandler.instance.sendToServer(new PacketSwitchGuis(GuiBridge.GUI_CRAFTING_STATUS)); @@ -266,27 +270,36 @@ public class GuiMEMonitorable extends AEBaseMEGui : 9 + ((this.width - this.standardSize) / 18); this.rows = calculateRowsCount(); - this.getMeSlots().clear(); - // make sure we have space at least for one row of normal slots, because pins not adjusted by scroll bar adjustPinsSize(); + super.initGui(); + int pinsRows = pinsState.ordinal(); + this.pinSlots = new VirtualMEPinSlot[pinsRows * this.perRow]; for (int y = 0; y < pinsRows; y++) { for (int x = 0; x < this.perRow; x++) { - this.getMeSlots() - .add(new PinSlotME(this.repo, x + y * this.perRow, this.offsetX + x * 18, y * 18 + 18)); + VirtualMEPinSlot slot = new VirtualMEPinSlot( + this.offsetRepoX + x * 18, + y * 18 + this.offsetRepoY, + this.repo, + y * this.perRow + x); + this.pinSlots[y * this.perRow + x] = slot; + this.registerVirtualSlots(slot); } } - for (int y = 0; y < this.rows - pinsRows; y++) { + int normalSlotRows = this.rows - pinsRows; + this.monitorableSlots = new VirtualMEMonitorableSlot[normalSlotRows * this.perRow]; + for (int y = 0; y < normalSlotRows; y++) { for (int x = 0; x < this.perRow; x++) { - this.getMeSlots().add( - new InternalSlotME( - this.repo, - x + y * this.perRow, - this.offsetX + x * 18, - 18 + y * 18 + pinsRows * 18)); + VirtualMEMonitorableSlot slot = new VirtualMEMonitorableSlot( + this.offsetRepoX + x * 18, + this.offsetRepoY + y * 18 + pinsRows * 18, + this.repo, + y * this.perRow + x); + this.monitorableSlots[y * this.perRow + x] = slot; + this.registerVirtualSlots(slot); } } @@ -296,7 +309,6 @@ public class GuiMEMonitorable extends AEBaseMEGui this.xSize = this.standardSize; } - super.initGui(); // full size : 204 // extra slots : 72 // slot 18 @@ -319,7 +331,7 @@ public class GuiMEMonitorable extends AEBaseMEGui offset += 20; } - if (this.viewCell || this instanceof GuiWirelessTerm) { + if (this.viewCell) { this.buttonList.add( this.ViewBox = new GuiImgButton( this.guiLeft - 18, @@ -328,15 +340,13 @@ public class GuiMEMonitorable extends AEBaseMEGui this.configSrc.getSetting(Settings.VIEW_MODE))); offset += 20; } - if (!AEApi.instance().registries().itemDisplay().getItemFilters().isEmpty()) { - this.buttonList.add( - this.typeFilter = new GuiImgButton( - this.guiLeft - 18, - offset, - Settings.TYPE_FILTER, - this.configSrc.getSetting(Settings.TYPE_FILTER))); - offset += 20; - } + this.buttonList.add( + this.typeFilter = new GuiImgButton( + this.guiLeft - 18, + offset, + Settings.TYPE_FILTER, + this.configSrc.getSetting(Settings.TYPE_FILTER))); + offset += 20; this.buttonList.add( this.SortDirBox = new GuiImgButton( @@ -362,7 +372,7 @@ public class GuiMEMonitorable extends AEBaseMEGui AEConfig.instance.preserveSearchBar ? YesNo.YES : YesNo.NO)); offset += 20; - if (!(this instanceof GuiMEPortableCell) || this instanceof GuiWirelessTerm) { + if (!(this instanceof GuiMEPortableCell)) { this.buttonList.add( this.terminalStyleBox = new GuiImgButton( this.guiLeft - 18, @@ -372,7 +382,9 @@ public class GuiMEMonitorable extends AEBaseMEGui offset += 20; } - if (this.viewCell || this instanceof GuiWirelessTerm) { + initCustomButtons(this.guiLeft - 18, offset); + + if (this.viewCell) { if (AEConfig.instance.getConfigManager().getSetting(Settings.CRAFTING_STATUS) .equals(CraftingStatus.BUTTON)) { this.buttonList.add( @@ -396,8 +408,8 @@ public class GuiMEMonitorable extends AEBaseMEGui if (hasPinHost) { this.buttonList.add( this.pinsStateButton = new GuiImgButton( - this.guiLeft + 178, - this.guiTop + 18 + (rows * 18) + 25, + getPinButtonX(), + getPinButtonY(), Settings.PINS_STATE, configSrc.getSetting(Settings.PINS_STATE))); } @@ -406,7 +418,7 @@ public class GuiMEMonitorable extends AEBaseMEGui final Enum searchMode = AEConfig.instance.settings.getSetting(Settings.SEARCH_MODE); this.canBeAutoFocused = SearchBoxMode.AUTOSEARCH == searchMode || SearchBoxMode.NEI_AUTOSEARCH == searchMode; - this.searchField.x = this.guiLeft + Math.max(80, this.offsetX); + this.searchField.x = this.guiLeft + this.offsetRepoX + 71; this.searchField.y = this.guiTop + 4; this.searchField.setFocused(this.canBeAutoFocused); this.isAutoFocused = this.canBeAutoFocused; @@ -458,6 +470,14 @@ public class GuiMEMonitorable extends AEBaseMEGui return Math.max(3, Math.min(this.getMaxRows(), (int) Math.floor(extraSpace / 18))); } + protected int getPinButtonX() { + return this.guiLeft + 178; + } + + protected int getPinButtonY() { + return this.guiTop + 18 + (rows * 18) + 25; + } + @Override public void drawFG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { this.fontRendererObj.drawString( @@ -471,18 +491,147 @@ public class GuiMEMonitorable extends AEBaseMEGui this.ySize - 96 + 3, GuiColors.MEMonitorableInventory.getColor()); + VirtualMEPinSlot.drawSlotsBackground(this.pinSlots, this.mc, this.zLevel); + this.currentMouseX = mouseX; this.currentMouseY = mouseY; } + @Override + public List handleItemTooltip(ItemStack stack, int mouseX, int mouseY, List currentToolTip) { + super.handleItemTooltip(stack, mouseX, mouseY, currentToolTip); + VirtualMESlot hoveredSlot = this.getVirtualMESlotUnderMouse(); + + final boolean isMonitorableSlot = hoveredSlot instanceof VirtualMEMonitorableSlot; + if (isMonitorableSlot || hoveredSlot instanceof VirtualMEPatternSlot) { + IAEStack aes = hoveredSlot.getAEStack(); + final int threshold = AEConfig.instance.getTerminalFontSize() == TerminalFontSize.SMALL ? 9999 : 999; + if (aes != null && aes.getStackSize() > threshold) { + final String local = isMonitorableSlot ? ButtonToolTips.ItemsStored.getLocal() + : ButtonToolTips.ItemCount.getLocal(); + final String formattedAmount = NumberFormat.getNumberInstance(Locale.US).format(aes.getStackSize()); + currentToolTip.add(EnumChatFormatting.GRAY + String.format(local, formattedAmount)); + } + } + + return currentToolTip; + } + @Override protected void mouseClicked(final int xCoord, final int yCoord, final int btn) { searchField.mouseClicked(xCoord, yCoord, btn); isAutoFocused = false; + if (handleViewCellClick(xCoord, yCoord, btn)) return; + super.mouseClicked(xCoord, yCoord, btn); } + private void sendAction(MonitorableAction action, @Nullable IAEStack stack, int custom) { + ((AEBaseContainer) this.inventorySlots).setTargetStack(stack); + final PacketMonitorableAction p = new PacketMonitorableAction(action, custom); + NetworkHandler.instance.sendToServer(p); + } + + @Override + protected boolean handleVirtualSlotClick(VirtualMESlot virtualSlot, final int mouseButton) { + if (this.handleMonitorableSlotClick(virtualSlot, mouseButton)) return true; + else return super.handleVirtualSlotClick(virtualSlot, mouseButton); + } + + private boolean handleMonitorableSlotClick(VirtualMESlot virtualSlot, final int mouseButton) { + if (!(virtualSlot instanceof VirtualMEMonitorableSlot slot)) return false; + IAEItemStack slotStack = slot.getAEStack() instanceof IAEItemStack ais ? ais : null; + + if (Keyboard.isKeyDown(Keyboard.KEY_SPACE)) { + if (slotStack != null) { + this.sendAction(MonitorableAction.MOVE_REGION, slotStack, -1); + return true; + } + return false; + } + + final EntityPlayer player = Minecraft.getMinecraft().thePlayer; + + final boolean isLShiftDown = isShiftKeyDown(); + final boolean isLControlDown = isCtrlKeyDown(); + + switch (mouseButton) { + case 0 -> { // left click + if (slot instanceof VirtualMEPinSlot && player.inventory.getItemStack() != null) { + this.sendAction( + isLControlDown ? MonitorableAction.SET_CONTAINER_PIN : MonitorableAction.SET_ITEM_PIN, + null, + slot.getSlotIndex()); + return true; + } + + if (isLControlDown) { + this.sendAction( + isLShiftDown ? MonitorableAction.FILL_CONTAINERS : MonitorableAction.FILL_SINGLE_CONTAINER, + slot.getAEStack(), + -1); + return true; + } + + if (isLShiftDown) { + this.sendAction(MonitorableAction.SHIFT_CLICK, slotStack, -1); + return true; + } + + if (slot.getAEStack() != null && slot.getAEStack().getStackSize() == 0 + && player.inventory.getItemStack() == null) { + this.sendAction(MonitorableAction.AUTO_CRAFT, slot.getAEStack(), -1); + return true; + } + this.sendAction(MonitorableAction.PICKUP_OR_SET_DOWN, slotStack, -1); + return true; + } + case 1 -> { // right click + if (slot instanceof VirtualMEPinSlot) { + if (isLShiftDown) { + this.sendAction(MonitorableAction.UNSET_PIN, null, slot.getSlotIndex()); + } else { + this.sendAction( + isLControlDown ? MonitorableAction.SET_CONTAINER_PIN : MonitorableAction.SET_ITEM_PIN, + null, + slot.getSlotIndex()); + } + return true; + } + + if (isLControlDown) { + this.sendAction( + isLShiftDown ? MonitorableAction.DRAIN_CONTAINERS + : MonitorableAction.DRAIN_SINGLE_CONTAINER, + slot.getAEStack(), + -1); + return true; + } + + if (isLShiftDown) { + this.sendAction(MonitorableAction.PICKUP_SINGLE, slotStack, -1); + return true; + } + + this.sendAction(MonitorableAction.SPLIT_OR_PLACE_SINGLE, slotStack, -1); + return true; + } + case 2 -> { // middle click + if (slot.getAEStack() != null && slot.getAEStack().isCraftable()) { + this.sendAction(MonitorableAction.AUTO_CRAFT, slot.getAEStack(), -1); + return true; + } else if (player.capabilities.isCreativeMode) { + this.sendAction(MonitorableAction.CREATIVE_DUPLICATE, slotStack, -1); + return true; + } + } + default -> {} + } + + return false; + } + private boolean handleViewCellClick(final int xCoord, final int yCoord, final int btn) { if (this.viewCell && monitorableContainer.canAccessViewCells && btn == 1) { Slot slot = getSlot(xCoord, yCoord); @@ -507,6 +656,30 @@ public class GuiMEMonitorable extends AEBaseMEGui return false; } + @Override + protected boolean mouseWheelEvent(int x, int y, int wheel) { + VirtualMESlot slot = this.getVirtualMESlotUnderMouse(); + if (!isShiftKeyDown() || !(slot instanceof VirtualMEMonitorableSlot)) return false; + + final MonitorableAction direction = wheel > 0 ? MonitorableAction.ROLL_DOWN : MonitorableAction.ROLL_UP; + if (direction == MonitorableAction.ROLL_DOWN + && Minecraft.getMinecraft().thePlayer.inventory.getItemStack() == null) { + return false; + } + if (direction == MonitorableAction.ROLL_UP && !(slot.getAEStack() instanceof IAEItemStack)) { + return false; + } + + ((AEBaseContainer) this.inventorySlots).setTargetStack(slot.getAEStack()); + final int times = Math.abs(wheel); + for (int i = 0; i < times; i++) { + final PacketMonitorableAction p = new PacketMonitorableAction(direction, -1); + NetworkHandler.instance.sendToServer(p); + } + + return true; + } + @Override public void onGuiClosed() { super.onGuiClosed(); @@ -537,6 +710,16 @@ public class GuiMEMonitorable extends AEBaseMEGui x_width, 99 + this.reservedSpace - this.lowerTextureOffset); + this.searchField.drawTextBox(); + + this.updateViewCells(); + } + + protected String getBackground() { + return "guis/terminal.png"; + } + + protected void updateViewCells() { if (this.viewCell) { boolean update = false; @@ -551,12 +734,6 @@ public class GuiMEMonitorable extends AEBaseMEGui this.repo.setViewCell(this.myCurrentViewCells); } } - - searchField.drawTextBox(); - } - - protected String getBackground() { - return "guis/terminal.png"; } @Override @@ -564,7 +741,7 @@ public class GuiMEMonitorable extends AEBaseMEGui return this.repo.hasPower(); } - int getMaxRows() { + protected int getMaxRows() { return AEConfig.instance.getConfigManager().getSetting(Settings.TERMINAL_STYLE) == TerminalStyle.SMALL ? AEConfig.instance.MEMonitorableSmallSize : Integer.MAX_VALUE; @@ -588,10 +765,9 @@ public class GuiMEMonitorable extends AEBaseMEGui if (CommonHelper.proxy.isActionKey(ActionKey.SEARCH_CONNECTED_INVENTORIES, key) && !(NEI.searchField.focused() || searchField.isFocused())) { - final boolean mouseInGui = this - .isPointInRegion(0, 0, this.xSize, this.ySize, this.currentMouseX, this.currentMouseY); - if (mouseInGui && getSlot(this.currentMouseX, this.currentMouseY) instanceof SlotME sme) { - IAEItemStack stack = sme.getAEStack(); + VirtualMESlot slot = this.getVirtualMESlotUnderMouse(); + if (slot instanceof VirtualMEMonitorableSlot monitorableSlot) { + IAEStack stack = monitorableSlot.getAEStack(); this.monitorableContainer.setTargetStack(stack); if (stack != null) { final PacketInventoryAction p = new PacketInventoryAction( @@ -705,11 +881,11 @@ public class GuiMEMonitorable extends AEBaseMEGui && pointY < rectY + rectHeight + 1; } - int getReservedSpace() { + protected int getReservedSpace() { return this.reservedSpace; } - void setReservedSpace(final int reservedSpace) { + protected void setReservedSpace(final int reservedSpace) { this.reservedSpace = reservedSpace; } @@ -760,7 +936,7 @@ public class GuiMEMonitorable extends AEBaseMEGui super.handleKeyboardInput(); // Pause the terminal when holding shift - if (enableShiftPause) this.repo.setPaused(hasShiftDown()); + if (enableShiftPause) this.repo.setPaused(isShiftKeyDown()); } public boolean hideItemPanelSlot(int tx, int ty, int tw, int th) { @@ -789,12 +965,8 @@ public class GuiMEMonitorable extends AEBaseMEGui return false; } - private boolean hasShiftDown() { - return Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) || Keyboard.isKeyDown(Keyboard.KEY_RSHIFT); - } - @Override - public void setAEPins(IAEItemStack[] pins) { + public void setAEPins(IAEStack[] pins) { repo.setAEPins(pins); } @@ -802,20 +974,4 @@ public class GuiMEMonitorable extends AEBaseMEGui public void setPinsState(PinsState state) { configSrc.putSetting(Settings.PINS_STATE, state); } - - /// returns all items visible from the terminal - /// @return the returned list is **read-only** - public IItemList getAvaibleItems() { - return repo.getAvailableItems(); - } - - // Moving items via hotbar keys in terminals isn't working anyway. - // Let's disable hotbar keys processing for terminal slots to allow proper input of numbers in the search field - @Override - protected boolean checkHotbarKeys(int keyCode) { - if (theSlot instanceof SlotME) { - return false; - } - return super.checkHotbarKeys(keyCode); - } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiMEPortableCell.java b/src/main/java/appeng/client/gui/implementations/GuiMEPortableCell.java index e18cc0434..7c81dcf94 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiMEPortableCell.java +++ b/src/main/java/appeng/client/gui/implementations/GuiMEPortableCell.java @@ -26,7 +26,7 @@ public class GuiMEPortableCell extends GuiMEMonitorable { } @Override - int getMaxRows() { + protected int getMaxRows() { return 3; } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiNetworkStatus.java b/src/main/java/appeng/client/gui/implementations/GuiNetworkStatus.java index 6e36f18f4..595a8a8c6 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiNetworkStatus.java +++ b/src/main/java/appeng/client/gui/implementations/GuiNetworkStatus.java @@ -21,7 +21,6 @@ import java.util.Map; import net.minecraft.client.gui.GuiButton; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.Slot; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraftforge.common.util.ForgeDirection; @@ -35,6 +34,7 @@ import appeng.api.config.SortOrder; import appeng.api.config.ViewItems; import appeng.api.implementations.guiobjects.INetworkTool; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.util.NamedDimensionalCoord; import appeng.client.gui.AEBaseGui; import appeng.client.gui.widgets.GuiContextMenu; @@ -42,7 +42,6 @@ import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.GuiScrollbar; import appeng.client.gui.widgets.ISortSource; import appeng.client.me.ItemRepo; -import appeng.client.me.SlotME; import appeng.client.render.highlighter.BlockPosHighlighter; import appeng.container.implementations.ContainerNetworkStatus; import appeng.core.AEConfig; @@ -131,10 +130,10 @@ public class GuiNetworkStatus extends AEBaseGui implements ISortSource { ItemStack is = null; if (tooltip > -1) { - final IAEItemStack aeStack = repo.getReferenceItem(tooltip); + final IAEStack aeStack = repo.getReferenceStack(tooltip); - if (aeStack != null) { - is = aeStack.getItemStack(); + if (aeStack instanceof IAEItemStack ais) { + is = ais.getItemStack(); } } @@ -278,10 +277,10 @@ public class GuiNetworkStatus extends AEBaseGui implements ISortSource { this.drawTexturedModalRect(offsetX, offsetY, 0, 0, this.xSize, this.ySize); } - public void postUpdate(final List list) { + public void postUpdate(final List> list) { this.repo.clear(); - for (final IAEItemStack is : list) { + for (final IAEStack is : list) { this.repo.postUpdate(is); } @@ -295,61 +294,6 @@ public class GuiNetworkStatus extends AEBaseGui implements ISortSource { this.getScrollBar().setRange(0, (size + 4) / 5 - this.rows, 1); } - // @Override - NEI - public List handleItemTooltip(final ItemStack stack, final int mouseX, final int mouseY, - final List currentToolTip) { - if (stack != null) { - final Slot s = this.getSlot(mouseX, mouseY); - if (s instanceof SlotME) { - IAEItemStack myStack = null; - - try { - final SlotME theSlotField = (SlotME) s; - myStack = theSlotField.getAEStack(); - } catch (final Throwable ignore) {} - - if (myStack != null) { - while (currentToolTip.size() > 1) { - currentToolTip.remove(1); - } - } - } - } - return currentToolTip; - } - - // Vanilla version... - protected void drawItemStackTooltip(final ItemStack stack, final int x, final int y) { - final Slot s = this.getSlot(x, y); - if (s instanceof SlotME && stack != null) { - IAEItemStack myStack = null; - - try { - final SlotME theSlotField = (SlotME) s; - myStack = theSlotField.getAEStack(); - } catch (final Throwable ignore) {} - - if (myStack != null) { - final List currentToolTip = stack - .getTooltip(this.mc.thePlayer, this.mc.gameSettings.advancedItemTooltips); - - while (currentToolTip.size() > 1) { - currentToolTip.remove(1); - } - - currentToolTip.add( - GuiText.Installed.getLocal() + ": " - + NumberFormat.getNumberInstance(Locale.US).format(myStack.getStackSize())); - currentToolTip.add( - GuiText.EnergyDrain.getLocal() + ": " - + Platform.formatPowerLong(myStack.getCountRequestable(), true)); - - this.drawTooltip(x, y, currentToolTip.toArray(new String[0])); - } - } - // super.drawItemStackTooltip( stack, x, y ); - } - @Override public Enum getSortBy() { return SortOrder.NAME; @@ -466,8 +410,8 @@ public class GuiNetworkStatus extends AEBaseGui implements ISortSource { int toolPosY = 0; for (int z = viewStart; z < Math.min(viewEnd, this.repo.size()); z++) { - final IAEItemStack refStack = this.repo.getReferenceItem(z); - if (refStack != null) { + final IAEStack aes = this.repo.getReferenceStack(z); + if (aes instanceof IAEItemStack refStack) { GL11.glPushMatrix(); GL11.glScaled(0.5, 0.5, 0.5); diff --git a/src/main/java/appeng/client/gui/implementations/GuiOptimizePatterns.java b/src/main/java/appeng/client/gui/implementations/GuiOptimizePatterns.java index e4e9093dd..3cb213d1d 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiOptimizePatterns.java +++ b/src/main/java/appeng/client/gui/implementations/GuiOptimizePatterns.java @@ -24,7 +24,8 @@ import appeng.api.config.Settings; import appeng.api.config.TerminalStyle; import appeng.api.storage.ITerminalHost; import appeng.api.storage.data.IAEItemStack; -import appeng.client.gui.AEBaseGui; +import appeng.api.storage.data.IAEStack; +import appeng.client.gui.GuiSub; import appeng.client.gui.IGuiTooltipHandler; import appeng.client.gui.widgets.GuiScrollbar; import appeng.container.implementations.ContainerOptimizePatterns; @@ -32,21 +33,15 @@ import appeng.core.AEConfig; import appeng.core.AELog; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketOptimizePatterns; import appeng.core.sync.packets.PacketSwitchGuis; -import appeng.helpers.WirelessTerminalGuiObject; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; -import appeng.parts.reporting.PartTerminal; import appeng.util.Platform; import appeng.util.ReadableNumberConverter; import appeng.util.calculators.ArithHelper; import appeng.util.calculators.Calculator; -public class GuiOptimizePatterns extends AEBaseGui implements IGuiTooltipHandler { +public class GuiOptimizePatterns extends GuiSub implements IGuiTooltipHandler { private GuiTextField amountToCraft; private int amountToCraftI = 1; @@ -57,7 +52,6 @@ public class GuiOptimizePatterns extends AEBaseGui implements IGuiTooltipHandler final GuiScrollbar scrollbar; - private GuiBridge OriginalGui; private GuiButton cancel; private GuiButton optimize; @@ -76,26 +70,6 @@ public class GuiOptimizePatterns extends AEBaseGui implements IGuiTooltipHandler scrollbar = new GuiScrollbar(); this.setScrollBar(scrollbar); - - if (te instanceof WirelessTerminalGuiObject) { - this.OriginalGui = GuiBridge.GUI_WIRELESS_TERM; - } - - if (te instanceof PartTerminal) { - this.OriginalGui = GuiBridge.GUI_ME; - } - - if (te instanceof PartCraftingTerminal) { - this.OriginalGui = GuiBridge.GUI_CRAFTING_TERMINAL; - } - - if (te instanceof PartPatternTerminal) { - this.OriginalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - if (te instanceof PartPatternTerminalEx) { - this.OriginalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } } @Override @@ -400,9 +374,7 @@ public class GuiOptimizePatterns extends AEBaseGui implements IGuiTooltipHandler super.actionPerformed(btn); if (btn == this.cancel) { - if (this.OriginalGui != null) { - NetworkHandler.instance.sendToServer(new PacketSwitchGuis(this.OriginalGui)); - } + NetworkHandler.instance.sendToServer(new PacketSwitchGuis()); } else if (btn == this.optimize && this.optimize.enabled) { try { NetworkHandler.instance.sendToServer(new PacketOptimizePatterns(multiplierMap)); @@ -425,10 +397,12 @@ public class GuiOptimizePatterns extends AEBaseGui implements IGuiTooltipHandler super.mouseClicked(xCoord, yCoord, btn); } - public void postUpdate(final List list, final byte ref) { + public void postUpdate(final List> list, final byte ref) { visual.clear(); - for (IAEItemStack stack : list) { - visual.add(stack.copy()); + for (IAEStack stack : list) { + if (stack instanceof IAEItemStack ais) { + visual.add(ais.copy()); + } } this.sortItems(); diff --git a/src/main/java/appeng/client/gui/implementations/GuiOreFilter.java b/src/main/java/appeng/client/gui/implementations/GuiOreFilter.java index c10fd3113..450979c05 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiOreFilter.java +++ b/src/main/java/appeng/client/gui/implementations/GuiOreFilter.java @@ -9,26 +9,21 @@ import net.minecraftforge.oredict.OreDictionary; import org.lwjgl.input.Keyboard; import org.lwjgl.input.Mouse; -import appeng.client.gui.AEBaseGui; +import appeng.client.gui.GuiSub; import appeng.client.gui.widgets.IDropToFillTextField; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; import appeng.container.implementations.ContainerOreFilter; import appeng.core.AELog; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; import appeng.helpers.IOreFilterable; import appeng.integration.modules.NEI; -import appeng.parts.automation.PartSharedItemBus; -import appeng.parts.misc.PartStorageBus; -import appeng.tile.misc.TileCellWorkbench; import appeng.util.prioitylist.OreFilteredList.OreFilterTextFormatter; -public class GuiOreFilter extends AEBaseGui implements IDropToFillTextField { +public class GuiOreFilter extends GuiSub implements IDropToFillTextField { private MEGuiTextField textField; @@ -151,14 +146,8 @@ public class GuiOreFilter extends AEBaseGui implements IDropToFillTextField { } catch (IOException e) { AELog.debug(e); } - final Object target = ((AEBaseContainer) this.inventorySlots).getTarget(); - GuiBridge OriginalGui = null; - if (target instanceof PartStorageBus) OriginalGui = GuiBridge.GUI_STORAGEBUS; - else if (target instanceof PartSharedItemBus) OriginalGui = GuiBridge.GUI_BUS; - else if (target instanceof TileCellWorkbench) OriginalGui = GuiBridge.GUI_CELL_WORKBENCH; - if (OriginalGui != null) NetworkHandler.instance.sendToServer(new PacketSwitchGuis(OriginalGui)); - else this.mc.thePlayer.closeScreen(); + NetworkHandler.instance.sendToServer(new PacketSwitchGuis()); } else if (!this.textField.textboxKeyTyped(character, key)) { super.keyTyped(character, key); diff --git a/src/main/java/appeng/client/gui/implementations/GuiPatternItemRenamer.java b/src/main/java/appeng/client/gui/implementations/GuiPatternItemRenamer.java index 2faf8ea1c..698697f55 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiPatternItemRenamer.java +++ b/src/main/java/appeng/client/gui/implementations/GuiPatternItemRenamer.java @@ -1,47 +1,32 @@ package appeng.client.gui.implementations; -import net.minecraft.client.Minecraft; -import net.minecraft.client.gui.inventory.GuiContainer; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.Slot; import net.minecraft.item.ItemStack; import org.lwjgl.input.Keyboard; import appeng.api.storage.ITerminalHost; -import appeng.client.gui.AEBaseGui; +import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.client.gui.GuiSub; import appeng.client.gui.widgets.IDropToFillTextField; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; -import appeng.container.implementations.ContainerPatternItemRenamer; +import appeng.container.implementations.ContainerPatternValueAmount; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; -import appeng.core.sync.packets.PacketPatternItemRenamer; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; +import appeng.core.sync.packets.PacketPatternValueSet; +import appeng.util.item.AEItemStack; -public class GuiPatternItemRenamer extends AEBaseGui implements IDropToFillTextField { +public class GuiPatternItemRenamer extends GuiSub implements IDropToFillTextField { + private final ContainerPatternValueAmount container; private final MEGuiTextField textField; - private final String oldName; - private final int valueIndex; - private GuiBridge originalGui; public GuiPatternItemRenamer(InventoryPlayer ip, ITerminalHost p) { - super(new ContainerPatternItemRenamer(ip, p)); - GuiContainer gui = (GuiContainer) Minecraft.getMinecraft().currentScreen; - if (gui != null && gui.theSlot != null && gui.theSlot.getHasStack()) { - Slot slot = gui.theSlot; - oldName = slot.getStack().getDisplayName(); - valueIndex = slot.slotNumber; - } else { - valueIndex = -1; - oldName = ""; - } + super(new ContainerPatternValueAmount(ip, p)); + this.container = (ContainerPatternValueAmount) this.inventorySlots; xSize = 256; - textField = new MEGuiTextField(231, 12); } @@ -52,10 +37,12 @@ public class GuiPatternItemRenamer extends AEBaseGui implements IDropToFillTextF textField.x = guiLeft + 12; textField.y = guiTop + 35; textField.setFocused(true); - textField.setText(oldName); + } + + public void update() { + textField.setText(container.getAEStack().getDisplayName()); textField.setCursorPositionEnd(); textField.setSelectionPos(0); - setOriginGUI(((AEBaseContainer) inventorySlots).getTarget()); } @Override @@ -76,24 +63,24 @@ public class GuiPatternItemRenamer extends AEBaseGui implements IDropToFillTextF super.mouseClicked(xCoord, yCoord, btn); } - protected void setOriginGUI(Object target) { - if (target instanceof PartPatternTerminal) { - originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } else if (target instanceof PartPatternTerminalEx) { - originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } - } - @Override protected void keyTyped(final char character, final int key) { if (key == Keyboard.KEY_RETURN || key == Keyboard.KEY_NUMPADENTER) { - NetworkHandler.instance - .sendToServer(new PacketPatternItemRenamer(originalGui.ordinal(), textField.getText(), valueIndex)); + NetworkHandler.instance.sendToServer( + new PacketPatternValueSet( + getNewNameStack(), + this.container.getInvName(), + this.container.getSlotIndex())); } else if (!textField.textboxKeyTyped(character, key)) { super.keyTyped(character, key); } } + private IAEStack getNewNameStack() { + return AEItemStack.create( + ((IAEItemStack) this.container.getAEStack()).getItemStack().setStackDisplayName(textField.getText())); + } + public boolean isOverTextField(final int mousex, final int mousey) { return textField.isMouseIn(mousex, mousey); } @@ -101,12 +88,4 @@ public class GuiPatternItemRenamer extends AEBaseGui implements IDropToFillTextF public void setTextFieldValue(final String displayName, final int mousex, final int mousey, final ItemStack stack) { textField.setText(displayName); } - - public int getValueIndex() { - return valueIndex; - } - - public String getText() { - return textField.getText(); - } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiPatternMulti.java b/src/main/java/appeng/client/gui/implementations/GuiPatternMulti.java index dab4bbea5..fb08bd075 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiPatternMulti.java +++ b/src/main/java/appeng/client/gui/implementations/GuiPatternMulti.java @@ -2,24 +2,17 @@ package appeng.client.gui.implementations; import net.minecraft.client.gui.GuiButton; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.item.ItemStack; -import appeng.api.AEApi; import appeng.api.config.ActionItems; import appeng.api.config.Settings; -import appeng.api.definitions.IDefinitions; -import appeng.api.definitions.IParts; import appeng.api.storage.ITerminalHost; import appeng.client.gui.widgets.GuiImgButton; import appeng.container.implementations.ContainerPatternMulti; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketPatternMultiSet; import appeng.helpers.Reflected; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; import appeng.util.calculators.ArithHelper; import appeng.util.calculators.Calculator; @@ -50,26 +43,6 @@ public class GuiPatternMulti extends GuiAmount { this.amountTextField.setSelectionPos(0); } - @Override - protected void setOriginGUI(Object target) { - final IDefinitions definitions = AEApi.instance().definitions(); - final IParts parts = definitions.parts(); - - if (target instanceof PartPatternTerminal) { - for (final ItemStack stack : parts.patternTerminal().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - else if (target instanceof PartPatternTerminalEx) { - for (final ItemStack stack : parts.patternTerminalEx().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } - } - @Override public void drawFG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { this.fontRendererObj @@ -101,8 +74,8 @@ public class GuiPatternMulti extends GuiAmount { if (btn == this.nextBtn && btn.enabled) { int resultI = getAmount(); - if (resultI > 1 || resultI < -1) NetworkHandler.instance - .sendToServer(new PacketPatternMultiSet(this.originalGui.ordinal(), resultI)); + if (resultI > 1 || resultI < -1) + NetworkHandler.instance.sendToServer(new PacketPatternMultiSet(resultI)); } } catch (final NumberFormatException e) { // nope.. diff --git a/src/main/java/appeng/client/gui/implementations/GuiPatternTerm.java b/src/main/java/appeng/client/gui/implementations/GuiPatternTerm.java index c54c3edda..79f4cf83e 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiPatternTerm.java +++ b/src/main/java/appeng/client/gui/implementations/GuiPatternTerm.java @@ -25,16 +25,21 @@ import appeng.api.config.ItemSubstitution; import appeng.api.config.PatternBeSubstitution; import appeng.api.config.Settings; import appeng.api.storage.ITerminalHost; +import appeng.api.storage.StorageName; +import appeng.client.gui.slots.VirtualMEPatternSlot; +import appeng.client.gui.slots.VirtualMEPhantomSlot; import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.GuiTabButton; import appeng.container.implementations.ContainerPatternTerm; import appeng.container.slot.AppEngSlot; +import appeng.core.AELog; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; +import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; -import appeng.core.sync.packets.PacketInventoryAction; +import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; -import appeng.helpers.InventoryAction; +import appeng.tile.inventory.IAEStackInventory; public class GuiPatternTerm extends GuiMEMonitorable { @@ -48,28 +53,35 @@ public class GuiPatternTerm extends GuiMEMonitorable { private GuiTabButton tabCraftButton; private GuiTabButton tabProcessButton; - private GuiImgButton substitutionsEnabledBtn; - private GuiImgButton substitutionsDisabledBtn; - private GuiImgButton beSubstitutionsEnabledBtn; - private GuiImgButton beSubstitutionsDisabledBtn; + protected GuiImgButton substitutionsEnabledBtn; + protected GuiImgButton substitutionsDisabledBtn; + protected GuiImgButton beSubstitutionsEnabledBtn; + protected GuiImgButton beSubstitutionsDisabledBtn; private GuiImgButton encodeBtn; - private GuiImgButton clearBtn; - private GuiImgButton doubleBtn; + protected GuiImgButton clearBtn; + protected GuiImgButton doubleBtn; + + protected VirtualMEPatternSlot[] craftingSlots; + protected VirtualMEPatternSlot[] outputSlots; + private boolean cragtingMode; + + public GuiPatternTerm(final InventoryPlayer inventoryPlayer, final ITerminalHost te, + final ContainerPatternTerm containerPatternTerm) { + super(inventoryPlayer, te, containerPatternTerm); + this.container = (ContainerPatternTerm) this.inventorySlots; + this.cragtingMode = this.container.isCraftingMode(); + this.setReservedSpace(81); + } public GuiPatternTerm(final InventoryPlayer inventoryPlayer, final ITerminalHost te) { - super(inventoryPlayer, te, new ContainerPatternTerm(inventoryPlayer, te)); - this.container = (ContainerPatternTerm) this.inventorySlots; - this.setReservedSpace(81); + this(inventoryPlayer, te, new ContainerPatternTerm(inventoryPlayer, te, true)); } @Override protected void mouseClicked(final int xCoord, final int yCoord, final int btn) { if (btn == 2 && doubleBtn.mousePressed(this.mc, xCoord, yCoord)) { // - InventoryAction action = InventoryAction.SET_PATTERN_MULTI; - - final PacketInventoryAction p = new PacketInventoryAction(action, 0, 0); - NetworkHandler.instance.sendToServer(p); + NetworkHandler.instance.sendToServer(new PacketSwitchGuis(GuiBridge.GUI_PATTERN_MULTI)); } else super.mouseClicked(xCoord, yCoord, btn); } @@ -80,6 +92,8 @@ public class GuiPatternTerm extends GuiMEMonitorable { try { if (this.tabCraftButton == btn || this.tabProcessButton == btn) { + this.cragtingMode = this.tabProcessButton == btn; + updateSlotVisibility(); NetworkHandler.instance.sendToServer( new PacketValueConfig( "PatternTerminal.CraftMode", @@ -108,29 +122,30 @@ public class GuiPatternTerm extends GuiMEMonitorable { .sendToServer(new PacketValueConfig("PatternTerminal.Double", String.valueOf(val))); } } catch (final IOException e) { - // TODO Auto-generated catch block - e.printStackTrace(); + AELog.error(e); } } @Override public void initGui() { super.initGui(); - this.tabCraftButton = new GuiTabButton( - this.guiLeft + 173, - this.guiTop + this.ySize - 177, - new ItemStack(Blocks.crafting_table), - GuiText.CraftingPattern.getLocal(), - itemRender); - this.buttonList.add(this.tabCraftButton); + if (this.container.getCraftingModeSupport()) { + this.tabCraftButton = new GuiTabButton( + this.guiLeft + 173, + this.guiTop + this.ySize - 177, + new ItemStack(Blocks.crafting_table), + GuiText.CraftingPattern.getLocal(), + itemRender); + this.buttonList.add(this.tabCraftButton); - this.tabProcessButton = new GuiTabButton( - this.guiLeft + 173, - this.guiTop + this.ySize - 177, - new ItemStack(Blocks.furnace), - GuiText.ProcessingPattern.getLocal(), - itemRender); - this.buttonList.add(this.tabProcessButton); + this.tabProcessButton = new GuiTabButton( + this.guiLeft + 173, + this.guiTop + this.ySize - 177, + new ItemStack(Blocks.furnace), + GuiText.ProcessingPattern.getLocal(), + itemRender); + this.buttonList.add(this.tabProcessButton); + } this.substitutionsEnabledBtn = new GuiImgButton( this.guiLeft + 84, @@ -187,13 +202,92 @@ public class GuiPatternTerm extends GuiMEMonitorable { this.doubleBtn.setHalfSize(true); this.buttonList.add(this.doubleBtn); this.updateButtonVisibility(); + + this.initVirtualSlots(); + } + + protected int getInputSlotOffsetX() { + return 18; + } + + protected int getInputSlotOffsetY() { + return 39; + } + + protected int getOutputSlotOffsetX() { + return 110; + } + + protected int getOutputSlotOffsetY() { + return 39; + } + + private void initVirtualSlots() { + final int inputSlotRow = container.getPatternInputsHeigh(); + final int inputSlotPerRow = container.getPatternInputsWidth(); + final int inputPage = container.getPatternInputPages(); + this.craftingSlots = new VirtualMEPatternSlot[inputSlotPerRow * inputSlotRow * inputPage]; + final IAEStackInventory inputInv = container.getPatternTerminal() + .getAEInventoryByName(StorageName.CRAFTING_INPUT); + for (int y = 0; y < inputSlotRow * inputPage; y++) { + for (int x = 0; x < inputSlotPerRow; x++) { + VirtualMEPatternSlot slot = new VirtualMEPatternSlot( + getInputSlotOffsetX() + 18 * x, + this.rows * 18 + getInputSlotOffsetY() + 18 * (y % (inputSlotRow)), + inputInv, + x + y * inputSlotPerRow); + this.craftingSlots[x + y * inputSlotPerRow] = slot; + this.registerVirtualSlots(slot); + } + } + + final int outputSlotRow = container.getPatternOutputsHeigh(); + final int outputSlotPerRow = container.getPatternOutputsWidth(); + final int outputPage = container.getPatternOutputPages(); + this.outputSlots = new VirtualMEPatternSlot[outputSlotPerRow * outputSlotRow * outputPage]; + final IAEStackInventory outputInv = container.getPatternTerminal() + .getAEInventoryByName(StorageName.CRAFTING_OUTPUT); + for (int y = 0; y < outputSlotRow * outputPage; y++) { + for (int x = 0; x < outputSlotPerRow; x++) { + VirtualMEPatternSlot slot = new VirtualMEPatternSlot( + getOutputSlotOffsetX(), + this.rows * 18 + getOutputSlotOffsetY() + 18 * (y % outputSlotRow), + outputInv, + x + y * outputSlotPerRow); + this.outputSlots[x + y * outputSlotPerRow] = slot; + this.registerVirtualSlots(slot); + } + } + updateSlotVisibility(); + } + + protected void updateSlotVisibility() { + if (this.cragtingMode) { + for (VirtualMEPhantomSlot outputSlot : outputSlots) { + outputSlot.setHidden(true); + } + } else { + for (VirtualMEPhantomSlot outputSlot : outputSlots) { + outputSlot.setHidden(false); + } + } } @Override public void drawFG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { this.updateButtonVisibility(); + if (this.cragtingMode != this.container.craftingMode) { + this.cragtingMode = this.container.craftingMode; + this.updateSlotVisibility(); + } + super.drawFG(offsetX, offsetY, mouseX, mouseY); + + drawTitle(); + } + + protected void drawTitle() { this.fontRendererObj.drawString( GuiText.PatternTerminal.getLocal(), 8, @@ -202,14 +296,16 @@ public class GuiPatternTerm extends GuiMEMonitorable { } private void updateButtonVisibility() { - if (!this.container.isCraftingMode()) { - this.tabCraftButton.visible = false; - this.tabProcessButton.visible = true; - this.doubleBtn.visible = true; - } else { - this.tabCraftButton.visible = true; - this.tabProcessButton.visible = false; - this.doubleBtn.visible = false; + if (this.tabCraftButton != null) { + if (!this.container.isCraftingMode()) { + this.tabCraftButton.visible = false; + this.tabProcessButton.visible = true; + this.doubleBtn.visible = true; + } else { + this.tabCraftButton.visible = true; + this.tabProcessButton.visible = false; + this.doubleBtn.visible = false; + } } if (this.container.substitute) { @@ -240,4 +336,13 @@ public class GuiPatternTerm extends GuiMEMonitorable { s.yDisplayPosition = s.getY() + this.ySize - 78 - 3; } } + + @Override + protected void handlePhantomSlotInteraction(VirtualMEPhantomSlot slot, int mouseButton) { + slot.handleMouseClicked(true, !cragtingMode, isCtrlKeyDown(), mouseButton); + } + + public VirtualMEPatternSlot[] getCraftingSlots() { + return craftingSlots; + } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiPatternTermEx.java b/src/main/java/appeng/client/gui/implementations/GuiPatternTermEx.java index cfc01da76..7985605cc 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiPatternTermEx.java +++ b/src/main/java/appeng/client/gui/implementations/GuiPatternTermEx.java @@ -5,44 +5,31 @@ import java.io.IOException; import net.minecraft.client.gui.GuiButton; import net.minecraft.entity.player.InventoryPlayer; -import org.lwjgl.input.Keyboard; import org.lwjgl.input.Mouse; -import appeng.api.config.ActionItems; -import appeng.api.config.ItemSubstitution; -import appeng.api.config.PatternBeSubstitution; import appeng.api.config.PatternSlotConfig; import appeng.api.config.Settings; import appeng.api.storage.ITerminalHost; +import appeng.client.gui.slots.VirtualMEPhantomSlot; import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.GuiScrollbar; import appeng.container.implementations.ContainerPatternTermEx; -import appeng.container.slot.AppEngSlot; +import appeng.core.AELog; import appeng.core.AppEng; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; import appeng.core.sync.network.NetworkHandler; -import appeng.core.sync.packets.PacketInventoryAction; import appeng.core.sync.packets.PacketValueConfig; -import appeng.helpers.InventoryAction; -public class GuiPatternTermEx extends GuiMEMonitorable { - - private static final String SUBSITUTION_DISABLE = "0"; - private static final String SUBSITUTION_ENABLE = "1"; +public class GuiPatternTermEx extends GuiPatternTerm { private final ContainerPatternTermEx container; - - private GuiImgButton substitutionsEnabledBtn; - private GuiImgButton substitutionsDisabledBtn; - private GuiImgButton beSubstitutionsEnabledBtn; - private GuiImgButton beSubstitutionsDisabledBtn; - private GuiImgButton encodeBtn; - private GuiImgButton clearBtn; private GuiImgButton invertBtn; - private GuiImgButton doubleBtn; private final GuiScrollbar processingScrollBar = new GuiScrollbar(); + private boolean isInverted; + private int activePage; + public GuiPatternTermEx(final InventoryPlayer inventoryPlayer, final ITerminalHost te) { super(inventoryPlayer, te, new ContainerPatternTermEx(inventoryPlayer, te)); this.container = (ContainerPatternTermEx) this.inventorySlots; @@ -50,6 +37,9 @@ public class GuiPatternTermEx extends GuiMEMonitorable { processingScrollBar.setHeight(70).setWidth(7).setLeft(6).setRange(0, 1, 1); processingScrollBar.setTexture(AppEng.MOD_ID, "guis/pattern3.png", 242, 0); + + this.isInverted = this.container.inverted; + this.activePage = this.container.activePage; } @Override @@ -57,35 +47,14 @@ public class GuiPatternTermEx extends GuiMEMonitorable { super.actionPerformed(btn); try { - if (this.encodeBtn == btn) { - NetworkHandler.instance.sendToServer( - new PacketValueConfig( - "PatternTerminalEx.Encode", - isCtrlKeyDown() ? (isShiftKeyDown() ? "6" : "1") : (isShiftKeyDown() ? "2" : "1"))); - } else if (this.clearBtn == btn) { - NetworkHandler.instance.sendToServer(new PacketValueConfig("PatternTerminalEx.Clear", "1")); - } else if (this.invertBtn == btn) { + if (this.invertBtn == btn) { NetworkHandler.instance.sendToServer( new PacketValueConfig("PatternTerminalEx.Invert", container.inverted ? "0" : "1")); - } else if (this.substitutionsEnabledBtn == btn || this.substitutionsDisabledBtn == btn) { - NetworkHandler.instance.sendToServer( - new PacketValueConfig( - "PatternTerminalEx.Substitute", - this.substitutionsEnabledBtn == btn ? SUBSITUTION_DISABLE : SUBSITUTION_ENABLE)); - } else if (this.beSubstitutionsEnabledBtn == btn || this.beSubstitutionsDisabledBtn == btn) { - NetworkHandler.instance.sendToServer( - new PacketValueConfig( - "PatternTerminalEx.BeSubstitute", - this.beSubstitutionsEnabledBtn == btn ? SUBSITUTION_DISABLE : SUBSITUTION_ENABLE)); - } else if (doubleBtn == btn) { - int val = Keyboard.isKeyDown(Keyboard.KEY_LSHIFT) ? 1 : 0; - if (Mouse.isButtonDown(1)) val |= 0b10; - NetworkHandler.instance - .sendToServer(new PacketValueConfig("PatternTerminalEx.Double", String.valueOf(val))); + container.getExPatternTerminal().setInverted(container.inverted); + this.updateSlotVisibility(); } } catch (final IOException e) { - // TODO Auto-generated catch block - e.printStackTrace(); + AELog.error(e); } } @@ -93,53 +62,6 @@ public class GuiPatternTermEx extends GuiMEMonitorable { public void initGui() { super.initGui(); - this.substitutionsEnabledBtn = new GuiImgButton( - this.guiLeft + 97, - this.guiTop + this.ySize - 163, - Settings.ACTIONS, - ItemSubstitution.ENABLED); - this.substitutionsEnabledBtn.setHalfSize(true); - this.buttonList.add(this.substitutionsEnabledBtn); - - this.substitutionsDisabledBtn = new GuiImgButton( - this.guiLeft + 97, - this.guiTop + this.ySize - 163, - Settings.ACTIONS, - ItemSubstitution.DISABLED); - this.substitutionsDisabledBtn.setHalfSize(true); - this.buttonList.add(this.substitutionsDisabledBtn); - - this.beSubstitutionsEnabledBtn = new GuiImgButton( - this.guiLeft + 97, - this.guiTop + this.ySize - 143, - Settings.ACTIONS, - PatternBeSubstitution.ENABLED); - this.beSubstitutionsEnabledBtn.setHalfSize(true); - this.buttonList.add(this.beSubstitutionsEnabledBtn); - - this.beSubstitutionsDisabledBtn = new GuiImgButton( - this.guiLeft + 97, - this.guiTop + this.ySize - 143, - Settings.ACTIONS, - PatternBeSubstitution.DISABLED); - this.beSubstitutionsDisabledBtn.setHalfSize(true); - this.buttonList.add(this.beSubstitutionsDisabledBtn); - - this.clearBtn = new GuiImgButton( - this.guiLeft + 87, - this.guiTop + this.ySize - 163, - Settings.ACTIONS, - ActionItems.CLOSE); - this.clearBtn.setHalfSize(true); - this.buttonList.add(this.clearBtn); - - this.encodeBtn = new GuiImgButton( - this.guiLeft + 147, - this.guiTop + this.ySize - 142, - Settings.ACTIONS, - ActionItems.ENCODE); - this.buttonList.add(this.encodeBtn); - invertBtn = new GuiImgButton( this.guiLeft + 87, this.guiTop + this.ySize - 153, @@ -148,20 +70,28 @@ public class GuiPatternTermEx extends GuiMEMonitorable { invertBtn.setHalfSize(true); this.buttonList.add(this.invertBtn); - this.doubleBtn = new GuiImgButton( - this.guiLeft + 97, - this.guiTop + this.ySize - 153, - Settings.ACTIONS, - ActionItems.DOUBLE); - this.doubleBtn.setHalfSize(true); - this.buttonList.add(this.doubleBtn); - processingScrollBar.setTop(this.ySize - 164); + this.updateSlotVisibility(); + } + + protected int getInputSlotOffsetX() { + return 15; + } + + protected int getInputSlotOffsetY() { + return 32; + } + + protected int getOutputSlotOffsetX() { + return this.isInverted ? 58 : 112; + } + + protected int getOutputSlotOffsetY() { + return 32; } @Override - public void drawFG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { - super.drawFG(offsetX, offsetY, mouseX, mouseY); + protected void drawTitle() { this.fontRendererObj.drawString( GuiText.PatternTerminalEx.getLocal(), 8, @@ -175,29 +105,8 @@ public class GuiPatternTermEx extends GuiMEMonitorable { return container.inverted ? "guis/pattern4.png" : "guis/pattern3.png"; } - @Override - protected void repositionSlot(final AppEngSlot s) { - if (s.isPlayerSide()) { - s.yDisplayPosition = s.getY() + this.ySize - 78 - 5; - } else { - s.yDisplayPosition = s.getY() + this.ySize - 78 - 3; - } - } - @Override public void drawScreen(final int mouseX, final int mouseY, final float btn) { - - if (container.substitute) { - substitutionsEnabledBtn.visible = true; - substitutionsDisabledBtn.visible = false; - } else { - substitutionsEnabledBtn.visible = false; - substitutionsDisabledBtn.visible = true; - } - - this.beSubstitutionsEnabledBtn.visible = this.container.beSubstitute; - this.beSubstitutionsDisabledBtn.visible = !this.container.beSubstitute; - final int offset = container.inverted ? 18 * -3 : 0; substitutionsEnabledBtn.xPosition = this.guiLeft + 97 + offset; @@ -210,6 +119,12 @@ public class GuiPatternTermEx extends GuiMEMonitorable { processingScrollBar.setCurrentScroll(container.activePage); + if (this.isInverted != this.container.inverted || this.activePage != this.container.activePage) { + this.isInverted = this.container.inverted; + this.activePage = this.container.activePage; + this.updateSlotVisibility(); + } + super.drawScreen(mouseX, mouseY, btn); } @@ -217,12 +132,8 @@ public class GuiPatternTermEx extends GuiMEMonitorable { protected void mouseClicked(final int xCoord, final int yCoord, final int btn) { final int currentScroll = this.processingScrollBar.getCurrentScroll(); this.processingScrollBar.click(this, xCoord - this.guiLeft, yCoord - this.guiTop); - if (btn == 2 && doubleBtn.mousePressed(this.mc, xCoord, yCoord)) { // - InventoryAction action = InventoryAction.SET_PATTERN_MULTI; - final PacketInventoryAction p = new PacketInventoryAction(action, 0, 0); - NetworkHandler.instance.sendToServer(p); - } else super.mouseClicked(xCoord, yCoord, btn); + super.mouseClicked(xCoord, yCoord, btn); if (currentScroll != this.processingScrollBar.getCurrentScroll()) { changeActivePage(); @@ -262,14 +173,44 @@ public class GuiPatternTermEx extends GuiMEMonitorable { } private void changeActivePage() { - try { NetworkHandler.instance.sendToServer( new PacketValueConfig( "PatternTerminalEx.ActivePage", String.valueOf(this.processingScrollBar.getCurrentScroll()))); + container.activePage = this.processingScrollBar.getCurrentScroll(); + this.updateSlotVisibility(); } catch (final IOException e) { - e.printStackTrace(); + AELog.error(e); + } + } + + @Override + protected void updateSlotVisibility() { + final int inputSlotRow = container.getPatternInputsHeigh(); + final int inputSlotPerRow = container.getPatternInputsWidth(); + for (int page = 0; page < container.getPatternInputPages(); page++) { + for (int y = 0; y < inputSlotRow; y++) { + for (int x = 0; x < inputSlotPerRow; x++) { + VirtualMEPhantomSlot slot = this.craftingSlots[x + y * inputSlotPerRow + + page * (inputSlotPerRow * inputSlotRow)]; + slot.setHidden(page != this.activePage); + slot.setX(getInputSlotOffsetX() + 18 * x); + } + } + } + + final int outputSlotRow = container.getPatternOutputsHeigh(); + final int outputSlotPerRow = container.getPatternOutputsWidth(); + for (int page = 0; page < container.getPatternOutputPages(); page++) { + for (int y = 0; y < outputSlotRow; y++) { + for (int x = 0; x < outputSlotPerRow; x++) { + VirtualMEPhantomSlot slot = this.outputSlots[x + y * outputSlotPerRow + + page * (outputSlotPerRow * outputSlotRow)]; + slot.setHidden(page != this.activePage); + slot.setX(getOutputSlotOffsetX()); + } + } } } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiPatternValueAmount.java b/src/main/java/appeng/client/gui/implementations/GuiPatternValueAmount.java index 5e9694f03..60ed21693 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiPatternValueAmount.java +++ b/src/main/java/appeng/client/gui/implementations/GuiPatternValueAmount.java @@ -1,71 +1,34 @@ package appeng.client.gui.implementations; -import net.minecraft.client.Minecraft; import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.inventory.GuiContainer; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.Slot; -import net.minecraft.item.ItemStack; -import appeng.api.AEApi; -import appeng.api.definitions.IDefinitions; -import appeng.api.definitions.IParts; import appeng.api.storage.ITerminalHost; +import appeng.client.gui.slots.VirtualMESlotSingle; import appeng.container.implementations.ContainerPatternValueAmount; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketPatternValueSet; import appeng.helpers.Reflected; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; public class GuiPatternValueAmount extends GuiAmount { - private final int valueIndex; - private final int originalAmount; + private final ContainerPatternValueAmount container; + private final VirtualMESlotSingle slot; @Reflected public GuiPatternValueAmount(final InventoryPlayer inventoryPlayer, final ITerminalHost te) { super(new ContainerPatternValueAmount(inventoryPlayer, te)); - GuiContainer gui = (GuiContainer) Minecraft.getMinecraft().currentScreen; - if (gui != null && gui.theSlot != null && gui.theSlot.getHasStack()) { - Slot slot = gui.theSlot; - originalAmount = slot.getStack().stackSize; - valueIndex = slot.slotNumber; - } else { - valueIndex = -1; - originalAmount = 0; - } + this.container = (ContainerPatternValueAmount) this.inventorySlots; + + this.slot = new VirtualMESlotSingle(34, 53, 0, null); } @Override public void initGui() { super.initGui(); - this.amountTextField.setText(String.valueOf(originalAmount)); - this.amountTextField.setCursorPositionEnd(); - this.amountTextField.setSelectionPos(0); - } - - @Override - protected void setOriginGUI(Object target) { - final IDefinitions definitions = AEApi.instance().definitions(); - final IParts parts = definitions.parts(); - - if (target instanceof PartPatternTerminal) { - for (final ItemStack stack : parts.patternTerminal().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - if (target instanceof PartPatternTerminalEx) { - for (final ItemStack stack : parts.patternTerminalEx().maybeStack(1).asSet()) { - myIcon = stack; - } - this.originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } + this.registerVirtualSlots(this.slot); } @Override @@ -78,10 +41,9 @@ public class GuiPatternValueAmount extends GuiAmount { public void drawBG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { super.drawBG(offsetX, offsetY, mouseX, mouseY); this.nextBtn.displayString = GuiText.Set.getLocal(); - this.nextBtn.enabled = valueIndex >= 0; try { - int resultI = getAmount(); + long resultI = getAmountLong(); this.nextBtn.enabled = resultI > 0; } catch (final NumberFormatException e) { this.nextBtn.enabled = false; @@ -95,9 +57,12 @@ public class GuiPatternValueAmount extends GuiAmount { super.actionPerformed(btn); try { - if (btn == this.nextBtn && btn.enabled) { - NetworkHandler.instance - .sendToServer(new PacketPatternValueSet(originalGui.ordinal(), getAmount(), valueIndex)); + if (btn == this.nextBtn && btn.enabled && slot.getAEStack() != null) { + NetworkHandler.instance.sendToServer( + new PacketPatternValueSet( + this.container.getAEStack().setStackSize(getAmountLong()), + this.container.getInvName(), + this.container.getSlotIndex())); } } catch (final NumberFormatException e) { // nope.. @@ -108,4 +73,11 @@ public class GuiPatternValueAmount extends GuiAmount { protected String getBackground() { return "guis/craftAmt.png"; } + + public void update() { + this.slot.setAEStack(this.container.getAEStack()); + this.amountTextField.setText(String.valueOf(this.container.getAEStack().getStackSize())); + this.amountTextField.setCursorPositionEnd(); + this.amountTextField.setSelectionPos(0); + } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiPriority.java b/src/main/java/appeng/client/gui/implementations/GuiPriority.java index 88d0b3b49..2b1eaa6bb 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiPriority.java +++ b/src/main/java/appeng/client/gui/implementations/GuiPriority.java @@ -13,27 +13,15 @@ package appeng.client.gui.implementations; import java.io.IOException; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.item.ItemStack; -import appeng.api.AEApi; -import appeng.api.definitions.IBlocks; -import appeng.api.definitions.IDefinitions; -import appeng.api.definitions.IParts; import appeng.container.implementations.ContainerPriority; import appeng.core.AEConfig; import appeng.core.AELog; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketValueConfig; import appeng.helpers.IPriorityHost; -import appeng.parts.automation.PartFormationPlane; -import appeng.parts.misc.PartInterface; -import appeng.parts.misc.PartStorageBus; -import appeng.tile.misc.TileInterface; -import appeng.tile.storage.TileChest; -import appeng.tile.storage.TileDrive; import appeng.util.calculators.ArithHelper; import appeng.util.calculators.Calculator; @@ -60,55 +48,6 @@ public class GuiPriority extends GuiAmount { ((ContainerPriority) this.inventorySlots).setTextField(this.amountTextField); } - @Override - protected void setOriginGUI(Object target) { - final IDefinitions definitions = AEApi.instance().definitions(); - final IParts parts = definitions.parts(); - final IBlocks blocks = definitions.blocks(); - - if (target instanceof PartStorageBus) { - for (final ItemStack storageBusStack : parts.storageBus().maybeStack(1).asSet()) { - myIcon = storageBusStack; - } - this.originalGui = GuiBridge.GUI_STORAGEBUS; - } - - if (target instanceof PartFormationPlane) { - for (final ItemStack formationPlaneStack : parts.formationPlane().maybeStack(1).asSet()) { - myIcon = formationPlaneStack; - } - this.originalGui = GuiBridge.GUI_FORMATION_PLANE; - } - - if (target instanceof TileDrive) { - for (final ItemStack driveStack : blocks.drive().maybeStack(1).asSet()) { - myIcon = driveStack; - } - this.originalGui = GuiBridge.GUI_DRIVE; - } - - if (target instanceof TileChest) { - for (final ItemStack chestStack : blocks.chest().maybeStack(1).asSet()) { - myIcon = chestStack; - } - this.originalGui = GuiBridge.GUI_CHEST; - } - - if (target instanceof TileInterface) { - for (final ItemStack interfaceStack : blocks.iface().maybeStack(1).asSet()) { - myIcon = interfaceStack; - } - this.originalGui = GuiBridge.GUI_INTERFACE; - } - - if (target instanceof PartInterface) { - for (final ItemStack interfaceStack : parts.iface().maybeStack(1).asSet()) { - myIcon = interfaceStack; - } - this.originalGui = GuiBridge.GUI_INTERFACE; - } - } - @Override public void drawFG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { this.fontRendererObj.drawString(GuiText.Priority.getLocal(), 8, 6, GuiColors.PriorityTitle.getColor()); diff --git a/src/main/java/appeng/client/gui/implementations/GuiRenamer.java b/src/main/java/appeng/client/gui/implementations/GuiRenamer.java index 938b5c4df..6bb6a28a2 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiRenamer.java +++ b/src/main/java/appeng/client/gui/implementations/GuiRenamer.java @@ -7,7 +7,7 @@ import net.minecraft.item.ItemStack; import org.lwjgl.input.Keyboard; -import appeng.client.gui.AEBaseGui; +import appeng.client.gui.GuiSub; import appeng.client.gui.widgets.IDropToFillTextField; import appeng.client.gui.widgets.MEGuiTextField; import appeng.container.implementations.ContainerRenamer; @@ -18,7 +18,7 @@ import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketValueConfig; import appeng.helpers.ICustomNameObject; -public class GuiRenamer extends AEBaseGui implements IDropToFillTextField { +public class GuiRenamer extends GuiSub implements IDropToFillTextField { private MEGuiTextField textField; diff --git a/src/main/java/appeng/client/gui/implementations/GuiStorageBus.java b/src/main/java/appeng/client/gui/implementations/GuiStorageBus.java index 852fff2f5..c743018a4 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiStorageBus.java +++ b/src/main/java/appeng/client/gui/implementations/GuiStorageBus.java @@ -16,12 +16,17 @@ import net.minecraft.client.gui.GuiButton; import net.minecraft.entity.player.InventoryPlayer; import org.lwjgl.input.Mouse; +import org.lwjgl.opengl.GL11; import appeng.api.config.AccessRestriction; import appeng.api.config.ActionItems; import appeng.api.config.FuzzyMode; import appeng.api.config.Settings; import appeng.api.config.StorageFilter; +import appeng.api.config.Upgrades; +import appeng.api.parts.IStorageBus; +import appeng.api.storage.StorageChannel; +import appeng.client.gui.slots.VirtualMEPhantomSlot; import appeng.client.gui.widgets.GuiImgButton; import appeng.client.gui.widgets.GuiTabButton; import appeng.container.implementations.ContainerStorageBus; @@ -33,7 +38,7 @@ import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketConfigButton; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketValueConfig; -import appeng.parts.misc.PartStorageBus; +import appeng.tile.inventory.IAEStackInventory; public class GuiStorageBus extends GuiUpgradeable { @@ -42,9 +47,12 @@ public class GuiStorageBus extends GuiUpgradeable { private GuiTabButton priority; private GuiImgButton partition; private GuiImgButton clear; + private VirtualMEPhantomSlot[] configSlots; + private final ContainerStorageBus containerStorageBus; - public GuiStorageBus(final InventoryPlayer inventoryPlayer, final PartStorageBus te) { + public GuiStorageBus(final InventoryPlayer inventoryPlayer, final IStorageBus te) { super(new ContainerStorageBus(inventoryPlayer, te)); + this.containerStorageBus = (ContainerStorageBus) inventorySlots; this.ySize = 251; } @@ -90,6 +98,12 @@ public class GuiStorageBus extends GuiUpgradeable { this.buttonList.add(this.oreFilter); } + @Override + public void initGui() { + super.initGui(); + initVirtualSlots(); + } + @Override public void drawFG(final int offsetX, final int offsetY, final int mouseX, final int mouseY) { this.fontRendererObj.drawString( @@ -117,6 +131,28 @@ public class GuiStorageBus extends GuiUpgradeable { this.partition.set(csb.getPartitionMode()); } } + + updateSlotVisibility(); + } + + @Override + public void drawBG(int offsetX, int offsetY, int mouseX, int mouseY) { + super.drawBG(offsetX, offsetY, mouseX, mouseY); + + for (int i = 0; i < 5; i++) { + if (i >= this.containerStorageBus.getUpgradeable().getInstalledUpgrades(Upgrades.CAPACITY)) { + GL11.glPushAttrib(GL11.GL_ALL_ATTRIB_BITS); + GL11.glColor4f(1.0F, 1.0F, 1.0F, 0.4F); + GL11.glEnable(GL11.GL_BLEND); + } + + this.drawTexturedModalRect(offsetX + 7, offsetY + 64 + (18 * i), 7, 28, 162, 18); + + if (i >= this.containerStorageBus.getUpgradeable().getInstalledUpgrades(Upgrades.CAPACITY)) { + GL11.glColor4f(1.0F, 1.0F, 1.0F, 1.0F); + GL11.glPopAttrib(); + } + } } @Override @@ -148,4 +184,37 @@ public class GuiStorageBus extends GuiUpgradeable { AELog.debug(e); } } + + private void initVirtualSlots() { + this.configSlots = new VirtualMEPhantomSlot[63]; + final IAEStackInventory inputInv = this.containerStorageBus.getConfig(); + final int xo = 8; + final int yo = -133; + + for (int y = 0; y < 7; y++) { + for (int x = 0; x < 9; x++) { + VirtualMEPhantomSlot slot = new VirtualMEPhantomSlot( + xo + x * 18, + yo + y * 18 + 9 * 18, + inputInv, + x + y * 9); + this.configSlots[x + y * 9] = slot; + this.registerVirtualSlots(slot); + } + } + } + + protected void updateSlotVisibility() { + for (VirtualMEPhantomSlot slot : this.configSlots) { + slot.setHidden( + slot.getSlotIndex() > (18 + + (9 * this.containerStorageBus.getUpgradeable().getInstalledUpgrades(Upgrades.CAPACITY)))); + } + } + + @Override + protected void handlePhantomSlotInteraction(VirtualMEPhantomSlot slot, int mouseButton) { + StorageChannel channel = containerStorageBus.getStorageChannel(); + slot.handleMouseClicked(channel == StorageChannel.ITEMS, channel == StorageChannel.FLUIDS, false); + } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiUpgradeable.java b/src/main/java/appeng/client/gui/implementations/GuiUpgradeable.java index f02750f89..b4e1b822f 100644 --- a/src/main/java/appeng/client/gui/implementations/GuiUpgradeable.java +++ b/src/main/java/appeng/client/gui/implementations/GuiUpgradeable.java @@ -10,17 +10,8 @@ package appeng.client.gui.implementations; -import java.awt.Rectangle; -import java.util.ArrayList; -import java.util.Collections; -import java.util.List; - import net.minecraft.client.gui.GuiButton; -import net.minecraft.client.gui.inventory.GuiContainer; -import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.item.ItemStack; -import org.apache.commons.lang3.tuple.Pair; import org.lwjgl.input.Mouse; import appeng.api.config.ActionItems; @@ -34,23 +25,16 @@ import appeng.api.implementations.IUpgradeableHost; import appeng.client.gui.AEBaseGui; import appeng.client.gui.widgets.GuiImgButton; import appeng.container.implementations.ContainerUpgradeable; -import appeng.container.slot.SlotFake; import appeng.core.localization.GuiColors; import appeng.core.localization.GuiText; import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketConfigButton; -import appeng.core.sync.packets.PacketNEIDragClick; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.parts.automation.PartExportBus; import appeng.parts.automation.PartImportBus; -import codechicken.nei.VisiblityData; -import codechicken.nei.api.INEIGuiHandler; -import codechicken.nei.api.TaggedInventoryArea; -import cpw.mods.fml.common.Optional; -@Optional.Interface(modid = "NotEnoughItems", iface = "codechicken.nei.api.INEIGuiHandler") -public class GuiUpgradeable extends AEBaseGui implements INEIGuiHandler { +public abstract class GuiUpgradeable extends AEBaseGui { protected final ContainerUpgradeable cvb; protected final IUpgradeableHost bc; @@ -61,10 +45,6 @@ public class GuiUpgradeable extends AEBaseGui implements INEIGuiHandler { protected GuiImgButton schedulingMode; protected GuiImgButton oreFilter; - public GuiUpgradeable(final InventoryPlayer inventoryPlayer, final IUpgradeableHost te) { - this(new ContainerUpgradeable(inventoryPlayer, te)); - } - public GuiUpgradeable(final ContainerUpgradeable te) { super(te); this.cvb = te; @@ -204,9 +184,7 @@ public class GuiUpgradeable extends AEBaseGui implements INEIGuiHandler { } } - protected String getBackground() { - return "guis/bus.png"; - } + protected abstract String getBackground(); protected String getAdvancedBackground() { return "guis/advanced_toolbox.png"; @@ -246,55 +224,4 @@ public class GuiUpgradeable extends AEBaseGui implements INEIGuiHandler { NetworkHandler.instance.sendToServer(new PacketSwitchGuis(GuiBridge.GUI_ORE_FILTER)); } } - - @Override - public VisiblityData modifyVisiblity(GuiContainer gui, VisiblityData currentVisibility) { - return currentVisibility; - } - - @Override - public Iterable getItemSpawnSlots(GuiContainer gui, ItemStack item) { - return Collections.emptyList(); - } - - @Override - public List getInventoryAreas(GuiContainer gui) { - return null; - } - - @Override - public boolean handleDragNDrop(GuiContainer gui, int mouseX, int mouseY, ItemStack draggedStack, int button) { - List> slots = new ArrayList<>(); - - if (this.inventorySlots.inventorySlots.size() > 0) { - for (int i = 0; i < this.inventorySlots.inventorySlots.size(); i++) { - Object slot = this.inventorySlots.inventorySlots.get(i); - if (slot instanceof SlotFake) { - slots.add(Pair.of((SlotFake) slot, i)); - } - } - } - for (Pair fakeSlotPair : slots) { - SlotFake fakeSlot = fakeSlotPair.getKey(); - if (fakeSlot.isEnabled() && getSlotArea(fakeSlot).contains(mouseX, mouseY)) { - fakeSlot.putStack(draggedStack); - NetworkHandler.instance.sendToServer(new PacketNEIDragClick(draggedStack, fakeSlotPair.getValue())); - if (draggedStack != null) { - draggedStack.stackSize = 0; - } - return true; - } - } - - return false; - } - - @Override - public boolean hideItemPanelSlot(GuiContainer gui, int x, int y, int w, int h) { - return false; - } - - private Rectangle getSlotArea(SlotFake slot) { - return new Rectangle(guiLeft + slot.getX(), guiTop + slot.getY(), 16, 16); - } } diff --git a/src/main/java/appeng/client/gui/implementations/GuiWirelessTerm.java b/src/main/java/appeng/client/gui/implementations/GuiWirelessTerm.java deleted file mode 100644 index 70255ab93..000000000 --- a/src/main/java/appeng/client/gui/implementations/GuiWirelessTerm.java +++ /dev/null @@ -1,27 +0,0 @@ -/* - * This file is part of Applied Energistics 2. Copyright (c) 2013 - 2014, AlgorithmX2, All rights reserved. Applied - * Energistics 2 is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General - * Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any - * later version. Applied Energistics 2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; - * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General - * Public License for more details. You should have received a copy of the GNU Lesser General Public License along with - * Applied Energistics 2. If not, see . - */ - -package appeng.client.gui.implementations; - -import net.minecraft.entity.player.InventoryPlayer; - -import appeng.api.implementations.guiobjects.IPortableCell; - -public class GuiWirelessTerm extends GuiMEPortableCell { - - public GuiWirelessTerm(final InventoryPlayer inventoryPlayer, final IPortableCell te) { - super(inventoryPlayer, te); - } - - @Override - int getMaxRows() { - return this.defaultGetMaxRows(); - } -} diff --git a/src/main/java/appeng/client/gui/slots/VirtualMEMonitorableSlot.java b/src/main/java/appeng/client/gui/slots/VirtualMEMonitorableSlot.java new file mode 100644 index 000000000..ee5aa9a4c --- /dev/null +++ b/src/main/java/appeng/client/gui/slots/VirtualMEMonitorableSlot.java @@ -0,0 +1,27 @@ +package appeng.client.gui.slots; + +import javax.annotation.Nullable; + +import appeng.api.storage.data.IAEStack; +import appeng.api.storage.data.IDisplayRepo; + +public class VirtualMEMonitorableSlot extends VirtualMESlot { + + protected final IDisplayRepo repo; + + public VirtualMEMonitorableSlot(int x, int y, IDisplayRepo repo, int slotIndex) { + super(x, y, slotIndex); + this.repo = repo; + this.showAmountAlways = true; + this.showCraftableText = true; + this.showCraftableIcon = true; + } + + @Override + public @Nullable IAEStack getAEStack() { + return this.repo.getReferenceStack(this.slotIndex); + } + + @Override + protected void drawNEIOverlay() {} +} diff --git a/src/main/java/appeng/client/gui/slots/VirtualMEPatternSlot.java b/src/main/java/appeng/client/gui/slots/VirtualMEPatternSlot.java new file mode 100644 index 000000000..762863281 --- /dev/null +++ b/src/main/java/appeng/client/gui/slots/VirtualMEPatternSlot.java @@ -0,0 +1,29 @@ +package appeng.client.gui.slots; + +import appeng.core.sync.GuiBridge; +import appeng.core.sync.network.NetworkHandler; +import appeng.core.sync.packets.PacketSwitchGuis; +import appeng.tile.inventory.IAEStackInventory; + +public class VirtualMEPatternSlot extends VirtualMEPhantomSlot { + + public VirtualMEPatternSlot(int x, int y, IAEStackInventory inventory, int slotIndex) { + super(x, y, inventory, slotIndex); + this.showAmount = true; + } + + @Override + public void handleMouseClicked(boolean acceptItem, boolean acceptFluid, boolean isExtraAction, int mouseButton) { + if (mouseButton == 2) { // middle click + if (this.getAEStack() != null) { + if (isExtraAction) { + NetworkHandler.instance.sendToServer(new PacketSwitchGuis(GuiBridge.GUI_PATTERN_ITEM_RENAMER)); + } else { + NetworkHandler.instance.sendToServer(new PacketSwitchGuis(GuiBridge.GUI_PATTERN_VALUE_AMOUNT)); + } + } + } + + super.handleMouseClicked(acceptItem, acceptFluid, isExtraAction, mouseButton); + } +} diff --git a/src/main/java/appeng/client/gui/slots/VirtualMEPhantomSlot.java b/src/main/java/appeng/client/gui/slots/VirtualMEPhantomSlot.java new file mode 100644 index 000000000..bbb098d48 --- /dev/null +++ b/src/main/java/appeng/client/gui/slots/VirtualMEPhantomSlot.java @@ -0,0 +1,105 @@ +package appeng.client.gui.slots; + +import javax.annotation.Nullable; + +import net.minecraft.client.Minecraft; +import net.minecraft.item.ItemStack; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.core.sync.network.NetworkHandler; +import appeng.core.sync.packets.PacketVirtualSlot; +import appeng.integration.IntegrationRegistry; +import appeng.integration.IntegrationType; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.FluidUtils; +import appeng.util.Platform; +import appeng.util.item.AEFluidStack; +import appeng.util.item.AEItemStack; +import codechicken.nei.ItemPanels; +import codechicken.nei.recipe.StackInfo; + +public class VirtualMEPhantomSlot extends VirtualMESlot { + + private final IAEStackInventory inventory; + + public VirtualMEPhantomSlot(int x, int y, IAEStackInventory inventory, int slotIndex) { + super(x, y, slotIndex); + this.inventory = inventory; + this.showAmount = false; + } + + @Nullable + @Override + public IAEStack getAEStack() { + return this.inventory.getAEStackInSlot(this.getSlotIndex()); + } + + public StorageName getStorageName() { + return this.inventory.getStorageName(); + } + + public void handleMouseClicked(boolean acceptItem, boolean acceptFluid, boolean isExtraAction) { + handleMouseClicked(acceptItem, acceptFluid, isExtraAction, 0); + } + + // try nei dragNDrop make frind with regular interaction, unfinished + public void handleMouseClicked(boolean acceptItem, boolean acceptFluid, boolean isExtraAction, int mouseButton) { + IAEStack currentStack = this.getAEStack(); + final ItemStack newStack = getTargetStack(); + + if (newStack != null && !this.showAmount) { + newStack.stackSize = 1; + } + + // need always convert display fluid stack from nei or nothing. + if (newStack != null && !FluidUtils.isFluidContainer(newStack) + && StackInfo.getFluid(Platform.copyStackWithSize(newStack, 1)) != null) { + isExtraAction = true; + acceptItem = false; + } + + switch (mouseButton) { + case 0 -> { // left click + if (newStack != null) { + if (acceptFluid && (!acceptItem || isExtraAction)) { + currentStack = AEFluidStack.create(FluidUtils.getFluidFromContainer(newStack)); + } else if (acceptItem) currentStack = AEItemStack.create(newStack); + } else currentStack = null; + } + case 1 -> { // right click + if (newStack != null) { + newStack.stackSize = 1; + + if (acceptFluid && (!acceptItem || isExtraAction)) + currentStack = AEFluidStack.create(FluidUtils.getFluidFromContainer(newStack)); + else if (acceptItem) currentStack = AEItemStack.create(newStack); + + if (currentStack != null && currentStack.equals(this.getAEStack())) { + currentStack = this.getAEStack(); + currentStack.decStackSize(-1); + } + } else if (currentStack != null) { + currentStack.decStackSize(1); + if (currentStack.getStackSize() <= 0) currentStack = null; + } + } + } + + // Set on the client to avoid lag on slow networks + inventory.putAEStackInSlot(this.getSlotIndex(), currentStack); + + NetworkHandler.instance + .sendToServer(new PacketVirtualSlot(this.getStorageName(), this.getSlotIndex(), currentStack)); + } + + private ItemStack getTargetStack() { + ItemStack is = Minecraft.getMinecraft().thePlayer.inventory.getItemStack(); + if (is == null && IntegrationRegistry.INSTANCE.isEnabled(IntegrationType.NEI)) { + is = ItemPanels.bookmarkPanel.draggedStack; + if (is == null) is = ItemPanels.itemPanel.draggedStack; + } + + return is != null ? is.copy() : null; + } +} diff --git a/src/main/java/appeng/client/gui/slots/VirtualMEPinSlot.java b/src/main/java/appeng/client/gui/slots/VirtualMEPinSlot.java new file mode 100644 index 000000000..49b8fed7a --- /dev/null +++ b/src/main/java/appeng/client/gui/slots/VirtualMEPinSlot.java @@ -0,0 +1,62 @@ +package appeng.client.gui.slots; + +import javax.annotation.Nullable; + +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.Tessellator; +import net.minecraft.util.ResourceLocation; + +import org.lwjgl.opengl.GL11; + +import appeng.api.storage.data.IAEStack; +import appeng.api.storage.data.IDisplayRepo; +import appeng.core.AppEng; + +public class VirtualMEPinSlot extends VirtualMEMonitorableSlot { + + private static final int PIN_ICON_INDEX = 5 * 16 + 14; + private static final int UV_Y = (int) Math.floor((double) PIN_ICON_INDEX / 16); + private static final int UV_X = PIN_ICON_INDEX - UV_Y * 16; + private static final int ICON_SIZE = 16; + private static final float PIN_ICON_OPACITY = 0.4f; + private static final ResourceLocation TEXTURE = new ResourceLocation(AppEng.MOD_ID, "textures/guis/states.png"); + + public VirtualMEPinSlot(int x, int y, IDisplayRepo repo, int slotIndex) { + super(x, y, repo, slotIndex); + } + + @Override + public @Nullable IAEStack getAEStack() { + return this.repo.getAEPin(this.slotIndex); + } + + public static void drawSlotsBackground(VirtualMEPinSlot[] slots, Minecraft mc, float z) { + mc.getTextureManager().bindTexture(TEXTURE); + final Tessellator tessellator = Tessellator.instance; + + GL11.glPushAttrib(GL11.GL_ENABLE_BIT); + GL11.glEnable(GL11.GL_BLEND); + GL11.glDisable(GL11.GL_LIGHTING); + GL11.glEnable(GL11.GL_TEXTURE_2D); + GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA); + + tessellator.startDrawingQuads(); + tessellator.setColorRGBA_F(1.0f, 1.0f, 1.0f, PIN_ICON_OPACITY); + for (VirtualMEPinSlot slot : slots) { + final float x = slot.getX(); + final float y = slot.getY(); + final float uvX = UV_X * 16; + final float uvY = UV_Y * 16; + + final float f1 = 0.00390625F; + final float f = 0.00390625F; + tessellator.addVertexWithUV(x + 0, y + ICON_SIZE, z, (uvX + 0) * f, (uvY + ICON_SIZE) * f1); + tessellator.addVertexWithUV(x + ICON_SIZE, y + ICON_SIZE, z, (uvX + ICON_SIZE) * f, (uvY + ICON_SIZE) * f1); + tessellator.addVertexWithUV(x + ICON_SIZE, y, z, (uvX + ICON_SIZE) * f, (uvY + 0) * f1); + tessellator.addVertexWithUV(x + 0, y, z, (uvX + 0) * f, (uvY + 0) * f1); + } + tessellator.setColorRGBA_F(1.0f, 1.0f, 1.0f, 1.0f); + tessellator.draw(); + GL11.glPopAttrib(); + } +} diff --git a/src/main/java/appeng/client/gui/slots/VirtualMESlot.java b/src/main/java/appeng/client/gui/slots/VirtualMESlot.java new file mode 100644 index 000000000..76dccb58f --- /dev/null +++ b/src/main/java/appeng/client/gui/slots/VirtualMESlot.java @@ -0,0 +1,145 @@ +package appeng.client.gui.slots; + +import static appeng.integration.modules.NEI.searchField; +import static codechicken.nei.NEIClientConfig.getSearchExpression; +import static net.minecraft.client.gui.Gui.drawRect; + +import javax.annotation.Nullable; + +import net.minecraft.client.Minecraft; +import net.minecraft.item.ItemStack; + +import org.lwjgl.opengl.GL11; + +import appeng.api.storage.data.IAEStack; +import codechicken.nei.NEIClientUtils; +import codechicken.nei.api.ItemFilter; + +public abstract class VirtualMESlot { + + private int xPos; + private int yPos; + private boolean isHidden = false; + + protected final int slotIndex; + + protected boolean showAmount = true; + protected boolean showAmountAlways = false; + protected boolean showCraftableText = false; + protected boolean showCraftableIcon = false; + + public VirtualMESlot(int x, int y, int slotIndex) { + this.xPos = x; + this.yPos = y; + this.slotIndex = slotIndex; + } + + public int getX() { + return this.xPos; + } + + public int getY() { + return this.yPos; + } + + public void setX(int x) { + this.xPos = x; + } + + public void setY(int y) { + this.yPos = y; + } + + public int getSlotIndex() { + return this.slotIndex; + } + + @Nullable + public abstract IAEStack getAEStack(); + + public boolean isHovered(int mouseX, int mouseY) { + return !this.isHidden && mouseX >= this.xPos + && mouseX < this.xPos + 18 + && mouseY >= this.yPos + && mouseY < this.yPos + 18; + } + + /** + * @return ture if hovered + */ + public boolean drawStackAndOverlay(Minecraft mc, int mouseX, int mouseY) { + if (this.isHidden) return false; + + IAEStack aes = this.getAEStack(); + if (aes != null) { + aes.drawInGui(mc, this.xPos, this.yPos); + aes.drawOverlayInGui( + mc, + this.xPos, + this.yPos, + this.showAmount, + this.showAmountAlways, + this.showCraftableText, + this.showCraftableIcon); + } + + this.drawNEIOverlay(); + + final boolean hovered = this.isHovered(mouseX, mouseY); + if (hovered) { + this.drawHoveredOverlay(); + } + return hovered; + } + + protected void drawHoveredOverlay() { + GL11.glDisable(GL11.GL_LIGHTING); + GL11.glDisable(GL11.GL_DEPTH_TEST); + GL11.glColorMask(true, true, true, false); + drawRect(this.xPos, this.yPos, this.xPos + 16, this.yPos + 16, -2130706433); + GL11.glColorMask(true, true, true, true); + GL11.glEnable(GL11.GL_LIGHTING); + GL11.glEnable(GL11.GL_DEPTH_TEST); + } + + protected void drawNEIOverlay() { + if (searchField.isSearchingInventory()) { + ItemFilter itemFilter = searchField.getItemFilter(); + if (itemFilter == null) return; + + IAEStack aes = this.getAEStack(); + ItemStack item = aes != null ? aes.getItemStackForNEI() : null; + if (aes == null || item == null ? !getSearchExpression().isEmpty() : !itemFilter.matches(item)) { + NEIClientUtils.gl2DRenderContext(() -> { + GL11.glTranslatef(0, 0, 150); + drawRect(this.xPos, this.yPos, this.xPos + 16, this.yPos + 16, 0x80000000); + GL11.glTranslatef(0, 0, -150); + }); + } + } + } + + public boolean isHidden() { + return this.isHidden; + } + + public void setHidden(boolean hidden) { + this.isHidden = hidden; + } + + public void setShowAmount(boolean showAmount) { + this.showAmount = showAmount; + } + + public void setShowAmountAlways(boolean showAmountAlways) { + this.showAmountAlways = showAmountAlways; + } + + public void setShowCraftableText(boolean showCraftableText) { + this.showCraftableText = showCraftableText; + } + + public void setShowCraftableIcon(boolean showCraftableIcon) { + this.showCraftableIcon = showCraftableIcon; + } +} diff --git a/src/main/java/appeng/client/gui/slots/VirtualMESlotSingle.java b/src/main/java/appeng/client/gui/slots/VirtualMESlotSingle.java new file mode 100644 index 000000000..3c307bf1c --- /dev/null +++ b/src/main/java/appeng/client/gui/slots/VirtualMESlotSingle.java @@ -0,0 +1,26 @@ +package appeng.client.gui.slots; + +import javax.annotation.Nullable; + +import appeng.api.storage.data.IAEStack; + +public class VirtualMESlotSingle extends VirtualMESlot { + + private IAEStack stack; + + public VirtualMESlotSingle(int x, int y, int slotIndex, IAEStack stack) { + super(x, y, slotIndex); + this.stack = stack; + this.showAmount = false; + } + + @Nullable + @Override + public IAEStack getAEStack() { + return stack; + } + + public void setAEStack(@Nullable final IAEStack stack) { + this.stack = stack; + } +} diff --git a/src/main/java/appeng/client/me/InternalSlotME.java b/src/main/java/appeng/client/me/InternalSlotME.java deleted file mode 100644 index ff8911c93..000000000 --- a/src/main/java/appeng/client/me/InternalSlotME.java +++ /dev/null @@ -1,51 +0,0 @@ -/* - * This file is part of Applied Energistics 2. Copyright (c) 2013 - 2014, AlgorithmX2, All rights reserved. Applied - * Energistics 2 is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General - * Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any - * later version. Applied Energistics 2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; - * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General - * Public License for more details. You should have received a copy of the GNU Lesser General Public License along with - * Applied Energistics 2. If not, see . - */ - -package appeng.client.me; - -import net.minecraft.item.ItemStack; - -import appeng.api.storage.data.IAEItemStack; -import appeng.api.storage.data.IDisplayRepo; - -public class InternalSlotME { - - protected final int offset; - private final int xPos; - private final int yPos; - protected final IDisplayRepo repo; - - public InternalSlotME(final IDisplayRepo def, final int offset, final int displayX, final int displayY) { - this.repo = def; - this.offset = offset; - this.xPos = displayX; - this.yPos = displayY; - } - - ItemStack getStack() { - return this.repo.getItem(this.offset); - } - - IAEItemStack getAEStack() { - return this.repo.getReferenceItem(this.offset); - } - - boolean hasPower() { - return this.repo.hasPower(); - } - - int getxPosition() { - return this.xPos; - } - - int getyPosition() { - return this.yPos; - } -} diff --git a/src/main/java/appeng/client/me/ItemRepo.java b/src/main/java/appeng/client/me/ItemRepo.java index 202086567..e202f8dbd 100644 --- a/src/main/java/appeng/client/me/ItemRepo.java +++ b/src/main/java/appeng/client/me/ItemRepo.java @@ -31,7 +31,9 @@ import appeng.api.config.SortOrder; import appeng.api.config.TypeFilter; import appeng.api.config.ViewItems; import appeng.api.storage.IItemDisplayRegistry; +import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IDisplayRepo; import appeng.api.storage.data.IItemList; import appeng.client.gui.widgets.IScrollSource; @@ -41,25 +43,23 @@ import appeng.integration.modules.NEI; import appeng.items.storage.ItemViewCell; import appeng.util.ItemSorters; import appeng.util.Platform; -import appeng.util.item.ItemImmutableList; import appeng.util.item.OreHelper; import appeng.util.item.OreReference; import appeng.util.prioitylist.IPartitionList; public class ItemRepo implements IDisplayRepo { - private final IItemList list = AEApi.instance().storage().createSortedItemList(); - private IAEItemStack[] pinsRepo = new IAEItemStack[0]; - private final ArrayList view = new ArrayList<>(); - private final ArrayList dsp = new ArrayList<>(); + private final IItemList> list = AEApi.instance().storage().createAEStackList(); + private IAEStack[] pinsRepo = new IAEStack[0]; + private final ArrayList> view = new ArrayList<>(); private final IScrollSource src; private final ISortSource sortSrc; private int rowSize = 9; private String searchString = ""; - private Map searchCache = new WeakHashMap<>(); - private IPartitionList myPartitionList; + private Map, Boolean> searchCache = new WeakHashMap<>(); + private IPartitionList myPartitionList; private boolean hasPower; private boolean paused = false; @@ -69,11 +69,11 @@ public class ItemRepo implements IDisplayRepo { } @Override - public void setAEPins(IAEItemStack[] newPins) { - IItemList oldPins = getPinsCache(); - pinsRepo = new IAEItemStack[newPins.length]; + public void setAEPins(IAEStack[] newPins) { + IItemList> oldPins = getPinsCache(); + pinsRepo = new IAEStack[newPins.length]; for (int i = 0; i < pinsRepo.length; i++) { - IAEItemStack isToPin = list.findPrecise(newPins[i]); + IAEStack isToPin = list.findPrecise(newPins[i]); if (isToPin == null) { // If the item is not found in the repo, try to find it in the previous pins. @@ -88,7 +88,7 @@ public class ItemRepo implements IDisplayRepo { } } - for (IAEItemStack ais : oldPins) { + for (IAEStack ais : oldPins) { if (ais.getStackSize() != -1) list.add(ais); } @@ -96,10 +96,10 @@ public class ItemRepo implements IDisplayRepo { } /** pin order is not keep */ - private IItemList getPinsCache() { - IItemList oldPins = AEApi.instance().storage().createItemList(); + private IItemList> getPinsCache() { + IItemList> oldPins = AEApi.instance().storage().createAEStackList(); - for (IAEItemStack pin : pinsRepo) { + for (IAEStack pin : pinsRepo) { if (pin != null) { oldPins.add(pin); } @@ -109,7 +109,7 @@ public class ItemRepo implements IDisplayRepo { } @Override - public IAEItemStack getAEPin(int idx) { + public IAEStack getAEPin(int idx) { if (idx < 0 || idx >= pinsRepo.length) return null; return pinsRepo[idx]; } @@ -118,6 +118,16 @@ public class ItemRepo implements IDisplayRepo { public IAEItemStack getReferenceItem(int idx) { idx += this.src.getCurrentScroll() * this.rowSize; + if (idx >= this.view.size()) { + return null; + } + return this.view.get(idx) instanceof IAEItemStack ais ? ais : null; + } + + @Override + public IAEStack getReferenceStack(int idx) { + idx += this.src.getCurrentScroll() * this.rowSize; + if (idx >= this.view.size()) { return null; } @@ -126,31 +136,21 @@ public class ItemRepo implements IDisplayRepo { @Override public ItemStack getItem(int idx) { - idx += this.src.getCurrentScroll() * this.rowSize; - - if (idx >= this.dsp.size()) { - return null; - } - return this.dsp.get(idx); + IAEStack stack = getReferenceStack(idx); + return stack instanceof IAEItemStack ais ? ais.getItemStack() : null; } @Override - public IItemList getAvailableItems() { - IItemList pins = AEApi.instance().storage().createItemList(); - for (IAEItemStack is : this.pinsRepo) { - if (is != null && is.getStackSize() > 0) { - pins.add(is); - } - } - return new ItemImmutableList(list, pins); + public void postUpdate(IAEItemStack stack) { + this.postUpdate((IAEStack) stack); } @Override - public void postUpdate(final IAEItemStack is) { - final IAEItemStack st = this.list.findPrecise(is); + public void postUpdate(final IAEStack is) { + final IAEStack st = this.list.findPrecise(is); - for (IAEItemStack pin : pinsRepo) { - if (pin != null && pin.isSameType(is)) { + for (IAEStack pin : pinsRepo) { + if (pin != null && pin.isSameType((Object) is)) { pin.reset(); pin.add(is); return; @@ -175,11 +175,11 @@ public class ItemRepo implements IDisplayRepo { public void updateView() { if (this.paused) { // Update existing view with new data - IItemList pins = getPinsCache(); + IItemList> pins = getPinsCache(); for (int i = 0; i < this.view.size(); i++) { - IAEItemStack entry = this.view.get(i); - IAEItemStack serverEntry = this.list.findPrecise(entry); - IAEItemStack pinsEntry = pins.findPrecise(serverEntry); + IAEStack entry = this.view.get(i); + IAEStack serverEntry = this.list.findPrecise(entry); + IAEStack pinsEntry = pins.findPrecise(serverEntry); if (serverEntry == null || pinsEntry != null) { entry.setStackSize(0); } else { @@ -188,9 +188,9 @@ public class ItemRepo implements IDisplayRepo { } // Append newly added item stacks to the end of the view - Set viewSet = new HashSet<>(this.view); - ArrayList entriesToAdd = new ArrayList<>(); - for (IAEItemStack serverEntry : this.list) { + Set> viewSet = new HashSet<>(this.view); + ArrayList> entriesToAdd = new ArrayList<>(); + for (IAEStack serverEntry : this.list) { if (!viewSet.contains(serverEntry)) { entriesToAdd.add(serverEntry); } @@ -219,23 +219,20 @@ public class ItemRepo implements IDisplayRepo { this.view.sort(ItemSorters.CONFIG_BASED_SORT_BY_NAME); } } - - this.dsp.clear(); - this.dsp.ensureCapacity(this.list.size()); - for (final IAEItemStack is : this.view) { - this.dsp.add(is.getItemStack()); - } } - private void addEntriesToView(Iterable entries) { + private void addEntriesToView(Iterable> entries) { final Enum viewMode = this.sortSrc.getSortDisplay(); final Enum typeFilter = this.sortSrc.getTypeFilter(); - Predicate itemFilter = null; + Predicate> itemFilter = null; if (!this.searchString.trim().isEmpty()) { if (NEI.searchField.existsSearchField()) { final Predicate neiFilter = NEI.searchField.getFilter(this.searchString); - itemFilter = is -> neiFilter.test(is.getItemStack()); + itemFilter = is -> { + ItemStack stack = is.getItemStackForNEI(); + return stack != null && neiFilter.test(stack); + }; } else { itemFilter = getFilter(this.searchString); } @@ -243,7 +240,7 @@ public class ItemRepo implements IDisplayRepo { IItemDisplayRegistry registry = AEApi.instance().registries().itemDisplay(); - out: for (IAEItemStack is : entries) { + out: for (IAEStack is : entries) { if (viewMode == ViewItems.CRAFTABLE && !is.isCraftable()) { continue; } @@ -256,15 +253,24 @@ public class ItemRepo implements IDisplayRepo { continue; } - if (registry.isBlacklisted(is.getItem()) || registry.isBlacklisted(is.getItem().getClass())) { - continue; + if (typeFilter == TypeFilter.ITEMS) { + if (!(is instanceof IAEItemStack)) continue; + } else if (typeFilter == TypeFilter.FLUIDS) { + if (!(is instanceof IAEFluidStack)) continue; } - for (final BiPredicate filter : registry.getItemFilters()) { - if (!filter.test((TypeFilter) typeFilter, is)) continue out; + if (is instanceof IAEItemStack ais) { + if (registry.isBlacklisted(ais.getItemStack().getItem()) + || registry.isBlacklisted(ais.getItemStack().getItem().getClass())) { + continue; + } + + for (final BiPredicate filter : registry.getItemFilters()) { + if (!filter.test((TypeFilter) typeFilter, ais)) continue out; + } } - if (itemFilter == null || Boolean.TRUE.equals(this.searchCache.computeIfAbsent(is, itemFilter::test))) { + if (itemFilter == null || this.searchCache.computeIfAbsent(is, itemFilter::test)) { if (viewMode == ViewItems.CRAFTABLE) { is = is.copy(); @@ -276,7 +282,7 @@ public class ItemRepo implements IDisplayRepo { } } - private Predicate getFilter(String innerSearch) { + private Predicate> getFilter(String innerSearch) { if (innerSearch.isEmpty()) { return stack -> true; @@ -293,19 +299,22 @@ public class ItemRepo implements IDisplayRepo { } else if ("@".equals(prefix)) { final Pattern pattern = getPattern(innerSearch.substring(1)); return stack -> { - String mod = Platform.getModId(stack); + String mod = stack.getModId(); return pattern.matcher(mod).find(); }; } else if ("$".equals(prefix)) { final Pattern pattern = getPattern(innerSearch.substring(1)); return stack -> { - OreReference ores = OreHelper.INSTANCE.isOre(stack.getItemStack()); - return ores != null && pattern.matcher(String.join("\n", ores.getEquivalents())).find(); + if (stack instanceof IAEItemStack ais) { + OreReference ores = OreHelper.INSTANCE.isOre(ais.getItemStack()); + return ores != null && pattern.matcher(String.join("\n", ores.getEquivalents())).find(); + } + return false; }; } else { final Pattern pattern = getPattern(innerSearch); return stack -> { - String name = Platform.getItemDisplayName(stack); + String name = stack.getDisplayName(); if (pattern.matcher(name).find()) { return true; diff --git a/src/main/java/appeng/client/me/PinSlotME.java b/src/main/java/appeng/client/me/PinSlotME.java deleted file mode 100644 index 2a9dfc504..000000000 --- a/src/main/java/appeng/client/me/PinSlotME.java +++ /dev/null @@ -1,23 +0,0 @@ -package appeng.client.me; - -import net.minecraft.item.ItemStack; - -import appeng.api.storage.data.IAEItemStack; -import appeng.api.storage.data.IDisplayRepo; - -public class PinSlotME extends InternalSlotME { - - public PinSlotME(final IDisplayRepo def, final int offset, final int displayX, final int displayY) { - super(def, offset, displayX, displayY); - } - - @Override - ItemStack getStack() { - return this.repo.getAEPin(offset) != null ? this.repo.getAEPin(offset).getItemStack() : null; - } - - @Override - IAEItemStack getAEStack() { - return this.repo.getAEPin(offset); - } -} diff --git a/src/main/java/appeng/client/me/SlotDisconnected.java b/src/main/java/appeng/client/me/SlotDisconnected.java deleted file mode 100644 index df1505495..000000000 --- a/src/main/java/appeng/client/me/SlotDisconnected.java +++ /dev/null @@ -1,83 +0,0 @@ -/* - * This file is part of Applied Energistics 2. Copyright (c) 2013 - 2014, AlgorithmX2, All rights reserved. Applied - * Energistics 2 is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General - * Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any - * later version. Applied Energistics 2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; - * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General - * Public License for more details. You should have received a copy of the GNU Lesser General Public License along with - * Applied Energistics 2. If not, see . - */ - -package appeng.client.me; - -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.IInventory; -import net.minecraft.item.ItemStack; - -import appeng.container.slot.AppEngSlot; -import appeng.items.misc.ItemEncodedPattern; -import appeng.util.Platform; - -public class SlotDisconnected extends AppEngSlot { - - private final ClientDCInternalInv mySlot; - - public SlotDisconnected(final ClientDCInternalInv me, final int which, final int x, final int y) { - super(me.getInventory(), which, x, y); - this.mySlot = me; - } - - @Override - public boolean isItemValid(final ItemStack par1ItemStack) { - return false; - } - - @Override - public void putStack(final ItemStack par1ItemStack) {} - - @Override - public boolean canTakeStack(final EntityPlayer par1EntityPlayer) { - return false; - } - - @Override - public ItemStack getDisplayStack() { - if (Platform.isClient()) { - final ItemStack is = super.getStack(); - if (is != null && is.getItem() instanceof ItemEncodedPattern iep) { - final ItemStack out = iep.getOutput(is); - if (out != null) { - return out; - } - } - } - return super.getStack(); - } - - @Override - public void onPickupFromSlot(final EntityPlayer par1EntityPlayer, final ItemStack par2ItemStack) {} - - @Override - public boolean getHasStack() { - return this.getStack() != null; - } - - @Override - public int getSlotStackLimit() { - return 0; - } - - @Override - public ItemStack decrStackSize(final int par1) { - return null; - } - - @Override - public boolean isSlotInInventory(final IInventory par1iInventory, final int par2) { - return false; - } - - public ClientDCInternalInv getSlot() { - return this.mySlot; - } -} diff --git a/src/main/java/appeng/client/me/SlotME.java b/src/main/java/appeng/client/me/SlotME.java deleted file mode 100644 index f8b02eb05..000000000 --- a/src/main/java/appeng/client/me/SlotME.java +++ /dev/null @@ -1,98 +0,0 @@ -/* - * This file is part of Applied Energistics 2. Copyright (c) 2013 - 2014, AlgorithmX2, All rights reserved. Applied - * Energistics 2 is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General - * Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any - * later version. Applied Energistics 2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; - * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General - * Public License for more details. You should have received a copy of the GNU Lesser General Public License along with - * Applied Energistics 2. If not, see . - */ - -package appeng.client.me; - -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.IInventory; -import net.minecraft.inventory.Slot; -import net.minecraft.item.ItemStack; - -import appeng.api.storage.data.IAEItemStack; - -public class SlotME extends Slot { - - private final InternalSlotME mySlot; - - public SlotME(final InternalSlotME me) { - super(null, 0, me.getxPosition(), me.getyPosition()); - this.mySlot = me; - } - - public IAEItemStack getAEStack() { - if (this.mySlot.hasPower()) { - return this.mySlot.getAEStack(); - } - return null; - } - - @Override - public void onPickupFromSlot(final EntityPlayer par1EntityPlayer, final ItemStack par2ItemStack) {} - - @Override - public boolean isItemValid(final ItemStack par1ItemStack) { - return false; - } - - @Override - public ItemStack getStack() { - if (this.mySlot.hasPower()) { - return this.mySlot.getStack(); - } - return null; - } - - @Override - public boolean getHasStack() { - if (this.mySlot.hasPower()) { - return this.getStack() != null; - } - return false; - } - - @Override - public void putStack(final ItemStack par1ItemStack) {} - - @Override - public int getSlotStackLimit() { - return 0; - } - - @Override - public ItemStack decrStackSize(final int par1) { - return null; - } - - @Override - public boolean isSlotInInventory(final IInventory par1iInventory, final int par2) { - return false; - } - - @Override - public boolean canTakeStack(final EntityPlayer par1EntityPlayer) { - return false; - } - - public boolean isPin() { - return mySlot instanceof PinSlotME; - } - - public int getPinIndex() { - return mySlot.offset; - } - - public int getPinIcon() { - return 5 * 16 + 14; - } - - public float getOpacityOfIcon() { - return 0.4f; - } -} diff --git a/src/main/java/appeng/container/AEBaseContainer.java b/src/main/java/appeng/container/AEBaseContainer.java index 180a61c2c..7ff9fe1ed 100644 --- a/src/main/java/appeng/container/AEBaseContainer.java +++ b/src/main/java/appeng/container/AEBaseContainer.java @@ -10,6 +10,10 @@ package appeng.container; +import static appeng.util.Platform.getItemFromPlayerInventoryBySlotIndex; +import static appeng.util.Platform.isStacksIdentical; +import static appeng.util.Platform.setPlayerInventorySlotByIndex; + import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.IOException; @@ -31,14 +35,15 @@ import net.minecraft.item.ItemStack; import net.minecraft.nbt.CompressedStreamTools; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.tileentity.TileEntity; -import net.minecraftforge.common.util.ForgeDirection; import org.apache.commons.lang3.ArrayUtils; import appeng.api.AEApi; import appeng.api.config.Actionable; +import appeng.api.config.PowerMultiplier; import appeng.api.config.SecurityPermissions; import appeng.api.implementations.guiobjects.IGuiItemObject; +import appeng.api.implementations.guiobjects.IPortableCell; import appeng.api.networking.IGrid; import appeng.api.networking.IGridHost; import appeng.api.networking.IGridNode; @@ -51,16 +56,16 @@ import appeng.api.networking.security.PlayerSource; import appeng.api.parts.IPart; import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; import appeng.api.util.ItemSearchDTO; -import appeng.client.me.InternalSlotME; -import appeng.client.me.SlotME; import appeng.container.guisync.GuiSync; import appeng.container.guisync.SyncData; import appeng.container.implementations.ContainerCellWorkbench; import appeng.container.implementations.ContainerUpgradeable; -import appeng.container.implementations.ContainerWirelessTerm; +import appeng.container.interfaces.IInventorySlotAware; import appeng.container.slot.AppEngSlot; import appeng.container.slot.SlotCraftingMatrix; import appeng.container.slot.SlotCraftingTerm; @@ -72,29 +77,32 @@ import appeng.container.slot.SlotPlayerHotBar; import appeng.container.slot.SlotPlayerInv; import appeng.core.AEConfig; import appeng.core.AELog; +import appeng.core.localization.PlayerMessages; +import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketHighlightBlockStorage; import appeng.core.sync.packets.PacketInventoryAction; import appeng.core.sync.packets.PacketPartialItem; import appeng.core.sync.packets.PacketValueConfig; +import appeng.core.sync.packets.PacketVirtualSlot; import appeng.helpers.ICustomNameObject; -import appeng.helpers.IPinsHandler; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.InventoryAction; +import appeng.helpers.WirelessTerminalGuiObject; import appeng.items.materials.ItemMultiMaterial; import appeng.me.Grid; import appeng.me.MachineSet; import appeng.me.NetworkList; -import appeng.me.cache.NetworkMonitor; import appeng.me.storage.MEInventoryHandler; import appeng.parts.automation.UpgradeInventory; import appeng.parts.misc.PartStorageBus; +import appeng.tile.inventory.IAEStackInventory; import appeng.tile.storage.TileChest; import appeng.tile.storage.TileDrive; -import appeng.util.InventoryAdaptor; import appeng.util.IterationCounter; import appeng.util.Platform; -import appeng.util.inv.AdaptorPlayerHand; import appeng.util.item.AEItemStack; +import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap; public abstract class AEBaseContainer extends Container { @@ -109,16 +117,20 @@ public abstract class AEBaseContainer extends Container { private boolean isContainerValid = true; private String customName; private ContainerOpenContext openContext; - private IMEInventoryHandler cellInv; + private IMEInventoryHandler cellItemInv; + private IMEInventoryHandler cellFluidInv; private IEnergySource powerSrc; private boolean sentCustomName; private int ticksSinceCheck = 900; - private IAEItemStack clientRequestedTargetItem = null; + private IAEStack clientRequestedTargetItem = null; + private PrimaryGui primaryGui; + @Deprecated public AEBaseContainer(final InventoryPlayer ip, final TileEntity myTile, final IPart myPart) { this(ip, myTile, myPart, null); } + @Deprecated public AEBaseContainer(final InventoryPlayer ip, final TileEntity myTile, final IPart myPart, final IGuiItemObject gio) { this.invPlayer = ip; @@ -180,6 +192,11 @@ public abstract class AEBaseContainer extends Container { throw new IllegalArgumentException("Must have a valid anchor, instead " + anchor + " in " + ip); } + if (obj instanceof IInventorySlotAware isa) { + final int slotIndex = isa.getInventorySlot(); + this.lockPlayerInventorySlot(slotIndex); + } + this.mySrc = new PlayerSource(ip.player, this.getActionHost()); this.prepareSync(); @@ -208,7 +225,7 @@ public abstract class AEBaseContainer extends Container { try { final NBTTagCompound data = CompressedStreamTools.readCompressed(new ByteArrayInputStream(buffer)); if (data != null) { - this.setTargetStack(AEApi.instance().storage().createItemStack(ItemStack.loadItemStackFromNBT(data))); + this.setTargetStack(Platform.readStackNBT(data)); } } catch (final IOException e) { AELog.debug(e); @@ -217,30 +234,32 @@ public abstract class AEBaseContainer extends Container { this.dataChunks.clear(); } - public IAEItemStack getTargetStack() { + public IAEStack getTargetStack() { return this.clientRequestedTargetItem; } - public void setTargetStack(final IAEItemStack stack) { + public void setTargetStack(final IAEStack stack) { // client doesn't need to re-send, makes for lower overhead rapid packets. if (Platform.isClient()) { - final ItemStack a = stack == null ? null : stack.getItemStack(); - final ItemStack b = this.clientRequestedTargetItem == null ? null - : this.clientRequestedTargetItem.getItemStack(); - - if (Platform.isSameItemPrecise(a, b)) { - return; + if (stack == null) { + if (this.clientRequestedTargetItem == null) { + return; + } + } else { + if (stack.equals(this.clientRequestedTargetItem)) { + return; + } } final ByteArrayOutputStream stream = new ByteArrayOutputStream(); - final NBTTagCompound item = new NBTTagCompound(); + final NBTTagCompound nbt = new NBTTagCompound(); if (stack != null) { - stack.writeToNBT(item); + Platform.writeStackNBT(stack, nbt, true); } try { - CompressedStreamTools.writeCompressed(item, stream); + CompressedStreamTools.writeCompressed(nbt, stream); final int maxChunkSize = 30000; final List miniPackets = new LinkedList<>(); @@ -395,15 +414,15 @@ public abstract class AEBaseContainer extends Container { this.sendCustomName(); if (Platform.isServer()) { - for (final Object crafter : this.crafters) { - final ICrafting icrafting = (ICrafting) crafter; - + for (final ICrafting crafter : this.crafters) { for (final SyncData sd : this.syncData.values()) { - sd.tick(icrafting); + sd.tick(crafter); } } } + portableSourceTick(); + super.detectAndSendChanges(); } @@ -413,18 +432,6 @@ public abstract class AEBaseContainer extends Container { return null; } - boolean hasMETiles = false; - for (final Object is : this.inventorySlots) { - if (is instanceof InternalSlotME) { - hasMETiles = true; - break; - } - } - - if (hasMETiles && Platform.isClient()) { - return null; - } - final AppEngSlot clickSlot = (AppEngSlot) this.inventorySlots.get(idx); // require AE SLots! if (clickSlot instanceof SlotDisabled || clickSlot instanceof SlotInaccessible) { @@ -443,8 +450,6 @@ public abstract class AEBaseContainer extends Container { * Gather a list of valid destinations. */ if (clickSlot.isPlayerSide()) { - tis = this.shiftStoreItem(tis); - // target slots in the container... for (final Object inventorySlot : this.inventorySlots) { final AppEngSlot cs = (AppEngSlot) inventorySlot; @@ -495,7 +500,7 @@ public abstract class AEBaseContainer extends Container { if (tis != null) { // find partials.. for (final Slot d : selectedSlots) { - if (d instanceof SlotDisabled || d instanceof SlotME) { + if (d instanceof SlotDisabled) { continue; } @@ -538,7 +543,7 @@ public abstract class AEBaseContainer extends Container { // any match.. for (final Slot d : selectedSlots) { - if (d instanceof SlotDisabled || d instanceof SlotME) { + if (d instanceof SlotDisabled) { continue; } @@ -727,195 +732,13 @@ public abstract class AEBaseContainer extends Container { } } - if (action == InventoryAction.SET_PIN && this instanceof IPinsHandler iph) { - if (id == -1) { - iph.setPin(null, slot); - return; - } - ItemStack hand = player.inventory.getItemStack(); - if (hand == null) return; - if (iph.getPin(slot) != null && hand.isItemEqual(iph.getPin(slot))) { - // put item in the terminal - doAction(player, InventoryAction.PICKUP_OR_SET_DOWN, this.inventorySlots.size(), id); - } else { - iph.setPin(player.inventory.getItemStack(), slot); - } - } - return; } // get target item. - final IAEItemStack slotItem = this.clientRequestedTargetItem; + final IAEItemStack slotItem = this.clientRequestedTargetItem instanceof IAEItemStack ais ? ais : null; switch (action) { - case SHIFT_CLICK -> { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return; - } - if (slotItem != null) { - IAEItemStack ais = slotItem.copy(); - ItemStack myItem = ais.getItemStack(); - - ais.setStackSize(myItem.getMaxStackSize()); - - final InventoryAdaptor adp = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); - myItem.stackSize = (int) ais.getStackSize(); - myItem = adp.simulateAdd(myItem); - - if (myItem != null) { - ais.setStackSize(ais.getStackSize() - myItem.stackSize); - } - - ais = Platform.poweredExtraction( - this.getPowerSource(), - this.getCellInventory(), - ais, - this.getActionSource()); - if (ais != null) { - adp.addItems(ais.getItemStack()); - } - } - } - case ROLL_DOWN -> { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return; - } - final int releaseQty = 1; - final ItemStack isg = player.inventory.getItemStack(); - if (isg != null && releaseQty > 0) { - IAEItemStack ais = AEApi.instance().storage().createItemStack(isg); - ais.setStackSize(1); - final IAEItemStack extracted = ais.copy(); - - ais = Platform - .poweredInsert(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); - if (ais == null) { - final InventoryAdaptor ia = new AdaptorPlayerHand(player); - - final ItemStack fail = ia.removeItems(1, extracted.getItemStack(), null); - if (fail == null) { - this.getCellInventory() - .extractItems(extracted, Actionable.MODULATE, this.getActionSource()); - } - - this.updateHeld(player); - } - } - } - case ROLL_UP, PICKUP_SINGLE -> { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return; - } - if (slotItem != null) { - int liftQty = 1; - final ItemStack item = player.inventory.getItemStack(); - - if (item != null) { - if (item.stackSize >= item.getMaxStackSize()) { - liftQty = 0; - } - if (!Platform.isSameItemPrecise(slotItem.getItemStack(), item)) { - liftQty = 0; - } - } - - if (liftQty > 0) { - IAEItemStack ais = slotItem.copy(); - ais.setStackSize(1); - ais = Platform.poweredExtraction( - this.getPowerSource(), - this.getCellInventory(), - ais, - this.getActionSource()); - if (ais != null) { - final InventoryAdaptor ia = new AdaptorPlayerHand(player); - - final ItemStack fail = ia.addItems(ais.getItemStack()); - if (fail != null) { - this.getCellInventory().injectItems(ais, Actionable.MODULATE, this.getActionSource()); - } - - this.updateHeld(player); - } - } - } - } - case PICKUP_OR_SET_DOWN -> { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return; - } - if (player.inventory.getItemStack() == null) { - if (slotItem != null) { - IAEItemStack ais = slotItem.copy(); - ais.setStackSize(ais.getItemStack().getMaxStackSize()); - ais = Platform.poweredExtraction( - this.getPowerSource(), - this.getCellInventory(), - ais, - this.getActionSource()); - if (ais != null) { - player.inventory.setItemStack(ais.getItemStack()); - } else { - player.inventory.setItemStack(null); - } - this.updateHeld(player); - } - } else { - IAEItemStack ais = AEApi.instance().storage().createItemStack(player.inventory.getItemStack()); - ais = Platform - .poweredInsert(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); - if (ais != null) { - player.inventory.setItemStack(ais.getItemStack()); - } else { - player.inventory.setItemStack(null); - } - this.updateHeld(player); - } - } - case SPLIT_OR_PLACE_SINGLE -> { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return; - } - if (player.inventory.getItemStack() == null) { - if (slotItem != null) { - IAEItemStack ais = slotItem.copy(); - final long maxSize = ais.getItemStack().getMaxStackSize(); - ais.setStackSize(maxSize); - ais = this.getCellInventory().extractItems(ais, Actionable.SIMULATE, this.getActionSource()); - - if (ais != null) { - final long stackSize = Math.min(maxSize, ais.getStackSize()); - ais.setStackSize((stackSize + 1) >> 1); - ais = Platform.poweredExtraction( - this.getPowerSource(), - this.getCellInventory(), - ais, - this.getActionSource()); - } - - if (ais != null) { - player.inventory.setItemStack(ais.getItemStack()); - } else { - player.inventory.setItemStack(null); - } - this.updateHeld(player); - } - } else { - IAEItemStack ais = AEApi.instance().storage().createItemStack(player.inventory.getItemStack()); - ais.setStackSize(1); - ais = Platform - .poweredInsert(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); - if (ais == null) { - final ItemStack is = player.inventory.getItemStack(); - is.stackSize--; - if (is.stackSize <= 0) { - player.inventory.setItemStack(null); - } - this.updateHeld(player); - } - } - } case CREATIVE_DUPLICATE -> { if (player.capabilities.isCreativeMode && slotItem != null) { final ItemStack is = slotItem.getItemStack(); @@ -924,39 +747,6 @@ public abstract class AEBaseContainer extends Container { this.updateHeld(player); } } - case MOVE_REGION -> { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return; - } - if (slotItem != null) { - final int playerInv = 9 * 4; - for (int slotNum = 0; slotNum < playerInv; slotNum++) { - IAEItemStack ais = slotItem.copy(); - ItemStack myItem = ais.getItemStack(); - - ais.setStackSize(myItem.getMaxStackSize()); - - final InventoryAdaptor adp = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); - myItem.stackSize = (int) ais.getStackSize(); - myItem = adp.simulateAdd(myItem); - - if (myItem != null) { - ais.setStackSize(ais.getStackSize() - myItem.stackSize); - } - - ais = Platform.poweredExtraction( - this.getPowerSource(), - this.getCellInventory(), - ais, - this.getActionSource()); - if (ais != null) { - adp.addItems(ais.getItemStack()); - } else { - return; - } - } - } - } case FIND_ITEMS -> { final Class[] checkedMachineClasses = new Class[] { TileDrive.class, TileChest.class, PartStorageBus.class, }; @@ -964,17 +754,12 @@ public abstract class AEBaseContainer extends Container { IGrid g = null; // Pull grid - if (this instanceof ContainerWirelessTerm wirelessTerm - && wirelessTerm.getMonitor() instanceof NetworkMonitornetworkMonitor) { - g = networkMonitor.getGrid(); - } else { - final IActionHost host = this.getActionHost(); - if (host == null) return; + final IActionHost host = this.getActionHost(); + if (host == null) return; - final IGridNode gn = host.getActionableNode(); - if (gn != null) { - g = gn.getGrid(); - } + final IGridNode gn = host.getActionableNode(); + if (gn != null) { + g = gn.getGrid(); } if (g == null) return; @@ -1031,7 +816,9 @@ public abstract class AEBaseContainer extends Container { } } if (machine instanceof PartStorageBus innerMachine) { - if (innerMachine.getConnectedGrid() != null) { // Check if storageBus is subnet + if (innerMachine.getConnectedGrid() != null + || innerMachine.getStorageChannel() != StorageChannel.ITEMS) { // Check if storageBus is + // subnet continue; } MEInventoryHandler handler = innerMachine.getInternalHandler(); @@ -1088,21 +875,6 @@ public abstract class AEBaseContainer extends Container { } } - private ItemStack shiftStoreItem(final ItemStack input) { - if (this.getPowerSource() == null || this.getCellInventory() == null) { - return input; - } - final IAEItemStack ais = Platform.poweredInsert( - this.getPowerSource(), - this.getCellInventory(), - AEApi.instance().storage().createItemStack(input), - this.getActionSource()); - if (ais == null) { - return null; - } - return ais.getItemStack(); - } - private void updateSlot(final Slot clickSlot) { // ??? this.detectAndSendChanges(); @@ -1231,11 +1003,19 @@ public abstract class AEBaseContainer extends Container { } public IMEInventoryHandler getCellInventory() { - return this.cellInv; + return this.cellItemInv; } public void setCellInventory(final IMEInventoryHandler cellInv) { - this.cellInv = cellInv; + this.cellItemInv = cellInv; + } + + public IMEInventoryHandler getCellFluidInventory() { + return this.cellFluidInv; + } + + public void setCellFluidInventory(final IMEInventoryHandler cellInv) { + this.cellFluidInv = cellInv; } public String getCustomName() { @@ -1273,4 +1053,111 @@ public abstract class AEBaseContainer extends Container { public void setPowerSource(final IEnergySource powerSrc) { this.powerSrc = powerSrc; } + + // used for secondary gui for able handle tertiary, quaternary etc. gui + public void setPrimaryGui(PrimaryGui primaryGui) { + this.primaryGui = primaryGui; + } + + private void createPrimaryGui() { + ContainerOpenContext context = getOpenContext(); + + this.primaryGui = new PrimaryGui( + GuiBridge.getGuiByContainerClass(this.getClass()), + getTarget() instanceof IPrimaryGuiIconProvider ip ? ip.getPrimaryGuiIcon() + : AEApi.instance().definitions().parts().terminal().maybeStack(1).orNull(), + context.getTile(), + context.getSide()); + } + + public PrimaryGui getPrimaryGui() { + if (primaryGui == null) createPrimaryGui(); + return primaryGui; + } + + private int ticks = 0; + private double powerMultiplier = 0.5; + + private double getPowerMultiplier() { + return this.powerMultiplier; + } + + protected void setPowerMultiplier(final double powerMultiplier) { + this.powerMultiplier = powerMultiplier; + } + + private void portableSourceTick() { + final Object obj = this.getTarget(); + if (obj instanceof WirelessTerminalGuiObject wtgo) { + if (!wtgo.rangeCheck()) { + if (Platform.isServer() && this.isValidContainer()) { + this.getPlayerInv().player.addChatMessage(PlayerMessages.OutOfRange.toChat()); + } + + this.setValidContainer(false); + } else { + this.setPowerMultiplier(AEConfig.instance.wireless_getDrainRate(wtgo.getRange())); + } + } + + if (obj instanceof IPortableCell ipc) { + final int slotIndex = ipc.getInventorySlot(); + final ItemStack currentItem = getItemFromPlayerInventoryBySlotIndex( + this.getInventoryPlayer().player, + slotIndex); + final ItemStack is = ipc.getItemStack(); + if (currentItem != is) { + if (currentItem != null) { + if (Platform.isSameItem(is, currentItem)) { + setPlayerInventorySlotByIndex(this.getInventoryPlayer().player, slotIndex, is); + } else { + this.setValidContainer(false); + } + } else { + this.setValidContainer(false); + } + } + } + + if (obj instanceof IEnergySource ies) { + // drain 1 ae t + this.ticks++; + if (this.ticks > 10) { + ies.extractAEPower(this.getPowerMultiplier() * this.ticks, Actionable.MODULATE, PowerMultiplier.CONFIG); + this.ticks = 0; + } + } + } + + // need for universal terminal, because getMode(ItemStack terminal) always have outdated mode + private int switchAbleGuiItemNext = Integer.MIN_VALUE; + + public int getSwitchAbleGuiNext() { + return this.switchAbleGuiItemNext; + } + + public void setSwitchAbleGuiNext(int n) { + this.switchAbleGuiItemNext = n; + } + + protected void updateVirtualSlots(StorageName invName, IAEStackInventory inventory, + IAEStack[] clientSlotsStacks) { + var list = new Int2ObjectOpenHashMap>(); + for (int i = 0; i < inventory.getSizeInventory(); ++i) { + IAEStack aes = inventory.getAEStackInSlot(i); + IAEStack aesClient = clientSlotsStacks[i]; + + if (!isStacksIdentical(aes, aesClient)) { + list.put(i, aes); + clientSlotsStacks[i] = aes != null ? aes.copy() : null; + } + } + + if (!list.isEmpty()) { + for (ICrafting crafter : this.crafters) { + final EntityPlayerMP emp = (EntityPlayerMP) crafter; + NetworkHandler.instance.sendTo(new PacketVirtualSlot(invName, list), emp); + } + } + } } diff --git a/src/main/java/appeng/container/ContainerSubGui.java b/src/main/java/appeng/container/ContainerSubGui.java new file mode 100644 index 000000000..032607697 --- /dev/null +++ b/src/main/java/appeng/container/ContainerSubGui.java @@ -0,0 +1,50 @@ +package appeng.container; + +import net.minecraft.entity.player.InventoryPlayer; +import net.minecraft.inventory.Slot; +import net.minecraft.item.ItemStack; + +import appeng.client.gui.IGuiSub; +import appeng.container.interfaces.IContainerSubGui; +import appeng.container.slot.SlotInaccessible; +import appeng.tile.inventory.AppEngInternalInventory; +import appeng.util.Platform; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public class ContainerSubGui extends AEBaseContainer implements IContainerSubGui { + + private final Slot primaryGuiButtonIcon; + + @SideOnly(Side.CLIENT) + private IGuiSub guiLink; + + public ContainerSubGui(InventoryPlayer ip, Object anchor) { + super(ip, anchor); + this.primaryGuiButtonIcon = new SlotInaccessible(new AppEngInternalInventory(null, 1), 0, 0, -9000); + this.addSlotToContainer(this.primaryGuiButtonIcon); + } + + @Override + public void setPrimaryGui(PrimaryGui primaryGui) { + super.setPrimaryGui(primaryGui); + this.primaryGuiButtonIcon.putStack(primaryGui.getIcon()); + } + + @SideOnly(Side.CLIENT) + public ItemStack getPrimaryGuiIcon() { + return this.primaryGuiButtonIcon.getStack(); + } + + @Override + public void onSlotChange(Slot s) { + if (Platform.isClient() && this.primaryGuiButtonIcon == s && this.primaryGuiButtonIcon.getHasStack()) { + this.guiLink.initPrimaryGuiButton(); + } + } + + @SideOnly(Side.CLIENT) + public void setGuiLink(IGuiSub gs) { + this.guiLink = gs; + } +} diff --git a/src/main/java/appeng/container/PrimaryGui.java b/src/main/java/appeng/container/PrimaryGui.java new file mode 100644 index 000000000..c49b4058c --- /dev/null +++ b/src/main/java/appeng/container/PrimaryGui.java @@ -0,0 +1,39 @@ +package appeng.container; + +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.item.ItemStack; +import net.minecraft.tileentity.TileEntity; +import net.minecraftforge.common.util.ForgeDirection; + +import appeng.core.sync.GuiBridge; +import appeng.util.Platform; + +public class PrimaryGui { + + final protected Object gui; + final protected ItemStack guiIcon; + final protected TileEntity te; + final protected ForgeDirection side; + protected int slotIndex = Integer.MIN_VALUE; + + public PrimaryGui(Object gui, ItemStack guiIcon, TileEntity te, ForgeDirection side) { + this.gui = gui; + this.guiIcon = guiIcon; + this.te = te; + this.side = side; + } + + public void open(EntityPlayer p) { + if (gui instanceof GuiBridge gb) { + Platform.openGUI(p, te, side, gb, slotIndex); + } + } + + public ItemStack getIcon() { + return guiIcon; + } + + public void setSlotIndex(int slotIndex) { + this.slotIndex = slotIndex; + } +} diff --git a/src/main/java/appeng/container/implementations/ContainerBusIO.java b/src/main/java/appeng/container/implementations/ContainerBusIO.java new file mode 100644 index 000000000..bfdb7f5e6 --- /dev/null +++ b/src/main/java/appeng/container/implementations/ContainerBusIO.java @@ -0,0 +1,40 @@ +package appeng.container.implementations; + +import static appeng.util.Platform.isServer; + +import net.minecraft.entity.player.InventoryPlayer; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.container.interfaces.IVirtualSlotHolder; +import appeng.parts.automation.PartSharedItemBus; +import appeng.tile.inventory.IAEStackInventory; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; + +public class ContainerBusIO extends ContainerUpgradeable implements IVirtualSlotHolder { + + public final IAEStack[] virtualSlotsClient = new IAEStack[9]; + private final PartSharedItemBus bus; + + public ContainerBusIO(final InventoryPlayer ip, final PartSharedItemBus te) { + super(ip, te); + this.bus = te; + } + + @Override + public void detectAndSendChanges() { + super.detectAndSendChanges(); + this.updateVirtualSlots(StorageName.NONE, this.bus.getAEInventoryByName(StorageName.NONE), virtualSlotsClient); + } + + @Override + public void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks) { + final IAEStackInventory storage = this.bus.getAEInventoryByName(StorageName.NONE); + for (var entry : slotStacks.int2ObjectEntrySet()) { + storage.putAEStackInSlot(entry.getIntKey(), entry.getValue()); + } + if (isServer()) { + this.updateVirtualSlots(StorageName.CRAFTING_OUTPUT, storage, virtualSlotsClient); + } + } +} diff --git a/src/main/java/appeng/container/implementations/ContainerCellRestriction.java b/src/main/java/appeng/container/implementations/ContainerCellRestriction.java index 869be079a..d46d5edff 100644 --- a/src/main/java/appeng/container/implementations/ContainerCellRestriction.java +++ b/src/main/java/appeng/container/implementations/ContainerCellRestriction.java @@ -1,18 +1,16 @@ package appeng.container.implementations; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.tileentity.TileEntity; -import appeng.api.parts.IPart; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.container.guisync.GuiSync; import appeng.helpers.ICellRestriction; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class ContainerCellRestriction extends AEBaseContainer { +public class ContainerCellRestriction extends ContainerSubGui { public static class CellData { @@ -78,7 +76,7 @@ public class ContainerCellRestriction extends AEBaseContainer { public String cellRestriction; public ContainerCellRestriction(final InventoryPlayer ip, final ICellRestriction te) { - super(ip, (TileEntity) (te instanceof TileEntity ? te : null), (IPart) (te instanceof IPart ? te : null)); + super(ip, te); this.Host = te; } diff --git a/src/main/java/appeng/container/implementations/ContainerCellWorkbench.java b/src/main/java/appeng/container/implementations/ContainerCellWorkbench.java index b629462e6..f5d830353 100644 --- a/src/main/java/appeng/container/implementations/ContainerCellWorkbench.java +++ b/src/main/java/appeng/container/implementations/ContainerCellWorkbench.java @@ -10,6 +10,8 @@ package appeng.container.implementations; +import static appeng.util.Platform.isServer; + import java.util.Iterator; import net.minecraft.entity.player.EntityPlayer; @@ -23,25 +25,28 @@ import appeng.api.AEApi; import appeng.api.config.CopyMode; import appeng.api.config.FuzzyMode; import appeng.api.config.Settings; +import appeng.api.implementations.tiles.ICellWorkbench; import appeng.api.storage.ICellWorkbenchItem; import appeng.api.storage.IMEInventory; import appeng.api.storage.StorageChannel; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.container.guisync.GuiSync; +import appeng.container.interfaces.IVirtualSlotHolder; import appeng.container.slot.OptionalSlotRestrictedInput; -import appeng.container.slot.SlotFakeTypeOnly; import appeng.container.slot.SlotRestrictedInput; import appeng.helpers.ICellRestriction; +import appeng.me.storage.CellInventory; import appeng.tile.inventory.AppEngNullInventory; -import appeng.tile.misc.TileCellWorkbench; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.IterationCounter; import appeng.util.Platform; -import appeng.util.iterators.NullIterator; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; -public class ContainerCellWorkbench extends ContainerUpgradeable { +public class ContainerCellWorkbench extends ContainerUpgradeable implements IVirtualSlotHolder { - private final TileCellWorkbench workBench; + private final ICellWorkbench workBench; private final AppEngNullInventory nullInventory = new AppEngNullInventory(); @GuiSync(2) @@ -50,7 +55,9 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { private ItemStack prevStack = null; private int lastUpgrades = 0; - public ContainerCellWorkbench(final InventoryPlayer ip, final TileCellWorkbench te) { + private final IAEStack[] configClientSlot = new IAEStack[63]; + + public ContainerCellWorkbench(final InventoryPlayer ip, final ICellWorkbench te) { super(ip, te); this.workBench = te; } @@ -88,19 +95,7 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { 8, this.getInventoryPlayer())); - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); final IInventory upgradeInventory = new Upgrades(); - // null, 3 * 8 ); - - int offset = 0; - final int x = 8; - final int y = 29; - for (int w = 0; w < 7; w++) { - for (int z = 0; z < 9; z++) { - this.addSlotToContainer(new SlotFakeTypeOnly(inv, offset, x + z * 18, y + w * 18)); - offset++; - } - } for (int zz = 0; zz < 3; zz++) { for (int z = 0; z < 8; z++) { @@ -117,13 +112,6 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { this.getInventoryPlayer())); } } - /* - * if ( supportCapacity() ) { for (int w = 0; w < 2; w++) for (int z = 0; z < 9; z++) addSlotToContainer( new - * OptionalSlotFakeTypeOnly( inv, this, offset++, x, y, z, w, 1 ) ); for (int w = 0; w < 2; w++) for (int z = 0; - * z < 9; z++) addSlotToContainer( new OptionalSlotFakeTypeOnly( inv, this, offset++, x, y, z, w + 2, 2 ) ); for - * (int w = 0; w < 2; w++) for (int z = 0; z < 9; z++) addSlotToContainer( new OptionalSlotFakeTypeOnly( inv, - * this, offset++, x, y, z, w + 4, 3 ) ); } - */ } @Override @@ -140,9 +128,7 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { public void detectAndSendChanges() { final ItemStack is = this.workBench.getInventoryByName("cell").getStackInSlot(0); if (Platform.isServer()) { - if (this.workBench.getWorldObj() - .getTileEntity(this.workBench.xCoord, this.workBench.yCoord, this.workBench.zCoord) - != this.workBench) { + if (!this.workBench.isSame(this.workBench)) { this.setValidContainer(false); } @@ -162,6 +148,11 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { this.setCopyMode(this.getWorkBenchCopyMode()); this.setFuzzyMode(this.getWorkBenchFuzzyMode()); + + this.updateVirtualSlots( + StorageName.NONE, + this.workBench.getAEInventoryByName(StorageName.NONE), + this.configClientSlot); } this.prevStack = is; @@ -197,9 +188,9 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { } public void clear() { - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); + final IAEStackInventory inv = this.workBench.getAEInventoryByName(StorageName.NONE); for (int x = 0; x < inv.getSizeInventory(); x++) { - inv.setInventorySlotContents(x, null); + inv.putAEStackInSlot(x, null); } this.detectAndSendChanges(); } @@ -213,28 +204,27 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { } public void partition() { - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); + final IAEStackInventory inv = this.workBench.getAEInventoryByName(StorageName.NONE); + final ItemStack is = this.getUpgradeable().getInventoryByName("cell").getStackInSlot(0); - final IMEInventory cellInv = AEApi.instance().registries().cell().getCellInventory( - this.getUpgradeable().getInventoryByName("cell").getStackInSlot(0), - null, - StorageChannel.ITEMS); + if (!(is != null && is.getItem() instanceof ICellWorkbenchItem wi)) return; - Iterator i = new NullIterator<>(); - if (cellInv != null) { - final IItemList list = cellInv.getAvailableItems( - AEApi.instance().storage().createSortedItemList(), - IterationCounter.fetchNewId()); - i = list.iterator(); - } + final IMEInventory cellInv = AEApi.instance().registries().cell() + .getCellInventory(is, null, wi.getStorageChannel()); + + if (!(cellInv instanceof CellInventory ci)) return; + + final IItemList list = ci + .getAvailableItems(ci.getChannel().createPrimitiveList(), IterationCounter.fetchNewId()); + Iterator i = list.iterator(); for (int x = 0; x < inv.getSizeInventory(); x++) { if (i.hasNext()) { - final ItemStack g = i.next().getItemStack(); - g.stackSize = 1; - inv.setInventorySlotContents(x, g); + final IAEStack g = (IAEStack) i.next(); + g.setStackSize(1); + inv.putAEStackInSlot(x, g); } else { - inv.setInventorySlotContents(x, null); + inv.putAEStackInSlot(x, null); } } @@ -249,6 +239,26 @@ public class ContainerCellWorkbench extends ContainerUpgradeable { this.copyMode = copyMode; } + @Override + public void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks) { + final IAEStackInventory config = this.workBench.getAEInventoryByName(StorageName.NONE); + for (var entry : slotStacks.int2ObjectEntrySet()) { + config.putAEStackInSlot(entry.getIntKey(), entry.getValue()); + } + + if (isServer()) { + this.updateVirtualSlots(StorageName.NONE, config, this.configClientSlot); + } + } + + public StorageChannel getStorageChannel() { + return this.workBench.getStorageChannel(); + } + + public IAEStackInventory getConfig() { + return this.workBench.getAEInventoryByName(StorageName.NONE); + } + public class Upgrades implements IInventory { @Override diff --git a/src/main/java/appeng/container/implementations/ContainerChest.java b/src/main/java/appeng/container/implementations/ContainerChest.java index 139b9c553..baa21a082 100644 --- a/src/main/java/appeng/container/implementations/ContainerChest.java +++ b/src/main/java/appeng/container/implementations/ContainerChest.java @@ -21,7 +21,7 @@ public class ContainerChest extends AEBaseContainer { private final TileChest chest; public ContainerChest(final InventoryPlayer ip, final TileChest chest) { - super(ip, chest, null); + super(ip, chest); this.chest = chest; this.addSlotToContainer( diff --git a/src/main/java/appeng/container/implementations/ContainerCondenser.java b/src/main/java/appeng/container/implementations/ContainerCondenser.java index f318713d2..faa6fbb2e 100644 --- a/src/main/java/appeng/container/implementations/ContainerCondenser.java +++ b/src/main/java/appeng/container/implementations/ContainerCondenser.java @@ -36,7 +36,7 @@ public class ContainerCondenser extends AEBaseContainer implements IProgressProv public CondenserOutput output = CondenserOutput.TRASH; public ContainerCondenser(final InventoryPlayer ip, final TileCondenser condenser) { - super(ip, condenser, null); + super(ip, condenser); this.condenser = condenser; this.addSlotToContainer( diff --git a/src/main/java/appeng/container/implementations/ContainerCraftAmount.java b/src/main/java/appeng/container/implementations/ContainerCraftAmount.java index a3a60029b..b9c446865 100644 --- a/src/main/java/appeng/container/implementations/ContainerCraftAmount.java +++ b/src/main/java/appeng/container/implementations/ContainerCraftAmount.java @@ -13,8 +13,10 @@ package appeng.container.implementations; import javax.annotation.Nonnull; import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.inventory.Slot; +import net.minecraft.item.ItemStack; import net.minecraft.tileentity.TileEntity; import net.minecraft.world.World; @@ -24,18 +26,19 @@ import appeng.api.networking.security.BaseActionSource; import appeng.api.networking.security.IActionHost; import appeng.api.networking.security.PlayerSource; import appeng.api.storage.ITerminalHost; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.container.guisync.GuiSync; -import appeng.container.slot.SlotInaccessible; import appeng.core.sync.GuiBridge; -import appeng.tile.inventory.AppEngInternalInventory; +import appeng.core.sync.network.NetworkHandler; +import appeng.core.sync.packets.PacketVirtualSlot; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class ContainerCraftAmount extends AEBaseContainer { +public class ContainerCraftAmount extends ContainerSubGui { @SideOnly(Side.CLIENT) private MEGuiTextField amountField; @@ -43,14 +46,10 @@ public class ContainerCraftAmount extends AEBaseContainer { @GuiSync(1) public long initialCraftAmount = -1; - private final Slot craftingItem; - private IAEItemStack itemToCreate; + private IAEStack itemToCreate; public ContainerCraftAmount(final InventoryPlayer ip, final ITerminalHost te) { super(ip, te); - - this.craftingItem = new SlotInaccessible(new AppEngInternalInventory(null, 1), 0, 34, 53); - this.addSlotToContainer(this.getCraftingItem()); } @Override @@ -72,16 +71,24 @@ public class ContainerCraftAmount extends AEBaseContainer { return new PlayerSource(this.getPlayerInv().player, (IActionHost) this.getTarget()); } + // addon public Slot getCraftingItem() { - return this.craftingItem; + return new Slot(null, 0, 0, 0) { + + @Override + public void putStack(ItemStack p_75215_1_) {} + }; } - public IAEItemStack getItemToCraft() { + public IAEStack getItemToCraft() { return this.itemToCreate; } - public void setItemToCraft(@Nonnull final IAEItemStack itemToCreate) { + public void setItemToCraft(@Nonnull final IAEStack itemToCreate) { this.itemToCreate = itemToCreate; + + final PacketVirtualSlot p = new PacketVirtualSlot(StorageName.NONE, 0, itemToCreate); + NetworkHandler.instance.sendTo(p, (EntityPlayerMP) this.getInventoryPlayer().player); } public void setInitialCraftAmount(long initialCraftAmount) { diff --git a/src/main/java/appeng/container/implementations/ContainerCraftConfirm.java b/src/main/java/appeng/container/implementations/ContainerCraftConfirm.java index c64ea6972..65c7a1215 100644 --- a/src/main/java/appeng/container/implementations/ContainerCraftConfirm.java +++ b/src/main/java/appeng/container/implementations/ContainerCraftConfirm.java @@ -21,7 +21,6 @@ import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.inventory.ICrafting; -import net.minecraft.tileentity.TileEntity; import net.minecraft.util.ChatComponentText; import net.minecraft.world.World; @@ -38,10 +37,10 @@ import appeng.api.networking.security.BaseActionSource; import appeng.api.networking.security.IActionHost; import appeng.api.networking.security.PlayerSource; import appeng.api.storage.ITerminalHost; -import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.container.guisync.GuiSync; import appeng.container.interfaces.ICraftingCPUSelectorContainer; import appeng.core.AELog; @@ -49,20 +48,14 @@ import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketCraftingTreeData; import appeng.core.sync.packets.PacketMEInventoryUpdate; -import appeng.core.sync.packets.PacketSwitchGuis; import appeng.crafting.MECraftingInventory; import appeng.crafting.v2.CraftingJobV2; -import appeng.helpers.WirelessTerminalGuiObject; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; -import appeng.parts.reporting.PartTerminal; import appeng.tile.misc.TilePatternOptimizationMatrix; import appeng.util.Platform; import io.netty.buffer.ByteBuf; import io.netty.buffer.Unpooled; -public class ContainerCraftConfirm extends AEBaseContainer implements ICraftingCPUSelectorContainer { +public class ContainerCraftConfirm extends ContainerSubGui implements ICraftingCPUSelectorContainer { private Future job; protected ICraftingJob result; @@ -263,15 +256,9 @@ public class ContainerCraftConfirm extends AEBaseContainer implements ICraftingC return h.getActionableNode().getGrid(); } - public IAEItemStack getItemToCraft() { - try { - ByteBuf deserialized = Unpooled.wrappedBuffer(serializedItemToCraft.getBytes(StandardCharsets.ISO_8859_1)); - return AEApi.instance().storage().readItemFromPacket(deserialized); - } catch (IOException e) { - AELog.debug(e); - AELog.debug("Deserializing IAEItemStack Failed"); - return null; - } + public IAEStack getItemToCraft() { + ByteBuf deserialized = Unpooled.wrappedBuffer(serializedItemToCraft.getBytes(StandardCharsets.ISO_8859_1)); + return Platform.readStackByte(deserialized); } public boolean cpuCraftingSameItem(final CraftingCPUStatus c) { @@ -330,36 +317,8 @@ public class ContainerCraftConfirm extends AEBaseContainer implements ICraftingC } public void switchToOriginalGUI() { - GuiBridge originalGui = null; - - final IActionHost ah = this.getActionHost(); - if (ah instanceof WirelessTerminalGuiObject) { - originalGui = GuiBridge.GUI_WIRELESS_TERM; - } - - if (ah instanceof PartTerminal) { - originalGui = GuiBridge.GUI_ME; - } - - if (ah instanceof PartCraftingTerminal) { - originalGui = GuiBridge.GUI_CRAFTING_TERMINAL; - } - - if (ah instanceof PartPatternTerminal) { - originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - if (ah instanceof PartPatternTerminalEx) { - originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } - - if (originalGui != null && this.getOpenContext() != null) { - NetworkHandler.instance - .sendTo(new PacketSwitchGuis(originalGui), (EntityPlayerMP) this.getInventoryPlayer().player); - - final TileEntity te = this.getOpenContext().getTile(); - Platform.openGUI(this.getInventoryPlayer().player, te, this.getOpenContext().getSide(), originalGui); - } + if (this.getInventoryPlayer().player.openContainer instanceof AEBaseContainer bc) + bc.getPrimaryGui().open(this.getInventoryPlayer().player); } private BaseActionSource getActionSrc() { @@ -464,14 +423,9 @@ public class ContainerCraftConfirm extends AEBaseContainer implements ICraftingC this.job = job; } - public void setItemToCraft(@Nonnull final IAEItemStack itemToCraft) { - try { - ByteBuf serialized = Unpooled.buffer(); - itemToCraft.writeToPacket(serialized); - this.serializedItemToCraft = serialized.toString(StandardCharsets.ISO_8859_1); - } catch (IOException e) { - AELog.debug(e); - AELog.debug("Deserializing IAEItemStack Failed"); - } + public void setItemToCraft(@Nonnull final IAEStack itemToCraft) { + ByteBuf serialized = Unpooled.buffer(); + Platform.writeStackByte(itemToCraft, serialized); + this.serializedItemToCraft = serialized.toString(StandardCharsets.ISO_8859_1); } } diff --git a/src/main/java/appeng/container/implementations/ContainerCraftingStatus.java b/src/main/java/appeng/container/implementations/ContainerCraftingStatus.java index e6cf2903f..3ea980f54 100644 --- a/src/main/java/appeng/container/implementations/ContainerCraftingStatus.java +++ b/src/main/java/appeng/container/implementations/ContainerCraftingStatus.java @@ -13,12 +13,23 @@ package appeng.container.implementations; import java.util.List; import net.minecraft.entity.player.InventoryPlayer; +import net.minecraft.inventory.Slot; +import net.minecraft.item.ItemStack; import appeng.api.storage.ITerminalHost; +import appeng.client.gui.IGuiSub; +import appeng.container.PrimaryGui; import appeng.container.guisync.GuiSync; +import appeng.container.interfaces.IContainerSubGui; import appeng.container.interfaces.ICraftingCPUSelectorContainer; +import appeng.container.slot.SlotInaccessible; +import appeng.tile.inventory.AppEngInternalInventory; +import appeng.util.Platform; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; -public class ContainerCraftingStatus extends ContainerCraftingCPU implements ICraftingCPUSelectorContainer { +public class ContainerCraftingStatus extends ContainerCraftingCPU + implements ICraftingCPUSelectorContainer, IContainerSubGui { @GuiSync.Recurse(5) public ContainerCPUTable cpuTable; @@ -26,6 +37,10 @@ public class ContainerCraftingStatus extends ContainerCraftingCPU implements ICr public ContainerCraftingStatus(final InventoryPlayer ip, final ITerminalHost te) { super(ip, te); cpuTable = new ContainerCPUTable(this, this::setCPU, true, c -> true); + + // sub gui copy paste + this.primaryGuiButtonIcon = new SlotInaccessible(new AppEngInternalInventory(null, 1), 0, 0, -9000); + this.addSlotToContainer(this.primaryGuiButtonIcon); } public ContainerCPUTable getCPUTable() { @@ -46,4 +61,33 @@ public class ContainerCraftingStatus extends ContainerCraftingCPU implements ICr public List getCPUs() { return cpuTable.getCPUs(); } + + // sub gui copy paste + private final Slot primaryGuiButtonIcon; + + @SideOnly(Side.CLIENT) + private IGuiSub guiLink; + + @Override + public void onSlotChange(Slot s) { + if (Platform.isClient() && this.primaryGuiButtonIcon == s && this.primaryGuiButtonIcon.getHasStack()) { + this.guiLink.initPrimaryGuiButton(); + } + } + + @Override + public void setPrimaryGui(PrimaryGui primaryGui) { + super.setPrimaryGui(primaryGui); + this.primaryGuiButtonIcon.putStack(primaryGui.getIcon()); + } + + @SideOnly(Side.CLIENT) + public ItemStack getPrimaryGuiIcon() { + return this.primaryGuiButtonIcon.getStack(); + } + + @SideOnly(Side.CLIENT) + public void setGuiLink(IGuiSub gs) { + this.guiLink = gs; + } } diff --git a/src/main/java/appeng/container/implementations/ContainerCraftingTerm.java b/src/main/java/appeng/container/implementations/ContainerCraftingTerm.java index aa99de6cb..3ff63d84f 100644 --- a/src/main/java/appeng/container/implementations/ContainerCraftingTerm.java +++ b/src/main/java/appeng/container/implementations/ContainerCraftingTerm.java @@ -16,12 +16,12 @@ import net.minecraft.inventory.InventoryCrafting; import net.minecraft.item.ItemStack; import net.minecraft.item.crafting.CraftingManager; +import appeng.api.parts.ICraftingTerminal; import appeng.api.storage.ITerminalHost; import appeng.container.ContainerNull; import appeng.container.slot.SlotCraftingMatrix; import appeng.container.slot.SlotCraftingTerm; import appeng.helpers.IContainerCraftingPacket; -import appeng.parts.reporting.PartCraftingTerminal; import appeng.tile.inventory.AppEngInternalInventory; import appeng.tile.inventory.IAEAppEngInventory; import appeng.tile.inventory.InvOperation; @@ -29,14 +29,14 @@ import appeng.tile.inventory.InvOperation; public class ContainerCraftingTerm extends ContainerMEMonitorable implements IAEAppEngInventory, IContainerCraftingPacket { - private final PartCraftingTerminal ct; + private final ICraftingTerminal ct; private final AppEngInternalInventory output = new AppEngInternalInventory(this, 1); private final SlotCraftingMatrix[] craftingSlots = new SlotCraftingMatrix[9]; private final SlotCraftingTerm outputSlot; public ContainerCraftingTerm(final InventoryPlayer ip, final ITerminalHost monitorable) { super(ip, monitorable, false); - this.ct = (PartCraftingTerminal) monitorable; + this.ct = (ICraftingTerminal) monitorable; final IInventory crafting = this.ct.getInventoryByName("crafting"); @@ -65,9 +65,11 @@ public class ContainerCraftingTerm extends ContainerMEMonitorable -72 + 18, this)); - this.bindPlayerInventory(ip, 0, 0); - this.onCraftMatrixChanged(crafting); + + // need because InventoryBogoSorter looking for specific slot number for bind buttons + // bindPlayerInventory in MEMonitorable break it + this.bindPlayerInventory(ip, 0, 0); } /** diff --git a/src/main/java/appeng/container/implementations/ContainerDrive.java b/src/main/java/appeng/container/implementations/ContainerDrive.java index 0b717ec81..fa5ffca90 100644 --- a/src/main/java/appeng/container/implementations/ContainerDrive.java +++ b/src/main/java/appeng/container/implementations/ContainerDrive.java @@ -19,7 +19,7 @@ import appeng.tile.storage.TileDrive; public class ContainerDrive extends AEBaseContainer { public ContainerDrive(final InventoryPlayer ip, final TileDrive drive) { - super(ip, drive, null); + super(ip, drive); for (int y = 0; y < 5; y++) { for (int x = 0; x < 2; x++) { diff --git a/src/main/java/appeng/container/implementations/ContainerGrinder.java b/src/main/java/appeng/container/implementations/ContainerGrinder.java index 4e8ddc8a7..4a1c24f35 100644 --- a/src/main/java/appeng/container/implementations/ContainerGrinder.java +++ b/src/main/java/appeng/container/implementations/ContainerGrinder.java @@ -21,7 +21,7 @@ import appeng.tile.grindstone.TileGrinder; public class ContainerGrinder extends AEBaseContainer { public ContainerGrinder(final InventoryPlayer ip, final TileGrinder grinder) { - super(ip, grinder, null); + super(ip, grinder); this.addSlotToContainer( new SlotRestrictedInput( diff --git a/src/main/java/appeng/container/implementations/ContainerInterfaceTerminal.java b/src/main/java/appeng/container/implementations/ContainerInterfaceTerminal.java index b752d9b56..06057dd7e 100644 --- a/src/main/java/appeng/container/implementations/ContainerInterfaceTerminal.java +++ b/src/main/java/appeng/container/implementations/ContainerInterfaceTerminal.java @@ -33,7 +33,7 @@ import com.google.common.primitives.Ints; import appeng.api.networking.IGrid; import appeng.api.networking.IGridNode; -import appeng.api.networking.security.IActionHost; +import appeng.api.parts.IInterfaceTerminal; import appeng.api.util.DimensionalCoord; import appeng.api.util.IInterfaceViewable; import appeng.container.AEBaseContainer; @@ -44,7 +44,6 @@ import appeng.helpers.InventoryAction; import appeng.items.misc.ItemEncodedPattern; import appeng.parts.AEBasePart; import appeng.parts.p2p.PartP2PTunnel; -import appeng.parts.reporting.PartInterfaceTerminal; import appeng.util.InventoryAdaptor; import appeng.util.Platform; import appeng.util.inv.AdaptorPlayerHand; @@ -59,10 +58,10 @@ public final class ContainerInterfaceTerminal extends AEBaseContainer { private PacketInterfaceTerminalUpdate dirty; private boolean isDirty; private IGrid grid; - private IActionHost anchor; + private final IInterfaceTerminal anchor; private boolean wasOff; - public ContainerInterfaceTerminal(final InventoryPlayer ip, final IActionHost anchor) { + public ContainerInterfaceTerminal(final InventoryPlayer ip, final IInterfaceTerminal anchor) { super(ip, anchor); assert anchor != null; this.anchor = anchor; @@ -110,7 +109,7 @@ public final class ContainerInterfaceTerminal extends AEBaseContainer { } this.wasOff = false; - if (anchor instanceof PartInterfaceTerminal terminal && terminal.needsUpdate()) { + if (anchor.needsUpdate()) { PacketInterfaceTerminalUpdate update = this.updateList(); if (update != null) { update.encode(); diff --git a/src/main/java/appeng/container/implementations/ContainerLevelEmitter.java b/src/main/java/appeng/container/implementations/ContainerLevelEmitter.java index 138d8ca8e..7b0430f7f 100644 --- a/src/main/java/appeng/container/implementations/ContainerLevelEmitter.java +++ b/src/main/java/appeng/container/implementations/ContainerLevelEmitter.java @@ -10,9 +10,13 @@ package appeng.container.implementations; +import static appeng.util.Platform.isServer; + import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.inventory.IInventory; +import net.minecraft.inventory.Slot; +import net.minecraft.item.ItemStack; import appeng.api.config.FuzzyMode; import appeng.api.config.LevelType; @@ -20,18 +24,26 @@ import appeng.api.config.RedstoneMode; import appeng.api.config.SecurityPermissions; import appeng.api.config.Settings; import appeng.api.config.YesNo; +import appeng.api.parts.ILevelEmitter; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.client.gui.IGuiSub; import appeng.client.gui.widgets.MEGuiTextField; +import appeng.container.PrimaryGui; import appeng.container.guisync.GuiSync; -import appeng.container.slot.SlotFakeTypeOnly; +import appeng.container.interfaces.IContainerSubGui; +import appeng.container.interfaces.IVirtualSlotHolder; +import appeng.container.slot.SlotInaccessible; import appeng.container.slot.SlotRestrictedInput; -import appeng.parts.automation.PartLevelEmitter; +import appeng.tile.inventory.AppEngInternalInventory; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; -public class ContainerLevelEmitter extends ContainerUpgradeable { +public class ContainerLevelEmitter extends ContainerUpgradeable implements IVirtualSlotHolder, IContainerSubGui { - private final PartLevelEmitter lvlEmitter; + private final ILevelEmitter lvlEmitter; @SideOnly(Side.CLIENT) private MEGuiTextField textField; @@ -45,9 +57,15 @@ public class ContainerLevelEmitter extends ContainerUpgradeable { @GuiSync(4) public YesNo cmType; - public ContainerLevelEmitter(final InventoryPlayer ip, final PartLevelEmitter te) { + private final IAEStack[] configClientSlot = new IAEStack[1]; + + public ContainerLevelEmitter(final InventoryPlayer ip, final ILevelEmitter te) { super(ip, te); this.lvlEmitter = te; + + // sub gui copy paste + this.primaryGuiButtonIcon = new SlotInaccessible(new AppEngInternalInventory(null, 1), 0, 0, -9000); + this.addSlotToContainer(this.primaryGuiButtonIcon); } @SideOnly(Side.CLIENT) @@ -103,9 +121,6 @@ public class ContainerLevelEmitter extends ContainerUpgradeable { 8 + 18 * 3, this.getInventoryPlayer())).setNotDraggable()); } - - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); - this.addSlotToContainer(new SlotFakeTypeOnly(inv, 0, 17, 42)); } @Override @@ -131,6 +146,10 @@ public class ContainerLevelEmitter extends ContainerUpgradeable { this.setFuzzyMode((FuzzyMode) this.getUpgradeable().getConfigManager().getSetting(Settings.FUZZY_MODE)); this.setRedStoneMode( (RedstoneMode) this.getUpgradeable().getConfigManager().getSetting(Settings.REDSTONE_EMITTER)); + this.updateVirtualSlots( + StorageName.NONE, + this.lvlEmitter.getAEInventoryByName(StorageName.NONE), + this.configClientSlot); } this.standardDetectAndSendChanges(); @@ -166,4 +185,53 @@ public class ContainerLevelEmitter extends ContainerUpgradeable { private void setLevelMode(final LevelType lvType) { this.lvType = lvType; } + + public ILevelEmitter getLvlEmitter() { + return this.lvlEmitter; + } + + @Override + public void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks) { + for (var entry : slotStacks.int2ObjectEntrySet()) { + this.lvlEmitter.getAEInventoryByName(StorageName.NONE) + .putAEStackInSlot(entry.getIntKey(), entry.getValue()); + } + + if (isServer()) { + this.updateVirtualSlots( + StorageName.NONE, + this.lvlEmitter.getAEInventoryByName(StorageName.NONE), + this.configClientSlot); + } + } + + // for level terminal + // sub gui copypaste + private final Slot primaryGuiButtonIcon; + + @SideOnly(Side.CLIENT) + private IGuiSub guiLink; + + @Override + public void onSlotChange(Slot s) { + if (Platform.isClient() && this.primaryGuiButtonIcon == s && this.primaryGuiButtonIcon.getHasStack()) { + this.guiLink.initPrimaryGuiButton(); + } + } + + @Override + public void setPrimaryGui(PrimaryGui primaryGui) { + super.setPrimaryGui(primaryGui); + this.primaryGuiButtonIcon.putStack(primaryGui.getIcon()); + } + + @SideOnly(Side.CLIENT) + public ItemStack getPrimaryGuiIcon() { + return this.primaryGuiButtonIcon.getStack(); + } + + @SideOnly(Side.CLIENT) + public void setGuiLink(IGuiSub gs) { + this.guiLink = gs; + } } diff --git a/src/main/java/appeng/container/implementations/ContainerMEMonitorable.java b/src/main/java/appeng/container/implementations/ContainerMEMonitorable.java index 1437dd95d..b6c915afe 100644 --- a/src/main/java/appeng/container/implementations/ContainerMEMonitorable.java +++ b/src/main/java/appeng/container/implementations/ContainerMEMonitorable.java @@ -10,6 +10,15 @@ package appeng.container.implementations; +import static appeng.util.FluidUtils.clearFluidContainer; +import static appeng.util.FluidUtils.fillFluidContainer; +import static appeng.util.FluidUtils.getFilledFluidContainer; +import static appeng.util.FluidUtils.getFluidContainerCapacity; +import static appeng.util.FluidUtils.getFluidFromContainer; +import static appeng.util.FluidUtils.isFilledFluidContainer; +import static appeng.util.FluidUtils.isFluidContainer; +import static appeng.util.IterationCounter.fetchNewId; + import java.io.IOException; import java.nio.BufferOverflowException; import java.util.ArrayList; @@ -23,8 +32,10 @@ import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.inventory.ICrafting; import net.minecraft.inventory.Slot; import net.minecraft.item.ItemStack; -import net.minecraft.tileentity.TileEntity; import net.minecraftforge.common.util.ForgeDirection; +import net.minecraftforge.fluids.FluidContainerRegistry; +import net.minecraftforge.fluids.FluidStack; +import net.minecraftforge.fluids.IFluidContainerItem; import com.google.common.collect.ImmutableList; import com.google.common.collect.ImmutableSet; @@ -40,7 +51,6 @@ import appeng.api.config.SortDir; import appeng.api.config.SortOrder; import appeng.api.config.TypeFilter; import appeng.api.config.ViewItems; -import appeng.api.implementations.IUpgradeableHost; import appeng.api.implementations.guiobjects.IPortableCell; import appeng.api.implementations.tiles.IMEChest; import appeng.api.implementations.tiles.IViewCellStorage; @@ -50,43 +60,52 @@ import appeng.api.networking.IGridNode; import appeng.api.networking.crafting.ICraftingCPU; import appeng.api.networking.crafting.ICraftingGrid; import appeng.api.networking.energy.IEnergyGrid; -import appeng.api.networking.energy.IEnergySource; import appeng.api.networking.security.BaseActionSource; import appeng.api.networking.security.PlayerSource; import appeng.api.networking.storage.IBaseMonitor; -import appeng.api.parts.IPart; import appeng.api.storage.IMEMonitor; import appeng.api.storage.IMEMonitorHandlerReceiver; import appeng.api.storage.ITerminalHost; import appeng.api.storage.ITerminalPins; +import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.api.util.IConfigManager; import appeng.api.util.IConfigurableObject; import appeng.container.AEBaseContainer; import appeng.container.guisync.GuiSync; +import appeng.container.slot.AppEngSlot; +import appeng.container.slot.SlotDisabled; +import appeng.container.slot.SlotInaccessible; import appeng.container.slot.SlotRestrictedInput; -import appeng.container.slot.SlotRestrictedInput.PlacableItemType; import appeng.core.AELog; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketMEInventoryUpdate; import appeng.core.sync.packets.PacketValueConfig; import appeng.helpers.IPinsHandler; +import appeng.helpers.MonitorableAction; import appeng.helpers.WirelessTerminalGuiObject; import appeng.items.contents.PinsHandler; import appeng.items.storage.ItemViewCell; import appeng.me.helpers.ChannelPowerSrc; import appeng.util.ConfigManager; import appeng.util.IConfigManagerHost; +import appeng.util.InventoryAdaptor; import appeng.util.Platform; +import appeng.util.inv.AdaptorPlayerHand; +import appeng.util.item.AEFluidStack; import appeng.util.item.AEItemStack; +import it.unimi.dsi.fastutil.objects.ObjectIntPair; public class ContainerMEMonitorable extends AEBaseContainer - implements IConfigManagerHost, IConfigurableObject, IMEMonitorHandlerReceiver, IPinsHandler { + implements IConfigManagerHost, IConfigurableObject, IMEMonitorHandlerReceiver>, IPinsHandler { private final SlotRestrictedInput[] cellView = new SlotRestrictedInput[5]; - private final IMEMonitor monitor; + private final IMEMonitor monitorItems; + private final IMEMonitor monitorFluids; private final IItemList items = AEApi.instance().storage().createItemList(); + private final IItemList fluids = AEApi.instance().storage().createFluidList(); private final IConfigManager clientCM; private final ITerminalHost host; @@ -109,10 +128,7 @@ public class ContainerMEMonitorable extends AEBaseContainer protected ContainerMEMonitorable(final InventoryPlayer ip, final ITerminalHost monitorable, final boolean bindInventory) { - super( - ip, - monitorable instanceof TileEntity ? (TileEntity) monitorable : null, - monitorable instanceof IPart ? (IPart) monitorable : null); + super(ip, monitorable); this.host = monitorable; this.clientCM = new ConfigManager(this); @@ -124,46 +140,54 @@ public class ContainerMEMonitorable extends AEBaseContainer this.clientCM.registerSetting(Settings.PINS_STATE, PinsState.DISABLED); // use for GUI if (Platform.isServer()) { - if (monitorable instanceof ITerminalPins t) { - pinsHandler = t.getPinsHandler(ip.player); + this.pinsHandler = t.getPinsHandler(ip.player); } this.serverCM = monitorable.getConfigManager(); - this.monitor = monitorable.getItemInventory(); - if (this.monitor != null) { - this.monitor.addListener(this, null); + this.monitorItems = monitorable.getItemInventory(); + if (monitorItems != null) { + this.monitorItems.addListener(this, null); + this.setCellInventory(this.monitorItems); + } - this.setCellInventory(this.monitor); + this.monitorFluids = monitorable.getFluidInventory(); + if (monitorFluids != null) { + this.monitorFluids.addListener(this, null); + this.setCellFluidInventory(this.monitorFluids); + } - if (monitorable instanceof IPortableCell) { - this.setPowerSource((IEnergySource) monitorable); - } else if (monitorable instanceof IMEChest) { - this.setPowerSource((IEnergySource) monitorable); - } else if (monitorable instanceof IGridHost) { - final IGridNode node = ((IGridHost) monitorable).getGridNode(ForgeDirection.UNKNOWN); - if (node != null) { - this.networkNode = node; - final IGrid g = node.getGrid(); - if (g != null) { - this.setPowerSource(new ChannelPowerSrc(this.networkNode, g.getCache(IEnergyGrid.class))); - } - } - } - } else { + if (this.monitorItems == null && this.monitorFluids == null) { this.setValidContainer(false); + return; + } + + if (monitorable instanceof IGridHost igh) { + this.networkNode = igh.getGridNode(ForgeDirection.UNKNOWN); + } + + if (monitorable instanceof IPortableCell pc) { + this.setPowerSource(pc); + } else if (monitorable instanceof IMEChest imc) { + this.setPowerSource(imc); + } else if (this.networkNode != null) { + final IGrid g = this.networkNode.getGrid(); + if (g != null) { + this.setPowerSource(new ChannelPowerSrc(this.networkNode, g.getCache(IEnergyGrid.class))); + } } } else { - this.monitor = null; + this.monitorItems = null; + this.monitorFluids = null; } this.canAccessViewCells = false; - if (monitorable instanceof IViewCellStorage) { + if (monitorable instanceof IViewCellStorage vcs) { for (int y = 0; y < 5; y++) { this.cellView[y] = new SlotRestrictedInput( SlotRestrictedInput.PlacableItemType.VIEW_CELL, - ((IViewCellStorage) monitorable).getViewCellStorage(), + vcs.getViewCellStorage(), y, 206, y * 18 + 8, @@ -172,16 +196,6 @@ public class ContainerMEMonitorable extends AEBaseContainer this.addSlotToContainer(this.cellView[y]); } } - if (isAPatternTerminal()) { - patternRefiller = new SlotRestrictedInput( - PlacableItemType.UPGRADES, - ((IUpgradeableHost) monitorable).getInventoryByName("upgrades"), - 0, - 206, - 5 * 18 + 11, - this.getInventoryPlayer()); - addSlotToContainer(patternRefiller); - } if (bindInventory) { this.bindPlayerInventory(ip, 0, 0); @@ -195,7 +209,8 @@ public class ContainerMEMonitorable extends AEBaseContainer @Override public void detectAndSendChanges() { if (Platform.isServer()) { - if (this.monitor != this.host.getItemInventory()) { + if (this.monitorItems != this.host.getItemInventory() + || this.monitorFluids != this.host.getFluidInventory()) { this.setValidContainer(false); } @@ -226,35 +241,24 @@ public class ContainerMEMonitorable extends AEBaseContainer } } - if (!this.items.isEmpty()) { - try { - final IItemList monitorCache = this.monitor.getStorageList(); + try { + final PacketMEInventoryUpdate piu = new PacketMEInventoryUpdate(); - final PacketMEInventoryUpdate piu = new PacketMEInventoryUpdate(); + if (this.monitorItems != null) updateList(piu, this.monitorItems.getStorageList(), this.items); - for (final IAEItemStack is : this.items) { - final IAEItemStack send = monitorCache.findPrecise(is); - if (send == null) { - is.setStackSize(0); - piu.appendItem(is); - } else { - piu.appendItem(send); + if (this.monitorFluids != null) updateList(piu, this.monitorFluids.getStorageList(), this.fluids); + + if (!piu.isEmpty()) { + this.items.resetStatus(); + this.fluids.resetStatus(); + + for (final Object c : this.crafters) { + if (c instanceof EntityPlayer) { + NetworkHandler.instance.sendTo(piu, (EntityPlayerMP) c); } } - - if (!piu.isEmpty()) { - this.items.resetStatus(); - - for (final Object c : this.crafters) { - if (c instanceof EntityPlayer) { - NetworkHandler.instance.sendTo(piu, (EntityPlayerMP) c); - } - } - } - } catch (final IOException e) { - AELog.debug(e); } - } + } catch (Exception ignored) {} this.updatePowerStatus(); @@ -273,6 +277,24 @@ public class ContainerMEMonitorable extends AEBaseContainer } } + private void updateList(PacketMEInventoryUpdate piu, IItemList monitorCache, IItemList list) { + if (!list.isEmpty()) { + try { + for (final IAEStack aes : list) { + final IAEStack send = monitorCache.findPrecise(aes); + if (send == null) { + aes.setStackSize(0); + piu.appendItem(aes); + } else { + piu.appendItem(send); + } + } + } catch (final IOException e) { + AELog.debug(e); + } + } + } + protected void updatePowerStatus() { try { if (this.networkNode != null) { @@ -308,43 +330,56 @@ public class ContainerMEMonitorable extends AEBaseContainer } private void queueInventory(final ICrafting c) { - if (Platform.isServer() && c instanceof EntityPlayer && this.monitor != null) { + if (Platform.isServer() && c instanceof EntityPlayerMP pmp) { try { PacketMEInventoryUpdate piu = new PacketMEInventoryUpdate(); - final IItemList monitorCache = this.monitor.getStorageList(); - for (final IAEItemStack send : monitorCache) { - try { - piu.appendItem(send); - } catch (final BufferOverflowException boe) { - NetworkHandler.instance.sendTo(piu, (EntityPlayerMP) c); + if (this.monitorItems != null) queueInventoryList(piu, this.monitorItems.getStorageList(), pmp); - piu = new PacketMEInventoryUpdate(); - piu.appendItem(send); - } - } + if (this.monitorFluids != null) queueInventoryList(piu, this.monitorFluids.getStorageList(), pmp); - NetworkHandler.instance.sendTo(piu, (EntityPlayerMP) c); + NetworkHandler.instance.sendTo(piu, pmp); } catch (final IOException e) { AELog.debug(e); } } } + private void queueInventoryList(PacketMEInventoryUpdate piu, IItemList monitorCache, EntityPlayerMP c) { + try { + for (final IAEStack send : (IItemList) monitorCache) { + try { + piu.appendItem(send); + } catch (final BufferOverflowException boe) { + NetworkHandler.instance.sendTo(piu, c); + + piu = new PacketMEInventoryUpdate(); + piu.appendItem(send); + } + } + } catch (Exception ignored) {} + } + @Override public void removeCraftingFromCrafters(final ICrafting c) { super.removeCraftingFromCrafters(c); - if (this.crafters.isEmpty() && this.monitor != null) { - this.monitor.removeListener(this); + if (this.crafters.isEmpty() && this.monitorItems != null) { + this.monitorItems.removeListener(this); + } + if (this.crafters.isEmpty() && this.monitorFluids != null) { + this.monitorFluids.removeListener(this); } } @Override public void onContainerClosed(final EntityPlayer player) { super.onContainerClosed(player); - if (this.monitor != null) { - this.monitor.removeListener(this); + if (this.monitorItems != null) { + this.monitorItems.removeListener(this); + } + if (this.monitorFluids != null) { + this.monitorFluids.removeListener(this); } } @@ -354,10 +389,14 @@ public class ContainerMEMonitorable extends AEBaseContainer } @Override - public void postChange(final IBaseMonitor monitor, final Iterable change, - final BaseActionSource source) { - for (final IAEItemStack is : change) { - this.items.add(is); + public void postChange(IBaseMonitor> monitor, Iterable> change, + BaseActionSource actionSource) { + for (final IAEStack aes : change) { + if (aes instanceof IAEItemStack ais) { + this.items.add(ais); + } else if (aes instanceof IAEFluidStack afs) { + this.fluids.add(afs); + } } } @@ -435,28 +474,11 @@ public class ContainerMEMonitorable extends AEBaseContainer } public IMEMonitor getMonitor() { - return monitor; + return monitorItems; } - // to avoid duplicating this method in 2 pattern terminals - protected void refillBlankPatterns(Slot slot) { - if (Platform.isServer()) { - ItemStack blanks = slot.getStack(); - int blanksToRefill = 64; - if (blanks != null) blanksToRefill -= blanks.stackSize; - if (blanksToRefill <= 0) return; - final AEItemStack request = AEItemStack - .create(AEApi.instance().definitions().materials().blankPattern().maybeStack(blanksToRefill).get()); - final IAEItemStack extracted = Platform - .poweredExtraction(this.getPowerSource(), this.getCellInventory(), request, this.getActionSource()); - if (extracted != null) { - if (blanks != null) blanks.stackSize += extracted.getStackSize(); - else { - blanks = extracted.getItemStack(); - } - slot.putStack(blanks); - } - } + public IMEMonitor getFluidMonitor() { + return monitorFluids; } private int lastUpdate = 0; @@ -472,19 +494,20 @@ public class ContainerMEMonitorable extends AEBaseContainer final ICraftingGrid cc = itp.getGrid().getCache(ICraftingGrid.class); final ImmutableList cpuList = cc.getCpus().asList(); - List craftedItems = new ArrayList<>(); + List> craftedItems = new ArrayList<>(); // fetch the first available crafting output for (int i = 0; i < cpuList.size(); i++) { ICraftingCPU cpu = cpuList.get(i); - if (cpu.getCraftingAllowMode() != CraftingAllow.ONLY_NONPLAYER && cpu.getFinalOutput() != null + IAEStack output = cpu.getFinalMultiOutput(); + if (cpu.getCraftingAllowMode() != CraftingAllow.ONLY_NONPLAYER && output != null && cpu.getCurrentJobSource() instanceof PlayerSource src && src.player == pinsHandler.getPlayer()) { - if (craftedItems.contains(cpu.getFinalOutput())) { + if (craftedItems.contains(output)) { continue; // skip if already added } - if (cpu.isBusy()) craftedItems.add(0, cpu.getFinalOutput().copy()); - else craftedItems.add(cpu.getFinalOutput().copy()); + if (cpu.isBusy()) craftedItems.add(0, output.copy()); + else craftedItems.add(output.copy()); } } @@ -495,15 +518,16 @@ public class ContainerMEMonitorable extends AEBaseContainer } @Override - public void setPin(ItemStack is, int idx) { + public void setPin(IAEStack is, int idx) { if (pinsHandler == null || !(host instanceof ITerminalPins itp)) return; if (is == null) { final ICraftingGrid cc = itp.getGrid().getCache(ICraftingGrid.class); final ImmutableSet cpuSet = cc.getCpus(); for (ICraftingCPU cpu : cpuSet) { - if (cpu.getCraftingAllowMode() != CraftingAllow.ONLY_NONPLAYER && cpu.getFinalOutput() != null - && cpu.getFinalOutput().isSameType(getPin(idx))) { + IAEStack output = cpu.getFinalMultiOutput(); + if (cpu.getCraftingAllowMode() != CraftingAllow.ONLY_NONPLAYER && output != null + && output.isSameType(getPin(idx))) { if (!cpu.isBusy()) { cpu.resetFinalOutput(); } else { @@ -517,7 +541,7 @@ public class ContainerMEMonitorable extends AEBaseContainer } @Override - public ItemStack getPin(int idx) { + public IAEStack getPin(int idx) { if (pinsHandler == null) return null; return pinsHandler.getPin(idx); } @@ -536,4 +560,466 @@ public class ContainerMEMonitorable extends AEBaseContainer public PinsHandler getPinsHandler() { return pinsHandler; } + + public void doMonitorableAction(MonitorableAction action, int custom, final EntityPlayerMP player) { + IAEItemStack slotItem = null; + IAEFluidStack slotFluid = null; + if (this.getTargetStack() instanceof IAEFluidStack afs) { + slotFluid = this.getCellFluidInventory().getAvailableItem(afs, fetchNewId()); + } else if (this.getTargetStack() instanceof IAEItemStack ais) { + slotItem = this.getCellInventory().getAvailableItem(ais, fetchNewId()); + } + + switch (action) { + case AUTO_CRAFT -> {} // handled in PacketMonitorableAction + case SET_ITEM_PIN -> { + ItemStack hand = player.inventory.getItemStack(); + if (hand == null) return; + + if (this.getPin(custom) != null && this.getPin(custom) instanceof IAEItemStack pinStack + && hand.isItemEqual(pinStack.getItemStack())) { + // put item in the terminal + doMonitorableAction(MonitorableAction.PICKUP_OR_SET_DOWN, this.inventorySlots.size(), player); + } else { + this.setPin(AEItemStack.create(hand), custom); + } + } + case SET_CONTAINER_PIN -> { + ItemStack hand = player.inventory.getItemStack(); + if (!isFilledFluidContainer(hand)) return; + FluidStack fluid = getFluidFromContainer(hand); + if (fluid == null) return; + + if (this.getPin(custom) != null && this.getPin(custom) instanceof IAEFluidStack pinStack + && fluid.isFluidEqual(pinStack.getFluidStack())) { + // put item in the terminal + doMonitorableAction(MonitorableAction.FILL_SINGLE_CONTAINER, this.inventorySlots.size(), player); + } else { + this.setPin(AEFluidStack.create(fluid), custom); + } + } + case UNSET_PIN -> { + this.setPin(null, custom); + } + case SHIFT_CLICK -> { // shift left click + if (this.getPowerSource() == null || this.getCellInventory() == null || slotItem == null) { + return; + } + + IAEItemStack ais = slotItem.copy(); + ItemStack myItem = ais.getItemStack(); + ais.setStackSize(myItem.getMaxStackSize()); + myItem.stackSize = (int) ais.getStackSize(); + + final InventoryAdaptor adaptor = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + myItem = adaptor.simulateAdd(myItem); + + if (myItem != null) { + ais.setStackSize(ais.getStackSize() - myItem.stackSize); + } + + ais = Platform + .poweredExtraction(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); + if (ais != null) { + adaptor.addItems(ais.getItemStack()); + } + } + case PICKUP_SINGLE, ROLL_UP -> { // shift right click, roll up + if (this.getPowerSource() == null || this.getCellInventory() == null || slotItem == null) { + return; + } + + final ItemStack hand = player.inventory.getItemStack(); + + if (hand != null) { + if (hand.stackSize >= hand.getMaxStackSize()) return; + if (!Platform.isSameItemPrecise(slotItem.getItemStack(), hand)) return; + } + + IAEItemStack ais = slotItem.copy(); + ais.setStackSize(1); + ais = Platform + .poweredExtraction(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); + if (ais != null) { + final InventoryAdaptor ia = new AdaptorPlayerHand(player); + + final ItemStack fail = ia.addItems(ais.getItemStack()); + if (fail != null) { + this.getCellInventory().injectItems(ais, Actionable.MODULATE, this.getActionSource()); + } + + this.updateHeld(player); + } + } + case PICKUP_OR_SET_DOWN -> { // left click + if (this.getPowerSource() == null || this.getCellInventory() == null) { + return; + } + + ItemStack hand = player.inventory.getItemStack(); + if (hand == null) { + if (slotItem == null) return; + + IAEItemStack ais = slotItem.copy(); + ais.setStackSize(ais.getItemStack().getMaxStackSize()); + ais = Platform.poweredExtraction( + this.getPowerSource(), + this.getCellInventory(), + ais, + this.getActionSource()); + if (ais != null) { + player.inventory.setItemStack(ais.getItemStack()); + } else { + player.inventory.setItemStack(null); + } + this.updateHeld(player); + } else { + IAEItemStack ais = AEApi.instance().storage().createItemStack(hand); + ais = Platform + .poweredInsert(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); + if (ais != null) { + player.inventory.setItemStack(ais.getItemStack()); + } else { + player.inventory.setItemStack(null); + } + this.updateHeld(player); + } + } + case SPLIT_OR_PLACE_SINGLE -> { // right click + if (this.getPowerSource() == null || this.getCellInventory() == null) { + return; + } + + ItemStack hand = player.inventory.getItemStack(); + if (hand == null) { + if (slotItem == null) return; + + IAEItemStack ais = slotItem.copy(); + final long maxSize = ais.getItemStack().getMaxStackSize(); + ais.setStackSize(maxSize); + ais = this.getCellInventory().extractItems(ais, Actionable.SIMULATE, this.getActionSource()); + + if (ais != null) { + final long stackSize = Math.min(maxSize, ais.getStackSize()); + ais.setStackSize((stackSize + 1) >> 1); + ais = Platform.poweredExtraction( + this.getPowerSource(), + this.getCellInventory(), + ais, + this.getActionSource()); + } + + if (ais != null) { + player.inventory.setItemStack(ais.getItemStack()); + } else { + player.inventory.setItemStack(null); + } + this.updateHeld(player); + } else { + IAEItemStack ais = AEApi.instance().storage().createItemStack(player.inventory.getItemStack()); + ais.setStackSize(1); + ais = Platform + .poweredInsert(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); + if (ais == null) { + final ItemStack is = player.inventory.getItemStack(); + is.stackSize--; + if (is.stackSize <= 0) { + player.inventory.setItemStack(null); + } + this.updateHeld(player); + } + } + } + case ROLL_DOWN -> { + final ItemStack hand = player.inventory.getItemStack(); + if (this.getPowerSource() == null || this.getCellInventory() == null || hand == null) { + return; + } + + IAEItemStack ais = AEItemStack.create(hand); + ais.setStackSize(1); + + ais = Platform + .poweredInsert(this.getPowerSource(), this.getCellInventory(), ais, this.getActionSource()); + if (ais == null) { + hand.stackSize--; + if (hand.stackSize <= 0) { + player.inventory.setItemStack(null); + } + this.updateHeld(player); + } + } + case MOVE_REGION -> { + if (slotItem == null) return; + + final long maxSize = slotItem.getItemStack().getMaxStackSize(); + final InventoryAdaptor adaptor = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + while (true) { + IAEItemStack ais = slotItem.copy(); + ais.setStackSize(maxSize); + ais = this.getCellInventory().extractItems(ais, Actionable.SIMULATE, this.getActionSource()); + + if (ais == null || ais.getStackSize() <= 0) break; + + ItemStack myItem = ais.getItemStack(); + myItem = adaptor.simulateAdd(myItem); + + if (myItem != null) { + if (ais.getStackSize() == myItem.stackSize) break; + ais.setStackSize(ais.getStackSize() - myItem.stackSize); + } + + ais = Platform.poweredExtraction( + this.getPowerSource(), + this.getCellInventory(), + ais, + this.getActionSource()); + if (ais == null || ais.getStackSize() <= 0) break; + adaptor.addItems(ais.getItemStack()); + } + } + case CREATIVE_DUPLICATE -> { + if (player.capabilities.isCreativeMode && slotItem != null) { + final ItemStack is = slotItem.getItemStack(); + is.stackSize = is.getMaxStackSize(); + player.inventory.setItemStack(is); + this.updateHeld(player); + } + } + case DRAIN_SINGLE_CONTAINER -> { + ItemStack hand = player.inventory.getItemStack(); + if (!isFilledFluidContainer(hand)) return; + + if (hand.stackSize == 1) { + extractFromSingleFluidContainer(player, hand); + } else { + final InventoryAdaptor adaptor = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + if (hand.getItem() instanceof IFluidContainerItem container) { + ItemStack itemToInject = hand.copy(); + itemToInject.stackSize = 1; + FluidStack fluid = container.getFluid(itemToInject); + IAEFluidStack aes = AEFluidStack.create(fluid); + IAEFluidStack leftover = this.getCellFluidInventory() + .injectItems(aes, Actionable.SIMULATE, this.getActionSource()); + int injected = leftover == null ? fluid.amount : (int) (fluid.amount - leftover.getStackSize()); + if (injected == 0) return; + + container.drain(itemToInject, injected, true); + if (adaptor.addItems(itemToInject) != null) return; + + this.getCellFluidInventory().injectItems(aes, Actionable.MODULATE, this.getActionSource()); + hand.stackSize--; + this.updateHeld(player); + } else if (FluidContainerRegistry.isContainer(hand)) { + FluidStack fluid = FluidContainerRegistry.getFluidForFilledItem(hand); + IAEFluidStack toInject = AEFluidStack.create(fluid); + IAEFluidStack leftover = this.getCellFluidInventory() + .injectItems(toInject, Actionable.SIMULATE, this.getActionSource()); + if (leftover != null) return; + ItemStack emptyContainer = FluidContainerRegistry.drainFluidContainer(hand); + if (adaptor.addItems(emptyContainer) != null) return; + + this.getCellFluidInventory().injectItems(toInject, Actionable.MODULATE, this.getActionSource()); + hand.stackSize--; + this.updateHeld(player); + } + } + + } + case DRAIN_CONTAINERS -> { + final ItemStack hand = player.inventory.getItemStack(); + if (!isFilledFluidContainer(hand)) return; + + if (hand.stackSize == 1) { + extractFromSingleFluidContainer(player, hand); + } else { + FluidStack fluid = getFluidFromContainer(hand); + IAEFluidStack toInject = AEFluidStack.create(fluid); + long toInjectAmount = (long) fluid.amount * hand.stackSize; + toInject.setStackSize(toInjectAmount); + IAEFluidStack leftover = this.getCellFluidInventory() + .injectItems(toInject, Actionable.SIMULATE, this.getActionSource()); + long injected = leftover == null ? toInjectAmount : toInjectAmount - leftover.getStackSize(); + if (injected <= 0) return; + + ItemStack cleared = hand.copy(); + cleared.stackSize = 1; + cleared = clearFluidContainer(cleared); + if (cleared == null) return; + + if (injected == toInjectAmount && hand.stackSize <= cleared.getMaxStackSize()) { + toInject.setStackSize(toInjectAmount); + this.getCellFluidInventory().injectItems(toInject, Actionable.MODULATE, this.getActionSource()); + cleared.stackSize = hand.stackSize; + player.inventory.setItemStack(cleared); + this.updateHeld(player); + } else { + int stackSize = hand.stackSize; + int fluidAmountPerItem = getFluidFromContainer(hand).amount; + if (fluidAmountPerItem <= 0) return; + + final InventoryAdaptor adaptor = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + for (int i = 0; i < stackSize; i++) { + toInject.setStackSize(fluidAmountPerItem); + leftover = this.getCellFluidInventory() + .injectItems(toInject, Actionable.SIMULATE, this.getActionSource()); + injected = leftover == null ? fluidAmountPerItem : toInjectAmount - leftover.getStackSize(); + if (injected != fluidAmountPerItem) break; + + if (adaptor.addItems(cleared.copy()) != null) break; + + toInject.setStackSize(fluidAmountPerItem); + this.getCellFluidInventory() + .injectItems(toInject, Actionable.MODULATE, this.getActionSource()); + hand.stackSize--; + } + this.updateHeld(player); + } + } + } + case FILL_SINGLE_CONTAINER -> { + ItemStack hand = player.inventory.getItemStack(); + if (slotFluid == null || slotFluid.getStackSize() <= 0 || !isFluidContainer(hand)) return; + + if (hand.stackSize == 1) { + // Set filled item to player hand + fillSingleFluidContainer(player, hand, slotFluid); + } else { + // Insert filled item to player inventory + ItemStack itemToFill = hand.copy(); + itemToFill.stackSize = 1; + ObjectIntPair filledPair = fillFluidContainer(itemToFill, slotFluid.getFluidStack()); + ItemStack filledContainer = filledPair.left(); + int filledAmount = filledPair.rightInt(); + if (filledContainer == null || filledAmount <= 0) return; + + final InventoryAdaptor adaptor = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + if (adaptor.addItems(filledContainer) != null) return; + + IAEFluidStack afs = slotFluid.copy(); + afs.setStackSize(filledAmount); + this.getCellFluidInventory().extractItems(afs, Actionable.MODULATE, this.getActionSource()); + hand.stackSize--; + this.updateHeld(player); + } + } + case FILL_CONTAINERS -> { + ItemStack hand = player.inventory.getItemStack(); + if (slotFluid == null || slotFluid.getStackSize() <= 0 || !isFluidContainer(hand)) return; + + // Set filled item to player hand + if (hand.stackSize == 1) { + fillSingleFluidContainer(player, hand, slotFluid); + } else { + int capacity = getFluidContainerCapacity(hand, slotFluid.getFluidStack()); + if (capacity == 0) return; + + ItemStack filledContainer = getFilledFluidContainer(hand, slotFluid.getFluidStack()); + if (filledContainer.getMaxStackSize() >= hand.stackSize + && (long) capacity * hand.stackSize <= slotFluid.getStackSize()) { + // Fill all item in player hand + IAEFluidStack toExtract = slotFluid.copy(); + toExtract.setStackSize((long) capacity * hand.stackSize); + this.getCellFluidInventory() + .extractItems(toExtract, Actionable.MODULATE, this.getActionSource()); + filledContainer.stackSize = hand.stackSize; + player.inventory.setItemStack(filledContainer); + this.updateHeld(player); + } else { + // Set all filled item to player hand + IAEFluidStack afs = slotFluid.copy(); + final InventoryAdaptor adaptor = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + int stackSize = hand.stackSize; + for (int i = 0; i < stackSize; i++) { + ItemStack itemToFill = hand.copy(); + itemToFill.stackSize = 1; + FluidStack fluidForFill = afs.getFluidStack(); + ObjectIntPair filled = fillFluidContainer(itemToFill, fluidForFill); + filledContainer = filled.left(); + int filledAmount = filled.rightInt(); + if (filledContainer == null || filledAmount <= 0) break; + + if (adaptor.addItems(filledContainer) != null) break; + + long amountBeforeExtract = afs.getStackSize(); + afs.setStackSize(filledAmount); + this.getCellFluidInventory().extractItems(afs, Actionable.MODULATE, this.getActionSource()); + afs.setStackSize(amountBeforeExtract - filledAmount); + hand.stackSize--; + } + this.updateHeld(player); + } + } + } + } + } + + private void fillSingleFluidContainer(EntityPlayerMP player, ItemStack hand, IAEFluidStack slotFluid) { + ObjectIntPair filledPair = fillFluidContainer(hand, slotFluid.getFluidStack()); + ItemStack filledContainer = filledPair.left(); + int filledAmount = filledPair.rightInt(); + if (filledContainer == null || filledAmount <= 0) return; + + IAEFluidStack afs = slotFluid.copy(); + afs.setStackSize(filledAmount); + this.getCellFluidInventory().extractItems(afs, Actionable.MODULATE, this.getActionSource()); + player.inventory.setItemStack(filledContainer); + this.updateHeld(player); + } + + private void extractFromSingleFluidContainer(EntityPlayerMP player, ItemStack hand) { + if (hand.getItem() instanceof IFluidContainerItem container) { + FluidStack fluid = container.getFluid(hand); + IAEFluidStack leftover = this.getCellFluidInventory() + .injectItems(AEFluidStack.create(fluid), Actionable.MODULATE, this.getActionSource()); + int injected = leftover == null ? fluid.amount : (int) (fluid.amount - leftover.getStackSize()); + if (injected == 0) return; + container.drain(hand, injected, true); + } else if (FluidContainerRegistry.isContainer(hand)) { + FluidStack fluid = FluidContainerRegistry.getFluidForFilledItem(hand); + IAEFluidStack toInject = AEFluidStack.create(fluid); + IAEFluidStack leftover = this.getCellFluidInventory() + .injectItems(toInject, Actionable.SIMULATE, this.getActionSource()); + if (leftover != null) return; + this.getCellFluidInventory().injectItems(toInject, Actionable.MODULATE, this.getActionSource()); + player.inventory.setItemStack(FluidContainerRegistry.drainFluidContainer(hand)); + } + this.updateHeld(player); + } + + @Override + public ItemStack transferStackInSlot(EntityPlayer p, int idx) { + if (Platform.isClient()) { + return null; + } + + final AppEngSlot clickSlot = (AppEngSlot) this.inventorySlots.get(idx); // require AE SLots! + + if (clickSlot instanceof SlotDisabled || clickSlot instanceof SlotInaccessible) { + return null; + } + + if (clickSlot != null && clickSlot.getHasStack() && clickSlot.isPlayerSide()) { + ItemStack tis = clickSlot.getStack(); + tis = this.shiftStoreItem(tis); + clickSlot.putStack(tis); + } + + return super.transferStackInSlot(p, idx); + } + + private ItemStack shiftStoreItem(final ItemStack input) { + if (this.getPowerSource() == null || this.getCellInventory() == null) { + return input; + } + final IAEItemStack ais = Platform.poweredInsert( + this.getPowerSource(), + this.getCellInventory(), + AEApi.instance().storage().createItemStack(input), + this.getActionSource()); + if (ais == null) { + return null; + } + return ais.getItemStack(); + } } diff --git a/src/main/java/appeng/container/implementations/ContainerMEPortableCell.java b/src/main/java/appeng/container/implementations/ContainerMEPortableCell.java index 8f4f68f61..b2871e3f4 100644 --- a/src/main/java/appeng/container/implementations/ContainerMEPortableCell.java +++ b/src/main/java/appeng/container/implementations/ContainerMEPortableCell.java @@ -11,75 +11,13 @@ package appeng.container.implementations; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.item.ItemStack; -import appeng.api.config.Actionable; -import appeng.api.config.PowerMultiplier; import appeng.api.implementations.guiobjects.IPortableCell; -import appeng.container.interfaces.IInventorySlotAware; -import appeng.util.Platform; public class ContainerMEPortableCell extends ContainerMEMonitorable { - private double powerMultiplier = 0.5; - - private final IPortableCell civ; - private int ticks = 0; - private final int slot; - public ContainerMEPortableCell(final InventoryPlayer ip, final IPortableCell monitorable) { - super(ip, monitorable, false); - if (monitorable instanceof IInventorySlotAware) { - final int slotIndex = ((IInventorySlotAware) monitorable).getInventorySlot(); - this.lockPlayerInventorySlot(slotIndex); - this.slot = slotIndex; - } else { - this.slot = -1; - this.lockPlayerInventorySlot(ip.currentItem); - } - this.civ = monitorable; - this.bindPlayerInventory(ip, 0, 0); - } - - @Override - public void detectAndSendChanges() { - final ItemStack currentItem = this.slot < 0 ? this.getPlayerInv().getCurrentItem() - : this.getPlayerInv().getStackInSlot(this.slot); - - if (this.civ != null) { - if (currentItem != this.civ.getItemStack()) { - if (currentItem != null) { - if (Platform.isSameItem(this.civ.getItemStack(), currentItem)) { - this.getPlayerInv() - .setInventorySlotContents(this.getPlayerInv().currentItem, this.civ.getItemStack()); - } else { - this.setValidContainer(false); - } - } else { - this.setValidContainer(false); - } - } - } else { - this.setValidContainer(false); - } - - // drain 1 ae t - this.ticks++; - if (this.ticks > 10) { - this.civ.extractAEPower( - this.getPowerMultiplier() * this.ticks, - Actionable.MODULATE, - PowerMultiplier.CONFIG); - this.ticks = 0; - } - super.detectAndSendChanges(); - } - - private double getPowerMultiplier() { - return this.powerMultiplier; - } - - void setPowerMultiplier(final double powerMultiplier) { - this.powerMultiplier = powerMultiplier; + super(ip, monitorable); + setPowerMultiplier(0.5); } } diff --git a/src/main/java/appeng/container/implementations/ContainerNetworkStatus.java b/src/main/java/appeng/container/implementations/ContainerNetworkStatus.java index 7e16a05f7..83caf0f55 100644 --- a/src/main/java/appeng/container/implementations/ContainerNetworkStatus.java +++ b/src/main/java/appeng/container/implementations/ContainerNetworkStatus.java @@ -150,7 +150,7 @@ public class ContainerNetworkStatus extends AEBaseContainer { private boolean isConsume = true; public ContainerNetworkStatus(final InventoryPlayer ip, final INetworkTool te) { - super(ip, null, null); + super(ip, te); final IGridHost host = te.getGridHost(); if (host != null) { diff --git a/src/main/java/appeng/container/implementations/ContainerNetworkTool.java b/src/main/java/appeng/container/implementations/ContainerNetworkTool.java index 9271a3c26..9f6efe14d 100644 --- a/src/main/java/appeng/container/implementations/ContainerNetworkTool.java +++ b/src/main/java/appeng/container/implementations/ContainerNetworkTool.java @@ -29,7 +29,7 @@ public class ContainerNetworkTool extends AEBaseContainer { public boolean facadeMode; public ContainerNetworkTool(final InventoryPlayer ip, final INetworkTool te) { - super(ip, null, null); + super(ip, te); this.toolInv = te; this.lockPlayerInventorySlot(ip.currentItem); diff --git a/src/main/java/appeng/container/implementations/ContainerOptimizePatterns.java b/src/main/java/appeng/container/implementations/ContainerOptimizePatterns.java index ce19f35f7..dc51916ce 100644 --- a/src/main/java/appeng/container/implementations/ContainerOptimizePatterns.java +++ b/src/main/java/appeng/container/implementations/ContainerOptimizePatterns.java @@ -13,7 +13,6 @@ import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; -import net.minecraft.tileentity.TileEntity; import org.apache.commons.lang3.tuple.Pair; @@ -25,30 +24,22 @@ import appeng.api.networking.security.IActionHost; import appeng.api.storage.ITerminalHost; import appeng.api.storage.data.IAEStack; import appeng.api.util.IInterfaceViewable; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.core.AELog; import appeng.core.features.registries.InterfaceTerminalRegistry; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketMEInventoryUpdate; -import appeng.core.sync.packets.PacketSwitchGuis; import appeng.crafting.v2.CraftingContext; import appeng.crafting.v2.CraftingJobV2; import appeng.crafting.v2.resolvers.CraftableItemResolver.CraftFromPatternTask; import appeng.crafting.v2.resolvers.CraftingTask; -import appeng.helpers.WirelessTerminalGuiObject; import appeng.me.cache.CraftingGridCache; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; -import appeng.parts.reporting.PartTerminal; import appeng.tile.misc.TilePatternOptimizationMatrix; import appeng.util.PatternMultiplierHelper; -import appeng.util.Platform; import codechicken.nei.ItemStackMap; import codechicken.nei.ItemStackSet; -public class ContainerOptimizePatterns extends AEBaseContainer { +public class ContainerOptimizePatterns extends ContainerSubGui { private ICraftingJob result; @@ -185,36 +176,7 @@ public class ContainerOptimizePatterns extends AEBaseContainer { } public void switchToOriginalGUI() { - GuiBridge originalGui = null; - - final IActionHost ah = this.getActionHost(); - if (ah instanceof WirelessTerminalGuiObject) { - originalGui = GuiBridge.GUI_WIRELESS_TERM; - } - - if (ah instanceof PartTerminal) { - originalGui = GuiBridge.GUI_ME; - } - - if (ah instanceof PartCraftingTerminal) { - originalGui = GuiBridge.GUI_CRAFTING_TERMINAL; - } - - if (ah instanceof PartPatternTerminal) { - originalGui = GuiBridge.GUI_PATTERN_TERMINAL; - } - - if (ah instanceof PartPatternTerminalEx) { - originalGui = GuiBridge.GUI_PATTERN_TERMINAL_EX; - } - - if (originalGui != null && this.getOpenContext() != null) { - NetworkHandler.instance - .sendTo(new PacketSwitchGuis(originalGui), (EntityPlayerMP) this.getInventoryPlayer().player); - - final TileEntity te = this.getOpenContext().getTile(); - Platform.openGUI(this.getInventoryPlayer().player, te, this.getOpenContext().getSide(), originalGui); - } + getPrimaryGui().open(this.getInventoryPlayer().player); } public static int getBitMultiplier(long currentCrafts, long perCraft, long maximumCrafts) { diff --git a/src/main/java/appeng/container/implementations/ContainerOreFilter.java b/src/main/java/appeng/container/implementations/ContainerOreFilter.java index 2156069d6..d2a42004c 100644 --- a/src/main/java/appeng/container/implementations/ContainerOreFilter.java +++ b/src/main/java/appeng/container/implementations/ContainerOreFilter.java @@ -1,18 +1,16 @@ package appeng.container.implementations; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.tileentity.TileEntity; -import appeng.api.parts.IPart; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.container.guisync.GuiSync; import appeng.helpers.IOreFilterable; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class ContainerOreFilter extends AEBaseContainer { +public class ContainerOreFilter extends ContainerSubGui { private final IOreFilterable filterHost; @@ -23,7 +21,7 @@ public class ContainerOreFilter extends AEBaseContainer { public String filter = ""; public ContainerOreFilter(final InventoryPlayer ip, final IOreFilterable te) { - super(ip, (TileEntity) (te instanceof TileEntity ? te : null), (IPart) (te instanceof IPart ? te : null)); + super(ip, te); this.filterHost = te; } diff --git a/src/main/java/appeng/container/implementations/ContainerPatternItemRenamer.java b/src/main/java/appeng/container/implementations/ContainerPatternItemRenamer.java index c2977910b..5e567b6c5 100644 --- a/src/main/java/appeng/container/implementations/ContainerPatternItemRenamer.java +++ b/src/main/java/appeng/container/implementations/ContainerPatternItemRenamer.java @@ -1,35 +1,12 @@ package appeng.container.implementations; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.Slot; -import net.minecraft.world.World; -import appeng.api.networking.IGrid; -import appeng.api.networking.security.IActionHost; import appeng.api.storage.ITerminalHost; -import appeng.container.AEBaseContainer; -import appeng.container.slot.SlotInaccessible; -import appeng.tile.inventory.AppEngInternalInventory; -public class ContainerPatternItemRenamer extends AEBaseContainer { - - private final Slot patternValue; +public class ContainerPatternItemRenamer extends ContainerPatternValueAmount { public ContainerPatternItemRenamer(final InventoryPlayer ip, final ITerminalHost te) { super(ip, te); - patternValue = new SlotInaccessible(new AppEngInternalInventory(null, 1), 0, 34, 53); - } - - public IGrid getGrid() { - final IActionHost h = ((IActionHost) getTarget()); - return h.getActionableNode().getGrid(); - } - - public World getWorld() { - return getPlayerInv().player.worldObj; - } - - public Slot getPatternValue() { - return patternValue; } } diff --git a/src/main/java/appeng/container/implementations/ContainerPatternMulti.java b/src/main/java/appeng/container/implementations/ContainerPatternMulti.java index b0c2668fa..7e472f675 100644 --- a/src/main/java/appeng/container/implementations/ContainerPatternMulti.java +++ b/src/main/java/appeng/container/implementations/ContainerPatternMulti.java @@ -9,9 +9,9 @@ import appeng.api.networking.security.BaseActionSource; import appeng.api.networking.security.IActionHost; import appeng.api.networking.security.PlayerSource; import appeng.api.storage.ITerminalHost; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; -public class ContainerPatternMulti extends AEBaseContainer { +public class ContainerPatternMulti extends ContainerSubGui { public ContainerPatternMulti(final InventoryPlayer ip, final ITerminalHost te) { super(ip, te); diff --git a/src/main/java/appeng/container/implementations/ContainerPatternTerm.java b/src/main/java/appeng/container/implementations/ContainerPatternTerm.java index f49c98a4d..0abb85d58 100644 --- a/src/main/java/appeng/container/implementations/ContainerPatternTerm.java +++ b/src/main/java/appeng/container/implementations/ContainerPatternTerm.java @@ -10,17 +10,16 @@ package appeng.container.implementations; +import static appeng.parts.reporting.PartPatternTerminal.*; +import static appeng.util.Platform.isServer; import static appeng.util.Platform.writeStackNBT; import java.util.ArrayList; -import java.util.Arrays; import java.util.List; -import java.util.stream.Collectors; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.ICrafting; import net.minecraft.inventory.IInventory; import net.minecraft.inventory.InventoryCrafting; import net.minecraft.inventory.Slot; @@ -28,53 +27,62 @@ import net.minecraft.inventory.SlotCrafting; import net.minecraft.item.ItemStack; import net.minecraft.item.crafting.CraftingManager; import net.minecraft.item.crafting.IRecipe; -import net.minecraft.nbt.NBTBase; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagList; import net.minecraftforge.common.util.ForgeDirection; import appeng.api.AEApi; import appeng.api.config.Actionable; -import appeng.api.definitions.IDefinitions; import appeng.api.networking.security.MachineSource; +import appeng.api.parts.IPatternTerminal; import appeng.api.storage.IMEMonitor; import appeng.api.storage.ITerminalHost; +import appeng.api.storage.StorageName; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.container.ContainerNull; import appeng.container.guisync.GuiSync; +import appeng.container.interfaces.IVirtualSlotHolder; +import appeng.container.interfaces.IVirtualSlotSource; import appeng.container.slot.IOptionalSlotHost; -import appeng.container.slot.OptionalSlotFake; -import appeng.container.slot.SlotFake; -import appeng.container.slot.SlotFakeCraftingMatrix; -import appeng.container.slot.SlotPatternOutputs; import appeng.container.slot.SlotPatternTerm; import appeng.container.slot.SlotRestrictedInput; import appeng.core.sync.packets.PacketPatternSlot; import appeng.helpers.IContainerCraftingPacket; +import appeng.items.contents.WirelessPatternTerminalGuiObject; import appeng.items.storage.ItemViewCell; -import appeng.parts.reporting.PartPatternTerminal; import appeng.tile.inventory.AppEngInternalInventory; import appeng.tile.inventory.IAEAppEngInventory; +import appeng.tile.inventory.IAEStackInventory; import appeng.tile.inventory.InvOperation; import appeng.util.InventoryAdaptor; import appeng.util.Platform; import appeng.util.inv.AdaptorPlayerHand; import appeng.util.item.AEItemStack; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; -public class ContainerPatternTerm extends ContainerMEMonitorable - implements IAEAppEngInventory, IOptionalSlotHost, IContainerCraftingPacket { +public class ContainerPatternTerm extends ContainerMEMonitorable implements IAEAppEngInventory, IOptionalSlotHost, + IContainerCraftingPacket, IVirtualSlotHolder, IVirtualSlotSource { public static final int MULTIPLE_OF_BUTTON_CLICK = 2; public static final int MULTIPLE_OF_BUTTON_CLICK_ON_SHIFT = 8; - private final PartPatternTerminal patternTerminal; + protected final IPatternTerminal patternTerminal; private final AppEngInternalInventory cOut = new AppEngInternalInventory(null, 1); - private final IInventory crafting; - private final SlotFakeCraftingMatrix[] craftingSlots = new SlotFakeCraftingMatrix[9]; - private final OptionalSlotFake[] outputSlots = new OptionalSlotFake[3]; + private final IAEStackInventory inputs; + private final IAEStackInventory outputs; + public final IAEStack[] craftingSlotsClient = new IAEStack[getPatternInputsWidth() * getPatternInputsHeigh() + * getPatternOutputPages()]; + private final IInventory craftingMatrix; + public final IAEStack[] outputSlotsClient = new IAEStack[getPatternOutputsWidth() * getPatternOutputsHeigh() + * getPatternOutputPages()]; + private final SlotPatternTerm craftSlot; private final SlotRestrictedInput patternSlotIN; private final SlotRestrictedInput patternSlotOUT; + private final boolean craftingModeSupport; + + boolean isFirstUpdate = true; @GuiSync(97) public boolean craftingMode = true; @@ -86,45 +94,49 @@ public class ContainerPatternTerm extends ContainerMEMonitorable public boolean beSubstitute = true; public ContainerPatternTerm(final InventoryPlayer ip, final ITerminalHost monitorable) { + this(ip, monitorable, true); + } + + public ContainerPatternTerm(final InventoryPlayer ip, final ITerminalHost monitorable, + boolean craftingModeSupport) { super(ip, monitorable, false); - this.patternTerminal = (PartPatternTerminal) monitorable; + this.patternTerminal = (IPatternTerminal) monitorable; - final IInventory patternInv = this.getPatternTerminal().getInventoryByName("pattern"); - final IInventory output = this.getPatternTerminal().getInventoryByName("output"); - - this.crafting = this.getPatternTerminal().getInventoryByName("crafting"); - - for (int y = 0; y < 3; y++) { - for (int x = 0; x < 3; x++) { - this.addSlotToContainer( - this.craftingSlots[x + y * 3] = new SlotFakeCraftingMatrix( - this.crafting, - x + y * 3, - 18 + x * 18, - -76 + y * 18)); - } + if (monitorable instanceof WirelessPatternTerminalGuiObject wptgo) { + wptgo.setInventorySize( + getPatternInputsWidth() * getPatternInputsHeigh() * getPatternInputPages(), + getPatternOutputsWidth() * getPatternOutputsHeigh() * getPatternOutputPages()); + wptgo.readInventory(); } - this.addSlotToContainer( - this.craftSlot = new SlotPatternTerm( - ip.player, - this.getActionSource(), - this.getPowerSource(), - monitorable, - this.crafting, - patternInv, - this.cOut, - 110, - -76 + 18, - this, - 2, - this)); - this.craftSlot.setIIcon(-1); + this.craftingModeSupport = craftingModeSupport; - for (int y = 0; y < 3; y++) { + final IInventory patternInv = this.getPatternTerminal() + .getInventoryByName(StorageName.CRAFTING_PATTERN.getName()); + + this.inputs = this.getPatternTerminal().getAEInventoryByName(StorageName.CRAFTING_INPUT); + this.outputs = this.getPatternTerminal().getAEInventoryByName(StorageName.CRAFTING_OUTPUT); + + if (craftingModeSupport) { + this.craftingMatrix = new AppEngInternalInventory(null, 9); this.addSlotToContainer( - this.outputSlots[y] = new SlotPatternOutputs(output, this, y, 110, -76 + y * 18, 0, 0, 1)); - this.outputSlots[y].setRenderDisabled(false); + this.craftSlot = new SlotPatternTerm( + ip.player, + this.getActionSource(), + this.getPowerSource(), + monitorable, + this.craftingMatrix, + patternInv, + this.cOut, + 110, + -76 + 18, + this, + 2, + this)); + this.craftSlot.setIIcon(-1); + } else { + this.craftingMatrix = null; + this.craftSlot = null; } this.addSlotToContainer( @@ -146,27 +158,40 @@ public class ContainerPatternTerm extends ContainerMEMonitorable this.patternSlotOUT.setStackLimit(1); - this.bindPlayerInventory(ip, 0, 0); this.updateOrderOfOutputSlots(); - if (getPatternTerminal().hasRefillerUpgrade()) refillBlankPatterns(patternSlotIN); + refillBlankPatterns(patternSlotIN); + + // need because InventoryBogoSorter looking for specific slot number for bind buttons + // bindPlayerInventory in MEMonitorable break it + this.bindPlayerInventory(ip, 0, 0); } private void updateOrderOfOutputSlots() { - if (!this.isCraftingMode()) { - this.craftSlot.xDisplayPosition = -9000; - - for (int y = 0; y < 3; y++) { - this.outputSlots[y].xDisplayPosition = this.outputSlots[y].getX(); - } - } else { - this.craftSlot.xDisplayPosition = this.craftSlot.getX(); - - for (int y = 0; y < 3; y++) { - this.outputSlots[y].xDisplayPosition = -9000; + if (craftingModeSupport) { + if (!this.isCraftingMode()) { + this.craftSlot.xDisplayPosition = -9000; + } else { + this.craftSlot.xDisplayPosition = this.craftSlot.getX(); } } } + private void copyToMatrix() { + for (int i = 0; i < this.craftingMatrix.getSizeInventory(); i++) { + IAEStack aes = this.inputs.getAEStackInSlot(i); + if (aes instanceof IAEItemStack ais) { + ais.setStackSize(1); + ItemStack is = ais.getItemStack(); + this.craftingMatrix.setInventorySlotContents(i, is); + } else { + this.inputs.putAEStackInSlot(i, null); + this.craftingMatrix.setInventorySlotContents(i, null); + } + } + this.getAndUpdateOutput(); + this.updateVirtualSlots(StorageName.CRAFTING_INPUT, this.inputs, craftingSlotsClient); + } + @Override public void putStackInSlot(final int par1, final ItemStack par2ItemStack) { super.putStackInSlot(par1, par2ItemStack); @@ -179,15 +204,21 @@ public class ContainerPatternTerm extends ContainerMEMonitorable this.getAndUpdateOutput(); } + @Override + public void onCraftMatrixChanged(IInventory p_75130_1_) {} + private ItemStack getAndUpdateOutput() { + if (!craftingModeSupport || !isCraftingMode() || !isServer()) return null; final InventoryCrafting ic = new InventoryCrafting(this, 3, 3); for (int x = 0; x < ic.getSizeInventory(); x++) { - ic.setInventorySlotContents(x, this.crafting.getStackInSlot(x)); + ic.setInventorySlotContents(x, this.craftingMatrix.getStackInSlot(x)); } final ItemStack is = CraftingManager.getInstance().findMatchingRecipe(ic, this.getPlayerInv().player.worldObj); this.cOut.setInventorySlotContents(0, is); + super.detectAndSendChanges(); + return is; } @@ -211,15 +242,15 @@ public class ContainerPatternTerm extends ContainerMEMonitorable getPlayerInv().player.entityDropItem(output, 0); } this.patternSlotOUT.putStack(null); - if (getPatternTerminal().hasRefillerUpgrade()) refillBlankPatterns(patternSlotIN); + refillBlankPatterns(patternSlotIN); } } public void encode() { ItemStack output = this.patternSlotOUT.getStack(); - final ItemStack[] in = this.getInputs(); - final ItemStack[] out = this.getOutputs(); + final IAEStack[] in = this.getInputs(); + final IAEStack[] out = this.getOutputs(); // if there is no input, this would be silly. if (in == null || out == null) { @@ -227,36 +258,33 @@ public class ContainerPatternTerm extends ContainerMEMonitorable } // first check the output slots, should either be null, or a pattern - if (output != null && !this.isPattern(output)) { - return; + if (output != null) { + if (!this.isEncodedPattern(output) && !this.isUltimatePattern(output)) { + return; + } } // if nothing is there we should snag a new pattern. - else if (output == null) { - output = this.patternSlotIN.getStack(); - if (!this.isPattern(output)) { - return; // no blanks. + else { + ItemStack blank = this.patternSlotIN.getStack(); + if (!this.isBlankPattern(blank)) { + return; } // remove one, and clear the input slot. - output.stackSize--; - if (output.stackSize == 0) { + blank.stackSize--; + if (blank.stackSize == 0) { this.patternSlotIN.putStack(null); } + refillBlankPatterns(patternSlotIN); + // add a new encoded pattern. if (isCraftingMode()) { - for (final ItemStack encodedPatternStack : AEApi.instance().definitions().items().encodedPattern() - .maybeStack(1).asSet()) { - output = encodedPatternStack; - this.patternSlotOUT.putStack(output); - } + output = AEApi.instance().definitions().items().encodedPattern().maybeStack(1).orNull(); + this.patternSlotOUT.putStack(output); } else { - for (final ItemStack encodedPatternStack : AEApi.instance().definitions().items() - .encodedUltimatePattern().maybeStack(1).asSet()) { - output = encodedPatternStack; - this.patternSlotOUT.putStack(output); - } + output = AEApi.instance().definitions().items().encodedUltimatePattern().maybeStack(1).orNull(); + this.patternSlotOUT.putStack(output); } - if (getPatternTerminal().hasRefillerUpgrade()) refillBlankPatterns(patternSlotIN); } // encode the slot. @@ -265,14 +293,12 @@ public class ContainerPatternTerm extends ContainerMEMonitorable final NBTTagList tagIn = new NBTTagList(); final NBTTagList tagOut = new NBTTagList(); - for (final ItemStack i : in) { - if (isCraftingMode()) tagIn.appendTag(this.createItemTag(i)); - else tagIn.appendTag(writeStackNBT(AEItemStack.create(i), new NBTTagCompound(), true)); + for (final IAEStack i : in) { + tagIn.appendTag(writeStackNBT(i, new NBTTagCompound(), true)); } - for (final ItemStack i : out) { - if (isCraftingMode()) tagOut.appendTag(this.createItemTag(i)); - else tagOut.appendTag(writeStackNBT(AEItemStack.create(i), new NBTTagCompound(), true)); + for (final IAEStack i : out) { + tagOut.appendTag(writeStackNBT(i, new NBTTagCompound(), true)); } encodedValue.setTag("in", tagIn); @@ -285,13 +311,13 @@ public class ContainerPatternTerm extends ContainerMEMonitorable output.setTagCompound(encodedValue); } - private ItemStack[] getInputs() { - final ItemStack[] input = new ItemStack[9]; + private IAEStack[] getInputs() { + final IAEStack[] input = new IAEStack[this.inputs.getSizeInventory()]; boolean hasValue = false; - for (int x = 0; x < this.craftingSlots.length; x++) { - input[x] = this.craftingSlots[x].getStack(); - if (input[x] != null) { + for (int i = 0; i < this.inputs.getSizeInventory(); i++) { + input[i] = this.inputs.getAEStackInSlot(i); + if (input[i] != null) { hasValue = true; } } @@ -303,65 +329,52 @@ public class ContainerPatternTerm extends ContainerMEMonitorable return null; } - private ItemStack[] getOutputs() { + private IAEStack[] getOutputs() { if (this.isCraftingMode()) { - final ItemStack out = this.getAndUpdateOutput(); + final IAEStack out = AEItemStack.create(this.getAndUpdateOutput()); - if (out != null && out.stackSize > 0) { - return new ItemStack[] { out }; + if (out != null && out.getStackSize() > 0) { + return new IAEStack[] { out }; } } else { - final List list = new ArrayList<>(3); + final List> list = new ArrayList<>(3); boolean hasValue = false; - for (final OptionalSlotFake outputSlot : this.outputSlots) { - final ItemStack out = outputSlot.getStack(); + for (int i = 0; i < this.outputs.getSizeInventory(); i++) { + final IAEStack out = this.outputs.getAEStackInSlot(i); - if (out != null && out.stackSize > 0) { + if (out != null && out.getStackSize() > 0) { list.add(out); hasValue = true; } } if (hasValue) { - return list.toArray(new ItemStack[0]); + return list.toArray(new IAEStack[0]); } } return null; } - private boolean isPattern(final ItemStack output) { - if (output == null) { - return false; - } - - final IDefinitions definitions = AEApi.instance().definitions(); - - boolean isPattern = definitions.items().encodedPattern().isSameAs(output); - boolean isUltimatePattern = definitions.items().encodedUltimatePattern().isSameAs(output); - isPattern |= definitions.materials().blankPattern().isSameAs(output); - - return isPattern || isUltimatePattern; + private boolean isBlankPattern(final ItemStack stack) { + return stack != null && AEApi.instance().definitions().materials().blankPattern().isSameAs(stack); } - private NBTBase createItemTag(final ItemStack i) { - final NBTTagCompound c = new NBTTagCompound(); + private boolean isEncodedPattern(final ItemStack stack) { + return stack != null && AEApi.instance().definitions().items().encodedPattern().isSameAs(stack); + } - if (i != null) { - i.writeToNBT(c); - c.setInteger("Count", i.stackSize); - } - - return c; + private boolean isUltimatePattern(final ItemStack stack) { + return stack != null && AEApi.instance().definitions().items().encodedUltimatePattern().isSameAs(stack); } @Override public boolean isSlotEnabled(final int idx) { if (idx == 1) { - return Platform.isServer() ? !this.getPatternTerminal().isCraftingRecipe() : !this.isCraftingMode(); + return isServer() ? !this.getPatternTerminal().isCraftingRecipe() : !this.isCraftingMode(); } else if (idx == 2) { - return Platform.isServer() ? this.getPatternTerminal().isCraftingRecipe() : this.isCraftingMode(); + return isServer() ? this.getPatternTerminal().isCraftingRecipe() : this.isCraftingMode(); } else { return false; } @@ -470,14 +483,23 @@ public class ContainerPatternTerm extends ContainerMEMonitorable @Override public void detectAndSendChanges() { super.detectAndSendChanges(); - if (Platform.isServer()) { + if (isServer()) { if (this.isCraftingMode() != this.getPatternTerminal().isCraftingRecipe()) { this.setCraftingMode(this.getPatternTerminal().isCraftingRecipe()); - this.updateOrderOfOutputSlots(); } this.substitute = this.patternTerminal.isSubstitution(); this.beSubstitute = this.patternTerminal.canBeSubstitution(); + + if (this.isFirstUpdate) { + if (isCraftingMode()) { + this.copyToMatrix(); + } else { + this.updateVirtualSlots(StorageName.CRAFTING_INPUT, this.inputs, craftingSlotsClient); + } + this.updateVirtualSlots(StorageName.CRAFTING_OUTPUT, this.outputs, outputSlotsClient); + this.isFirstUpdate = false; + } } } @@ -493,19 +515,9 @@ public class ContainerPatternTerm extends ContainerMEMonitorable @Override public void onSlotChange(final Slot s) { - if (!Platform.isServer()) return; + if (!isServer()) return; if (s == this.patternSlotOUT) { - for (final Object crafter : this.crafters) { - final ICrafting icrafting = (ICrafting) crafter; - - for (final Object g : this.inventorySlots) { - if (g instanceof OptionalSlotFake || g instanceof SlotFakeCraftingMatrix) { - final Slot sri = (Slot) g; - icrafting.sendSlotContents(this, sri.slotNumber, sri.getStack()); - } - } - ((EntityPlayerMP) icrafting).isChangingQuantityOnly = false; - } + this.isFirstUpdate = true; this.detectAndSendChanges(); } else if (s == patternRefiller && patternRefiller.getStack() != null) { refillBlankPatterns(patternSlotIN); @@ -514,16 +526,41 @@ public class ContainerPatternTerm extends ContainerMEMonitorable } public void clear() { - for (final Slot s : this.craftingSlots) { - s.putStack(null); + for (int i = 0; i < this.inputs.getSizeInventory(); ++i) { + this.inputs.putAEStackInSlot(i, null); + } + for (int i = 0; i < this.outputs.getSizeInventory(); ++i) { + this.outputs.putAEStackInSlot(i, null); + } + if (this.craftingMatrix != null) { + for (int i = 0; i < this.craftingMatrix.getSizeInventory(); ++i) { + this.craftingMatrix.setInventorySlotContents(i, null); + } } - for (final Slot s : this.outputSlots) { - s.putStack(null); - } - - this.detectAndSendChanges(); this.getAndUpdateOutput(); + this.updateVirtualSlots(StorageName.CRAFTING_INPUT, this.inputs, craftingSlotsClient); + this.updateVirtualSlots(StorageName.CRAFTING_OUTPUT, this.outputs, outputSlotsClient); + } + + protected void refillBlankPatterns(Slot slot) { + if (Platform.isServer()) { + ItemStack blanks = slot.getStack(); + int blanksToRefill = 64; + if (blanks != null) blanksToRefill -= blanks.stackSize; + if (blanksToRefill <= 0) return; + final AEItemStack request = AEItemStack + .create(AEApi.instance().definitions().materials().blankPattern().maybeStack(blanksToRefill).get()); + final IAEItemStack extracted = Platform + .poweredExtraction(this.getPowerSource(), this.getCellInventory(), request, this.getActionSource()); + if (extracted != null) { + if (blanks != null) blanks.stackSize += (int) extracted.getStackSize(); + else { + blanks = extracted.getItemStack(); + } + slot.putStack(blanks); + } + } } @Override @@ -550,11 +587,14 @@ public class ContainerPatternTerm extends ContainerMEMonitorable return this.craftingMode; } - private void setCraftingMode(final boolean craftingMode) { + public void setCraftingMode(final boolean craftingMode) { this.craftingMode = craftingMode; + this.patternTerminal.setCraftingRecipe(craftingMode); + if (craftingMode && craftingModeSupport) copyToMatrix(); + this.updateOrderOfOutputSlots(); } - public PartPatternTerminal getPatternTerminal() { + public IPatternTerminal getPatternTerminal() { return this.patternTerminal; } @@ -580,45 +620,49 @@ public class ContainerPatternTerm extends ContainerMEMonitorable * ((val & 2) != 0 ? -1 : 1)); } - static boolean canMultiplyOrDivide(SlotFake[] slots, int mult) { + static boolean canMultiplyOrDivide(IAEStackInventory inventory, int mult) { if (mult > 0) { - for (Slot s : slots) { - if (s.getStack() != null) { - long val = (long) s.getStack().stackSize * mult; - if (val > Integer.MAX_VALUE) return false; + for (int i = 0; i < inventory.getSizeInventory(); i++) { + IAEStack aes = inventory.getAEStackInSlot(i); + if (aes != null) { + double val = (double) aes.getStackSize() * mult; + if (val > Long.MAX_VALUE) return false; } } + return true; } else if (mult < 0) { mult = -mult; - for (Slot s : slots) { - if (s.getStack() != null) { // Although % is a very inefficient algorithm, it is not a performance issue - // here. :> - if (s.getStack().stackSize % mult != 0) return false; + for (int i = 0; i < inventory.getSizeInventory(); i++) { + IAEStack aes = inventory.getAEStackInSlot(i); + if (aes != null) { // Although % is a very inefficient algorithm, it is not a performance + // issue + // here. :> + if (aes.getStackSize() % mult != 0) return false; } } + return true; } return false; } - static void multiplyOrDivideStacksInternal(SlotFake[] slots, int mult) { - List enabledSlots = Arrays.stream(slots).filter(SlotFake::isEnabled).collect(Collectors.toList()); + static void multiplyOrDivideStacksInternal(IAEStackInventory inventory, int mult) { if (mult > 0) { - for (final Slot s : enabledSlots) { - ItemStack st = s.getStack(); + for (int i = 0; i < inventory.getSizeInventory(); i++) { + IAEStack st = inventory.getAEStackInSlot(i); if (st != null) { - st.stackSize *= mult; - s.putStack(st); + st.setStackSize(st.getStackSize() * mult); + inventory.putAEStackInSlot(i, st); } } } else if (mult < 0) { mult = -mult; - for (final Slot s : enabledSlots) { - ItemStack st = s.getStack(); + for (int i = 0; i < inventory.getSizeInventory(); i++) { + IAEStack st = inventory.getAEStackInSlot(i); if (st != null) { - st.stackSize /= mult; - s.putStack(st); + st.setStackSize(st.getStackSize() / mult); + inventory.putAEStackInSlot(i, st); } } } @@ -626,20 +670,114 @@ public class ContainerPatternTerm extends ContainerMEMonitorable /** * Multiply or divide a number - * + * * @param multi Positive numbers are multiplied and negative numbers are divided */ public void multiplyOrDivideStacks(int multi) { if (!isCraftingMode()) { - if (canMultiplyOrDivide(this.craftingSlots, multi) && canMultiplyOrDivide(this.outputSlots, multi)) { - multiplyOrDivideStacksInternal(this.craftingSlots, multi); - multiplyOrDivideStacksInternal(this.outputSlots, multi); + if (canMultiplyOrDivide(this.inputs, multi) && canMultiplyOrDivide(this.outputs, multi)) { + multiplyOrDivideStacksInternal(this.inputs, multi); + multiplyOrDivideStacksInternal(this.outputs, multi); + + this.updateVirtualSlots(StorageName.CRAFTING_INPUT, this.inputs, craftingSlotsClient); + this.updateVirtualSlots(StorageName.CRAFTING_OUTPUT, this.outputs, outputSlotsClient); } - this.detectAndSendChanges(); } } public boolean isAPatternTerminal() { return true; } + + public boolean getCraftingModeSupport() { + return craftingModeSupport; + } + + public int getPatternInputsWidth() { + return patternInputsWidth; + } + + public int getPatternInputsHeigh() { + return patternInputsHeigh; + } + + public int getPatternInputPages() { + return patternInputsPages; + } + + public int getPatternOutputsWidth() { + return patternOutputsWidth; + } + + public int getPatternOutputsHeigh() { + return patternOutputsHeigh; + } + + public int getPatternOutputPages() { + return patternOutputPages; + } + + @Override + public void updateVirtualSlot(StorageName invName, int slotId, IAEStack aes) { + switch (invName) { + case CRAFTING_INPUT -> { + if (isCraftingMode() && aes != null) { + aes.setStackSize(1); + } + this.inputs.putAEStackInSlot(slotId, aes); + if (isServer()) { + this.updateVirtualSlots(StorageName.CRAFTING_INPUT, this.inputs, craftingSlotsClient); + if (isCraftingMode()) { + if (aes != null) { + IAEItemStack ais = ((IAEItemStack) aes); + this.craftingMatrix.setInventorySlotContents(slotId, ais.getItemStack()); + } else { + this.craftingMatrix.setInventorySlotContents(slotId, null); + } + this.getAndUpdateOutput(); + } + } + } + case CRAFTING_OUTPUT -> { + this.outputs.putAEStackInSlot(slotId, aes); + if (isServer()) { + this.updateVirtualSlots(StorageName.CRAFTING_OUTPUT, this.outputs, outputSlotsClient); + } + } + } + } + + @Override + public void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks) { + switch (invName) { + case CRAFTING_INPUT -> { + for (var entry : slotStacks.int2ObjectEntrySet()) { + IAEStack aes = entry.getValue(); + if (isServer() && isCraftingMode() && aes != null) { + aes.setStackSize(1); + } + this.inputs.putAEStackInSlot(entry.getIntKey(), aes); + if (isServer() && isCraftingMode()) { + this.craftingMatrix.setInventorySlotContents( + entry.getIntKey(), + aes != null ? ((IAEItemStack) aes).getItemStack() : null); + } + } + if (isServer()) { + this.updateVirtualSlots(StorageName.CRAFTING_INPUT, this.inputs, craftingSlotsClient); + if (isCraftingMode()) { + this.getAndUpdateOutput(); + } + } + } + case CRAFTING_OUTPUT -> { + for (var entry : slotStacks.int2ObjectEntrySet()) { + this.outputs.putAEStackInSlot(entry.getIntKey(), entry.getValue()); + } + if (isServer()) { + this.updateVirtualSlots(StorageName.CRAFTING_OUTPUT, this.outputs, outputSlotsClient); + } + } + } + } } diff --git a/src/main/java/appeng/container/implementations/ContainerPatternTermEx.java b/src/main/java/appeng/container/implementations/ContainerPatternTermEx.java index 96f326aaa..71ae65267 100644 --- a/src/main/java/appeng/container/implementations/ContainerPatternTermEx.java +++ b/src/main/java/appeng/container/implementations/ContainerPatternTermEx.java @@ -1,78 +1,15 @@ package appeng.container.implementations; -import static appeng.container.implementations.ContainerPatternTerm.MULTIPLE_OF_BUTTON_CLICK; -import static appeng.container.implementations.ContainerPatternTerm.MULTIPLE_OF_BUTTON_CLICK_ON_SHIFT; -import static appeng.container.implementations.ContainerPatternTerm.canMultiplyOrDivide; -import static appeng.container.implementations.ContainerPatternTerm.multiplyOrDivideStacksInternal; -import static appeng.util.Platform.writeStackNBT; +import static appeng.parts.reporting.PartPatternTerminalEx.*; -import java.util.ArrayList; -import java.util.List; - -import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.ICrafting; -import net.minecraft.inventory.IInventory; -import net.minecraft.inventory.Slot; -import net.minecraft.item.ItemStack; -import net.minecraft.nbt.NBTBase; -import net.minecraft.nbt.NBTTagCompound; -import net.minecraft.nbt.NBTTagList; -import appeng.api.AEApi; -import appeng.api.definitions.IDefinitions; +import appeng.api.parts.IPatternTerminalEx; import appeng.api.storage.ITerminalHost; import appeng.container.guisync.GuiSync; -import appeng.container.slot.IOptionalSlotHost; -import appeng.container.slot.OptionalSlotFake; -import appeng.container.slot.SlotFakeCraftingMatrix; -import appeng.container.slot.SlotRestrictedInput; -import appeng.helpers.IContainerCraftingPacket; -import appeng.parts.reporting.PartPatternTerminalEx; import appeng.util.Platform; -import appeng.util.item.AEItemStack; -public class ContainerPatternTermEx extends ContainerMEMonitorable - implements IOptionalSlotHost, IContainerCraftingPacket { - - private static final int CRAFTING_GRID_PAGES = 2; - private static final int CRAFTING_GRID_WIDTH = 4; - private static final int CRAFTING_GRID_HEIGHT = 4; - private static final int CRAFTING_GRID_SLOTS = CRAFTING_GRID_WIDTH * CRAFTING_GRID_HEIGHT; - - private static class ProcessingSlotFake extends OptionalSlotFake { - - private static final int POSITION_SHIFT = 9000; - private boolean hidden = false; - - public ProcessingSlotFake(IInventory inv, IOptionalSlotHost containerBus, int idx, int x, int y, int offX, - int offY, int groupNum) { - super(inv, containerBus, idx, x, y, offX, offY, groupNum); - this.setRenderDisabled(false); - } - - public void setHidden(boolean hide) { - if (this.hidden != hide) { - this.hidden = hide; - this.xDisplayPosition += (hide ? -1 : 1) * POSITION_SHIFT; - } - } - } - - private final PartPatternTerminalEx patternTerminal; - - private final ProcessingSlotFake[] craftingSlots = new ProcessingSlotFake[CRAFTING_GRID_SLOTS - * CRAFTING_GRID_PAGES]; - private final ProcessingSlotFake[] outputSlots = new ProcessingSlotFake[CRAFTING_GRID_SLOTS * CRAFTING_GRID_PAGES]; - - private final SlotRestrictedInput patternSlotIN; - private final SlotRestrictedInput patternSlotOUT; - - @GuiSync(96 + (17 - 9) + 12) - public boolean substitute = false; - - @GuiSync(96 + (17 - 9) + 13) - public boolean beSubstitute = false; +public class ContainerPatternTermEx extends ContainerPatternTerm { @GuiSync(96 + (17 - 9) + 16) public boolean inverted; @@ -82,218 +19,7 @@ public class ContainerPatternTermEx extends ContainerMEMonitorable public ContainerPatternTermEx(final InventoryPlayer ip, final ITerminalHost monitorable) { super(ip, monitorable, false); - this.patternTerminal = (PartPatternTerminalEx) monitorable; - inverted = patternTerminal.isInverted(); - final IInventory patternInv = this.getPatternTerminal().getInventoryByName("pattern"); - final IInventory output = this.getPatternTerminal().getInventoryByName("output"); - final IInventory crafting = this.getPatternTerminal().getInventoryByName("crafting"); - - for (int page = 0; page < CRAFTING_GRID_PAGES; page++) { - for (int y = 0; y < CRAFTING_GRID_HEIGHT; y++) { - for (int x = 0; x < CRAFTING_GRID_WIDTH; x++) { - this.addSlotToContainer( - this.craftingSlots[x + y * CRAFTING_GRID_WIDTH - + page * CRAFTING_GRID_SLOTS] = new ProcessingSlotFake( - crafting, - this, - x + y * CRAFTING_GRID_WIDTH + page * CRAFTING_GRID_SLOTS, - 15, - -83, - x, - y, - x + 4)); - } - } - - for (int x = 0; x < CRAFTING_GRID_WIDTH; x++) { - for (int y = 0; y < CRAFTING_GRID_HEIGHT; y++) { - this.addSlotToContainer( - this.outputSlots[x * CRAFTING_GRID_HEIGHT + y - + page * CRAFTING_GRID_SLOTS] = new ProcessingSlotFake( - output, - this, - x * CRAFTING_GRID_HEIGHT + y + page * CRAFTING_GRID_SLOTS, - 112, - -83, - -x, - y, - x)); - } - } - } - - this.addSlotToContainer( - this.patternSlotIN = new SlotRestrictedInput( - SlotRestrictedInput.PlacableItemType.BLANK_PATTERN, - patternInv, - 0, - 147, - -72 - 9, - this.getInventoryPlayer())); - this.addSlotToContainer( - this.patternSlotOUT = new SlotRestrictedInput( - SlotRestrictedInput.PlacableItemType.ENCODED_PATTERN, - patternInv, - 1, - 147, - -72 + 34, - this.getInventoryPlayer())); - - this.patternSlotOUT.setStackLimit(1); - - this.bindPlayerInventory(ip, 0, 0); - if (getPatternTerminal().hasRefillerUpgrade()) refillBlankPatterns(patternSlotIN); - } - - public void encodeAndMoveToInventory(boolean encodeWholeStack) { - encode(); - ItemStack output = this.patternSlotOUT.getStack(); - if (output != null) { - if (encodeWholeStack) { - ItemStack blanks = this.patternSlotIN.getStack(); - this.patternSlotIN.putStack(null); - if (blanks != null) output.stackSize += blanks.stackSize; - } - if (!getPlayerInv().addItemStackToInventory(output)) { - getPlayerInv().player.entityDropItem(output, 0); - } - this.patternSlotOUT.putStack(null); - if (getPatternTerminal().hasRefillerUpgrade()) refillBlankPatterns(patternSlotIN); - } - } - - public void encode() { - ItemStack output = this.patternSlotOUT.getStack(); - - final ItemStack[] in = this.getInputs(); - final ItemStack[] out = this.getOutputs(); - - // if there is no input, this would be silly. - if (in == null || out == null) { - return; - } - - // first check the output slots, should either be null, or a pattern - if (output != null && this.isNotPattern(output)) { - return; - } // if nothing is there we should snag a new pattern. - else if (output == null) { - output = this.patternSlotIN.getStack(); - if (this.isNotPattern(output)) { - return; // no blanks. - } - - // remove one, and clear the input slot. - output.stackSize--; - if (output.stackSize == 0) { - this.patternSlotIN.putStack(null); - } - - // add a new encoded pattern. - for (final ItemStack encodedPatternStack : AEApi.instance().definitions().items().encodedUltimatePattern() - .maybeStack(1).asSet()) { - output = encodedPatternStack; - this.patternSlotOUT.putStack(output); - } - if (getPatternTerminal().hasRefillerUpgrade()) refillBlankPatterns(patternSlotIN); - } - - // encode the slot. - final NBTTagCompound encodedValue = new NBTTagCompound(); - - final NBTTagList tagIn = new NBTTagList(); - final NBTTagList tagOut = new NBTTagList(); - - for (final ItemStack i : in) { - tagIn.appendTag(writeStackNBT(AEItemStack.create(i), new NBTTagCompound(), true)); - } - - for (final ItemStack i : out) { - tagOut.appendTag(writeStackNBT(AEItemStack.create(i), new NBTTagCompound(), true)); - } - - encodedValue.setTag("in", tagIn); - encodedValue.setTag("out", tagOut); - encodedValue.setBoolean("crafting", false); - encodedValue.setBoolean("substitute", this.isSubstitute()); - encodedValue.setBoolean("beSubstitute", this.canBeSubstitute()); - encodedValue.setString("author", this.getPlayerInv().player.getCommandSenderName()); - - output.setTagCompound(encodedValue); - } - - private ItemStack[] getInputs() { - final ItemStack[] input = new ItemStack[CRAFTING_GRID_SLOTS * CRAFTING_GRID_PAGES]; - boolean hasValue = false; - - for (int x = 0; x < this.craftingSlots.length; x++) { - input[x] = this.craftingSlots[x].getStack(); - if (input[x] != null) { - hasValue = true; - } - } - - if (hasValue) { - return input; - } - - return null; - } - - private ItemStack[] getOutputs() { - final List list = new ArrayList<>(CRAFTING_GRID_SLOTS * CRAFTING_GRID_PAGES); - boolean hasValue = false; - - for (final OptionalSlotFake outputSlot : this.outputSlots) { - final ItemStack out = outputSlot.getStack(); - - if (out != null && out.stackSize > 0) { - list.add(out); - hasValue = true; - } - } - - if (hasValue) { - return list.toArray(new ItemStack[0]); - } - - return null; - } - - private boolean isNotPattern(final ItemStack output) { - if (output == null) { - return true; - } - - final IDefinitions definitions = AEApi.instance().definitions(); - - boolean isPattern = definitions.items().encodedPattern().isSameAs(output); - boolean isUltimatePattern = definitions.items().encodedUltimatePattern().isSameAs(output); - isPattern |= definitions.materials().blankPattern().isSameAs(output); - - return !isPattern && !isUltimatePattern; - } - - private NBTBase createItemTag(final ItemStack i) { - final NBTTagCompound c = new NBTTagCompound(); - - if (i != null) { - i.writeToNBT(c); - c.setInteger("Count", i.stackSize); - } - - return c; - } - - @Override - public boolean isSlotEnabled(final int idx) { - - if (idx < 4) // outputs - { - return inverted || idx == 0; - } else { - return !inverted || idx == 4; - } + inverted = getExPatternTerminal().isInverted(); } @Override @@ -301,133 +27,45 @@ public class ContainerPatternTermEx extends ContainerMEMonitorable super.detectAndSendChanges(); if (Platform.isServer()) { - substitute = patternTerminal.isSubstitution(); - beSubstitute = patternTerminal.canBeSubstitution(); - - if (inverted != patternTerminal.isInverted() || activePage != patternTerminal.getActivePage()) { - inverted = patternTerminal.isInverted(); - activePage = patternTerminal.getActivePage(); - offsetSlots(); - } + final IPatternTerminalEx temp = getExPatternTerminal(); + substitute = temp.isSubstitution(); + beSubstitute = temp.canBeSubstitution(); + inverted = temp.isInverted(); + activePage = temp.getActivePage(); } } - private void offsetSlots() { - - for (int page = 0; page < CRAFTING_GRID_PAGES; page++) { - for (int y = 0; y < CRAFTING_GRID_HEIGHT; y++) { - for (int x = 0; x < CRAFTING_GRID_WIDTH; x++) { - this.craftingSlots[x + y * CRAFTING_GRID_WIDTH + page * CRAFTING_GRID_SLOTS] - .setHidden(page != activePage || x > 0 && inverted); - this.outputSlots[x * CRAFTING_GRID_HEIGHT + y + page * CRAFTING_GRID_SLOTS] - .setHidden(page != activePage || x > 0 && !inverted); - } - } - } + public IPatternTerminalEx getExPatternTerminal() { + return (IPatternTerminalEx) getPatternTerminal(); } @Override - public void onUpdate(final String field, final Object oldValue, final Object newValue) { - super.onUpdate(field, oldValue, newValue); - - if (field.equals("inverted") || field.equals("activePage")) { - offsetSlots(); - } + public int getPatternInputsWidth() { + return exPatternInputsWidth; } @Override - public void onSlotChange(final Slot s) { - if (!Platform.isServer()) return; - if (s == this.patternSlotOUT) { - inverted = patternTerminal.isInverted(); - - for (final Object crafter : this.crafters) { - final ICrafting icrafting = (ICrafting) crafter; - - for (final Object g : this.inventorySlots) { - if (g instanceof OptionalSlotFake || g instanceof SlotFakeCraftingMatrix) { - final Slot sri = (Slot) g; - icrafting.sendSlotContents(this, sri.slotNumber, sri.getStack()); - } - } - ((EntityPlayerMP) icrafting).isChangingQuantityOnly = false; - } - - this.detectAndSendChanges(); - } else if (s == patternRefiller && patternRefiller.getStack() != null) { - refillBlankPatterns(patternSlotIN); - detectAndSendChanges(); - } - } - - public void clear() { - for (final Slot s : this.craftingSlots) { - s.putStack(null); - } - - for (final Slot s : this.outputSlots) { - s.putStack(null); - } - - this.detectAndSendChanges(); + public int getPatternInputsHeigh() { + return exPatternInputsHeigh; } @Override - public IInventory getInventoryByName(final String name) { - if (name.equals("player")) { - return this.getInventoryPlayer(); - } - return this.getPatternTerminal().getInventoryByName(name); + public int getPatternInputPages() { + return exPatternInputsPages; } @Override - public boolean useRealItems() { - return false; + public int getPatternOutputsWidth() { + return exPatternOutputsWidth; } - public PartPatternTerminalEx getPatternTerminal() { - return this.patternTerminal; + @Override + public int getPatternOutputsHeigh() { + return exPatternOutputsHeigh; } - private boolean isSubstitute() { - return this.substitute; - } - - private boolean canBeSubstitute() { - return this.beSubstitute; - } - - public void setSubstitute(final boolean substitute) { - this.substitute = substitute; - } - - public void setCanBeSubstitute(final boolean beSubstitute) { - this.beSubstitute = beSubstitute; - } - - public void setActivePage(final int activePage) { - this.activePage = activePage; - } - - public int getActivePage() { - return this.activePage; - } - - public void doubleStacks(int val) { - multiplyOrDivideStacks( - ((val & 1) != 0 ? MULTIPLE_OF_BUTTON_CLICK_ON_SHIFT : MULTIPLE_OF_BUTTON_CLICK) - * ((val & 2) != 0 ? -1 : 1)); - } - - public void multiplyOrDivideStacks(int multi) { - if (canMultiplyOrDivide(this.craftingSlots, multi) && canMultiplyOrDivide(this.outputSlots, multi)) { - multiplyOrDivideStacksInternal(this.craftingSlots, multi); - multiplyOrDivideStacksInternal(this.outputSlots, multi); - } - this.detectAndSendChanges(); - } - - public boolean isAPatternTerminal() { - return true; + @Override + public int getPatternOutputPages() { + return exPatternOutputPages; } } diff --git a/src/main/java/appeng/container/implementations/ContainerPatternValueAmount.java b/src/main/java/appeng/container/implementations/ContainerPatternValueAmount.java index 3cee46598..b88e757c0 100644 --- a/src/main/java/appeng/container/implementations/ContainerPatternValueAmount.java +++ b/src/main/java/appeng/container/implementations/ContainerPatternValueAmount.java @@ -1,58 +1,64 @@ package appeng.container.implementations; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.Slot; -import net.minecraft.world.World; +import net.minecraft.inventory.ICrafting; -import appeng.api.config.SecurityPermissions; -import appeng.api.networking.IGrid; -import appeng.api.networking.security.BaseActionSource; -import appeng.api.networking.security.IActionHost; -import appeng.api.networking.security.PlayerSource; import appeng.api.storage.ITerminalHost; -import appeng.container.AEBaseContainer; -import appeng.container.slot.SlotInaccessible; -import appeng.tile.inventory.AppEngInternalInventory; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.client.gui.implementations.GuiPatternItemRenamer; +import appeng.client.gui.implementations.GuiPatternValueAmount; +import appeng.container.ContainerSubGui; +import appeng.container.interfaces.IVirtualSlotHolder; +import appeng.core.sync.network.NetworkHandler; +import appeng.core.sync.packets.PacketVirtualSlot; +import appeng.util.Platform; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; -public class ContainerPatternValueAmount extends AEBaseContainer { +public class ContainerPatternValueAmount extends ContainerSubGui implements IVirtualSlotHolder { - private final Slot patternValue; - private int valueIndex; + private StorageName invName; + private IAEStack aes; + private int slotIndex; public ContainerPatternValueAmount(final InventoryPlayer ip, final ITerminalHost te) { super(ip, te); - this.patternValue = new SlotInaccessible(new AppEngInternalInventory(null, 1), 0, 34, 53); - this.addSlotToContainer(patternValue); } @Override - public void detectAndSendChanges() { - super.detectAndSendChanges(); - this.verifyPermissions(SecurityPermissions.CRAFT, false); + public void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks) { + var entry = slotStacks.int2ObjectEntrySet().iterator().next(); + this.invName = invName; + this.aes = entry.getValue(); + this.slotIndex = entry.getIntKey(); + + if (Platform.isServer()) { + for (ICrafting crafter : this.crafters) { + final EntityPlayerMP emp = (EntityPlayerMP) crafter; + NetworkHandler.instance.sendTo(new PacketVirtualSlot(invName, slotIndex, aes), emp); + } + } else { + final GuiScreen gs = Minecraft.getMinecraft().currentScreen; + if (gs instanceof GuiPatternValueAmount gpva) { + gpva.update(); + } else if (gs instanceof GuiPatternItemRenamer gpir) { + gpir.update(); + } + } } - public IGrid getGrid() { - final IActionHost h = ((IActionHost) this.getTarget()); - return h.getActionableNode().getGrid(); + public StorageName getInvName() { + return invName; } - public World getWorld() { - return this.getPlayerInv().player.worldObj; + public IAEStack getAEStack() { + return aes; } - public BaseActionSource getActionSrc() { - return new PlayerSource(this.getPlayerInv().player, (IActionHost) this.getTarget()); - } - - public Slot getPatternValue() { - return patternValue; - } - - public int getValueIndex() { - return valueIndex; - } - - public void setValueIndex(int valueIndex) { - this.valueIndex = valueIndex; + public int getSlotIndex() { + return slotIndex; } } diff --git a/src/main/java/appeng/container/implementations/ContainerPriority.java b/src/main/java/appeng/container/implementations/ContainerPriority.java index 0df94e105..42bb475f9 100644 --- a/src/main/java/appeng/container/implementations/ContainerPriority.java +++ b/src/main/java/appeng/container/implementations/ContainerPriority.java @@ -16,14 +16,14 @@ import net.minecraft.entity.player.InventoryPlayer; import appeng.api.config.SecurityPermissions; import appeng.api.implementations.guiobjects.IGuiItemObject; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.container.guisync.GuiSync; import appeng.helpers.IPriorityHost; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class ContainerPriority extends AEBaseContainer { +public class ContainerPriority extends ContainerSubGui { private final IPriorityHost priHost; diff --git a/src/main/java/appeng/container/implementations/ContainerQNB.java b/src/main/java/appeng/container/implementations/ContainerQNB.java index 55ca2bc91..5f9c0821f 100644 --- a/src/main/java/appeng/container/implementations/ContainerQNB.java +++ b/src/main/java/appeng/container/implementations/ContainerQNB.java @@ -19,7 +19,7 @@ import appeng.tile.qnb.TileQuantumBridge; public class ContainerQNB extends AEBaseContainer { public ContainerQNB(final InventoryPlayer ip, final TileQuantumBridge quantumBridge) { - super(ip, quantumBridge, null); + super(ip, quantumBridge); this.addSlotToContainer( (new SlotRestrictedInput( diff --git a/src/main/java/appeng/container/implementations/ContainerQuartzKnife.java b/src/main/java/appeng/container/implementations/ContainerQuartzKnife.java index 80065467e..cc76f0be2 100644 --- a/src/main/java/appeng/container/implementations/ContainerQuartzKnife.java +++ b/src/main/java/appeng/container/implementations/ContainerQuartzKnife.java @@ -38,7 +38,7 @@ public class ContainerQuartzKnife extends AEBaseContainer implements IAEAppEngIn private String myName = ""; public ContainerQuartzKnife(final InventoryPlayer ip, final QuartzKnifeObj te) { - super(ip, null, null); + super(ip, te); this.toolInv = te; this.metals = new SlotRestrictedInput( diff --git a/src/main/java/appeng/container/implementations/ContainerRenamer.java b/src/main/java/appeng/container/implementations/ContainerRenamer.java index f44e00feb..8386ce1ca 100644 --- a/src/main/java/appeng/container/implementations/ContainerRenamer.java +++ b/src/main/java/appeng/container/implementations/ContainerRenamer.java @@ -1,18 +1,16 @@ package appeng.container.implementations; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.tileentity.TileEntity; import appeng.api.config.SecurityPermissions; -import appeng.api.parts.IPart; import appeng.client.gui.widgets.MEGuiTextField; -import appeng.container.AEBaseContainer; +import appeng.container.ContainerSubGui; import appeng.helpers.ICustomNameObject; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class ContainerRenamer extends AEBaseContainer { +public class ContainerRenamer extends ContainerSubGui { private final ICustomNameObject namedObject; @@ -20,7 +18,7 @@ public class ContainerRenamer extends AEBaseContainer { private MEGuiTextField textField; public ContainerRenamer(InventoryPlayer ip, ICustomNameObject obj) { - super(ip, obj instanceof TileEntity ? (TileEntity) obj : null, obj instanceof IPart ? (IPart) obj : null); + super(ip, obj); namedObject = obj; } diff --git a/src/main/java/appeng/container/implementations/ContainerSecurity.java b/src/main/java/appeng/container/implementations/ContainerSecurity.java index 815f14c7c..0e3ecedf9 100644 --- a/src/main/java/appeng/container/implementations/ContainerSecurity.java +++ b/src/main/java/appeng/container/implementations/ContainerSecurity.java @@ -45,7 +45,7 @@ public class ContainerSecurity extends ContainerMEMonitorable implements IAEAppE public int permissionMode = 0; public ContainerSecurity(final InventoryPlayer ip, final ITerminalHost monitorable) { - super(ip, monitorable, false); + super(ip, monitorable); this.securityBox = (TileSecurity) monitorable; @@ -67,8 +67,6 @@ public class ContainerSecurity extends ContainerMEMonitorable implements IAEAppE 10, ip)); this.addSlotToContainer(this.wirelessOut = new SlotOutput(this.wirelessEncoder, 1, 212, 68, -1)); - - this.bindPlayerInventory(ip, 0, 0); } public void toggleSetting(final String value, final EntityPlayer player) { diff --git a/src/main/java/appeng/container/implementations/ContainerSkyChest.java b/src/main/java/appeng/container/implementations/ContainerSkyChest.java index ff1601ef0..0938df9dc 100644 --- a/src/main/java/appeng/container/implementations/ContainerSkyChest.java +++ b/src/main/java/appeng/container/implementations/ContainerSkyChest.java @@ -24,7 +24,7 @@ public class ContainerSkyChest extends AEBaseContainer { private final TileSkyChest chest; public ContainerSkyChest(final InventoryPlayer ip, final TileSkyChest chest) { - super(ip, chest, null); + super(ip, chest); this.chest = chest; for (int y = 0; y < 4; y++) { diff --git a/src/main/java/appeng/container/implementations/ContainerSpatialIOPort.java b/src/main/java/appeng/container/implementations/ContainerSpatialIOPort.java index 1929ad289..8878a9375 100644 --- a/src/main/java/appeng/container/implementations/ContainerSpatialIOPort.java +++ b/src/main/java/appeng/container/implementations/ContainerSpatialIOPort.java @@ -43,7 +43,7 @@ public class ContainerSpatialIOPort extends AEBaseContainer { private int delay = 40; public ContainerSpatialIOPort(final InventoryPlayer ip, final TileSpatialIOPort spatialIOPort) { - super(ip, spatialIOPort, null); + super(ip, spatialIOPort); if (Platform.isServer()) { this.network = spatialIOPort.getGridNode(ForgeDirection.UNKNOWN).getGrid(); diff --git a/src/main/java/appeng/container/implementations/ContainerStorageBus.java b/src/main/java/appeng/container/implementations/ContainerStorageBus.java index 3d3c70471..1f7b9680d 100644 --- a/src/main/java/appeng/container/implementations/ContainerStorageBus.java +++ b/src/main/java/appeng/container/implementations/ContainerStorageBus.java @@ -10,17 +10,15 @@ package appeng.container.implementations; +import static appeng.util.Platform.isServer; + import java.util.HashMap; import java.util.Iterator; import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.ICrafting; import net.minecraft.inventory.IInventory; -import net.minecraft.item.ItemStack; -import appeng.api.AEApi; import appeng.api.config.AccessRestriction; import appeng.api.config.ActionItems; import appeng.api.config.FuzzyMode; @@ -29,20 +27,24 @@ import appeng.api.config.Settings; import appeng.api.config.StorageFilter; import appeng.api.config.Upgrades; import appeng.api.config.YesNo; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.parts.IStorageBus; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.container.guisync.GuiSync; -import appeng.container.slot.OptionalSlotFakeTypeOnly; +import appeng.container.interfaces.IVirtualSlotHolder; import appeng.container.slot.SlotRestrictedInput; import appeng.me.storage.MEInventoryHandler; -import appeng.parts.misc.PartStorageBus; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.IterationCounter; import appeng.util.Platform; import appeng.util.prioitylist.PrecisePriorityList; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; -public class ContainerStorageBus extends ContainerUpgradeable { +public class ContainerStorageBus extends ContainerUpgradeable implements IVirtualSlotHolder { - private final PartStorageBus storageBus; + private final IStorageBus storageBus; @GuiSync(3) public AccessRestriction rwMode = AccessRestriction.READ_WRITE; @@ -58,7 +60,9 @@ public class ContainerStorageBus extends ContainerUpgradeable { @GuiSync(8) public ActionItems partitionMode; // use for icon and tooltip - public ContainerStorageBus(final InventoryPlayer ip, final PartStorageBus te) { + private final IAEStack[] configClientSlot = new IAEStack[63]; + + public ContainerStorageBus(final InventoryPlayer ip, final IStorageBus te) { super(ip, te); this.storageBus = te; partitionMode = PartitionIteratorMap.containsKey(ip.player) ? ActionItems.NEXT_PARTITION : ActionItems.WRENCH; @@ -71,16 +75,6 @@ public class ContainerStorageBus extends ContainerUpgradeable { @Override protected void setupConfig() { - final int xo = 8; - final int yo = 23 + 6; - - final IInventory config = this.getUpgradeable().getInventoryByName("config"); - for (int y = 0; y < 7; y++) { - for (int x = 0; x < 9; x++) { - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(config, this, y * 9 + x, xo, yo, x, y, y)); - } - } - final IInventory upgrades = this.getUpgradeable().getInventoryByName("upgrades"); this.addSlotToContainer( (new SlotRestrictedInput( @@ -134,36 +128,6 @@ public class ContainerStorageBus extends ContainerUpgradeable { return 5; } - private int rowToUpdate = 0; - - /** - * @param row the specific row to send, -1 indicates sending all. - * @param upgrades number of installed capacity cards - */ - private void sendRow(int row, int upgrades) { - IInventory inv = this.getUpgradeable().getInventoryByName("config"); - // start at first filter slot or at specific row - int from = row <= -1 ? 18 : 9 + (9 * row); - // end at last filter slot or at end of specific row - int to = row <= -1 ? inv.getSizeInventory() : 18 + (9 * row); - - int offset = getToolboxSizeInventory(); - for (; from < to; from++) { - if (upgrades <= (from / 9 - 2)) break; - - ItemStack stack = inv.getStackInSlot(from); - if (stack == null) continue; - - for (ICrafting crafter : this.crafters) { - if (crafter instanceof EntityPlayerMP playerMP) { - // necessary to ensure that the package is sent correctly - playerMP.isChangingQuantityOnly = false; - } - crafter.sendSlotContents(this, from + offset, stack); - } - } - } - @Override public void detectAndSendChanges() { this.verifyPermissions(SecurityPermissions.BUILD, false); @@ -175,20 +139,9 @@ public class ContainerStorageBus extends ContainerUpgradeable { this.setStorageFilter( (StorageFilter) this.getUpgradeable().getConfigManager().getSetting(Settings.STORAGE_FILTER)); this.setStickyMode((YesNo) this.getUpgradeable().getConfigManager().getSetting(Settings.STICKY_MODE)); - } - final int upgrades = this.getUpgradeable().getInstalledUpgrades(Upgrades.CAPACITY); - if (upgrades > 0) { // sync filter slots - boolean needSync = this.storageBus.needSyncGUI; - int row; - if (needSync) { - row = -1; // send all rows - rowToUpdate = upgrades; // force update of last row at next call - this.storageBus.needSyncGUI = false; - } else row = rowToUpdate++; - - if (row >= upgrades) rowToUpdate = 0; - sendRow(row, upgrades); + final IAEStackInventory config = this.storageBus.getAEInventoryByName(StorageName.NONE); + this.updateVirtualSlots(StorageName.NONE, config, this.configClientSlot); } this.standardDetectAndSendChanges(); @@ -204,9 +157,9 @@ public class ContainerStorageBus extends ContainerUpgradeable { } public void clear() { - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); + final IAEStackInventory inv = this.storageBus.getAEInventoryByName(StorageName.NONE); for (int x = 0; x < inv.getSizeInventory(); x++) { - inv.setInventorySlotContents(x, null); + inv.putAEStackInSlot(x, null); } this.detectAndSendChanges(); } @@ -222,9 +175,9 @@ public class ContainerStorageBus extends ContainerUpgradeable { clearPartitionIterator(player); return; } - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); + final IAEStackInventory inv = this.storageBus.getAEInventoryByName(StorageName.NONE); - final MEInventoryHandler cellInv = this.storageBus.getInternalHandler(); + final MEInventoryHandler cellInv = this.storageBus.getInternalHandler(); if (cellInv == null) { clearPartitionIterator(player); @@ -233,10 +186,9 @@ public class ContainerStorageBus extends ContainerUpgradeable { IteratorState it; if (!PartitionIteratorMap.containsKey(player)) { // clear filter for fetching items - cellInv.setPartitionList(new PrecisePriorityList<>(AEApi.instance().storage().createItemList())); - final IItemList list = cellInv.getAvailableItems( - AEApi.instance().storage().createItemFilterList(), - IterationCounter.fetchNewId()); + cellInv.setPartitionList(new PrecisePriorityList<>(this.storageBus.getItemList())); + final IItemList list = cellInv + .getAvailableItems(this.storageBus.getItemList(), IterationCounter.fetchNewId()); it = new IteratorState(list.iterator()); PartitionIteratorMap.put(player, it); partitionMode = ActionItems.NEXT_PARTITION; @@ -246,23 +198,23 @@ public class ContainerStorageBus extends ContainerUpgradeable { boolean skip = false; for (int x = 0; x < inv.getSizeInventory(); x++) { if (skip) { - inv.setInventorySlotContents(x, null); + inv.putAEStackInSlot(x, null); continue; } if (this.isSlotEnabled(x / 9)) { - IAEItemStack AEis = it.next(); + IAEStack AEis = it.next(); if (AEis != null) { - final ItemStack is = AEis.getItemStack(); - is.stackSize = 1; - inv.setInventorySlotContents(x, is); + final IAEStack tempAes = AEis.copy(); + tempAes.setStackSize(1); + inv.putAEStackInSlot(x, tempAes); } else { clearPartitionIterator(player); skip = true; - inv.setInventorySlotContents(x, null); + inv.putAEStackInSlot(x, null); } } else { skip = true; - inv.setInventorySlotContents(x, null); + inv.putAEStackInSlot(x, null); } } @@ -304,21 +256,41 @@ public class ContainerStorageBus extends ContainerUpgradeable { private static class IteratorState { - private final Iterator it; + private final Iterator> it; private boolean hasNext; // cache hasNext(), call next of internal iterator - public IteratorState(Iterator it) { + public IteratorState(Iterator> it) { this.it = it; this.hasNext = it.hasNext(); } - public IAEItemStack next() { + public IAEStack next() { if (this.hasNext) { - IAEItemStack is = it.next(); + IAEStack is = it.next(); hasNext = it.hasNext(); return is; } return null; } } + + @Override + public void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks) { + final IAEStackInventory config = this.storageBus.getAEInventoryByName(StorageName.NONE); + for (var entry : slotStacks.int2ObjectEntrySet()) { + config.putAEStackInSlot(entry.getIntKey(), entry.getValue()); + } + + if (isServer()) { + this.updateVirtualSlots(StorageName.NONE, config, this.configClientSlot); + } + } + + public StorageChannel getStorageChannel() { + return this.storageBus.getStorageChannel(); + } + + public IAEStackInventory getConfig() { + return this.storageBus.getAEInventoryByName(StorageName.NONE); + } } diff --git a/src/main/java/appeng/container/implementations/ContainerUpgradeable.java b/src/main/java/appeng/container/implementations/ContainerUpgradeable.java index a7a1079f3..8313d7095 100644 --- a/src/main/java/appeng/container/implementations/ContainerUpgradeable.java +++ b/src/main/java/appeng/container/implementations/ContainerUpgradeable.java @@ -33,12 +33,11 @@ import appeng.container.AEBaseContainer; import appeng.container.guisync.GuiSync; import appeng.container.slot.IOptionalSlotHost; import appeng.container.slot.OptionalSlotFake; -import appeng.container.slot.OptionalSlotFakeTypeOnly; import appeng.container.slot.SlotRestrictedInput; -import appeng.parts.automation.PartExportBus; +import appeng.parts.automation.PartBaseExportBus; import appeng.util.Platform; -public class ContainerUpgradeable extends AEBaseContainer implements IOptionalSlotHost { +public abstract class ContainerUpgradeable extends AEBaseContainer implements IOptionalSlotHost { private final IUpgradeableHost upgradeable; @@ -59,7 +58,7 @@ public class ContainerUpgradeable extends AEBaseContainer implements IOptionalSl private INetworkTool tbInventory; public ContainerUpgradeable(final InventoryPlayer ip, final IUpgradeableHost te) { - super(ip, (TileEntity) (te instanceof TileEntity ? te : null), (IPart) (te instanceof IPart ? te : null)); + super(ip, te); this.upgradeable = te; World w = null; @@ -91,7 +90,7 @@ public class ContainerUpgradeable extends AEBaseContainer implements IOptionalSl this.lockPlayerInventorySlot(x); this.tbSlot = x; this.tbInventory = (INetworkTool) ((IGuiItem) pii.getItem()) - .getGuiObject(pii, w, xCoord, yCoord, zCoord); + .getGuiObject(pii, w, getInventoryPlayer().player, xCoord, yCoord, zCoord); break; } } @@ -137,22 +136,6 @@ public class ContainerUpgradeable extends AEBaseContainer implements IOptionalSl protected void setupConfig() { this.setupUpgrades(); - - final IInventory inv = this.getUpgradeable().getInventoryByName("config"); - final int y = 40; - final int x = 80; - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 0, x, y, 0, 0, 0)); - if (this.supportCapacity()) { - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 1, x, y, -1, 0, 1)); - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 2, x, y, 1, 0, 1)); - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 3, x, y, 0, -1, 1)); - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 4, x, y, 0, 1, 1)); - - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 5, x, y, -1, -1, 2)); - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 6, x, y, 1, -1, 2)); - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 7, x, y, -1, 1, 2)); - this.addSlotToContainer(new OptionalSlotFakeTypeOnly(inv, this, 8, x, y, 1, 1, 2)); - } } protected void setupUpgrades() { @@ -232,7 +215,7 @@ public class ContainerUpgradeable extends AEBaseContainer implements IOptionalSl protected void loadSettingsFromHost(final IConfigManager cm) { this.setFuzzyMode((FuzzyMode) cm.getSetting(Settings.FUZZY_MODE)); this.setRedStoneMode((RedstoneMode) cm.getSetting(Settings.REDSTONE_CONTROLLED)); - if (this.getUpgradeable() instanceof PartExportBus) { + if (this.getUpgradeable() instanceof PartBaseExportBus) { this.setCraftingMode((YesNo) cm.getSetting(Settings.CRAFT_ONLY)); this.setSchedulingMode((SchedulingMode) cm.getSetting(Settings.SCHEDULING_MODE)); } diff --git a/src/main/java/appeng/container/implementations/ContainerVibrationChamber.java b/src/main/java/appeng/container/implementations/ContainerVibrationChamber.java index 1452cbfaa..1ff5c896b 100644 --- a/src/main/java/appeng/container/implementations/ContainerVibrationChamber.java +++ b/src/main/java/appeng/container/implementations/ContainerVibrationChamber.java @@ -32,7 +32,7 @@ public class ContainerVibrationChamber extends AEBaseContainer implements IProgr public int burnSpeed = 100; public ContainerVibrationChamber(final InventoryPlayer ip, final TileVibrationChamber vibrationChamber) { - super(ip, vibrationChamber, null); + super(ip, vibrationChamber); this.vibrationChamber = vibrationChamber; this.addSlotToContainer( diff --git a/src/main/java/appeng/container/implementations/ContainerWireless.java b/src/main/java/appeng/container/implementations/ContainerWireless.java index c73bc1ac4..4c840073c 100644 --- a/src/main/java/appeng/container/implementations/ContainerWireless.java +++ b/src/main/java/appeng/container/implementations/ContainerWireless.java @@ -31,7 +31,7 @@ public class ContainerWireless extends AEBaseContainer { public long drain = 0; public ContainerWireless(final InventoryPlayer ip, final TileWireless te) { - super(ip, te, null); + super(ip, te); this.wirelessTerminal = te; this.addSlotToContainer( diff --git a/src/main/java/appeng/container/implementations/ContainerWirelessTerm.java b/src/main/java/appeng/container/implementations/ContainerWirelessTerm.java deleted file mode 100644 index 997811c1f..000000000 --- a/src/main/java/appeng/container/implementations/ContainerWirelessTerm.java +++ /dev/null @@ -1,47 +0,0 @@ -/* - * This file is part of Applied Energistics 2. Copyright (c) 2013 - 2014, AlgorithmX2, All rights reserved. Applied - * Energistics 2 is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General - * Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any - * later version. Applied Energistics 2 is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; - * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General - * Public License for more details. You should have received a copy of the GNU Lesser General Public License along with - * Applied Energistics 2. If not, see . - */ - -package appeng.container.implementations; - -import net.minecraft.entity.player.InventoryPlayer; - -import appeng.core.AEConfig; -import appeng.core.localization.PlayerMessages; -import appeng.helpers.WirelessTerminalGuiObject; -import appeng.util.Platform; - -public class ContainerWirelessTerm extends ContainerMEPortableCell { - - private final WirelessTerminalGuiObject wirelessTerminalGUIObject; - - public ContainerWirelessTerm(final InventoryPlayer ip, final WirelessTerminalGuiObject gui) { - super(ip, gui); - this.wirelessTerminalGUIObject = gui; - } - - @Override - public void detectAndSendChanges() { - super.detectAndSendChanges(); - - if (!this.wirelessTerminalGUIObject.rangeCheck()) { - if (Platform.isServer() && this.isValidContainer()) { - this.getPlayerInv().player.addChatMessage(PlayerMessages.OutOfRange.toChat()); - } - - this.setValidContainer(false); - } else { - this.setPowerMultiplier(AEConfig.instance.wireless_getDrainRate(this.wirelessTerminalGUIObject.getRange())); - } - } - - public WirelessTerminalGuiObject getWirelessTerminalGUIObject() { - return this.wirelessTerminalGUIObject; - } -} diff --git a/src/main/java/appeng/container/interfaces/IContainerSubGui.java b/src/main/java/appeng/container/interfaces/IContainerSubGui.java new file mode 100644 index 000000000..dab3e6257 --- /dev/null +++ b/src/main/java/appeng/container/interfaces/IContainerSubGui.java @@ -0,0 +1,19 @@ +package appeng.container.interfaces; + +import net.minecraft.item.ItemStack; + +import appeng.client.gui.IGuiSub; +import appeng.container.PrimaryGui; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public interface IContainerSubGui { + + void setPrimaryGui(PrimaryGui pg); + + @SideOnly(Side.CLIENT) + ItemStack getPrimaryGuiIcon(); + + @SideOnly(Side.CLIENT) + void setGuiLink(IGuiSub gs); +} diff --git a/src/main/java/appeng/container/interfaces/IVirtualSlotHolder.java b/src/main/java/appeng/container/interfaces/IVirtualSlotHolder.java new file mode 100644 index 000000000..af1ac98b6 --- /dev/null +++ b/src/main/java/appeng/container/interfaces/IVirtualSlotHolder.java @@ -0,0 +1,10 @@ +package appeng.container.interfaces; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; + +public interface IVirtualSlotHolder { + + void receiveSlotStacks(StorageName invName, Int2ObjectMap> slotStacks); +} diff --git a/src/main/java/appeng/container/interfaces/IVirtualSlotSource.java b/src/main/java/appeng/container/interfaces/IVirtualSlotSource.java new file mode 100644 index 000000000..4b8720eb4 --- /dev/null +++ b/src/main/java/appeng/container/interfaces/IVirtualSlotSource.java @@ -0,0 +1,9 @@ +package appeng.container.interfaces; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; + +public interface IVirtualSlotSource { + + void updateVirtualSlot(StorageName invName, int slotId, IAEStack aes); +} diff --git a/src/main/java/appeng/container/slot/SlotDisabled.java b/src/main/java/appeng/container/slot/SlotDisabled.java index 2278cf87f..a697c0577 100644 --- a/src/main/java/appeng/container/slot/SlotDisabled.java +++ b/src/main/java/appeng/container/slot/SlotDisabled.java @@ -18,6 +18,7 @@ public class SlotDisabled extends AppEngSlot { public SlotDisabled(final IInventory par1iInventory, final int slotIndex, final int x, final int y) { super(par1iInventory, slotIndex, x, y); + this.setPlayerSide(true); } @Override diff --git a/src/main/java/appeng/core/CommonHelper.java b/src/main/java/appeng/core/CommonHelper.java index 430f5eae2..a8a286d83 100644 --- a/src/main/java/appeng/core/CommonHelper.java +++ b/src/main/java/appeng/core/CommonHelper.java @@ -64,6 +64,10 @@ public abstract class CommonHelper { return false; } + public int getKeybind(ActionKey key) { + return 0; + } + public boolean isActionKey(ActionKey key, int pressedKeyCode) { return false; } diff --git a/src/main/java/appeng/core/Registration.java b/src/main/java/appeng/core/Registration.java index 9d903bdc6..66a278f2c 100644 --- a/src/main/java/appeng/core/Registration.java +++ b/src/main/java/appeng/core/Registration.java @@ -62,7 +62,6 @@ import appeng.core.features.IAEFeature; import appeng.core.features.IFeatureHandler; import appeng.core.features.registries.BlockingModeIgnoreItemRegistry; import appeng.core.features.registries.P2PTunnelRegistry; -import appeng.core.features.registries.entries.BasicCellHandler; import appeng.core.features.registries.entries.CreativeCellHandler; import appeng.core.features.registries.entries.VoidCellHandler; import appeng.core.localization.GuiText; @@ -548,7 +547,7 @@ public final class Registration { registries.externalStorage().addExternalStorageInterface(new AEExternalHandler()); - registries.cell().addCellHandler(new BasicCellHandler()); + // BasicCellHandler is built into the Registry, so there is no need to register it here. registries.cell().addCellHandler(new CreativeCellHandler()); registries.cell().addCellHandler(new VoidCellHandler()); diff --git a/src/main/java/appeng/core/features/registries/CellRegistry.java b/src/main/java/appeng/core/features/registries/CellRegistry.java index 2a3888fa1..0db974c11 100644 --- a/src/main/java/appeng/core/features/registries/CellRegistry.java +++ b/src/main/java/appeng/core/features/registries/CellRegistry.java @@ -20,11 +20,15 @@ import appeng.api.storage.ICellRegistry; import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.ISaveProvider; import appeng.api.storage.StorageChannel; +import appeng.core.features.registries.entries.BasicCellHandler; public class CellRegistry implements ICellRegistry { private final List handlers; + // BasicCellHandler is valid for all cells that implement IStorageCell, so it should be checked last. + private final ICellHandler basicCellHandler = new BasicCellHandler(); + public CellRegistry() { this.handlers = new ArrayList<>(); } @@ -46,7 +50,7 @@ public class CellRegistry implements ICellRegistry { return true; } } - return false; + return basicCellHandler.isCell(is); } @Override @@ -59,7 +63,7 @@ public class CellRegistry implements ICellRegistry { return ch; } } - return null; + return basicCellHandler.isCell(is) ? basicCellHandler : null; } @Override @@ -73,6 +77,6 @@ public class CellRegistry implements ICellRegistry { return ch.getCellInventory(is, container, chan); } } - return null; + return basicCellHandler.isCell(is) ? basicCellHandler.getCellInventory(is, container, chan) : null; } } diff --git a/src/main/java/appeng/core/features/registries/WirelessRegistry.java b/src/main/java/appeng/core/features/registries/WirelessRegistry.java index b02d3fd87..d31486a8c 100644 --- a/src/main/java/appeng/core/features/registries/WirelessRegistry.java +++ b/src/main/java/appeng/core/features/registries/WirelessRegistry.java @@ -22,7 +22,7 @@ import appeng.api.features.ILocatable; import appeng.api.features.IWirelessTermHandler; import appeng.api.features.IWirelessTermRegistry; import appeng.core.localization.PlayerMessages; -import appeng.core.sync.GuiBridge; +import appeng.items.tools.powered.ToolWirelessTerminal; import appeng.util.Platform; public final class WirelessRegistry implements IWirelessTermRegistry { @@ -60,35 +60,42 @@ public final class WirelessRegistry implements IWirelessTermRegistry { return null; } - @Override - public void openWirelessTerminalGui(final ItemStack item, final World w, final EntityPlayer player) { + public boolean performCheck(final ItemStack item, final EntityPlayer player) { if (Platform.isClient()) { - return; + return false; } if (!this.isWirelessTerminal(item)) { player.addChatMessage(PlayerMessages.DeviceNotWirelessTerminal.toChat()); - return; + return false; } final IWirelessTermHandler handler = this.getWirelessTerminalHandler(item); final String unparsedKey = handler.getEncryptionKey(item); if (unparsedKey.isEmpty()) { player.addChatMessage(PlayerMessages.DeviceNotLinked.toChat()); - return; + return false; } final long parsedKey = Long.parseLong(unparsedKey); final ILocatable securityStation = AEApi.instance().registries().locatable().getLocatableBy(parsedKey); if (securityStation == null) { player.addChatMessage(PlayerMessages.StationCanNotBeLocated.toChat()); - return; + return false; } - if (handler.hasPower(player, 0.5, item)) { - Platform.openGUI(player, null, null, GuiBridge.GUI_WIRELESS_TERM); + if (item.getItem() instanceof ToolWirelessTerminal + && (handler.hasInfinityPower(item) || handler.hasPower(player, 0.5, item))) { + return true; } else { player.addChatMessage(PlayerMessages.DeviceNotPowered.toChat()); } + + return false; + } + + @Override + public void openWirelessTerminalGui(final ItemStack item, final World w, final EntityPlayer player) { + if (performCheck(item, player)) ((ToolWirelessTerminal) item.getItem()).openGui(item, w, player, null); } } diff --git a/src/main/java/appeng/core/features/registries/entries/BasicCellHandler.java b/src/main/java/appeng/core/features/registries/entries/BasicCellHandler.java index a06d57841..451cdf647 100644 --- a/src/main/java/appeng/core/features/registries/entries/BasicCellHandler.java +++ b/src/main/java/appeng/core/features/registries/entries/BasicCellHandler.java @@ -15,6 +15,7 @@ import net.minecraft.item.ItemStack; import net.minecraft.tileentity.TileEntity; import net.minecraft.util.IIcon; +import appeng.api.implementations.items.IStorageCell; import appeng.api.implementations.tiles.IChestOrDrive; import appeng.api.storage.ICellHandler; import appeng.api.storage.ICellInventory; @@ -39,8 +40,8 @@ public class BasicCellHandler implements ICellHandler { @Override public IMEInventoryHandler getCellInventory(final ItemStack is, final ISaveProvider container, final StorageChannel channel) { - if (channel == StorageChannel.ITEMS) { - return CellInventory.getCell(is, container); + if (is != null && is.getItem() instanceof IStorageCell cell && cell.getStorageChannel() == channel) { + return CellInventory.getCell(is, container, channel); } return null; } diff --git a/src/main/java/appeng/core/features/registries/entries/CreativeCellHandler.java b/src/main/java/appeng/core/features/registries/entries/CreativeCellHandler.java index 88191e0a0..315e62612 100644 --- a/src/main/java/appeng/core/features/registries/entries/CreativeCellHandler.java +++ b/src/main/java/appeng/core/features/registries/entries/CreativeCellHandler.java @@ -23,7 +23,7 @@ import appeng.api.storage.ISaveProvider; import appeng.api.storage.StorageChannel; import appeng.client.texture.ExtraBlockTextures; import appeng.core.sync.GuiBridge; -import appeng.items.storage.ItemCreativeStorageCell; +import appeng.items.AEBaseInfiniteCell; import appeng.me.storage.CreativeCellInventory; import appeng.util.Platform; @@ -31,15 +31,16 @@ public class CreativeCellHandler implements ICellHandler { @Override public boolean isCell(final ItemStack is) { - return is != null && is.getItem() instanceof ItemCreativeStorageCell; + return is != null && is.getItem() instanceof AEBaseInfiniteCell; } @Override public IMEInventoryHandler getCellInventory(final ItemStack is, final ISaveProvider container, final StorageChannel channel) { - if (channel == StorageChannel.ITEMS && is != null && is.getItem() instanceof ItemCreativeStorageCell) { - return CreativeCellInventory.getCell(is); + if (is != null && is.getItem() instanceof AEBaseInfiniteCell cell && channel == cell.getStorageChannel()) { + return CreativeCellInventory.getCell(is, channel); } + return null; } diff --git a/src/main/java/appeng/core/features/registries/entries/VoidCellHandler.java b/src/main/java/appeng/core/features/registries/entries/VoidCellHandler.java index 9a0199eb1..4ff50117c 100644 --- a/src/main/java/appeng/core/features/registries/entries/VoidCellHandler.java +++ b/src/main/java/appeng/core/features/registries/entries/VoidCellHandler.java @@ -24,8 +24,8 @@ public class VoidCellHandler implements ICellHandler { @Override @SuppressWarnings("rawtypes") public IMEInventoryHandler getCellInventory(ItemStack is, ISaveProvider host, StorageChannel channel) { - if (channel == StorageChannel.ITEMS && is != null && is.getItem() instanceof ItemVoidStorageCell) { - return VoidCellInventory.getCell(is); + if (is.getItem() instanceof ItemVoidStorageCell isc && isc.getStorageChannel() == channel) { + return VoidCellInventory.getCell(is, channel); } return null; } diff --git a/src/main/java/appeng/core/sync/AppEngPacketHandlerBase.java b/src/main/java/appeng/core/sync/AppEngPacketHandlerBase.java index 0e0dd0781..f6d924dd1 100644 --- a/src/main/java/appeng/core/sync/AppEngPacketHandlerBase.java +++ b/src/main/java/appeng/core/sync/AppEngPacketHandlerBase.java @@ -33,6 +33,7 @@ import appeng.core.sync.packets.PacketLightning; import appeng.core.sync.packets.PacketMEInventoryUpdate; import appeng.core.sync.packets.PacketMatterCannon; import appeng.core.sync.packets.PacketMockExplosion; +import appeng.core.sync.packets.PacketMonitorableAction; import appeng.core.sync.packets.PacketMultiPart; import appeng.core.sync.packets.PacketNEIBookmark; import appeng.core.sync.packets.PacketNEIDragClick; @@ -43,7 +44,6 @@ import appeng.core.sync.packets.PacketOptimizePatterns; import appeng.core.sync.packets.PacketPaintedEntity; import appeng.core.sync.packets.PacketPartPlacement; import appeng.core.sync.packets.PacketPartialItem; -import appeng.core.sync.packets.PacketPatternItemRenamer; import appeng.core.sync.packets.PacketPatternMultiSet; import appeng.core.sync.packets.PacketPatternSlot; import appeng.core.sync.packets.PacketPatternValueSet; @@ -53,6 +53,7 @@ import appeng.core.sync.packets.PacketSwapSlots; import appeng.core.sync.packets.PacketSwitchGuis; import appeng.core.sync.packets.PacketTransitionEffect; import appeng.core.sync.packets.PacketValueConfig; +import appeng.core.sync.packets.PacketVirtualSlot; import io.netty.buffer.ByteBuf; public class AppEngPacketHandlerBase { @@ -122,9 +123,10 @@ public class AppEngPacketHandlerBase { PACKET_INTERFACE_TERMINAL_UPDATE(PacketInterfaceTerminalUpdate.class), PACKET_OPTIMIZE_PATTERNS(PacketOptimizePatterns.class), PACKET_NETWORK_STATUS_SELECTED(PacketNetworkStatusSelected.class), - PACKET_PATTERN_ITEM_RENAMER(PacketPatternItemRenamer.class), PACKET_PINS_UPDATE(PacketPinsUpdate.class), - PACKET_HIGHLIGHT_BLOCKS(PacketHighlightBlockStorage.class); + PACKET_MONITORABLE_ACTION(PacketMonitorableAction.class), + PACKET_HIGHLIGHT_BLOCKS(PacketHighlightBlockStorage.class), + PACKET_VIRTUAL_SLOT(PacketVirtualSlot.class); private final Class packetClass; private final Constructor packetConstructor; diff --git a/src/main/java/appeng/core/sync/GuiBridge.java b/src/main/java/appeng/core/sync/GuiBridge.java index a3003183e..4027ddd6c 100644 --- a/src/main/java/appeng/core/sync/GuiBridge.java +++ b/src/main/java/appeng/core/sync/GuiBridge.java @@ -10,6 +10,9 @@ package appeng.core.sync; +import static appeng.util.Platform.getItemFromPlayerInventoryBySlotIndex; +import static appeng.util.Platform.itemGuiSlotOffset; + import java.lang.reflect.Constructor; import java.util.List; @@ -29,17 +32,23 @@ import appeng.api.definitions.IComparableDefinition; import appeng.api.definitions.IMaterials; import appeng.api.exceptions.AppEngException; import appeng.api.features.IWirelessTermHandler; -import appeng.api.implementations.IUpgradeableHost; import appeng.api.implementations.guiobjects.IGuiItem; import appeng.api.implementations.guiobjects.INetworkTool; import appeng.api.implementations.guiobjects.IPortableCell; +import appeng.api.implementations.tiles.ICellWorkbench; import appeng.api.networking.IGrid; import appeng.api.networking.IGridNode; import appeng.api.networking.energy.IEnergyGrid; import appeng.api.networking.security.IActionHost; import appeng.api.networking.security.ISecurityGrid; +import appeng.api.parts.ICraftingTerminal; +import appeng.api.parts.IInterfaceTerminal; +import appeng.api.parts.ILevelEmitter; import appeng.api.parts.IPart; import appeng.api.parts.IPartHost; +import appeng.api.parts.IPatternTerminal; +import appeng.api.parts.IPatternTerminalEx; +import appeng.api.parts.IStorageBus; import appeng.api.storage.ITerminalHost; import appeng.api.util.DimensionalCoord; import appeng.client.gui.GuiNull; @@ -47,6 +56,7 @@ import appeng.container.AEBaseContainer; import appeng.container.ContainerNull; import appeng.container.ContainerOpenContext; import appeng.container.implementations.ContainerAdvancedNetworkTool; +import appeng.container.implementations.ContainerBusIO; import appeng.container.implementations.ContainerCellRestriction; import appeng.container.implementations.ContainerCellWorkbench; import appeng.container.implementations.ContainerChest; @@ -85,10 +95,8 @@ import appeng.container.implementations.ContainerSecurity; import appeng.container.implementations.ContainerSkyChest; import appeng.container.implementations.ContainerSpatialIOPort; import appeng.container.implementations.ContainerStorageBus; -import appeng.container.implementations.ContainerUpgradeable; import appeng.container.implementations.ContainerVibrationChamber; import appeng.container.implementations.ContainerWireless; -import appeng.container.implementations.ContainerWirelessTerm; import appeng.core.stats.Achievements; import appeng.helpers.ICellRestriction; import appeng.helpers.ICustomNameObject; @@ -99,16 +107,10 @@ import appeng.helpers.WirelessTerminalGuiObject; import appeng.items.contents.PriorityCardObject; import appeng.items.contents.QuartzKnifeObj; import appeng.parts.automation.PartFormationPlane; -import appeng.parts.automation.PartLevelEmitter; -import appeng.parts.misc.PartStorageBus; -import appeng.parts.reporting.PartCraftingTerminal; -import appeng.parts.reporting.PartInterfaceTerminal; -import appeng.parts.reporting.PartPatternTerminal; -import appeng.parts.reporting.PartPatternTerminalEx; +import appeng.parts.automation.PartSharedItemBus; import appeng.tile.crafting.TileCraftingTile; import appeng.tile.crafting.TileMolecularAssembler; import appeng.tile.grindstone.TileGrinder; -import appeng.tile.misc.TileCellWorkbench; import appeng.tile.misc.TileCondenser; import appeng.tile.misc.TileInscriber; import appeng.tile.misc.TileSecurity; @@ -128,6 +130,24 @@ public enum GuiBridge implements IGuiHandler { GUI_Handler(), + // Terminal + + GUI_ME(ContainerMEMonitorable.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, null), + + GUI_CRAFTING_TERMINAL(ContainerCraftingTerm.class, ICraftingTerminal.class, GuiHostType.ITEM_OR_WORLD, + SecurityPermissions.CRAFT), + + GUI_PATTERN_TERMINAL(ContainerPatternTerm.class, IPatternTerminal.class, GuiHostType.ITEM_OR_WORLD, + SecurityPermissions.CRAFT), + + GUI_PATTERN_TERMINAL_EX(ContainerPatternTermEx.class, IPatternTerminalEx.class, GuiHostType.ITEM_OR_WORLD, + SecurityPermissions.CRAFT), + + GUI_INTERFACE_TERMINAL(ContainerInterfaceTerminal.class, IInterfaceTerminal.class, GuiHostType.ITEM_OR_WORLD, + SecurityPermissions.BUILD), + + GUI_PORTABLE_CELL(ContainerMEPortableCell.class, IPortableCell.class, GuiHostType.ITEM, null), + GUI_GRINDER(ContainerGrinder.class, TileGrinder.class, GuiHostType.WORLD, null), GUI_QNB(ContainerQNB.class, TileQuantumBridge.class, GuiHostType.WORLD, SecurityPermissions.BUILD), @@ -138,12 +158,6 @@ public enum GuiBridge implements IGuiHandler { GUI_WIRELESS(ContainerWireless.class, TileWireless.class, GuiHostType.WORLD, SecurityPermissions.BUILD), - GUI_ME(ContainerMEMonitorable.class, ITerminalHost.class, GuiHostType.WORLD, null), - - GUI_PORTABLE_CELL(ContainerMEPortableCell.class, IPortableCell.class, GuiHostType.ITEM, null), - - GUI_WIRELESS_TERM(ContainerWirelessTerm.class, WirelessTerminalGuiObject.class, GuiHostType.ITEM, null), - GUI_NETWORK_STATUS(ContainerNetworkStatus.class, INetworkTool.class, GuiHostType.ITEM, null), GUI_CRAFTING_CPU(ContainerCraftingCPU.class, TileCraftingTile.class, GuiHostType.WORLD, SecurityPermissions.CRAFT), @@ -164,11 +178,11 @@ public enum GuiBridge implements IGuiHandler { GUI_INTERFACE(ContainerInterface.class, IInterfaceHost.class, GuiHostType.WORLD, SecurityPermissions.BUILD), - GUI_BUS(ContainerUpgradeable.class, IUpgradeableHost.class, GuiHostType.WORLD, SecurityPermissions.BUILD), + GUI_BUS(ContainerBusIO.class, PartSharedItemBus.class, GuiHostType.WORLD, SecurityPermissions.BUILD), GUI_IOPORT(ContainerIOPort.class, TileIOPort.class, GuiHostType.WORLD, SecurityPermissions.BUILD), - GUI_STORAGEBUS(ContainerStorageBus.class, PartStorageBus.class, GuiHostType.WORLD, SecurityPermissions.BUILD), + GUI_STORAGEBUS(ContainerStorageBus.class, IStorageBus.class, GuiHostType.WORLD, SecurityPermissions.BUILD), GUI_FORMATION_PLANE(ContainerFormationPlane.class, PartFormationPlane.class, GuiHostType.WORLD, SecurityPermissions.BUILD), @@ -177,17 +191,8 @@ public enum GuiBridge implements IGuiHandler { GUI_SECURITY(ContainerSecurity.class, TileSecurity.class, GuiHostType.WORLD, SecurityPermissions.SECURITY), - GUI_CRAFTING_TERMINAL(ContainerCraftingTerm.class, PartCraftingTerminal.class, GuiHostType.WORLD, - SecurityPermissions.CRAFT), - - GUI_PATTERN_TERMINAL(ContainerPatternTerm.class, PartPatternTerminal.class, GuiHostType.WORLD, - SecurityPermissions.CRAFT), - - GUI_PATTERN_TERMINAL_EX(ContainerPatternTermEx.class, PartPatternTerminalEx.class, GuiHostType.WORLD, - SecurityPermissions.CRAFT), - // extends (Container/Gui) + Bus - GUI_LEVEL_EMITTER(ContainerLevelEmitter.class, PartLevelEmitter.class, GuiHostType.WORLD, + GUI_LEVEL_EMITTER(ContainerLevelEmitter.class, ILevelEmitter.class, GuiHostType.ITEM_OR_WORLD, SecurityPermissions.BUILD), GUI_SPATIAL_IO_PORT(ContainerSpatialIOPort.class, TileSpatialIOPort.class, GuiHostType.WORLD, @@ -195,16 +200,18 @@ public enum GuiBridge implements IGuiHandler { GUI_INSCRIBER(ContainerInscriber.class, TileInscriber.class, GuiHostType.WORLD, null), - GUI_CELL_WORKBENCH(ContainerCellWorkbench.class, TileCellWorkbench.class, GuiHostType.WORLD, null), + GUI_CELL_WORKBENCH(ContainerCellWorkbench.class, ICellWorkbench.class, GuiHostType.WORLD, null), GUI_MAC(ContainerMAC.class, TileMolecularAssembler.class, GuiHostType.WORLD, null), GUI_CRAFTING_AMOUNT(ContainerCraftAmount.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, SecurityPermissions.CRAFT), - GUI_PATTERN_VALUE_AMOUNT(ContainerPatternValueAmount.class, ITerminalHost.class, GuiHostType.WORLD, - SecurityPermissions.CRAFT), - GUI_PATTERN_MULTI(ContainerPatternMulti.class, ITerminalHost.class, GuiHostType.WORLD, SecurityPermissions.CRAFT), + GUI_PATTERN_VALUE_AMOUNT(ContainerPatternValueAmount.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, null), + + GUI_PATTERN_MULTI(ContainerPatternMulti.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, null), + + GUI_PATTERN_ITEM_RENAMER(ContainerPatternItemRenamer.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, null), GUI_CRAFTING_CONFIRM(ContainerCraftConfirm.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, SecurityPermissions.CRAFT), @@ -212,9 +219,6 @@ public enum GuiBridge implements IGuiHandler { GUI_OPTIMIZE_PATTERNS(ContainerOptimizePatterns.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, SecurityPermissions.BUILD), - GUI_INTERFACE_TERMINAL(ContainerInterfaceTerminal.class, PartInterfaceTerminal.class, GuiHostType.WORLD, - SecurityPermissions.BUILD), - GUI_CRAFTING_STATUS(ContainerCraftingStatus.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, SecurityPermissions.CRAFT), @@ -222,9 +226,7 @@ public enum GuiBridge implements IGuiHandler { GUI_ORE_FILTER(ContainerOreFilter.class, IOreFilterable.class, GuiHostType.ITEM_OR_WORLD, null), - GUI_CELL_RESTRICTION(ContainerCellRestriction.class, ICellRestriction.class, GuiHostType.ITEM_OR_WORLD, null), - - GUI_PATTERN_ITEM_RENAMER(ContainerPatternItemRenamer.class, ITerminalHost.class, GuiHostType.ITEM_OR_WORLD, null); + GUI_CELL_RESTRICTION(ContainerCellRestriction.class, ICellRestriction.class, GuiHostType.ITEM_OR_WORLD, null); private final Class tileClass; private final Class containerClass; @@ -279,17 +281,23 @@ public enum GuiBridge implements IGuiHandler { final ForgeDirection side = ForgeDirection.getOrientation(ordinal & 0x07); final GuiBridge ID = values()[ordinal >> 5]; final boolean stem = ((ordinal >> 3) & 1) == 1; - final boolean xIsSlotIndex = ((ordinal >> 4) & 1) == 1; - if (ID.type.isItem()) { - ItemStack it = null; - if (stem) { - it = player.inventory.getCurrentItem(); - } else if (xIsSlotIndex && x >= 0 && x < player.inventory.mainInventory.length) { - it = player.inventory.getStackInSlot(x); - } - final Object myItem = this.getGuiObject(it, player, w, x, y, z); + final boolean pastXLimit = x >= itemGuiSlotOffset; + final int slotIndex = x - itemGuiSlotOffset; + + if (ID.type.isItem() && pastXLimit) { + final ItemStack it = stem ? player.inventory.getCurrentItem() + : getItemFromPlayerInventoryBySlotIndex(player, slotIndex); + + final Object myItem = this.getGuiObject(it, player, w, slotIndex, y, z); if (myItem != null && ID.CorrectTileOrPart(myItem)) { - return this.updateGui(ID.ConstructContainer(player.inventory, side, myItem), w, x, y, z, side, myItem); + return this.updateGui( + ID.ConstructContainer(player.inventory, side, myItem), + w, + slotIndex, + y, + z, + side, + myItem); } } if (ID.type.isTile()) { @@ -312,8 +320,8 @@ public enum GuiBridge implements IGuiHandler { private Object getGuiObject(final ItemStack it, final EntityPlayer player, final World w, final int x, final int y, final int z) { if (it != null) { - if (it.getItem() instanceof IGuiItem) { - return ((IGuiItem) it.getItem()).getGuiObject(it, w, x, y, z); + if (it.getItem() instanceof IGuiItem igi) { + return igi.getGuiObject(it, w, player, x, y, z); } final IWirelessTermHandler wh = AEApi.instance().registries().wireless().getWirelessTerminalHandler(it); @@ -428,20 +436,19 @@ public enum GuiBridge implements IGuiHandler { final ForgeDirection side = ForgeDirection.getOrientation(ordinal & 0x07); final GuiBridge ID = values()[ordinal >> 5]; final boolean stem = ((ordinal >> 3) & 1) == 1; - final boolean xIsSlotIndex = ((ordinal >> 4) & 1) == 1; - if (ID.type.isItem()) { - ItemStack it = null; - if (stem) { - it = player.inventory.getCurrentItem(); - } else if (xIsSlotIndex && x >= 0 && x < player.inventory.mainInventory.length) { - it = player.inventory.getStackInSlot(x); - } - final Object myItem = this.getGuiObject(it, player, w, x, y, z); + final boolean pastXLimit = x >= itemGuiSlotOffset; + final int slotIndex = x - itemGuiSlotOffset; + + if (ID.type.isItem() && pastXLimit) { + final ItemStack it = stem ? player.inventory.getCurrentItem() + : getItemFromPlayerInventoryBySlotIndex(player, slotIndex); + + final Object myItem = this.getGuiObject(it, player, w, slotIndex, y, z); if (myItem != null && ID.CorrectTileOrPart(myItem)) { return ID.ConstructGui(player.inventory, side, myItem); } } - if (ID.type.isTile()) { + if (ID.type.isTile() && !pastXLimit) { final TileEntity TE = w.getTileEntity(x, y, z); if (TE instanceof IPartHost) { ((IPartHost) TE).getPart(side); @@ -482,33 +489,29 @@ public enum GuiBridge implements IGuiHandler { public boolean hasPermissions(final TileEntity te, final int x, final int y, final int z, final ForgeDirection side, final EntityPlayer player) { final World w = player.getEntityWorld(); + final boolean pastXLimit = x >= itemGuiSlotOffset; + final int slotIndex = x - itemGuiSlotOffset; if (Platform.hasPermissions( te != null ? new DimensionalCoord(te) : new DimensionalCoord(player.worldObj, x, y, z), player)) { - if (this.type.isItem()) { - final ItemStack it = player.inventory.getCurrentItem(); - if (it != null && it.getItem() instanceof IGuiItem) { - final Object myItem = ((IGuiItem) it.getItem()).getGuiObject(it, w, x, y, z); - if (this.CorrectTileOrPart(myItem)) { - return true; - } - } - } - - if (this.type.isTile()) { - final TileEntity TE = w.getTileEntity(x, y, z); - if (TE instanceof IPartHost) { - ((IPartHost) TE).getPart(side); - final IPart part = ((IPartHost) TE).getPart(side); + if (te != null && this.type.isTile()) { + if (te instanceof IPartHost host) { + host.getPart(side); + final IPart part = host.getPart(side); if (this.CorrectTileOrPart(part)) { return this.securityCheck(part, player); } } else { - if (this.CorrectTileOrPart(TE)) { - return this.securityCheck(TE, player); + if (this.CorrectTileOrPart(te)) { + return this.securityCheck(te, player); } } + } else if (this.type.isItem() && pastXLimit) { + final ItemStack it = getItemFromPlayerInventoryBySlotIndex(player, slotIndex); + if (it != null && it.getItem() instanceof IGuiItem guiItem) { + return this.CorrectTileOrPart(guiItem.getGuiObject(it, w, player, slotIndex, y, z)); + } } } return false; @@ -543,4 +546,17 @@ public enum GuiBridge implements IGuiHandler { public GuiHostType getType() { return this.type; } + + public Class getContainerClass() { + return containerClass; + } + + public static GuiBridge getGuiByContainerClass(Class cs) { + for (GuiBridge gb : GuiBridge.values()) { + if (gb.containerClass == cs) { + return gb; + } + } + return null; + } } diff --git a/src/main/java/appeng/core/sync/packets/PacketCraftRequest.java b/src/main/java/appeng/core/sync/packets/PacketCraftRequest.java index 1f3b44503..7bb1a3726 100644 --- a/src/main/java/appeng/core/sync/packets/PacketCraftRequest.java +++ b/src/main/java/appeng/core/sync/packets/PacketCraftRequest.java @@ -23,6 +23,7 @@ import appeng.api.networking.IGridNode; import appeng.api.networking.crafting.ICraftingGrid; import appeng.api.networking.crafting.ICraftingJob; import appeng.container.ContainerOpenContext; +import appeng.container.PrimaryGui; import appeng.container.implementations.ContainerCraftAmount; import appeng.container.implementations.ContainerCraftConfirm; import appeng.core.AELog; @@ -73,6 +74,7 @@ public class PacketCraftRequest extends AppEngPacket { @Override public void serverPacketData(final INetworkInfo manager, final AppEngPacket packet, final EntityPlayer player) { if (player.openContainer instanceof ContainerCraftAmount cca) { + final PrimaryGui pg = cca.getPrimaryGui(); final Object target = cca.getTarget(); if (target instanceof IGridHost gh) { final IGridNode gn = gh.getGridNode(ForgeDirection.UNKNOWN); @@ -116,6 +118,7 @@ public class PacketCraftRequest extends AppEngPacket { ccc.setAutoStart(this.heldShift && !this.heldCtrl); ccc.setAutoStartAndFollow(!this.heldShift && this.heldCtrl); ccc.setJob(futureJob); + ccc.setPrimaryGui(pg); cca.detectAndSendChanges(); } } diff --git a/src/main/java/appeng/core/sync/packets/PacketCraftingItemInterface.java b/src/main/java/appeng/core/sync/packets/PacketCraftingItemInterface.java index 072291a37..47ca420ea 100644 --- a/src/main/java/appeng/core/sync/packets/PacketCraftingItemInterface.java +++ b/src/main/java/appeng/core/sync/packets/PacketCraftingItemInterface.java @@ -6,13 +6,11 @@ import net.minecraft.client.Minecraft; import net.minecraft.client.gui.GuiScreen; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; -import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; -import appeng.api.AEApi; import appeng.api.networking.IGridHost; import appeng.api.networking.crafting.ICraftingCPU; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.util.NamedDimensionalCoord; import appeng.client.gui.implementations.GuiCraftingCPU; import appeng.container.ContainerOpenContext; @@ -23,6 +21,7 @@ import appeng.core.sync.network.INetworkInfo; import appeng.core.sync.network.NetworkHandler; import appeng.me.cluster.implementations.CraftingCPUCluster; import appeng.util.Platform; +import cpw.mods.fml.common.network.ByteBufUtils; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; import io.netty.buffer.ByteBuf; @@ -30,19 +29,42 @@ import io.netty.buffer.Unpooled; public class PacketCraftingItemInterface extends AppEngPacket { - private IAEItemStack is; + private IAEStack is; + NBTTagCompound nbt; public PacketCraftingItemInterface(final ByteBuf stream) throws IOException { - this.is = AEApi.instance().storage().readItemFromPacket(stream); + if (stream.readBoolean()) { + this.is = Platform.readStackByte(stream); + } + if (stream.readBoolean()) { + this.nbt = ByteBufUtils.readTag(stream); + } } - public PacketCraftingItemInterface(IAEItemStack is) throws IOException { + // Client -> Server + public PacketCraftingItemInterface(IAEStack is) throws IOException { this.is = is; final ByteBuf data = Unpooled.buffer(); data.writeInt(this.getPacketID()); - is.writeToPacket(data); + data.writeBoolean(true); + Platform.writeStackByte(is, data); + data.writeBoolean(false); + + this.configureWrite(data); + } + + // Server -> Client + public PacketCraftingItemInterface(NBTTagCompound nbt) throws IOException { + this.nbt = nbt; + + final ByteBuf data = Unpooled.buffer(); + + data.writeInt(this.getPacketID()); + data.writeBoolean(false); + data.writeBoolean(true); + ByteBufUtils.writeTag(data, this.nbt); this.configureWrite(data); } @@ -62,15 +84,12 @@ public class PacketCraftingItemInterface extends AppEngPacket { } if (cpu instanceof CraftingCPUCluster cpuc) { - ItemStack itemStack = is.getItemStack(); - NBTTagCompound data = Platform.openNbtData(itemStack); - NamedDimensionalCoord.writeListToNBTNamed(data, cpuc.getProviders(is)); + NBTTagCompound data = new NBTTagCompound(); + NamedDimensionalCoord.writeListToNBTNamed(data, cpuc.getProviders(this.is)); data.setInteger("ScheduledReason", cpuc.getScheduledReason(is).ordinal()); try { - NetworkHandler.instance.sendTo( - new PacketCraftingItemInterface( - AEApi.instance().storage().createItemStack(itemStack)), - (EntityPlayerMP) player); + NetworkHandler.instance + .sendTo(new PacketCraftingItemInterface(data), (EntityPlayerMP) player); } catch (Exception ignored) {} } } @@ -83,8 +102,8 @@ public class PacketCraftingItemInterface extends AppEngPacket { public void clientPacketData(final INetworkInfo network, final AppEngPacket packet, final EntityPlayer player) { final GuiScreen gs = Minecraft.getMinecraft().currentScreen; - if (gs instanceof GuiCraftingCPU) { - ((GuiCraftingCPU) gs).postUpdate(this.is); + if (gs instanceof GuiCraftingCPU guiCraftingCPU) { + guiCraftingCPU.postUpdateTooltip(this.nbt); } } } diff --git a/src/main/java/appeng/core/sync/packets/PacketInventoryAction.java b/src/main/java/appeng/core/sync/packets/PacketInventoryAction.java index 674198b1d..a5afa97b9 100644 --- a/src/main/java/appeng/core/sync/packets/PacketInventoryAction.java +++ b/src/main/java/appeng/core/sync/packets/PacketInventoryAction.java @@ -20,10 +20,8 @@ import appeng.api.storage.data.IAEItemStack; import appeng.client.ClientHelper; import appeng.container.AEBaseContainer; import appeng.container.ContainerOpenContext; +import appeng.container.PrimaryGui; import appeng.container.implementations.ContainerCraftAmount; -import appeng.container.implementations.ContainerPatternItemRenamer; -import appeng.container.implementations.ContainerPatternMulti; -import appeng.container.implementations.ContainerPatternValueAmount; import appeng.core.sync.AppEngPacket; import appeng.core.sync.GuiBridge; import appeng.core.sync.network.INetworkInfo; @@ -105,6 +103,7 @@ public class PacketInventoryAction extends AppEngPacket { public void serverPacketData(final INetworkInfo manager, final AppEngPacket packet, final EntityPlayer player) { final EntityPlayerMP sender = (EntityPlayerMP) player; if (sender.openContainer instanceof AEBaseContainer baseContainer) { + final PrimaryGui pg = baseContainer.getPrimaryGui(); if (this.action == InventoryAction.AUTO_CRAFT) { final ContainerOpenContext context = baseContainer.getOpenContext(); if (context != null) { @@ -116,9 +115,8 @@ public class PacketInventoryAction extends AppEngPacket { GuiBridge.GUI_CRAFTING_AMOUNT); if (sender.openContainer instanceof ContainerCraftAmount cca) { - + cca.setPrimaryGui(pg); if (baseContainer.getTargetStack() != null) { - cca.getCraftingItem().putStack(baseContainer.getTargetStack().getItemStack()); cca.setItemToCraft(baseContainer.getTargetStack()); cca.setInitialCraftAmount(this.id); } @@ -126,48 +124,6 @@ public class PacketInventoryAction extends AppEngPacket { cca.detectAndSendChanges(); } } - } else if (this.action == InventoryAction.SET_PATTERN_VALUE) { - final ContainerOpenContext context = baseContainer.getOpenContext(); - if (context != null) { - final TileEntity te = context.getTile(); - Platform.openGUI( - sender, - te, - baseContainer.getOpenContext().getSide(), - GuiBridge.GUI_PATTERN_VALUE_AMOUNT); - if (sender.openContainer instanceof ContainerPatternValueAmount cpv) { - if (baseContainer.getTargetStack() != null) { - cpv.setValueIndex(this.slot); - cpv.getPatternValue().putStack(baseContainer.getTargetStack().getItemStack()); - } - cpv.detectAndSendChanges(); - } - } - } else if (this.action == InventoryAction.SET_PATTERN_MULTI) { - final ContainerOpenContext context = baseContainer.getOpenContext(); - if (context != null) { - final TileEntity te = context.getTile(); - Platform.openGUI(sender, te, baseContainer.getOpenContext().getSide(), GuiBridge.GUI_PATTERN_MULTI); - if (sender.openContainer instanceof ContainerPatternMulti cpm) { - cpm.detectAndSendChanges(); - } - } - } else if (this.action == InventoryAction.RENAME_PATTERN_ITEM) { - final ContainerOpenContext context = baseContainer.getOpenContext(); - if (context != null) { - final TileEntity te = context.getTile(); - Platform.openGUI( - sender, - te, - baseContainer.getOpenContext().getSide(), - GuiBridge.GUI_PATTERN_ITEM_RENAMER); - if (sender.openContainer instanceof ContainerPatternItemRenamer cpir) { - if (baseContainer.getTargetStack() != null) { - cpir.getPatternValue().putStack(baseContainer.getTargetStack().getItemStack()); - } - cpir.detectAndSendChanges(); - } - } } else { baseContainer.doAction(sender, this.action, this.slot, this.id); } diff --git a/src/main/java/appeng/core/sync/packets/PacketMEInventoryUpdate.java b/src/main/java/appeng/core/sync/packets/PacketMEInventoryUpdate.java index 65c755920..a44a8f4bb 100644 --- a/src/main/java/appeng/core/sync/packets/PacketMEInventoryUpdate.java +++ b/src/main/java/appeng/core/sync/packets/PacketMEInventoryUpdate.java @@ -11,7 +11,6 @@ package appeng.core.sync.packets; import static appeng.util.Platform.readStackByte; -import static appeng.util.Platform.stackConvert; import static appeng.util.Platform.writeStackByte; import java.io.IOException; @@ -29,7 +28,6 @@ import net.minecraft.client.Minecraft; import net.minecraft.client.gui.GuiScreen; import net.minecraft.entity.player.EntityPlayer; -import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; import appeng.client.gui.implementations.GuiCraftConfirm; import appeng.client.gui.implementations.GuiCraftingCPU; @@ -54,7 +52,7 @@ public class PacketMEInventoryUpdate extends AppEngPacket { // input. @Nullable - private final List list; + private final List> list; // output... private final byte ref; @@ -98,11 +96,8 @@ public class PacketMEInventoryUpdate extends AppEngPacket { } gzReader.close(); - // int uncompressedBytes = uncompressed.readableBytes(); - // AELog.info( "Receiver: " + originalBytes + " -> " + uncompressedBytes ); - while (uncompressed.readableBytes() > 0) { - this.list.add(stackConvert(readStackByte(uncompressed))); + this.list.add(readStackByte(uncompressed)); } this.empty = this.list.isEmpty(); @@ -190,6 +185,10 @@ public class PacketMEInventoryUpdate extends AppEngPacket { return this.data.readableBytes(); } + public int getSize() { + return this.list.size(); + } + public boolean isEmpty() { return this.empty; } diff --git a/src/main/java/appeng/core/sync/packets/PacketMonitorableAction.java b/src/main/java/appeng/core/sync/packets/PacketMonitorableAction.java new file mode 100644 index 000000000..f925276bb --- /dev/null +++ b/src/main/java/appeng/core/sync/packets/PacketMonitorableAction.java @@ -0,0 +1,69 @@ +package appeng.core.sync.packets; + +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.entity.player.EntityPlayerMP; +import net.minecraft.tileentity.TileEntity; + +import appeng.container.ContainerOpenContext; +import appeng.container.PrimaryGui; +import appeng.container.implementations.ContainerCraftAmount; +import appeng.container.implementations.ContainerMEMonitorable; +import appeng.core.sync.AppEngPacket; +import appeng.core.sync.GuiBridge; +import appeng.core.sync.network.INetworkInfo; +import appeng.helpers.MonitorableAction; +import appeng.util.Platform; +import io.netty.buffer.ByteBuf; +import io.netty.buffer.Unpooled; + +public class PacketMonitorableAction extends AppEngPacket { + + private final MonitorableAction action; + private final int custom; + + @SuppressWarnings("unused") + public PacketMonitorableAction(final ByteBuf stream) { + this.action = MonitorableAction.values()[stream.readInt()]; + this.custom = stream.readInt(); + } + + public PacketMonitorableAction(final MonitorableAction action, final int custom) { + this.action = action; + this.custom = custom; + + final ByteBuf data = Unpooled.buffer(); + + data.writeInt(this.getPacketID()); + data.writeInt(action.ordinal()); + data.writeInt(custom); + + this.configureWrite(data); + } + + @Override + public void serverPacketData(INetworkInfo manager, AppEngPacket packet, EntityPlayer player) { + if (!(player.openContainer instanceof ContainerMEMonitorable container)) return; + + if (action == MonitorableAction.AUTO_CRAFT) { + final PrimaryGui pGui = container.getPrimaryGui(); + final ContainerOpenContext context = container.getOpenContext(); + if (context != null) { + final TileEntity te = context.getTile(); + Platform.openGUI(player, te, container.getOpenContext().getSide(), GuiBridge.GUI_CRAFTING_AMOUNT); + + if (player.openContainer instanceof ContainerCraftAmount cca) { + if (container.getTargetStack() != null) { + cca.setPrimaryGui(pGui); + cca.setItemToCraft(container.getTargetStack()); + cca.setInitialCraftAmount(1); + } + + cca.detectAndSendChanges(); + } + } + return; + } + + container.doMonitorableAction(action, custom, (EntityPlayerMP) player); + } +} diff --git a/src/main/java/appeng/core/sync/packets/PacketPatternItemRenamer.java b/src/main/java/appeng/core/sync/packets/PacketPatternItemRenamer.java deleted file mode 100644 index 5eeffdd89..000000000 --- a/src/main/java/appeng/core/sync/packets/PacketPatternItemRenamer.java +++ /dev/null @@ -1,86 +0,0 @@ -package appeng.core.sync.packets; - -import java.io.ByteArrayInputStream; -import java.io.ByteArrayOutputStream; -import java.io.DataInputStream; -import java.io.DataOutputStream; -import java.io.IOException; - -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.Slot; -import net.minecraft.item.ItemStack; -import net.minecraft.tileentity.TileEntity; - -import appeng.api.networking.IGridHost; -import appeng.container.ContainerOpenContext; -import appeng.container.implementations.ContainerPatternItemRenamer; -import appeng.core.sync.AppEngPacket; -import appeng.core.sync.GuiBridge; -import appeng.core.sync.network.INetworkInfo; -import appeng.helpers.IContainerCraftingPacket; -import appeng.util.Platform; -import io.netty.buffer.ByteBuf; -import io.netty.buffer.Unpooled; - -public class PacketPatternItemRenamer extends AppEngPacket { - - private final GuiBridge originGui; - private String name = ""; - private final int valueIndex; - - public PacketPatternItemRenamer(final ByteBuf stream) { - originGui = GuiBridge.values()[stream.readInt()]; - valueIndex = stream.readInt(); - - final DataInputStream dis = new DataInputStream( - new ByteArrayInputStream(stream.array(), stream.readerIndex(), stream.readableBytes())); - try { - name = dis.readUTF(); - } catch (IOException ignored) {} - } - - public PacketPatternItemRenamer(int originalGui, String newName, int newValueIndex) { - originGui = GuiBridge.values()[originalGui]; - name = newName; - valueIndex = newValueIndex; - - final ByteBuf data = Unpooled.buffer(); - - data.writeInt(getPacketID()); - data.writeInt(originalGui); - data.writeInt(valueIndex); - - final ByteArrayOutputStream bos = new ByteArrayOutputStream(); - final DataOutputStream dos = new DataOutputStream(bos); - - try { - dos.writeUTF(name); - } catch (IOException ignored) {} - - data.writeBytes(bos.toByteArray()); - - configureWrite(data); - } - - @Override - public void serverPacketData(INetworkInfo manager, AppEngPacket packet, EntityPlayer player) { - if (player.openContainer instanceof ContainerPatternItemRenamer cpv) { - final Object target = cpv.getTarget(); - if (target instanceof IGridHost) { - final ContainerOpenContext context = cpv.getOpenContext(); - if (context != null) { - final TileEntity te = context.getTile(); - Platform.openGUI(player, te, cpv.getOpenContext().getSide(), originGui); - if (player.openContainer instanceof IContainerCraftingPacket) { - Slot slot = player.openContainer.getSlot(valueIndex); - if (slot != null && slot.getHasStack()) { - ItemStack nextStack = slot.getStack().copy(); - nextStack.setStackDisplayName(name); - slot.putStack(nextStack); - } - } - } - } - } - } -} diff --git a/src/main/java/appeng/core/sync/packets/PacketPatternMultiSet.java b/src/main/java/appeng/core/sync/packets/PacketPatternMultiSet.java index e7b8d5faa..c9f83d155 100644 --- a/src/main/java/appeng/core/sync/packets/PacketPatternMultiSet.java +++ b/src/main/java/appeng/core/sync/packets/PacketPatternMultiSet.java @@ -1,38 +1,28 @@ package appeng.core.sync.packets; import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.tileentity.TileEntity; -import appeng.api.networking.IGridHost; -import appeng.container.ContainerOpenContext; import appeng.container.implementations.ContainerPatternMulti; import appeng.container.implementations.ContainerPatternTerm; -import appeng.container.implementations.ContainerPatternTermEx; import appeng.core.sync.AppEngPacket; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.INetworkInfo; -import appeng.util.Platform; import io.netty.buffer.ByteBuf; import io.netty.buffer.Unpooled; public class PacketPatternMultiSet extends AppEngPacket { - private final GuiBridge originGui; private final int multi; public PacketPatternMultiSet(final ByteBuf stream) { - this.originGui = GuiBridge.values()[stream.readInt()]; this.multi = stream.readInt(); } - public PacketPatternMultiSet(int originalGui, int multi) { - this.originGui = GuiBridge.values()[originalGui]; + public PacketPatternMultiSet(int multi) { this.multi = multi; final ByteBuf data = Unpooled.buffer(); data.writeInt(this.getPacketID()); - data.writeInt(originalGui); data.writeInt(this.multi); this.configureWrite(data); @@ -41,18 +31,9 @@ public class PacketPatternMultiSet extends AppEngPacket { @Override public void serverPacketData(INetworkInfo manager, AppEngPacket packet, EntityPlayer player) { if (player.openContainer instanceof ContainerPatternMulti cpv) { - final Object target = cpv.getTarget(); - if (target instanceof IGridHost) { - final ContainerOpenContext context = cpv.getOpenContext(); - if (context != null) { - final TileEntity te = context.getTile(); - Platform.openGUI(player, te, cpv.getOpenContext().getSide(), originGui); - if (player.openContainer instanceof ContainerPatternTerm cpt) { - cpt.multiplyOrDivideStacks(multi); - } else if (player.openContainer instanceof ContainerPatternTermEx cpt) { - cpt.multiplyOrDivideStacks(multi); - } - } + cpv.getPrimaryGui().open(player); + if (player.openContainer instanceof ContainerPatternTerm cpt) { + cpt.multiplyOrDivideStacks(multi); } } } diff --git a/src/main/java/appeng/core/sync/packets/PacketPatternValueSet.java b/src/main/java/appeng/core/sync/packets/PacketPatternValueSet.java index 81f36c2b3..b111e0066 100644 --- a/src/main/java/appeng/core/sync/packets/PacketPatternValueSet.java +++ b/src/main/java/appeng/core/sync/packets/PacketPatternValueSet.java @@ -1,68 +1,52 @@ package appeng.core.sync.packets; -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.Slot; -import net.minecraft.item.ItemStack; -import net.minecraft.tileentity.TileEntity; +import static appeng.util.Platform.readStackByte; +import static appeng.util.Platform.writeStackByte; -import appeng.api.networking.IGridHost; -import appeng.container.ContainerOpenContext; -import appeng.container.implementations.ContainerPatternTerm; -import appeng.container.implementations.ContainerPatternTermEx; -import appeng.container.implementations.ContainerPatternValueAmount; +import net.minecraft.entity.player.EntityPlayer; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.container.AEBaseContainer; +import appeng.container.interfaces.IVirtualSlotSource; import appeng.core.sync.AppEngPacket; -import appeng.core.sync.GuiBridge; import appeng.core.sync.network.INetworkInfo; -import appeng.util.Platform; import io.netty.buffer.ByteBuf; import io.netty.buffer.Unpooled; public class PacketPatternValueSet extends AppEngPacket { - private final GuiBridge originGui; - private final int amount; - private final int valueIndex; + private final IAEStack aes; + private final StorageName invName; + private final int slotIndex; public PacketPatternValueSet(final ByteBuf stream) { - this.originGui = GuiBridge.values()[stream.readInt()]; - this.amount = stream.readInt(); - this.valueIndex = stream.readInt(); + this.aes = readStackByte(stream); + this.invName = StorageName.values()[stream.readInt()]; + this.slotIndex = stream.readInt(); } - public PacketPatternValueSet(int originalGui, int amount, int valueIndex) { - this.originGui = GuiBridge.values()[originalGui]; - this.amount = amount; - this.valueIndex = valueIndex; + public PacketPatternValueSet(IAEStack aes, StorageName invName, int slotIndex) { + this.aes = aes; + this.invName = invName; + this.slotIndex = slotIndex; final ByteBuf data = Unpooled.buffer(); data.writeInt(this.getPacketID()); - data.writeInt(originalGui); - data.writeInt(this.amount); - data.writeInt(this.valueIndex); + writeStackByte(aes, data); + data.writeInt(invName.ordinal()); + data.writeInt(slotIndex); this.configureWrite(data); } @Override public void serverPacketData(INetworkInfo manager, AppEngPacket packet, EntityPlayer player) { - if (player.openContainer instanceof ContainerPatternValueAmount cpv) { - final Object target = cpv.getTarget(); - if (target instanceof IGridHost) { - final ContainerOpenContext context = cpv.getOpenContext(); - if (context != null) { - final TileEntity te = context.getTile(); - Platform.openGUI(player, te, cpv.getOpenContext().getSide(), originGui); - if (player.openContainer instanceof ContainerPatternTerm - || player.openContainer instanceof ContainerPatternTermEx) { - Slot slot = player.openContainer.getSlot(valueIndex); - if (slot != null && slot.getHasStack()) { - ItemStack nextStack = slot.getStack().copy(); - nextStack.stackSize = amount; - slot.putStack(nextStack); - } - } - } + if (player.openContainer instanceof AEBaseContainer bc) { + bc.getPrimaryGui().open(player); + if (player.openContainer instanceof IVirtualSlotSource vss) { + vss.updateVirtualSlot(invName, slotIndex, aes); } } } diff --git a/src/main/java/appeng/core/sync/packets/PacketPinsUpdate.java b/src/main/java/appeng/core/sync/packets/PacketPinsUpdate.java index 9eb241d99..93b0f8877 100644 --- a/src/main/java/appeng/core/sync/packets/PacketPinsUpdate.java +++ b/src/main/java/appeng/core/sync/packets/PacketPinsUpdate.java @@ -11,10 +11,11 @@ import net.minecraft.entity.player.EntityPlayerMP; import appeng.api.config.PinsState; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.core.sync.AppEngPacket; import appeng.core.sync.network.INetworkInfo; import appeng.helpers.IPinsHandler; -import appeng.util.item.AEItemStack; +import appeng.util.Platform; import io.netty.buffer.ByteBuf; import io.netty.buffer.Unpooled; @@ -22,7 +23,7 @@ public class PacketPinsUpdate extends AppEngPacket { // input. @Nullable - private final IAEItemStack[] list; + private final IAEStack[] list; @Nullable private final PinsState state; @@ -38,15 +39,15 @@ public class PacketPinsUpdate extends AppEngPacket { return; } - list = new IAEItemStack[arrLength]; + list = new IAEStack[arrLength]; for (int i = 0; i < list.length; i++) { if (stream.readBoolean()) { - list[i] = AEItemStack.loadItemStackFromPacket(stream); + list[i] = Platform.readStackByte(stream); } } } - public PacketPinsUpdate(IAEItemStack[] arr, PinsState state) throws IOException { + public PacketPinsUpdate(IAEStack[] arr, PinsState state) throws IOException { list = arr; this.state = state; @@ -57,10 +58,10 @@ public class PacketPinsUpdate extends AppEngPacket { data.writeInt(arr.length); data.writeInt(state.ordinal()); - for (IAEItemStack aeItemStack : arr) { + for (IAEStack aeItemStack : arr) { if (aeItemStack != null) { data.writeBoolean(true); - aeItemStack.writeToPacket(data); + Platform.writeStackByte(aeItemStack, data); } else { data.writeBoolean(false); } diff --git a/src/main/java/appeng/core/sync/packets/PacketSwitchGuis.java b/src/main/java/appeng/core/sync/packets/PacketSwitchGuis.java index 647682333..f80e10973 100644 --- a/src/main/java/appeng/core/sync/packets/PacketSwitchGuis.java +++ b/src/main/java/appeng/core/sync/packets/PacketSwitchGuis.java @@ -17,6 +17,9 @@ import net.minecraft.tileentity.TileEntity; import appeng.client.gui.AEBaseGui; import appeng.container.AEBaseContainer; import appeng.container.ContainerOpenContext; +import appeng.container.PrimaryGui; +import appeng.container.interfaces.IContainerSubGui; +import appeng.container.interfaces.IInventorySlotAware; import appeng.core.sync.AppEngPacket; import appeng.core.sync.GuiBridge; import appeng.core.sync.network.INetworkInfo; @@ -30,7 +33,8 @@ public class PacketSwitchGuis extends AppEngPacket { // automatic. public PacketSwitchGuis(final ByteBuf stream) { - this.newGui = GuiBridge.values()[stream.readInt()]; + if (stream.readBoolean()) this.newGui = GuiBridge.values()[stream.readInt()]; + else this.newGui = null; } // api @@ -44,7 +48,27 @@ public class PacketSwitchGuis extends AppEngPacket { final ByteBuf data = Unpooled.buffer(); data.writeInt(this.getPacketID()); - data.writeInt(newGui.ordinal()); + if (newGui != null) { + data.writeBoolean(true); + data.writeInt(newGui.ordinal()); + } else data.writeBoolean(false); + + this.configureWrite(data); + } + + // api + public PacketSwitchGuis() { + this.newGui = null; + + if (Platform.isClient()) { + AEBaseGui.setSwitchingGuis(true); + } + + final ByteBuf data = Unpooled.buffer(); + + data.writeInt(this.getPacketID()); + + data.writeBoolean(false); this.configureWrite(data); } @@ -53,10 +77,24 @@ public class PacketSwitchGuis extends AppEngPacket { public void serverPacketData(final INetworkInfo manager, final AppEngPacket packet, final EntityPlayer player) { final Container c = player.openContainer; if (c instanceof AEBaseContainer bc) { + final PrimaryGui pGui = bc.getPrimaryGui(); final ContainerOpenContext context = bc.getOpenContext(); + if (context != null) { final TileEntity te = context.getTile(); - Platform.openGUI(player, te, context.getSide(), this.newGui); + int slotIndex = te == null && bc.getTarget() instanceof IInventorySlotAware isa ? isa.getInventorySlot() + : Integer.MIN_VALUE; + + if (this.newGui == null) { + pGui.setSlotIndex(slotIndex); + pGui.open(player); + } else { + Platform.openGUI(player, te, context.getSide(), this.newGui, slotIndex); + } + } + + if (player.openContainer instanceof IContainerSubGui sg) { + sg.setPrimaryGui(pGui); } } } diff --git a/src/main/java/appeng/core/sync/packets/PacketValueConfig.java b/src/main/java/appeng/core/sync/packets/PacketValueConfig.java index 9e914eb32..9cce954af 100644 --- a/src/main/java/appeng/core/sync/packets/PacketValueConfig.java +++ b/src/main/java/appeng/core/sync/packets/PacketValueConfig.java @@ -117,6 +117,7 @@ public class PacketValueConfig extends AppEngPacket { qk.setName(this.Value); } else if (this.Name.equals("QuartzKnife.ReName") && c instanceof final ContainerRenamer qk) { qk.setNewName(this.Value); + qk.getPrimaryGui().open(player); } else if (this.Name.equals("TileSecurity.ToggleOption") && c instanceof ContainerSecurity sc) { sc.toggleSetting(this.Value, player); } else if (this.Name.equals("PriorityHost.Priority") && c instanceof ContainerPriority pc) { @@ -141,18 +142,8 @@ public class PacketValueConfig extends AppEngPacket { } } else if (this.Name.startsWith("PatternTerminalEx.") && c instanceof final ContainerPatternTermEx cpt) { switch (this.Name) { - case "PatternTerminalEx.Encode" -> { - if (this.Value.equals("2")) cpt.encodeAndMoveToInventory(false); - else if (this.Value.equals("6")) cpt.encodeAndMoveToInventory(true); - else cpt.encode(); - } - case "PatternTerminalEx.Clear" -> cpt.clear(); - case "PatternTerminalEx.Substitute" -> cpt.getPatternTerminal().setSubstitution(this.Value.equals("1")); - case "PatternTerminalEx.BeSubstitute" -> cpt.getPatternTerminal() - .setCanBeSubstitution(this.Value.equals("1")); - case "PatternTerminalEx.Invert" -> cpt.getPatternTerminal().setInverted(Value.equals("1")); - case "PatternTerminalEx.Double" -> cpt.doubleStacks(Integer.parseInt(this.Value)); - case "PatternTerminalEx.ActivePage" -> cpt.getPatternTerminal().setActivePage(Integer.parseInt(Value)); + case "PatternTerminalEx.Invert" -> cpt.getExPatternTerminal().setInverted(Value.equals("1")); + case "PatternTerminalEx.ActivePage" -> cpt.getExPatternTerminal().setActivePage(Integer.parseInt(Value)); } } else if (this.Name.startsWith("StorageBus.") && c instanceof final ContainerStorageBus ccw) { if (this.Name.equals("StorageBus.Action")) { diff --git a/src/main/java/appeng/core/sync/packets/PacketVirtualSlot.java b/src/main/java/appeng/core/sync/packets/PacketVirtualSlot.java new file mode 100644 index 000000000..a4c03284e --- /dev/null +++ b/src/main/java/appeng/core/sync/packets/PacketVirtualSlot.java @@ -0,0 +1,95 @@ +package appeng.core.sync.packets; + +import java.io.IOException; + +import net.minecraft.client.Minecraft; +import net.minecraft.entity.player.EntityPlayer; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.container.interfaces.IVirtualSlotHolder; +import appeng.core.sync.AppEngPacket; +import appeng.core.sync.network.INetworkInfo; +import appeng.util.Platform; +import io.netty.buffer.ByteBuf; +import io.netty.buffer.Unpooled; +import it.unimi.dsi.fastutil.ints.Int2ObjectMap; +import it.unimi.dsi.fastutil.ints.Int2ObjectOpenHashMap; + +public class PacketVirtualSlot extends AppEngPacket { + + final StorageName invName; + final Int2ObjectMap> slotStacks; + + public PacketVirtualSlot(final ByteBuf buf) throws IOException { + this.invName = StorageName.values()[buf.readInt()]; + this.slotStacks = new Int2ObjectOpenHashMap<>(); + + final int size = buf.readInt(); + for (int i = 0; i < size; i++) { + final int slot = buf.readInt(); + if (buf.readBoolean()) { + this.slotStacks.put(slot, Platform.readStackByte(buf)); + } else { + this.slotStacks.put(slot, null); + } + } + } + + public PacketVirtualSlot(final StorageName invName, final Int2ObjectMap> slotStacks) { + this.invName = invName; + this.slotStacks = null; + + final ByteBuf buf = Unpooled.buffer(); + buf.writeInt(this.getPacketID()); + + buf.writeInt(invName.ordinal()); + buf.writeInt(slotStacks.size()); + for (Int2ObjectMap.Entry> entry : slotStacks.int2ObjectEntrySet()) { + buf.writeInt(entry.getIntKey()); + IAEStack stack = entry.getValue(); + buf.writeBoolean(stack != null); + if (stack != null) { + Platform.writeStackByte(stack, buf); + } + } + + this.configureWrite(buf); + } + + public PacketVirtualSlot(final StorageName invName, final int slotIndex, final IAEStack stack) { + this.invName = invName; + this.slotStacks = null; + + final ByteBuf buf = Unpooled.buffer(); + buf.writeInt(this.getPacketID()); + + buf.writeInt(invName.ordinal()); + buf.writeInt(1); + buf.writeInt(slotIndex); + buf.writeBoolean(stack != null); + if (stack != null) { + Platform.writeStackByte(stack, buf); + } + + this.configureWrite(buf); + } + + @Override + public void clientPacketData(INetworkInfo network, AppEngPacket packet, EntityPlayer player) { + if (player.openContainer instanceof IVirtualSlotHolder container) { + container.receiveSlotStacks(this.invName, this.slotStacks); + return; + } + if (Minecraft.getMinecraft().currentScreen instanceof IVirtualSlotHolder container) { + container.receiveSlotStacks(this.invName, this.slotStacks); + } + } + + @Override + public void serverPacketData(INetworkInfo manager, AppEngPacket packet, EntityPlayer player) { + if (player.openContainer instanceof IVirtualSlotHolder container) { + container.receiveSlotStacks(this.invName, this.slotStacks); + } + } +} diff --git a/src/main/java/appeng/crafting/MECraftingInventory.java b/src/main/java/appeng/crafting/MECraftingInventory.java index 5ece70589..5b24d117a 100644 --- a/src/main/java/appeng/crafting/MECraftingInventory.java +++ b/src/main/java/appeng/crafting/MECraftingInventory.java @@ -15,7 +15,6 @@ import static appeng.api.storage.data.IItemList.LIST_ITEM; import static appeng.api.storage.data.IItemList.LIST_MIXED; import static appeng.util.Platform.convertStack; import static appeng.util.Platform.isAE2FCLoaded; -import static appeng.util.Platform.stackConvert; import static appeng.util.Platform.writeAEStackListNBT; import java.text.NumberFormat; @@ -284,11 +283,7 @@ public class MECraftingInventory implements IMEInventory { if (is == null) return null; if (is instanceof IAEItemStack ais) { - if (isAE2FCLoaded && ais.getItem() instanceof ItemFluidDrop) { - return (StackType) stackConvert(localFluidCache.findPrecise((IAEFluidStack) convertStack(ais))); - } else { - return (StackType) localItemCache.findPrecise((IAEItemStack) is); - } + return (StackType) localItemCache.findPrecise((IAEItemStack) is); } else { return (StackType) localFluidCache.findPrecise((IAEFluidStack) is); } diff --git a/src/main/java/appeng/helpers/ICustomButtonDataObject.java b/src/main/java/appeng/helpers/ICustomButtonDataObject.java new file mode 100644 index 000000000..d8c3d065d --- /dev/null +++ b/src/main/java/appeng/helpers/ICustomButtonDataObject.java @@ -0,0 +1,28 @@ +package appeng.helpers; + +import java.util.List; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.nbt.NBTTagCompound; + +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; +import io.netty.buffer.ByteBuf; + +public interface ICustomButtonDataObject { + + @SideOnly(Side.CLIENT) + void initCustomButtons(int guiLeft, int guiTop, int xSize, int ySize, int xOffset, int yOffset, + List buttonList); + + @SideOnly(Side.CLIENT) + boolean actionPerformedCustomButtons(final GuiButton btn); + + void readData(NBTTagCompound tag); + + void writeData(NBTTagCompound tag); + + void writeByte(ByteBuf buf); + + void readByte(ByteBuf buf); +} diff --git a/src/main/java/appeng/helpers/ICustomButtonProvider.java b/src/main/java/appeng/helpers/ICustomButtonProvider.java new file mode 100644 index 000000000..a9657f9d0 --- /dev/null +++ b/src/main/java/appeng/helpers/ICustomButtonProvider.java @@ -0,0 +1,26 @@ +package appeng.helpers; + +import java.util.List; + +import net.minecraft.client.gui.GuiButton; + +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public interface ICustomButtonProvider { + + @SideOnly(Side.CLIENT) + void initCustomButtons(int guiLeft, int guiTop, int xSize, int ySize, int xOffset, int yOffset, + List buttonList); + + @SideOnly(Side.CLIENT) + boolean actionPerformedCustomButtons(final GuiButton btn); + + void writeCustomButtonData(); + + void readCustomButtonData(); + + ICustomButtonDataObject getDataObject(); + + void setDataObject(ICustomButtonDataObject dataObject); +} diff --git a/src/main/java/appeng/helpers/ICustomButtonSource.java b/src/main/java/appeng/helpers/ICustomButtonSource.java new file mode 100644 index 000000000..620791800 --- /dev/null +++ b/src/main/java/appeng/helpers/ICustomButtonSource.java @@ -0,0 +1,6 @@ +package appeng.helpers; + +public interface ICustomButtonSource { + + ICustomButtonDataObject getCustomDataObject(ICustomButtonProvider provider); +} diff --git a/src/main/java/appeng/helpers/IPinsHandler.java b/src/main/java/appeng/helpers/IPinsHandler.java index be62e7341..35298f45f 100644 --- a/src/main/java/appeng/helpers/IPinsHandler.java +++ b/src/main/java/appeng/helpers/IPinsHandler.java @@ -1,9 +1,7 @@ package appeng.helpers; -import net.minecraft.item.ItemStack; - import appeng.api.config.PinsState; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; public interface IPinsHandler { @@ -11,19 +9,19 @@ public interface IPinsHandler { return PinsState.getPinsCount(); } - default void setPin(ItemStack is, int idx) { + default void setPin(IAEStack is, int idx) { throw new UnsupportedOperationException("setPin is not supported by this handler"); } - default void setAEPins(IAEItemStack[] pins) { + default void setAEPins(IAEStack[] pins) { throw new UnsupportedOperationException("setAEPins is not supported by this handler"); } - default ItemStack getPin(int idx) { + default IAEStack getPin(int idx) { throw new UnsupportedOperationException("getPin is not supported by this handler"); } - default IAEItemStack getAEPin(int idx) { + default IAEStack getAEPin(int idx) { throw new UnsupportedOperationException("getAEPin is not supported by this handler"); } diff --git a/src/main/java/appeng/helpers/IPrimaryGuiIconProvider.java b/src/main/java/appeng/helpers/IPrimaryGuiIconProvider.java new file mode 100644 index 000000000..a07bf23c0 --- /dev/null +++ b/src/main/java/appeng/helpers/IPrimaryGuiIconProvider.java @@ -0,0 +1,9 @@ +package appeng.helpers; + +import net.minecraft.item.ItemStack; + +public interface IPrimaryGuiIconProvider { + + ItemStack getPrimaryGuiIcon(); + +} diff --git a/src/main/java/appeng/helpers/InventoryAction.java b/src/main/java/appeng/helpers/InventoryAction.java index 34bcff042..494111c57 100644 --- a/src/main/java/appeng/helpers/InventoryAction.java +++ b/src/main/java/appeng/helpers/InventoryAction.java @@ -24,15 +24,8 @@ public enum InventoryAction { // extra... MOVE_REGION, - PICKUP_SINGLE, UPDATE_HAND, - ROLL_UP, - ROLL_DOWN, AUTO_CRAFT, PLACE_SINGLE, - SET_PATTERN_VALUE, - SET_PATTERN_MULTI, - RENAME_PATTERN_ITEM, - SET_PIN, FIND_ITEMS } diff --git a/src/main/java/appeng/helpers/MonitorableAction.java b/src/main/java/appeng/helpers/MonitorableAction.java new file mode 100644 index 000000000..e0f45a19c --- /dev/null +++ b/src/main/java/appeng/helpers/MonitorableAction.java @@ -0,0 +1,20 @@ +package appeng.helpers; + +public enum MonitorableAction { + SPLIT_OR_PLACE_SINGLE, + PICKUP_OR_SET_DOWN, + SHIFT_CLICK, + PICKUP_SINGLE, + ROLL_UP, + ROLL_DOWN, + MOVE_REGION, + AUTO_CRAFT, + CREATIVE_DUPLICATE, + SET_ITEM_PIN, + SET_CONTAINER_PIN, + UNSET_PIN, + FILL_SINGLE_CONTAINER, + FILL_CONTAINERS, + DRAIN_SINGLE_CONTAINER, + DRAIN_CONTAINERS, +} diff --git a/src/main/java/appeng/helpers/MultiCraftingTracker.java b/src/main/java/appeng/helpers/MultiCraftingTracker.java index a5eb645b8..a8fbb8b9c 100644 --- a/src/main/java/appeng/helpers/MultiCraftingTracker.java +++ b/src/main/java/appeng/helpers/MultiCraftingTracker.java @@ -10,8 +10,6 @@ package appeng.helpers; -import static appeng.util.Platform.convertStack; - import java.util.concurrent.ExecutionException; import java.util.concurrent.Future; @@ -29,6 +27,7 @@ import appeng.api.networking.crafting.ICraftingLink; import appeng.api.networking.crafting.ICraftingRequester; import appeng.api.networking.security.BaseActionSource; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.core.AELog; import appeng.util.InventoryAdaptor; @@ -74,7 +73,12 @@ public class MultiCraftingTracker { public boolean handleCrafting(final int x, final long itemToCraft, final IAEItemStack ais, final InventoryAdaptor d, final World w, final IGrid g, final ICraftingGrid cg, final BaseActionSource mySrc) { - if (ais != null && d.simulateAddStack(convertStack(ais), InsertionMode.DEFAULT) == null) { + return handleCrafting(x, itemToCraft, (IAEStack) ais, d, w, g, cg, mySrc); + } + + public boolean handleCrafting(final int x, final long itemToCraft, final IAEStack aes, final InventoryAdaptor d, + final World w, final IGrid g, final ICraftingGrid cg, final BaseActionSource mySrc) { + if (aes != null && d.simulateAddStack(aes, InsertionMode.DEFAULT) == null) { final Future craftingJob = this.getJob(x); if (this.getLink(x) != null) { @@ -102,7 +106,7 @@ public class MultiCraftingTracker { } } else { if (this.getLink(x) == null) { - final IAEItemStack aisC = ais.copy(); + final IAEStack aisC = aes.copy(); aisC.setStackSize(itemToCraft); this.setJob(x, cg.beginCraftingJob(w, g, mySrc, aisC, null)); diff --git a/src/main/java/appeng/helpers/PatternHelper.java b/src/main/java/appeng/helpers/PatternHelper.java index 02b883601..cbf1e96ce 100644 --- a/src/main/java/appeng/helpers/PatternHelper.java +++ b/src/main/java/appeng/helpers/PatternHelper.java @@ -86,6 +86,8 @@ public class PatternHelper implements ICraftingPatternDetails, Comparable itemStorage; private IWirelessAccessPoint myWap; private double sqRange = Double.MAX_VALUE; private double myRange = Double.MAX_VALUE; private final int inventorySlot; private final WirelessTerminalViewCells viewCells; private final PinsHolder pinsInv; + private final boolean infinityRange; + private final boolean infinityEnergy; public WirelessTerminalGuiObject(final IWirelessTermHandler wh, final ItemStack is, final EntityPlayer ep, final World w, final int x, final int y, final int z) { this.encryptionKey = wh.getEncryptionKey(is); + this.infinityRange = wh.hasInfinityRange(is); + this.infinityEnergy = wh.hasInfinityPower(is); this.effectiveItem = is; this.myPlayer = ep; this.wth = wh; @@ -92,16 +94,18 @@ public class WirelessTerminalGuiObject this.targetGrid = n.getGrid(); if (this.targetGrid != null) { this.sg = this.targetGrid.getCache(IStorageGrid.class); - if (this.sg != null) { - this.itemStorage = this.sg.getItemInventory(); - } } } } + + if (getItemStack().getItem() instanceof ICustomButtonSource icbs) { + customButtonDataObject = icbs.getCustomDataObject(this); + customButtonDataObject.readData(getItemStack().getTagCompound()); + } } public double getRange() { - return this.myRange; + return this.infinityRange ? 16 : this.myRange; } @Override @@ -120,116 +124,10 @@ public class WirelessTerminalGuiObject return this.sg.getFluidInventory(); } - @Override - public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { - if (this.itemStorage != null) { - this.itemStorage.addListener(l, verificationToken); - } - } - - @Override - public void removeListener(final IMEMonitorHandlerReceiver l) { - if (this.itemStorage != null) { - this.itemStorage.removeListener(l); - } - } - - @Override - public IItemList getAvailableItems(final IItemList out, int iteration) { - if (this.itemStorage != null) { - return this.itemStorage.getAvailableItems(out, iteration); - } - return out; - } - - @Override - public IAEItemStack getAvailableItem(@Nonnull IAEItemStack request, int iteration) { - if (this.itemStorage != null) { - return this.itemStorage.getAvailableItem(request, iteration); - } - return null; - } - - @Override - public IItemList getStorageList() { - if (this.itemStorage != null) { - return this.itemStorage.getStorageList(); - } - return null; - } - - @Override - public AccessRestriction getAccess() { - if (this.itemStorage != null) { - return this.itemStorage.getAccess(); - } - return AccessRestriction.NO_ACCESS; - } - - @Override - public boolean isPrioritized(final IAEItemStack input) { - if (this.itemStorage != null) { - return this.itemStorage.isPrioritized(input); - } - return false; - } - - @Override - public boolean canAccept(final IAEItemStack input) { - if (this.itemStorage != null) { - return this.itemStorage.canAccept(input); - } - return false; - } - - @Override - public int getPriority() { - if (this.itemStorage != null) { - return this.itemStorage.getPriority(); - } - return 0; - } - - @Override - public int getSlot() { - if (this.itemStorage != null) { - return this.itemStorage.getSlot(); - } - return 0; - } - - @Override - public boolean validForPass(final int i) { - return this.itemStorage.validForPass(i); - } - - @Override - public IAEItemStack injectItems(final IAEItemStack input, final Actionable type, final BaseActionSource src) { - if (this.itemStorage != null) { - return this.itemStorage.injectItems(input, type, src); - } - return input; - } - - @Override - public IAEItemStack extractItems(final IAEItemStack request, final Actionable mode, final BaseActionSource src) { - if (this.itemStorage != null) { - return this.itemStorage.extractItems(request, mode, src); - } - return null; - } - - @Override - public StorageChannel getChannel() { - if (this.itemStorage != null) { - return this.itemStorage.getChannel(); - } - return StorageChannel.ITEMS; - } - @Override public double extractAEPower(final double amt, final Actionable mode, final PowerMultiplier usePowerMultiplier) { if (this.wth != null && this.effectiveItem != null) { + if (this.infinityEnergy) return amt; if (mode == Actionable.SIMULATE) { return this.wth.hasPower(this.myPlayer, amt, this.effectiveItem) ? amt : 0; } @@ -271,32 +169,29 @@ public class WirelessTerminalGuiObject } public boolean rangeCheck() { + if (this.targetGrid == null) return false; + this.sqRange = this.myRange = Double.MAX_VALUE; - if (this.targetGrid != null && this.itemStorage != null) { - if (this.myWap != null) { - if (this.myWap.getGrid() == this.targetGrid) { - if (this.testWap(this.myWap)) { - return true; - } - } - return false; + if (this.myWap != null) { + if (this.myWap.getGrid() == this.targetGrid) { + return infinityRange || this.testWap(this.myWap); } - - final IMachineSet tw = this.targetGrid.getMachines(TileWireless.class); - - this.myWap = null; - - for (final IGridNode n : tw) { - final IWirelessAccessPoint wap = (IWirelessAccessPoint) n.getMachine(); - if (this.testWap(wap)) { - this.myWap = wap; - } - } - - return this.myWap != null; } - return false; + + final IMachineSet tw = this.targetGrid.getMachines(TileWireless.class); + + this.myWap = null; + + for (final IGridNode n : tw) { + final IWirelessAccessPoint wap = (IWirelessAccessPoint) n.getMachine(); + if (infinityRange || this.testWap(wap)) { + this.myWap = wap; + break; + } + } + + return this.myWap != null; } private boolean testWap(final IWirelessAccessPoint wap) { @@ -341,4 +236,57 @@ public class WirelessTerminalGuiObject public IGrid getGrid() { return targetGrid; } + + @Override + public GuiText getName() { + return GuiText.WirelessTerminal; + } + + public int getMode() { + return this.getItemStack().getTagCompound().getInteger("mode"); + } + + public void writeInventory() {} + + public void readInventory() {} + + @Override + public ItemStack getPrimaryGuiIcon() { + return this.effectiveItem.copy(); + } + + private ICustomButtonDataObject customButtonDataObject; + + @Override + public void writeCustomButtonData() { + this.customButtonDataObject.writeData(this.getItemStack().getTagCompound()); + } + + @Override + public void readCustomButtonData() { + this.customButtonDataObject.readData(this.getItemStack().getTagCompound()); + } + + @Override + public void initCustomButtons(int guiLeft, int guiTop, int xSize, int ySize, int xOffset, int yOffset, + List buttonList) { + if (customButtonDataObject != null) + customButtonDataObject.initCustomButtons(guiLeft, guiTop, xSize, ySize, xOffset, yOffset, buttonList); + } + + @SideOnly(Side.CLIENT) + @Override + public boolean actionPerformedCustomButtons(final GuiButton btn) { + return customButtonDataObject != null && customButtonDataObject.actionPerformedCustomButtons(btn); + } + + @Override + public ICustomButtonDataObject getDataObject() { + return customButtonDataObject; + } + + @Override + public void setDataObject(ICustomButtonDataObject dataObject) { + customButtonDataObject = dataObject; + } } diff --git a/src/main/java/appeng/integration/modules/NEI.java b/src/main/java/appeng/integration/modules/NEI.java index 02360d78e..66fbd11ee 100644 --- a/src/main/java/appeng/integration/modules/NEI.java +++ b/src/main/java/appeng/integration/modules/NEI.java @@ -34,7 +34,6 @@ import appeng.client.gui.implementations.GuiOptimizePatterns; import appeng.client.gui.implementations.GuiPatternTerm; import appeng.client.gui.implementations.GuiPatternTermEx; import appeng.client.gui.implementations.GuiSkyChest; -import appeng.client.gui.implementations.GuiWirelessTerm; import appeng.core.AEConfig; import appeng.core.AppEng; import appeng.core.features.AEFeature; @@ -134,9 +133,7 @@ public class NEI implements INEI, IContainerTooltipHandler, IIntegrationModule, // Terminal this.registerBookmarkContainerHandler .invoke(apiClass, GuiMEMonitorable.class, new NEIAETerminalBookmarkContainerHandler()); // Terminal - this.registerBookmarkContainerHandler - .invoke(apiClass, GuiWirelessTerm.class, new NEIAETerminalBookmarkContainerHandler()); // Wireless - // Terminal + this.registerBookmarkContainerHandler .invoke(apiClass, GuiPatternTerm.class, new NEIAETerminalBookmarkContainerHandler()); // Pattern // terminal diff --git a/src/main/java/appeng/integration/modules/NEIHelpers/NEISearchField.java b/src/main/java/appeng/integration/modules/NEIHelpers/NEISearchField.java index c3bae6c31..44838fd83 100644 --- a/src/main/java/appeng/integration/modules/NEIHelpers/NEISearchField.java +++ b/src/main/java/appeng/integration/modules/NEIHelpers/NEISearchField.java @@ -3,6 +3,8 @@ package appeng.integration.modules.NEIHelpers; import java.lang.reflect.Field; import java.util.function.Predicate; +import javax.annotation.Nullable; + import net.minecraft.item.ItemStack; import appeng.client.gui.widgets.MEGuiTextField; @@ -82,9 +84,17 @@ public class NEISearchField { return null; } + @Nullable + public ItemFilter getItemFilter() { + final SearchField searchField = getSearchField(); + if (searchField != null) { + return searchField.getFilter(); + } + return null; + } + public boolean focused() { final SearchField searchField = getSearchField(); - return searchField != null && searchField.focused(); } @@ -96,4 +106,8 @@ public class NEISearchField { } } + public boolean isSearchingInventory() { + return this.existsSearchField() && SearchField.searchInventories(); + } + } diff --git a/src/main/java/appeng/items/AEBaseCell.java b/src/main/java/appeng/items/AEBaseCell.java new file mode 100644 index 000000000..cc3151ffd --- /dev/null +++ b/src/main/java/appeng/items/AEBaseCell.java @@ -0,0 +1,411 @@ +package appeng.items; + +import java.text.NumberFormat; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.EnumSet; +import java.util.List; +import java.util.Locale; +import java.util.Set; +import java.util.stream.IntStream; + +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.entity.player.InventoryPlayer; +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; +import net.minecraft.util.EnumChatFormatting; +import net.minecraft.world.World; +import net.minecraftforge.common.util.ForgeDirection; +import net.minecraftforge.event.ForgeEventFactory; + +import com.google.common.base.Optional; + +import appeng.api.AEApi; +import appeng.api.config.FuzzyMode; +import appeng.api.config.IncludeExclude; +import appeng.api.definitions.IItemDefinition; +import appeng.api.exceptions.MissingDefinition; +import appeng.api.implementations.items.IItemGroup; +import appeng.api.implementations.items.IStorageCell; +import appeng.api.implementations.items.IUpgradeModule; +import appeng.api.storage.ICellHandler; +import appeng.api.storage.ICellInventoryHandler; +import appeng.api.storage.IMEInventoryHandler; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.api.storage.data.IItemList; +import appeng.core.AEConfig; +import appeng.core.features.AEFeature; +import appeng.core.localization.GuiText; +import appeng.helpers.ICellRestriction; +import appeng.items.contents.CellConfig; +import appeng.items.contents.CellConfigLegacy; +import appeng.items.contents.CellUpgrades; +import appeng.items.materials.MaterialType; +import appeng.items.storage.ItemBasicStorageCell; +import appeng.me.storage.CellInventory; +import appeng.me.storage.CellInventoryHandler; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.InventoryAdaptor; +import appeng.util.IterationCounter; +import appeng.util.Platform; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public abstract class AEBaseCell extends AEBaseItem implements IStorageCell, IItemGroup, ICellRestriction { + + protected MaterialType component; + protected long totalBytes; + protected int perType; + protected double idleDrain; + protected int totalTypes; + + @SuppressWarnings("Guava") + public AEBaseCell(final MaterialType whichCell, final long kilobytes) { + super(Optional.of(kilobytes + "k")); + + this.setFeature(EnumSet.of(AEFeature.StorageCells)); + this.setMaxStackSize(1); + this.totalBytes = kilobytes * 1024; + this.totalTypes = 63; + this.component = whichCell; + + switch (this.component) { + case Cell1kPart -> { + this.idleDrain = 0.5; + this.perType = 8; + } + case Cell4kPart -> { + this.idleDrain = 1.0; + this.perType = 32; + } + case Cell16kPart -> { + this.idleDrain = 1.5; + this.perType = 128; + } + case Cell64kPart -> { + this.idleDrain = 2.0; + this.perType = 512; + } + default -> { + this.idleDrain = 0.0; + this.perType = 8; + } + } + } + + @SuppressWarnings("Guava") + public AEBaseCell(final Optional subName) { + super(subName); + } + + public static boolean checkInvalidForLockingAndStickyCarding(ItemStack cell, ICellHandler cellHandler) { + return cellHandler == null || cell == null + || !(cell.getItem() instanceof ItemBasicStorageCell) + || (cell.getItem() instanceof ItemBasicStorageCell storageCell && storageCell.getTotalTypes(cell) == 0); + } + + public static boolean cellIsPartitioned(ICellInventoryHandler cellHandler) { + return cellHandler != null && cellHandler.getCellInv() != null + && cellHandler.getCellInv().getConfigAEInventory() != null + && IntStream.range(0, cellHandler.getCellInv().getConfigAEInventory().getSizeInventory()) + .anyMatch(i -> cellHandler.getCellInv().getConfigAEInventory().getAEStackInSlot(i) != null); + } + + @SideOnly(Side.CLIENT) + @Override + public void addCheckedInformation(final ItemStack stack, final EntityPlayer player, final List lines, + final boolean displayMoreInfo) { + final IMEInventoryHandler inventory = AEApi.instance().registries().cell() + .getCellInventory(stack, null, getStorageChannel()); + + if (!(inventory instanceof CellInventoryHandler handler)) { + return; + } + + if (!(handler.getCellInv() instanceof CellInventory cellInventory)) { + return; + } + + lines.add( + EnumChatFormatting.WHITE + NumberFormat.getInstance(Locale.ENGLISH).format(cellInventory.getUsedBytes()) + + EnumChatFormatting.GRAY + + " " + + GuiText.Of.getLocal() + + " " + + EnumChatFormatting.DARK_GREEN + + NumberFormat.getInstance().format(cellInventory.getTotalBytes()) + + " " + + EnumChatFormatting.GRAY + + GuiText.BytesUsed.getLocal()); + + lines.add( + EnumChatFormatting.WHITE + + NumberFormat.getInstance(Locale.ENGLISH).format(cellInventory.getStoredItemTypes()) + + EnumChatFormatting.GRAY + + " " + + GuiText.Of.getLocal() + + " " + + EnumChatFormatting.DARK_GREEN + + NumberFormat.getInstance().format(cellInventory.getMaxTypes()) + + " " + + EnumChatFormatting.GRAY + + GuiText.Types.getLocal()); + + if (cellInventory.getTotalItemTypes() == 1 && cellInventory.getStoredItemTypes() != 0) { + IAEStack aes = handler + .getAvailableItems(cellInventory.getChannel().createPrimitiveList(), IterationCounter.fetchNewId()) + .getFirstItem(); + lines.add(GuiText.Contains.getLocal() + ": " + aes.getDisplayName()); + } + + if (handler.isPreformatted()) { + String filter = cellInventory.getOreFilter(); + if (filter.isEmpty()) { + final String list = (handler.getIncludeExcludeMode() == IncludeExclude.WHITELIST ? GuiText.Included + : GuiText.Excluded).getLocal(); + + if (handler.isFuzzy()) { + lines.add(GuiText.Partitioned.getLocal() + " - " + list + ' ' + GuiText.Fuzzy.getLocal()); + } else { + lines.add(GuiText.Partitioned.getLocal() + " - " + list + ' ' + GuiText.Precise.getLocal()); + } + if (GuiScreen.isShiftKeyDown()) { + int usedFilters = 0; + ArrayList filtersTexts = new ArrayList<>(); + for (int i = 0; i < cellInventory.getConfigAEInventory().getSizeInventory(); ++i) { + final IAEStack s = cellInventory.getConfigAEInventory().getAEStackInSlot(i); + if (s != null) { + usedFilters++; + filtersTexts.add(s.getDisplayName()); + } + } + lines.add( + GuiText.Filter.getLocal() + " (" + + usedFilters + + "/" + + cellInventory.getConfigAEInventory().getSizeInventory() + + ")" + + ": "); + + if (!filtersTexts.isEmpty()) { + lines.addAll(filtersTexts); + } + + } + } else { + lines.add(GuiText.PartitionedOre.getLocal() + " : " + filter); + } + + if (handler.getSticky()) { + lines.add(GuiText.Sticky.getLocal()); + } + } + List restricted = handler.getRestricted(); + if (restricted != null && ((long) restricted.get(0) != 0 || (byte) restricted.get(1) != 0)) { + lines.add(GuiText.Restricted.getLocal()); + if (GuiScreen.isShiftKeyDown()) { + NumberFormat nf = NumberFormat.getNumberInstance(); + if ((long) restricted.get(0) != 0) + lines.add(GuiText.MaxItems.getLocal() + " " + nf.format((long) restricted.get(0))); + if ((byte) restricted.get(1) != 0) lines.add(GuiText.MaxTypes.getLocal() + " " + restricted.get(1)); + } + } + } + + @Override + public int getBytes(final ItemStack cellItem) { + return (int) this.totalBytes; + } + + @Override + public long getBytesLong(final ItemStack cellItem) { + return this.totalBytes; + } + + @Override + public int BytePerType(final ItemStack cell) { + return this.perType; + } + + @Override + public int getBytesPerType(final ItemStack cellItem) { + return this.perType; + } + + @Override + public int getTotalTypes(final ItemStack cellItem) { + return this.totalTypes; + } + + @Override + public boolean storableInStorageCell() { + return false; + } + + @Override + public boolean isStorageCell(final ItemStack i) { + return true; + } + + @Override + public double getIdleDrain() { + return this.idleDrain; + } + + @Override + public String getUnlocalizedGroupName(final Set others, final ItemStack is) { + return GuiText.StorageCells.getUnlocalized(); + } + + @Override + public boolean isEditable(final ItemStack is) { + return true; + } + + @Override + public IInventory getUpgradesInventory(final ItemStack is) { + return new CellUpgrades(is, 5); + } + + @Override + public IInventory getConfigInventory(final ItemStack is) { + return new CellConfigLegacy(new CellConfig(is), this.getStorageChannel()); + } + + @Override + public IAEStackInventory getConfigAEInventory(final ItemStack is) { + return new CellConfig(is); + } + + @Override + public FuzzyMode getFuzzyMode(final ItemStack is) { + return FuzzyMode.fromItemStack(is); + } + + @Override + public void setFuzzyMode(final ItemStack is, final FuzzyMode fzMode) { + Platform.openNbtData(is).setString("FuzzyMode", fzMode.name()); + } + + @Override + public String getOreFilter(ItemStack is) { + return Platform.openNbtData(is).getString("OreFilter"); + } + + @Override + public void setOreFilter(ItemStack is, String filter) { + Platform.openNbtData(is).setString("OreFilter", filter); + } + + @Override + public ItemStack onItemRightClick(final ItemStack stack, final World world, final EntityPlayer player) { + this.disassembleDrive(stack, world, player); + return stack; + } + + @SuppressWarnings({ "rawtypes", "unchecked" }) + private boolean disassembleDrive(final ItemStack stack, final World world, final EntityPlayer player) { + if (player.isSneaking()) { + if (Platform.isClient()) { + return false; + } + final InventoryPlayer playerInventory = player.inventory; + final IMEInventoryHandler inv = AEApi.instance().registries().cell() + .getCellInventory(stack, null, StorageChannel.ITEMS); + if (inv != null && playerInventory.getCurrentItem() == stack) { + final InventoryAdaptor ia = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); + final IItemList list = inv + .getAvailableItems(StorageChannel.ITEMS.createList(), IterationCounter.fetchNewId()); + if (list.isEmpty() && ia != null) { + playerInventory.setInventorySlotContents(playerInventory.currentItem, null); + + // drop core + final ItemStack extraB = ia.addItems(this.component.stack(1)); + if (extraB != null) { + player.dropPlayerItemWithRandomChoice(extraB, false); + } + + // drop upgrades + final IInventory upgradesInventory = this.getUpgradesInventory(stack); + for (int upgradeIndex = 0; upgradeIndex < upgradesInventory.getSizeInventory(); upgradeIndex++) { + final ItemStack upgradeStack = upgradesInventory.getStackInSlot(upgradeIndex); + final ItemStack leftStack = ia.addItems(upgradeStack); + if (leftStack != null && upgradeStack.getItem() instanceof IUpgradeModule) { + player.dropPlayerItemWithRandomChoice(upgradeStack, false); + } + } + + // drop empty storage cell case + for (final ItemStack storageCellStack : getStorageCellCase().maybeStack(1).asSet()) { + final ItemStack extraA = ia.addItems(storageCellStack); + if (extraA != null) { + player.dropPlayerItemWithRandomChoice(extraA, false); + } + } + + if (player.inventoryContainer != null) { + player.inventoryContainer.detectAndSendChanges(); + } + + return true; + } + } + } + return false; + } + + protected IItemDefinition getStorageCellCase() { + return AEApi.instance().definitions().materials().emptyStorageCell(); + } + + @Override + public boolean onItemUseFirst(final ItemStack stack, final EntityPlayer player, final World world, final int x, + final int y, final int z, final int side, final float hitX, final float hitY, final float hitZ) { + if (ForgeEventFactory.onItemUseStart(player, stack, 1) <= 0) return true; + + return this.disassembleDrive(stack, world, player); + } + + @Override + public ItemStack getContainerItem(final ItemStack itemStack) { + for (final ItemStack stack : AEApi.instance().definitions().materials().emptyStorageCell().maybeStack(1) + .asSet()) { + return stack; + } + + throw new MissingDefinition("Tried to use empty storage cells while basic storage cells are defined."); + } + + @Override + public boolean hasContainerItem(final ItemStack stack) { + return AEConfig.instance.isFeatureEnabled(AEFeature.EnableDisassemblyCrafting); + } + + @Override + public String getCellData(ItemStack is) { + return totalBytes + "," + + this.getTotalTypes(null) + + "," + + perType + + "," + + 8 + + "," + + Platform.openNbtData(is).getByte("cellRestrictionTypes") + + "," + + Platform.openNbtData(is).getLong("cellRestrictionAmount") + + "," + + "item"; + } + + @Override + public void setCellRestriction(ItemStack is, String newData) { + List data = Arrays.asList(newData.split(",", 2)); + Platform.openNbtData(is).setByte("cellRestrictionTypes", Byte.parseByte(data.get(0))); + Platform.openNbtData(is).setLong("cellRestrictionAmount", Long.parseLong(data.get(1))); + } + + public abstract StorageChannel getStorageChannel(); +} diff --git a/src/main/java/appeng/items/AEBaseInfiniteCell.java b/src/main/java/appeng/items/AEBaseInfiniteCell.java new file mode 100644 index 000000000..e235c34e2 --- /dev/null +++ b/src/main/java/appeng/items/AEBaseInfiniteCell.java @@ -0,0 +1,118 @@ +package appeng.items; + +import java.util.ArrayList; +import java.util.List; + +import net.minecraft.client.gui.GuiScreen; +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; + +import appeng.api.AEApi; +import appeng.api.config.FuzzyMode; +import appeng.api.implementations.items.IStorageCell; +import appeng.api.storage.ICellInventory; +import appeng.api.storage.IMEInventoryHandler; +import appeng.api.storage.data.IAEStack; +import appeng.core.localization.GuiText; +import appeng.items.contents.CellConfig; +import appeng.items.contents.CellUpgrades; +import appeng.me.storage.CellInventoryHandler; +import appeng.tile.inventory.IAEStackInventory; + +public abstract class AEBaseInfiniteCell extends AEBaseItem implements IStorageCell { + + @Override + protected void addCheckedInformation(ItemStack stack, EntityPlayer player, List lines, + boolean displayMoreInfo) { + final IMEInventoryHandler inventory = AEApi.instance().registries().cell() + .getCellInventory(stack, null, getStorageChannel()); + if (!(inventory instanceof CellInventoryHandlerhandler)) { + return; + } + ICellInventory cellInventory = handler.getCellInv(); + if (cellInventory == null) return; + + if (handler.isPreformatted()) { + lines.add(GuiText.Partitioned.getLocal()); + if (GuiScreen.isShiftKeyDown()) { + int usedFilters = 0; + ArrayList filtersTexts = new ArrayList<>(); + for (int i = 0; i < cellInventory.getConfigAEInventory().getSizeInventory(); ++i) { + final IAEStack s = cellInventory.getConfigAEInventory().getAEStackInSlot(i); + if (s != null) { + usedFilters++; + filtersTexts.add(s.getDisplayName()); + } + } + lines.add( + GuiText.Filter.getLocal() + " (" + + usedFilters + + "/" + + cellInventory.getConfigAEInventory().getSizeInventory() + + ")" + + ": "); + + if (!filtersTexts.isEmpty()) { + lines.addAll(filtersTexts); + } + + } + } + } + + @Override + public int getBytes(ItemStack cellItem) { + return 0; + } + + @Override + public long getBytesLong(ItemStack cellItem) { + return 0; + } + + @Override + public int BytePerType(ItemStack cellItem) { + return 0; + } + + @Override + public int getBytesPerType(ItemStack cellItem) { + return 0; + } + + @Override + public boolean storableInStorageCell() { + return false; + } + + @Override + public boolean isStorageCell(ItemStack i) { + return true; + } + + @Override + public double getIdleDrain() { + return 0; + } + + @Override + public IAEStackInventory getConfigAEInventory(ItemStack is) { + return new CellConfig(is); + } + + @Override + public IInventory getUpgradesInventory(ItemStack is) { + return new CellUpgrades(is, 0); + } + + @Override + public FuzzyMode getFuzzyMode(ItemStack is) { + return FuzzyMode.IGNORE_ALL; + } + + @Override + public void setFuzzyMode(ItemStack is, FuzzyMode fzMode) { + + } +} diff --git a/src/main/java/appeng/items/AEBasePortableCell.java b/src/main/java/appeng/items/AEBasePortableCell.java new file mode 100644 index 000000000..5b01b839c --- /dev/null +++ b/src/main/java/appeng/items/AEBasePortableCell.java @@ -0,0 +1,180 @@ +package appeng.items; + +import java.text.NumberFormat; +import java.util.EnumSet; +import java.util.List; +import java.util.Set; + +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; +import net.minecraft.util.EnumChatFormatting; +import net.minecraft.world.World; +import net.minecraftforge.common.util.ForgeDirection; + +import com.google.common.base.Optional; + +import appeng.api.AEApi; +import appeng.api.config.FuzzyMode; +import appeng.api.implementations.guiobjects.IGuiItem; +import appeng.api.implementations.guiobjects.IGuiItemObject; +import appeng.api.implementations.items.IItemGroup; +import appeng.api.implementations.items.IStorageCell; +import appeng.api.storage.ICellInventory; +import appeng.api.storage.StorageChannel; +import appeng.core.AEConfig; +import appeng.core.features.AEFeature; +import appeng.core.localization.GuiText; +import appeng.core.sync.GuiBridge; +import appeng.items.contents.CellConfig; +import appeng.items.contents.CellConfigLegacy; +import appeng.items.contents.CellUpgrades; +import appeng.items.contents.PortableCellViewer; +import appeng.items.tools.powered.powersink.AEBasePoweredItem; +import appeng.me.storage.CellInventoryHandler; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.Platform; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public abstract class AEBasePortableCell extends AEBasePoweredItem implements IStorageCell, IGuiItem, IItemGroup { + + public AEBasePortableCell() { + super(AEConfig.instance.portableCellBattery, Optional.absent()); + this.setFeature(EnumSet.of(AEFeature.PortableCell, AEFeature.StorageCells, AEFeature.PoweredTools)); + } + + @Override + public ItemStack onItemRightClick(final ItemStack item, final World w, final EntityPlayer player) { + Platform.openGUI(player, null, ForgeDirection.UNKNOWN, GuiBridge.GUI_PORTABLE_CELL); + return item; + } + + @SideOnly(Side.CLIENT) + @Override + public boolean isFull3D() { + return false; + } + + @SideOnly(Side.CLIENT) + @Override + public void addCheckedInformation(final ItemStack stack, final EntityPlayer player, final List lines, + final boolean displayMoreInfo) { + super.addCheckedInformation(stack, player, lines, displayMoreInfo); + + if (AEApi.instance().registries().cell() + .getCellInventory(stack, null, getStorageChannel()) instanceof CellInventoryHandlercih) { + final ICellInventory cd = cih.getCellInv(); + if (cd != null) { + lines.add( + EnumChatFormatting.WHITE + NumberFormat.getInstance().format(cd.getUsedBytes()) + + EnumChatFormatting.GRAY + + " " + + GuiText.Of.getLocal() + + " " + + EnumChatFormatting.DARK_GREEN + + cd.getTotalBytes() + + " " + + EnumChatFormatting.GRAY + + GuiText.BytesUsed.getLocal()); + lines.add( + EnumChatFormatting.WHITE + NumberFormat.getInstance().format(cd.getStoredItemTypes()) + + EnumChatFormatting.GRAY + + " " + + GuiText.Of.getLocal() + + " " + + EnumChatFormatting.DARK_GREEN + + cd.getTotalItemTypes() + + " " + + EnumChatFormatting.GRAY + + GuiText.Types.getLocal()); + } + } + } + + @Override + public int getBytes(final ItemStack cellItem) { + return 512; + } + + @Override + public int BytePerType(final ItemStack cell) { + return 8; + } + + @Override + public int getBytesPerType(final ItemStack cellItem) { + return 8; + } + + @Override + public int getTotalTypes(final ItemStack cellItem) { + return 27; + } + + @Override + public boolean storableInStorageCell() { + return false; + } + + @Override + public boolean isStorageCell(final ItemStack i) { + return true; + } + + @Override + public double getIdleDrain() { + return 0.5; + } + + @Override + public String getUnlocalizedGroupName(final Set others, final ItemStack is) { + return GuiText.StorageCells.getUnlocalized(); + } + + @Override + public boolean isEditable(final ItemStack is) { + return true; + } + + @Override + public IInventory getUpgradesInventory(final ItemStack is) { + return new CellUpgrades(is, 2); + } + + @Override + public IInventory getConfigInventory(final ItemStack is) { + return new CellConfigLegacy(new CellConfig(is), StorageChannel.ITEMS); + } + + @Override + public IAEStackInventory getConfigAEInventory(ItemStack is) { + return new CellConfig(is); + } + + @Override + public FuzzyMode getFuzzyMode(final ItemStack is) { + return FuzzyMode.fromItemStack(is); + } + + @Override + public void setFuzzyMode(final ItemStack is, final FuzzyMode fzMode) { + Platform.openNbtData(is).setString("FuzzyMode", fzMode.name()); + } + + @Override + public IGuiItemObject getGuiObject(final ItemStack is, final World w, final EntityPlayer p, final int x, + final int y, final int z) { + return new PortableCellViewer<>(is, x, getStorageChannel()); + } + + @Override + public String getOreFilter(ItemStack is) { + return Platform.openNbtData(is).getString("OreFilter"); + } + + @Override + public void setOreFilter(ItemStack is, String filter) { + Platform.openNbtData(is).setString("OreFilter", filter); + } +} diff --git a/src/main/java/appeng/items/contents/CellConfig.java b/src/main/java/appeng/items/contents/CellConfig.java index d34d319c2..6a9fd226f 100644 --- a/src/main/java/appeng/items/contents/CellConfig.java +++ b/src/main/java/appeng/items/contents/CellConfig.java @@ -12,10 +12,10 @@ package appeng.items.contents; import net.minecraft.item.ItemStack; -import appeng.tile.inventory.AppEngInternalInventory; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.Platform; -public class CellConfig extends AppEngInternalInventory { +public class CellConfig extends IAEStackInventory { private final ItemStack is; diff --git a/src/main/java/appeng/items/contents/CellConfigLegacy.java b/src/main/java/appeng/items/contents/CellConfigLegacy.java new file mode 100644 index 000000000..e962c9bee --- /dev/null +++ b/src/main/java/appeng/items/contents/CellConfigLegacy.java @@ -0,0 +1,102 @@ +package appeng.items.contents; + +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; + +import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEItemStack; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.item.AEItemStack; + +public class CellConfigLegacy implements IInventory { + + private final IAEStackInventory config; + private final StorageChannel storageChannel; + + public CellConfigLegacy(IAEStackInventory config, StorageChannel channel) { + this.config = config; + this.storageChannel = channel; + } + + @Override + public int getSizeInventory() { + return 63; + } + + @Override + public ItemStack getStackInSlot(int slotIn) { + if (this.config.getAEStackInSlot(slotIn) instanceof IAEItemStack ais) { + return ais.getItemStack(); + } + return null; + } + + @Override + public ItemStack decrStackSize(int index, int count) { + if (this.config.getAEStackInSlot(index) instanceof IAEItemStack ais) { + if (count >= ais.getStackSize()) { + this.config.putAEStackInSlot(index, null); + } else { + ais.decStackSize(count); + } + + this.markDirty(); + return ais.getItemStack(); + } + + return null; + } + + @Override + public ItemStack getStackInSlotOnClosing(int index) { + return null; + } + + @Override + public void setInventorySlotContents(int index, ItemStack stack) { + if (this.storageChannel == StorageChannel.ITEMS) { + this.config.putAEStackInSlot(index, AEItemStack.create(stack)); + } + } + + @Override + public String getInventoryName() { + return "legacy-cell-config"; + } + + @Override + public boolean hasCustomInventoryName() { + return false; + } + + @Override + public int getInventoryStackLimit() { + return 64; + } + + @Override + public void markDirty() { + this.config.markDirty(); + } + + @Override + public boolean isUseableByPlayer(EntityPlayer player) { + return true; + } + + @Override + public void openInventory() { + + } + + @Override + public void closeInventory() { + + } + + @Override + public boolean isItemValidForSlot(int index, ItemStack stack) { + return true; + } +} diff --git a/src/main/java/appeng/items/contents/CellConfigLegacyWrapper.java b/src/main/java/appeng/items/contents/CellConfigLegacyWrapper.java new file mode 100644 index 000000000..45189bb78 --- /dev/null +++ b/src/main/java/appeng/items/contents/CellConfigLegacyWrapper.java @@ -0,0 +1,65 @@ +package appeng.items.contents; + +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.item.AEItemStack; + +public class CellConfigLegacyWrapper extends IAEStackInventory { + + private final IInventory inventory; + + public CellConfigLegacyWrapper(IInventory inventory) { + super(null, 63); + this.inventory = inventory; + } + + @Override + public boolean isEmpty() { + int size = this.inventory.getSizeInventory(); + for (int i = 0; i < size; i++) { + ItemStack stack = this.inventory.getStackInSlot(i); + if (stack != null) return false; + } + return true; + } + + public IAEStack getAEStackInSlot(final int n) { + ItemStack stack = this.inventory.getStackInSlot(n); + return stack != null ? AEItemStack.create(stack) : null; + } + + public void putAEStackInSlot(final int n, IAEStack aes) { + if (aes instanceof IAEItemStack ais) { + this.inventory.setInventorySlotContents(n, ais.getItemStack()); + } else { + this.inventory.setInventorySlotContents(n, null); + } + markDirty(); + } + + public void writeToNBT(final NBTTagCompound data, final String name) { + + } + + public void readFromNBT(final NBTTagCompound data, final String name) { + + } + + public int getSizeInventory() { + return this.inventory.getSizeInventory(); + } + + public void markDirty() { + this.inventory.markDirty(); + } + + public StorageName getStorageName() { + return StorageName.NONE; + } +} diff --git a/src/main/java/appeng/items/contents/PinList.java b/src/main/java/appeng/items/contents/PinList.java new file mode 100644 index 000000000..3515992fa --- /dev/null +++ b/src/main/java/appeng/items/contents/PinList.java @@ -0,0 +1,28 @@ +package appeng.items.contents; + +import javax.annotation.Nullable; + +import appeng.api.config.PinsState; +import appeng.api.storage.data.IAEStack; + +public class PinList { + + IAEStack[] pins; + + public PinList() { + this.pins = new IAEStack[PinsState.getPinsCount()]; + } + + public int size() { + return this.pins.length; + } + + @Nullable + public IAEStack getPin(int index) { + return pins[index]; + } + + public void setPin(int index, @Nullable IAEStack pin) { + this.pins[index] = pin; + } +} diff --git a/src/main/java/appeng/items/contents/PinsHandler.java b/src/main/java/appeng/items/contents/PinsHandler.java index faec11135..b5384d184 100644 --- a/src/main/java/appeng/items/contents/PinsHandler.java +++ b/src/main/java/appeng/items/contents/PinsHandler.java @@ -7,25 +7,23 @@ import java.util.Iterator; import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayerMP; -import net.minecraft.item.ItemStack; import appeng.api.config.PinsState; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.core.AELog; import appeng.core.sync.network.NetworkHandler; import appeng.core.sync.packets.PacketPinsUpdate; -import appeng.tile.inventory.AppEngInternalAEInventory; public class PinsHandler { private final PinsHolder holder; - private final AppEngInternalAEInventory pinsInv; + private final PinList pinsInv; private PinsState pinsState; private final EntityPlayer player; private boolean needUpdate = true; - IAEItemStack[] cache = new IAEItemStack[0]; + IAEStack[] cache = new IAEStack[0]; public PinsHandler(PinsHolder holder, EntityPlayer player) { this.holder = holder; @@ -34,51 +32,54 @@ public class PinsHandler { setPinsState(this.holder.getPinsState(player)); } - public void setPin(int idx, ItemStack stack) { + public void setPin(int idx, IAEStack stack) { if (stack != null) { stack = stack.copy(); - stack.stackSize = 0; - for (int i = 0; i < pinsInv.getSizeInventory(); i++) { - if (pinsInv.getAEStackInSlot(i) != null && pinsInv.getAEStackInSlot(i).isSameType(stack)) { - pinsInv.setInventorySlotContents(i, pinsInv.getStackInSlot(idx)); // swap the pin + stack.setStackSize(0); + for (int i = 0; i < pinsInv.size(); i++) { + if (pinsInv.getPin(i) != null && pinsInv.getPin(i).isSameType(stack)) { + // pinsInv.setInventorySlotContents(i, pinsInv.getStackInSlot(idx)); // swap the pin + pinsInv.setPin(i, pinsInv.getPin(idx)); break; } } } - pinsInv.setInventorySlotContents(idx, stack); + // pinsInv.setInventorySlotContents(idx, stack); + pinsInv.setPin(idx, stack); needUpdate = true; holder.markDirty(); } - public ItemStack getPin(int idx) { - return pinsInv.getStackInSlot(idx); + public IAEStack getPin(int idx) { + return pinsInv.getPin(idx); } - public void addItemsToPins(Iterable pinsList) { - Iterator it = pinsList.iterator(); + public void addItemsToPins(Iterable> pinsList) { + Iterator> it = pinsList.iterator(); - final ArrayList checkCache = new ArrayList<>(); - for (int i = 0; i < pinsInv.getSizeInventory(); i++) { - IAEItemStack ais = pinsInv.getAEStackInSlot(i); + final ArrayList> checkCache = new ArrayList<>(); + for (int i = 0; i < pinsInv.size(); i++) { + IAEStack ais = pinsInv.getPin(i); if (ais != null) checkCache.add(ais); } - ItemStack itemStack = null; - for (int i = 0; i < pinsInv.getSizeInventory(); i++) { - IAEItemStack AEis; + IAEStack itemStack = null; + for (int i = 0; i < pinsInv.size(); i++) { + IAEStack AEis; while (itemStack == null && it.hasNext()) { AEis = it.next(); if (AEis != null && !checkCache.contains(AEis)) { - itemStack = AEis.getItemStack(); - itemStack.stackSize = 0; + itemStack = AEis.copy(); + itemStack.setStackSize(0); break; } } if (itemStack == null) break; // no more items to add - if (pinsInv.getAEStackInSlot(i) != null) continue; // skip if slot already has a item - pinsInv.setInventorySlotContents(i, itemStack); + if (pinsInv.getPin(i) != null) continue; // skip if slot already has a item + pinsInv.setPin(i, itemStack); + // pinsInv.setInventorySlotContents(i, itemStack); itemStack = null; } needUpdate = true; @@ -97,7 +98,7 @@ public class PinsHandler { } /** return an array of enabled pins, according to the current state */ - public IAEItemStack[] getEnabledPins() { + public IAEStack[] getEnabledPins() { if (needUpdate) update(); return cache; } @@ -112,10 +113,10 @@ public class PinsHandler { public void update(boolean forceSendPacket) { needUpdate = false; - final IAEItemStack[] newPins = new IAEItemStack[pinsState.ordinal() * 9]; + final IAEStack[] newPins = new IAEStack[pinsState.ordinal() * 9]; // fetch lines according to the setting for (int i = 0; i < pinsState.ordinal() * 9; i++) { - newPins[i] = pinsInv.getAEStackInSlot(i); + newPins[i] = pinsInv.getPin(i); } if (!forceSendPacket && Arrays.equals(cache, newPins)) return; cache = newPins; diff --git a/src/main/java/appeng/items/contents/PinsHolder.java b/src/main/java/appeng/items/contents/PinsHolder.java index e35f31590..a5596c701 100644 --- a/src/main/java/appeng/items/contents/PinsHolder.java +++ b/src/main/java/appeng/items/contents/PinsHolder.java @@ -12,51 +12,49 @@ import net.minecraft.nbt.NBTTagList; import appeng.api.config.PinsState; import appeng.api.storage.ITerminalPins; -import appeng.tile.inventory.AppEngInternalAEInventory; +import appeng.api.storage.data.IAEStack; import appeng.tile.inventory.IAEAppEngInventory; import appeng.tile.inventory.InvOperation; import appeng.util.Platform; +import appeng.util.item.AEItemStack; public class PinsHolder implements IAEAppEngInventory { - private final IAEAppEngInventory te; - private final ItemStack is; + private final ItemStack holder; - private final HashMap pinsMap = new HashMap<>(); + private final HashMap pinsMap = new HashMap<>(); private final HashMap pinsStateMap = new HashMap<>(); private boolean initialized = false; - public PinsHolder(final ItemStack is) { - this.is = is; - this.te = null; - this.readFromNBT(Platform.openNbtData(is), "pins"); + public PinsHolder(final ItemStack holder) { + this.holder = holder; + this.readFromNBT(Platform.openNbtData(holder), "pins"); this.initialized = true; } public PinsHolder(final ITerminalPins terminalPart) { - if (terminalPart instanceof IAEAppEngInventory _te) { - this.te = _te; - } else te = null; - is = null; + holder = null; this.initialized = true; } public void writeToNBT(final NBTTagCompound data, final String name) { final NBTTagList c = new NBTTagList(); - for (Entry entry : this.pinsMap.entrySet()) { + for (Entry entry : this.pinsMap.entrySet()) { final UUID playerId = entry.getKey(); - final AppEngInternalAEInventory pins = entry.getValue(); + final PinList pins = entry.getValue(); final NBTTagCompound itemList = new NBTTagCompound(); itemList.setString("playerId", playerId.toString()); int state = pinsStateMap.get(playerId) != null ? pinsStateMap.get(playerId).ordinal() : 0; itemList.setInteger("pinsState", state); - for (int x = 0; x < pins.getSizeInventory(); x++) { - final ItemStack pinStack = pins.getStackInSlot(x); + for (int x = 0; x < pins.size(); x++) { + // final ItemStack pinStack = pins.getStackInSlot(x); + final IAEStack pinStack = pins.getPin(x); if (pinStack != null) { - itemList.setTag("#" + x, pinStack.writeToNBT(new NBTTagCompound())); + // itemList.setTag("#" + x, pinStack.writeToNBT(new NBTTagCompound())); + itemList.setTag("#" + x, Platform.writeStackNBT(pinStack, new NBTTagCompound(), true)); } } c.appendTag(itemList); @@ -75,12 +73,20 @@ public class PinsHolder implements IAEAppEngInventory { final String playerIdStr = itemList.getString("playerId"); final UUID playerId = UUID.fromString(playerIdStr); - final AppEngInternalAEInventory pins = new AppEngInternalAEInventory(this, PinsState.getPinsCount()); + final PinList pins = new PinList(); - for (int x = 0; x < PinsState.getPinsCount(); x++) { + for (int x = 0; x < pins.size(); x++) { if (itemList.hasKey("#" + x)) { - ItemStack pinStack = ItemStack.loadItemStackFromNBT(itemList.getCompoundTag("#" + x)); - pins.setInventorySlotContents(x, pinStack); + NBTTagCompound tag = itemList.getCompoundTag("#" + x); + if (tag.hasKey("StackType")) { + IAEStack stack = Platform.readStackNBT(tag); + // pins.setInventorySlotContents(); + pins.setPin(x, stack); + } else { + ItemStack pinStack = ItemStack.loadItemStackFromNBT(itemList.getCompoundTag("#" + x)); + // pins.setInventorySlotContents(x, pinStack); + pins.setPin(x, AEItemStack.create(pinStack)); + } } } @@ -89,10 +95,10 @@ public class PinsHolder implements IAEAppEngInventory { } } - public AppEngInternalAEInventory getPinsInv(EntityPlayer player) { - AppEngInternalAEInventory pinsInv = this.pinsMap.get(player.getPersistentID()); + public PinList getPinsInv(EntityPlayer player) { + PinList pinsInv = this.pinsMap.get(player.getPersistentID()); if (pinsInv == null) { - pinsInv = new AppEngInternalAEInventory(this, PinsState.getPinsCount()); + pinsInv = new PinList(); this.pinsMap.put(player.getPersistentID(), pinsInv); } return pinsInv; @@ -108,8 +114,8 @@ public class PinsHolder implements IAEAppEngInventory { } public void markDirty() { - if (is == null || !initialized) return; - this.writeToNBT(Platform.openNbtData(is), "pins"); + if (holder == null || !initialized) return; + this.writeToNBT(Platform.openNbtData(holder), "pins"); } @Override diff --git a/src/main/java/appeng/items/contents/PortableCellViewer.java b/src/main/java/appeng/items/contents/PortableCellViewer.java index 605e6afff..a5309978e 100644 --- a/src/main/java/appeng/items/contents/PortableCellViewer.java +++ b/src/main/java/appeng/items/contents/PortableCellViewer.java @@ -21,24 +21,29 @@ import appeng.api.config.SortOrder; import appeng.api.config.ViewItems; import appeng.api.implementations.guiobjects.IPortableCell; import appeng.api.implementations.items.IAEItemPowerStorage; +import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.IMEMonitor; import appeng.api.storage.MEMonitorHandler; +import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.util.IConfigManager; -import appeng.container.interfaces.IInventorySlotAware; import appeng.me.storage.CellInventory; import appeng.util.ConfigManager; import appeng.util.Platform; -public class PortableCellViewer extends MEMonitorHandler implements IPortableCell, IInventorySlotAware { +public class PortableCellViewer> extends MEMonitorHandler + implements IPortableCell { private final ItemStack target; private final IAEItemPowerStorage ips; private final int inventorySlot; + private final StorageChannel sc; - public PortableCellViewer(final ItemStack is, final int slot) { - super(CellInventory.getCell(is, null)); + public PortableCellViewer(final ItemStack is, final int slot, StorageChannel sc) { + super((IMEInventoryHandler) CellInventory.getCell(is, null, sc)); + this.sc = sc; this.ips = (IAEItemPowerStorage) is.getItem(); this.target = is; this.inventorySlot = slot; @@ -67,11 +72,13 @@ public class PortableCellViewer extends MEMonitorHandler implement @Override public IMEMonitor getItemInventory() { - return this; + if (sc == StorageChannel.ITEMS) return (IMEMonitor) this; + return null; } @Override public IMEMonitor getFluidInventory() { + if (sc == StorageChannel.FLUIDS) return (IMEMonitor) this; return null; } diff --git a/src/main/java/appeng/items/contents/WirelessCraftingTerminalGuiObject.java b/src/main/java/appeng/items/contents/WirelessCraftingTerminalGuiObject.java new file mode 100644 index 000000000..ecab213fe --- /dev/null +++ b/src/main/java/appeng/items/contents/WirelessCraftingTerminalGuiObject.java @@ -0,0 +1,55 @@ +package appeng.items.contents; + +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.world.World; + +import appeng.api.features.IWirelessTermHandler; +import appeng.api.parts.ICraftingTerminal; +import appeng.api.util.IConfigManager; +import appeng.helpers.WirelessTerminalGuiObject; +import appeng.tile.inventory.AppEngInternalInventory; +import appeng.tile.inventory.InvOperation; + +public class WirelessCraftingTerminalGuiObject extends WirelessTerminalGuiObject implements ICraftingTerminal { + + final String nbtPrefix = "crafting"; + private final AppEngInternalInventory craftingGrid = new AppEngInternalInventory(this, 9); + + public WirelessCraftingTerminalGuiObject(IWirelessTermHandler wh, ItemStack is, EntityPlayer ep, World w, int x, + int y, int z) { + super(wh, is, ep, w, x, y, z); + readInventory(); + } + + @Override + public void readInventory() { + final NBTTagCompound tag = getItemStack().getTagCompound(); + craftingGrid.readFromNBT(tag, nbtPrefix); + } + + @Override + public void writeInventory() { + final NBTTagCompound tag = getItemStack().getTagCompound(); + craftingGrid.writeToNBT(tag, this.nbtPrefix); + } + + @Override + public void saveChanges() {} + + @Override + public void onChangeInventory(IInventory inv, int slot, InvOperation mc, ItemStack removedStack, + ItemStack newStack) { + if (mc != InvOperation.markDirty) writeInventory(); // couz spam + } + + @Override + public void updateSetting(IConfigManager manager, Enum settingName, Enum newValue) {} + + @Override + public IInventory getInventoryByName(String name) { + return this.craftingGrid; + } +} diff --git a/src/main/java/appeng/items/contents/WirelessInterfaceTerminalGuiObject.java b/src/main/java/appeng/items/contents/WirelessInterfaceTerminalGuiObject.java new file mode 100644 index 000000000..d957ecab2 --- /dev/null +++ b/src/main/java/appeng/items/contents/WirelessInterfaceTerminalGuiObject.java @@ -0,0 +1,137 @@ +package appeng.items.contents; + +import java.util.List; + +import net.minecraft.client.gui.GuiButton; +import net.minecraft.item.ItemStack; +import net.minecraftforge.common.util.ForgeDirection; + +import appeng.api.AEApi; +import appeng.api.features.ILocatable; +import appeng.api.features.IWirelessTermHandler; +import appeng.api.implementations.guiobjects.IGuiItemObject; +import appeng.api.networking.IGridHost; +import appeng.api.networking.IGridNode; +import appeng.api.networking.events.MENetworkBootingStatusChange; +import appeng.api.networking.events.MENetworkEventSubscribe; +import appeng.api.parts.IInterfaceTerminal; +import appeng.api.util.AECableType; +import appeng.container.interfaces.IInventorySlotAware; +import appeng.helpers.ICustomButtonDataObject; +import appeng.helpers.ICustomButtonProvider; +import appeng.helpers.ICustomButtonSource; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public class WirelessInterfaceTerminalGuiObject + implements IInterfaceTerminal, IGuiItemObject, ICustomButtonProvider, IInventorySlotAware { + + private boolean needsUpdate; + private final IGridNode node; + private final ItemStack is; + private final int slotIndex; + + public WirelessInterfaceTerminalGuiObject(final IWirelessTermHandler wh, final ItemStack is, final int slotIndex) { + this.is = is; + this.slotIndex = slotIndex; + + String encryptionKey = wh.getEncryptionKey(is); + ILocatable obj = null; + + try { + final long encKey = Long.parseLong(encryptionKey); + obj = AEApi.instance().registries().locatable().getLocatableBy(encKey); + } catch (final NumberFormatException err) { + // :P + } + + if (obj instanceof IGridHost gh) { + this.node = gh.getGridNode(ForgeDirection.UNKNOWN); + } else { + this.node = null; + } + + if (getItemStack().getItem() instanceof ICustomButtonSource icbs) { + customButtonDataObject = icbs.getCustomDataObject(this); + customButtonDataObject.readData(getItemStack().getTagCompound()); + } + } + + @Override + public IGridNode getActionableNode() { + return this.node; + } + + @Override + public IGridNode getGridNode(ForgeDirection dir) { + return this.node; + } + + @Override + public AECableType getCableConnectionType(ForgeDirection dir) { + return null; + } + + @Override + public void securityBreak() {} + + @Override + public boolean needsUpdate() { + boolean ret = needsUpdate; + + needsUpdate = false; + return ret; + } + + @MENetworkEventSubscribe + public void onNetworkBootingChanged(MENetworkBootingStatusChange event) { + if (!event.isBooting) { + this.needsUpdate = true; + } + } + + @Override + public ItemStack getItemStack() { + return this.is; + } + + private ICustomButtonDataObject customButtonDataObject; + + @Override + public void writeCustomButtonData() { + this.customButtonDataObject.writeData(this.getItemStack().getTagCompound()); + } + + @Override + public void readCustomButtonData() { + this.customButtonDataObject.readData(this.getItemStack().getTagCompound()); + } + + @Override + public void initCustomButtons(int guiLeft, int guiTop, int xSize, int ySize, int xOffset, int yOffset, + List buttonList) { + if (customButtonDataObject != null) + customButtonDataObject.initCustomButtons(guiLeft, guiTop, xSize, ySize, xOffset, yOffset, buttonList); + } + + @SideOnly(Side.CLIENT) + @Override + public boolean actionPerformedCustomButtons(final GuiButton btn) { + return customButtonDataObject != null && customButtonDataObject.actionPerformedCustomButtons(btn); + } + + @Override + public ICustomButtonDataObject getDataObject() { + return customButtonDataObject; + } + + @Override + public void setDataObject(ICustomButtonDataObject dataObject) { + customButtonDataObject = dataObject; + } + + @Override + public int getInventorySlot() { + return this.slotIndex; + } +} diff --git a/src/main/java/appeng/items/contents/WirelessPatternTerminalGuiObject.java b/src/main/java/appeng/items/contents/WirelessPatternTerminalGuiObject.java new file mode 100644 index 000000000..a1366e71e --- /dev/null +++ b/src/main/java/appeng/items/contents/WirelessPatternTerminalGuiObject.java @@ -0,0 +1,173 @@ +package appeng.items.contents; + +import java.util.Objects; + +import net.minecraft.entity.player.EntityPlayer; +import net.minecraft.inventory.IInventory; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.world.World; + +import appeng.api.features.IWirelessTermHandler; +import appeng.api.parts.IPatternTerminalEx; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.api.util.IConfigManager; +import appeng.helpers.WirelessTerminalGuiObject; +import appeng.tile.inventory.AppEngInternalInventory; +import appeng.tile.inventory.IAEStackInventory; +import appeng.tile.inventory.IIAEStackInventory; +import appeng.tile.inventory.InvOperation; + +public class WirelessPatternTerminalGuiObject extends WirelessTerminalGuiObject + implements IIAEStackInventory, IPatternTerminalEx { + + int craftingInvSize; + int outputInvSize; + IAEStackInventory crafting; + IAEStackInventory output; + + private final AppEngInternalInventory pattern = new AppEngInternalInventory(this, 2); + + private boolean craftingMode = true; + private boolean substitute = false; + private boolean beSubstitute = false; + private final String nbtPrefix; + + private boolean inverted; + private int activePage; + + public WirelessPatternTerminalGuiObject(IWirelessTermHandler wh, ItemStack is, EntityPlayer ep, World w, int x, + int y, int z) { + super(wh, is, ep, w, x, y, z); + this.nbtPrefix = getMode() == 2 ? "pattern" : "pattern_ex"; // ... + } + + public void setInventorySize(int inputs, int outputs) { + craftingInvSize = inputs; + outputInvSize = outputs; + } + + @Override + public void readInventory() { + crafting = new IAEStackInventory(this, craftingInvSize, StorageName.CRAFTING_INPUT); + output = new IAEStackInventory(this, outputInvSize, StorageName.CRAFTING_OUTPUT); + + final NBTTagCompound tag = getItemStack().getTagCompound().getCompoundTag(this.nbtPrefix); + this.craftingMode = tag.getBoolean("crafting"); + this.substitute = tag.getBoolean("substitute"); + this.beSubstitute = tag.getBoolean("beSubstitute"); + this.inverted = tag.getBoolean("inverted"); + this.activePage = tag.getInteger("activePage"); + this.pattern.readFromNBT(tag, "pattern"); + this.output.readFromNBT(tag, "outputList"); + this.crafting.readFromNBT(tag, "craftingGrid"); + } + + @Override + public void writeInventory() { + final NBTTagCompound tag = new NBTTagCompound(); + tag.setBoolean("crafting", this.craftingMode); + tag.setBoolean("substitute", this.substitute); + tag.setBoolean("beSubstitute", this.beSubstitute); + + if (Objects.equals(this.nbtPrefix, "pattern_ex")) { + tag.setBoolean("inverted", this.inverted); + tag.setInteger("activePage", this.activePage); + } + + this.pattern.writeToNBT(tag, "pattern"); + this.output.writeToNBT(tag, "outputList"); + this.crafting.writeToNBT(tag, "craftingGrid"); + getItemStack().getTagCompound().setTag(this.nbtPrefix, tag); + } + + @Override + public IAEStackInventory getAEInventoryByName(StorageName name) { + switch (name) { + case CRAFTING_INPUT -> { + return this.crafting; + } + case CRAFTING_OUTPUT -> { + return this.output; + } + } + return null; + } + + @Override + public boolean isInverted() { + return inverted; + } + + @Override + public void setInverted(boolean inverted) { + this.inverted = inverted; + } + + @Override + public int getActivePage() { + return this.activePage; + } + + @Override + public void setActivePage(int activePage) { + this.activePage = activePage; + } + + @Override + public boolean isCraftingRecipe() { + return this.craftingMode; + } + + @Override + public void setCraftingRecipe(boolean craftingMode) { + this.craftingMode = craftingMode; + } + + @Override + public boolean isSubstitution() { + return substitute; + } + + @Override + public boolean canBeSubstitution() { + return this.beSubstitute; + } + + @Override + public void setSubstitution(boolean canSubstitute) { + this.substitute = canSubstitute; + } + + @Override + public void setCanBeSubstitution(boolean beSubstitute) { + this.beSubstitute = beSubstitute; + } + + @Override + public IInventory getInventoryByName(final String name) { + if (name.equals("pattern")) { + return this.pattern; + } + return null; + } + + @Override + public void saveAEStackInv() { + writeInventory(); + } + + @Override + public void exPatternTerminalCall(IAEStack[] in, IAEStack[] out) {} + + @Override + public void saveChanges() {} + + @Override + public void onChangeInventory(IInventory inv, int slot, InvOperation mc, ItemStack removedStack, + ItemStack newStack) {} + + @Override + public void updateSetting(IConfigManager manager, Enum settingName, Enum newValue) {} +} diff --git a/src/main/java/appeng/items/misc/ItemEncodedPattern.java b/src/main/java/appeng/items/misc/ItemEncodedPattern.java index 76231e31e..894b916bd 100644 --- a/src/main/java/appeng/items/misc/ItemEncodedPattern.java +++ b/src/main/java/appeng/items/misc/ItemEncodedPattern.java @@ -214,7 +214,12 @@ public class ItemEncodedPattern extends AEBaseItem implements ICraftingPatternIt return null; } - SIMPLE_CACHE.put(item, out = stackConvertPacket(details.getCondensedAEOutputs()[0]).getItemStack()); + final IAEStack output = details.getCondensedAEOutputs()[0]; + out = stackConvertPacket(output).getItemStackForNEI(); + long count = output.getStackSize(); + if (out != null) out.stackSize = count > Integer.MAX_VALUE ? Integer.MAX_VALUE : (int) count; + + SIMPLE_CACHE.put(item, out); return out; } diff --git a/src/main/java/appeng/items/storage/ItemAdvancedStorageCell.java b/src/main/java/appeng/items/storage/ItemAdvancedStorageCell.java index ca691e481..5d211e417 100644 --- a/src/main/java/appeng/items/storage/ItemAdvancedStorageCell.java +++ b/src/main/java/appeng/items/storage/ItemAdvancedStorageCell.java @@ -22,6 +22,7 @@ public class ItemAdvancedStorageCell extends ItemBasicStorageCell { this.setMaxStackSize(1); this.totalBytes = kilobytes * 1024; this.component = whichCell; + this.totalTypes = 63; switch (this.component) { case Cell256kPart -> { diff --git a/src/main/java/appeng/items/storage/ItemBasicStorageCell.java b/src/main/java/appeng/items/storage/ItemBasicStorageCell.java index 37fe3652d..8b636fafa 100644 --- a/src/main/java/appeng/items/storage/ItemBasicStorageCell.java +++ b/src/main/java/appeng/items/storage/ItemBasicStorageCell.java @@ -10,405 +10,24 @@ package appeng.items.storage; -import java.text.NumberFormat; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.EnumSet; -import java.util.List; -import java.util.Locale; -import java.util.Set; -import java.util.stream.IntStream; - -import net.minecraft.client.gui.GuiScreen; -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.entity.player.InventoryPlayer; -import net.minecraft.inventory.IInventory; -import net.minecraft.item.ItemStack; -import net.minecraft.util.EnumChatFormatting; -import net.minecraft.world.World; -import net.minecraftforge.common.util.ForgeDirection; -import net.minecraftforge.event.ForgeEventFactory; - import com.google.common.base.Optional; -import appeng.api.AEApi; -import appeng.api.config.FuzzyMode; -import appeng.api.config.IncludeExclude; -import appeng.api.definitions.IItemDefinition; -import appeng.api.exceptions.MissingDefinition; -import appeng.api.implementations.items.IItemGroup; -import appeng.api.implementations.items.IStorageCell; -import appeng.api.implementations.items.IUpgradeModule; -import appeng.api.storage.ICellHandler; -import appeng.api.storage.ICellInventoryHandler; -import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.StorageChannel; -import appeng.api.storage.data.IAEItemStack; -import appeng.api.storage.data.IItemList; -import appeng.core.AEConfig; -import appeng.core.features.AEFeature; -import appeng.core.localization.GuiText; -import appeng.helpers.ICellRestriction; -import appeng.items.AEBaseItem; -import appeng.items.contents.CellConfig; -import appeng.items.contents.CellUpgrades; +import appeng.items.AEBaseCell; import appeng.items.materials.MaterialType; -import appeng.me.storage.CellInventory; -import appeng.me.storage.CellInventoryHandler; -import appeng.util.InventoryAdaptor; -import appeng.util.IterationCounter; -import appeng.util.Platform; -import appeng.util.item.ItemList; -import cpw.mods.fml.relauncher.Side; -import cpw.mods.fml.relauncher.SideOnly; -public class ItemBasicStorageCell extends AEBaseItem implements IStorageCell, IItemGroup, ICellRestriction { +public class ItemBasicStorageCell extends AEBaseCell { - protected MaterialType component; - protected long totalBytes; - protected int perType; - protected double idleDrain; - - @SuppressWarnings("Guava") - public ItemBasicStorageCell(final MaterialType whichCell, final long kilobytes) { - super(Optional.of(kilobytes + "k")); - - this.setFeature(EnumSet.of(AEFeature.StorageCells)); - this.setMaxStackSize(1); - this.totalBytes = kilobytes * 1024; - this.component = whichCell; - - switch (this.component) { - case Cell1kPart -> { - this.idleDrain = 0.5; - this.perType = 8; - } - case Cell4kPart -> { - this.idleDrain = 1.0; - this.perType = 32; - } - case Cell16kPart -> { - this.idleDrain = 1.5; - this.perType = 128; - } - case Cell64kPart -> { - this.idleDrain = 2.0; - this.perType = 512; - } - default -> { - this.idleDrain = 0.0; - this.perType = 8; - } - } + public ItemBasicStorageCell(MaterialType whichCell, long kilobytes) { + super(whichCell, kilobytes); } - @SuppressWarnings("Guava") public ItemBasicStorageCell(final Optional subName) { super(subName); } - public static boolean checkInvalidForLockingAndStickyCarding(ItemStack cell, ICellHandler cellHandler) { - return cellHandler == null || cell == null - || !(cell.getItem() instanceof ItemBasicStorageCell) - || (cell.getItem() instanceof ItemBasicStorageCell storageCell && storageCell.getTotalTypes(cell) == 0); - } - - public static boolean cellIsPartitioned(ICellInventoryHandler cellHandler) { - return cellHandler != null && cellHandler.getCellInv() != null - && cellHandler.getCellInv().getConfigInventory() != null - && IntStream.range(0, cellHandler.getCellInv().getConfigInventory().getSizeInventory()) - .anyMatch(i -> cellHandler.getCellInv().getConfigInventory().getStackInSlot(i) != null); - } - - @SideOnly(Side.CLIENT) @Override - public void addCheckedInformation(final ItemStack stack, final EntityPlayer player, final List lines, - final boolean displayMoreInfo) { - final IMEInventoryHandler inventory = AEApi.instance().registries().cell() - .getCellInventory(stack, null, StorageChannel.ITEMS); - - if (!(inventory instanceof CellInventoryHandler handler)) { - return; - } - - if (!(handler.getCellInv() instanceof CellInventory cellInventory)) { - return; - } - - lines.add( - EnumChatFormatting.WHITE + NumberFormat.getInstance(Locale.ENGLISH).format(cellInventory.getUsedBytes()) - + EnumChatFormatting.GRAY - + " " - + GuiText.Of.getLocal() - + " " - + EnumChatFormatting.DARK_GREEN - + NumberFormat.getInstance().format(cellInventory.getTotalBytes()) - + " " - + EnumChatFormatting.GRAY - + GuiText.BytesUsed.getLocal()); - - lines.add( - EnumChatFormatting.WHITE - + NumberFormat.getInstance(Locale.ENGLISH).format(cellInventory.getStoredItemTypes()) - + EnumChatFormatting.GRAY - + " " - + GuiText.Of.getLocal() - + " " - + EnumChatFormatting.DARK_GREEN - + NumberFormat.getInstance().format(cellInventory.getMaxItemTypes()) - + " " - + EnumChatFormatting.GRAY - + GuiText.Types.getLocal()); - - if (cellInventory.getTotalItemTypes() == 1 && cellInventory.getStoredItemTypes() != 0) { - ItemStack itemStack = handler.getAvailableItems(new ItemList(), IterationCounter.fetchNewId()) - .getFirstItem().getItemStack(); - lines.add(GuiText.Contains.getLocal() + ": " + itemStack.getDisplayName()); - } - - if (handler.isPreformatted()) { - String filter = cellInventory.getOreFilter(); - if (filter.isEmpty()) { - final String list = (handler.getIncludeExcludeMode() == IncludeExclude.WHITELIST ? GuiText.Included - : GuiText.Excluded).getLocal(); - - if (handler.isFuzzy()) { - lines.add(GuiText.Partitioned.getLocal() + " - " + list + ' ' + GuiText.Fuzzy.getLocal()); - } else { - lines.add(GuiText.Partitioned.getLocal() + " - " + list + ' ' + GuiText.Precise.getLocal()); - } - if (GuiScreen.isShiftKeyDown()) { - int usedFilters = 0; - ArrayList filtersTexts = new ArrayList<>(); - for (int i = 0; i < cellInventory.getConfigInventory().getSizeInventory(); ++i) { - ItemStack s = cellInventory.getConfigInventory().getStackInSlot(i); - if (s != null) { - usedFilters++; - filtersTexts.add(s.getDisplayName()); - } - } - lines.add( - GuiText.Filter.getLocal() + " (" - + usedFilters - + "/" - + cellInventory.getConfigInventory().getSizeInventory() - + ")" - + ": "); - - if (!filtersTexts.isEmpty()) { - lines.addAll(filtersTexts); - } - - } - } else { - lines.add(GuiText.PartitionedOre.getLocal() + " : " + filter); - } - - if (handler.getSticky()) { - lines.add(GuiText.Sticky.getLocal()); - } - } - List restricted = handler.getRestricted(); - if (restricted != null && ((long) restricted.get(0) != 0 || (byte) restricted.get(1) != 0)) { - lines.add(GuiText.Restricted.getLocal()); - if (GuiScreen.isShiftKeyDown()) { - NumberFormat nf = NumberFormat.getNumberInstance(); - if ((long) restricted.get(0) != 0) - lines.add(GuiText.MaxItems.getLocal() + " " + nf.format((long) restricted.get(0))); - if ((byte) restricted.get(1) != 0) lines.add(GuiText.MaxTypes.getLocal() + " " + restricted.get(1)); - } - } - } - - @Override - public int getBytes(final ItemStack cellItem) { - return (int) this.totalBytes; - } - - @Override - public long getBytesLong(final ItemStack cellItem) { - return this.totalBytes; - } - - @Override - public int BytePerType(final ItemStack cell) { - return this.perType; - } - - @Override - public int getBytesPerType(final ItemStack cellItem) { - return this.perType; - } - - @Override - public int getTotalTypes(final ItemStack cellItem) { - return 63; - } - - @Override - public boolean isBlackListed(final ItemStack cellItem, final IAEItemStack requestedAddition) { - return false; - } - - @Override - public boolean storableInStorageCell() { - return false; - } - - @Override - public boolean isStorageCell(final ItemStack i) { - return true; - } - - @Override - public double getIdleDrain() { - return this.idleDrain; - } - - @Override - public String getUnlocalizedGroupName(final Set others, final ItemStack is) { - return GuiText.StorageCells.getUnlocalized(); - } - - @Override - public boolean isEditable(final ItemStack is) { - return true; - } - - @Override - public IInventory getUpgradesInventory(final ItemStack is) { - return new CellUpgrades(is, 5); - } - - @Override - public IInventory getConfigInventory(final ItemStack is) { - return new CellConfig(is); - } - - @Override - public FuzzyMode getFuzzyMode(final ItemStack is) { - return FuzzyMode.fromItemStack(is); - } - - @Override - public void setFuzzyMode(final ItemStack is, final FuzzyMode fzMode) { - Platform.openNbtData(is).setString("FuzzyMode", fzMode.name()); - } - - @Override - public String getOreFilter(ItemStack is) { - return Platform.openNbtData(is).getString("OreFilter"); - } - - @Override - public void setOreFilter(ItemStack is, String filter) { - Platform.openNbtData(is).setString("OreFilter", filter); - } - - @Override - public ItemStack onItemRightClick(final ItemStack stack, final World world, final EntityPlayer player) { - this.disassembleDrive(stack, world, player); - return stack; - } - - @SuppressWarnings({ "rawtypes", "unchecked" }) - private boolean disassembleDrive(final ItemStack stack, final World world, final EntityPlayer player) { - if (player.isSneaking()) { - if (Platform.isClient()) { - return false; - } - final InventoryPlayer playerInventory = player.inventory; - final IMEInventoryHandler inv = AEApi.instance().registries().cell() - .getCellInventory(stack, null, StorageChannel.ITEMS); - if (inv != null && playerInventory.getCurrentItem() == stack) { - final InventoryAdaptor ia = InventoryAdaptor.getAdaptor(player, ForgeDirection.UNKNOWN); - final IItemList list = inv - .getAvailableItems(StorageChannel.ITEMS.createList(), IterationCounter.fetchNewId()); - if (list.isEmpty() && ia != null) { - playerInventory.setInventorySlotContents(playerInventory.currentItem, null); - - // drop core - final ItemStack extraB = ia.addItems(this.component.stack(1)); - if (extraB != null) { - player.dropPlayerItemWithRandomChoice(extraB, false); - } - - // drop upgrades - final IInventory upgradesInventory = this.getUpgradesInventory(stack); - for (int upgradeIndex = 0; upgradeIndex < upgradesInventory.getSizeInventory(); upgradeIndex++) { - final ItemStack upgradeStack = upgradesInventory.getStackInSlot(upgradeIndex); - final ItemStack leftStack = ia.addItems(upgradeStack); - if (leftStack != null && upgradeStack.getItem() instanceof IUpgradeModule) { - player.dropPlayerItemWithRandomChoice(upgradeStack, false); - } - } - - // drop empty storage cell case - for (final ItemStack storageCellStack : getStorageCellCase().maybeStack(1).asSet()) { - final ItemStack extraA = ia.addItems(storageCellStack); - if (extraA != null) { - player.dropPlayerItemWithRandomChoice(extraA, false); - } - } - - if (player.inventoryContainer != null) { - player.inventoryContainer.detectAndSendChanges(); - } - - return true; - } - } - } - return false; - } - - protected IItemDefinition getStorageCellCase() { - return AEApi.instance().definitions().materials().emptyStorageCell(); - } - - @Override - public boolean onItemUseFirst(final ItemStack stack, final EntityPlayer player, final World world, final int x, - final int y, final int z, final int side, final float hitX, final float hitY, final float hitZ) { - if (ForgeEventFactory.onItemUseStart(player, stack, 1) <= 0) return true; - - return this.disassembleDrive(stack, world, player); - } - - @Override - public ItemStack getContainerItem(final ItemStack itemStack) { - for (final ItemStack stack : AEApi.instance().definitions().materials().emptyStorageCell().maybeStack(1) - .asSet()) { - return stack; - } - - throw new MissingDefinition("Tried to use empty storage cells while basic storage cells are defined."); - } - - @Override - public boolean hasContainerItem(final ItemStack stack) { - return AEConfig.instance.isFeatureEnabled(AEFeature.EnableDisassemblyCrafting); - } - - @Override - public String getCellData(ItemStack is) { - return totalBytes + "," - + this.getTotalTypes(null) - + "," - + perType - + "," - + 8 - + "," - + Platform.openNbtData(is).getByte("cellRestrictionTypes") - + "," - + Platform.openNbtData(is).getLong("cellRestrictionAmount") - + "," - + "item"; - } - - @Override - public void setCellRestriction(ItemStack is, String newData) { - List data = Arrays.asList(newData.split(",", 2)); - Platform.openNbtData(is).setByte("cellRestrictionTypes", Byte.parseByte(data.get(0))); - Platform.openNbtData(is).setLong("cellRestrictionAmount", Long.parseLong(data.get(1))); + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; } } diff --git a/src/main/java/appeng/items/storage/ItemCreativeStorageCell.java b/src/main/java/appeng/items/storage/ItemCreativeStorageCell.java index 6b0b4380b..35737a440 100644 --- a/src/main/java/appeng/items/storage/ItemCreativeStorageCell.java +++ b/src/main/java/appeng/items/storage/ItemCreativeStorageCell.java @@ -12,16 +12,13 @@ package appeng.items.storage; import java.util.EnumSet; -import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; -import appeng.api.config.FuzzyMode; -import appeng.api.storage.ICellWorkbenchItem; +import appeng.api.storage.StorageChannel; import appeng.core.features.AEFeature; -import appeng.items.AEBaseItem; -import appeng.items.contents.CellConfig; +import appeng.items.AEBaseInfiniteCell; -public class ItemCreativeStorageCell extends AEBaseItem implements ICellWorkbenchItem { +public class ItemCreativeStorageCell extends AEBaseInfiniteCell { public ItemCreativeStorageCell() { this.setFeature(EnumSet.of(AEFeature.StorageCells, AEFeature.Creative)); @@ -34,28 +31,12 @@ public class ItemCreativeStorageCell extends AEBaseItem implements ICellWorkbenc } @Override - public IInventory getUpgradesInventory(final ItemStack is) { - return null; + public int getTotalTypes(ItemStack cellItem) { + return 63; } @Override - public IInventory getConfigInventory(final ItemStack is) { - return new CellConfig(is); + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; } - - @Override - public FuzzyMode getFuzzyMode(final ItemStack is) { - return FuzzyMode.IGNORE_ALL; - } - - @Override - public void setFuzzyMode(final ItemStack is, final FuzzyMode fzMode) {} - - @Override - public String getOreFilter(ItemStack is) { - return ""; - } - - @Override - public void setOreFilter(ItemStack is, String filter) {} } diff --git a/src/main/java/appeng/items/storage/ItemExtremeStorageCell.java b/src/main/java/appeng/items/storage/ItemExtremeStorageCell.java index 240037287..45edd4824 100644 --- a/src/main/java/appeng/items/storage/ItemExtremeStorageCell.java +++ b/src/main/java/appeng/items/storage/ItemExtremeStorageCell.java @@ -12,8 +12,6 @@ import appeng.core.features.AEFeature; public class ItemExtremeStorageCell extends ItemBasicStorageCell { - protected final int totalTypes; - @SuppressWarnings("Guava") public ItemExtremeStorageCell(String name, long bytes, int types, int perType, double drain) { super(Optional.of(name)); @@ -25,11 +23,6 @@ public class ItemExtremeStorageCell extends ItemBasicStorageCell { this.idleDrain = drain; } - @Override - public int getTotalTypes(final ItemStack cellItem) { - return totalTypes; - } - @Override public ItemStack onItemRightClick(final ItemStack stack, final World world, final EntityPlayer player) { return stack; diff --git a/src/main/java/appeng/items/storage/ItemViewCell.java b/src/main/java/appeng/items/storage/ItemViewCell.java index 72642b61f..b962793e7 100644 --- a/src/main/java/appeng/items/storage/ItemViewCell.java +++ b/src/main/java/appeng/items/storage/ItemViewCell.java @@ -25,16 +25,19 @@ import appeng.api.config.FuzzyMode; import appeng.api.config.Upgrades; import appeng.api.implementations.items.IUpgradeModule; import appeng.api.storage.ICellWorkbenchItem; +import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.core.features.AEFeature; import appeng.core.localization.ButtonToolTips; import appeng.core.localization.GuiText; import appeng.items.AEBaseItem; import appeng.items.contents.CellConfig; +import appeng.items.contents.CellConfigLegacy; import appeng.items.contents.CellUpgrades; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.Platform; -import appeng.util.item.AEItemStack; import appeng.util.prioitylist.FuzzyPriorityList; import appeng.util.prioitylist.IPartitionList; import appeng.util.prioitylist.MergedPriorityList; @@ -43,6 +46,7 @@ import appeng.util.prioitylist.PrecisePriorityList; public class ItemViewCell extends AEBaseItem implements ICellWorkbenchItem { + // TODO idk how deal with this public ItemViewCell() { this.setFeature(EnumSet.of(AEFeature.Core)); this.setMaxStackSize(1); @@ -61,7 +65,7 @@ public class ItemViewCell extends AEBaseItem implements ICellWorkbenchItem { if ((currentViewCell.getItem() instanceof ItemViewCell vc)) { if (!vc.getViewMode(currentViewCell)) continue; final IInventory upgrades = vc.getUpgradesInventory(currentViewCell); - final IInventory config = vc.getConfigInventory(currentViewCell); + final IAEStackInventory config = vc.getConfigAEInventory(currentViewCell); final FuzzyMode fzMode = vc.getFuzzyMode(currentViewCell); final String filter = vc.getOreFilter(currentViewCell); @@ -86,20 +90,20 @@ public class ItemViewCell extends AEBaseItem implements ICellWorkbenchItem { if (hasOreFilter && !filter.isEmpty()) { myMergedList.addNewList(new OreFilteredList(filter), !hasInverter); } else { - final IItemList priorityList = AEApi.instance().storage().createItemList(); + final IItemList priorityList = AEApi.instance().storage().createAEStackList(); for (int x = 0; x < config.getSizeInventory(); x++) { - final ItemStack is = config.getStackInSlot(x); - if (is != null) { - priorityList.add(AEItemStack.create(is)); + final IAEStack aes = config.getAEStackInSlot(x); + if (aes != null) { + priorityList.add(aes); } } if (!priorityList.isEmpty()) { if (hasFuzzy) { - myMergedList.addNewList(new FuzzyPriorityList<>(priorityList, fzMode), !hasInverter); + myMergedList.addNewList(new FuzzyPriorityList(priorityList, fzMode), !hasInverter); } else { - myMergedList.addNewList(new PrecisePriorityList<>(priorityList), !hasInverter); + myMergedList.addNewList(new PrecisePriorityList(priorityList), !hasInverter); } } } @@ -130,6 +134,11 @@ public class ItemViewCell extends AEBaseItem implements ICellWorkbenchItem { @Override public IInventory getConfigInventory(final ItemStack is) { + return new CellConfigLegacy(new CellConfig(is), StorageChannel.ITEMS); + } + + @Override + public IAEStackInventory getConfigAEInventory(ItemStack is) { return new CellConfig(is); } @@ -178,4 +187,9 @@ public class ItemViewCell extends AEBaseItem implements ICellWorkbenchItem { String filter = getOreFilter(stack); if (!filter.isEmpty()) lines.add(GuiText.PartitionedOre.getLocal() + " : " + filter); } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } } diff --git a/src/main/java/appeng/items/storage/ItemVoidStorageCell.java b/src/main/java/appeng/items/storage/ItemVoidStorageCell.java index 1514affbd..2b0d79587 100644 --- a/src/main/java/appeng/items/storage/ItemVoidStorageCell.java +++ b/src/main/java/appeng/items/storage/ItemVoidStorageCell.java @@ -11,12 +11,17 @@ import net.minecraft.item.ItemStack; import appeng.api.config.FuzzyMode; import appeng.api.config.IncludeExclude; import appeng.api.storage.ICellWorkbenchItem; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEStack; import appeng.core.features.AEFeature; import appeng.core.localization.GuiText; import appeng.items.AEBaseItem; import appeng.items.contents.CellConfig; +import appeng.items.contents.CellConfigLegacy; import appeng.items.contents.CellUpgrades; +import appeng.me.storage.CellInventoryHandler; import appeng.me.storage.VoidCellInventory; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; @@ -34,9 +39,10 @@ public class ItemVoidStorageCell extends AEBaseItem implements ICellWorkbenchIte final boolean displayMoreInfo) { lines.add(GuiText.VoidCellTooltip.getLocal()); lines.add(0 + " " + GuiText.Of.getLocal() + " \u00A7k9999\u00A77 " + GuiText.BytesUsed.getLocal()); - VoidCellInventory inv = (VoidCellInventory) VoidCellInventory.getCell(stack); - if (inv != null && stack.getItem() instanceof ItemVoidStorageCell cell) { - if (inv.isPreformatted()) { + if (stack.getItem() instanceof ItemVoidStorageCell cell) { + CellInventoryHandler inv = (CellInventoryHandler) VoidCellInventory + .getCell(stack, cell.getStorageChannel()); + if (inv != null && inv.isPreformatted()) { String filter = cell.getOreFilter(stack); if (filter.isEmpty()) { final String list = (inv.getWhitelist() == IncludeExclude.WHITELIST ? GuiText.Included @@ -48,8 +54,8 @@ public class ItemVoidStorageCell extends AEBaseItem implements ICellWorkbenchIte } if (GuiScreen.isShiftKeyDown()) { lines.add(GuiText.Filter.getLocal() + ": "); - for (int i = 0; i < cell.getConfigInventory(stack).getSizeInventory(); ++i) { - ItemStack s = cell.getConfigInventory(stack).getStackInSlot(i); + for (int i = 0; i < cell.getConfigAEInventory(stack).getSizeInventory(); ++i) { + final IAEStack s = cell.getConfigAEInventory(stack).getAEStackInSlot(i); if (s != null) lines.add(s.getDisplayName()); } } @@ -75,6 +81,11 @@ public class ItemVoidStorageCell extends AEBaseItem implements ICellWorkbenchIte @Override public IInventory getConfigInventory(ItemStack is) { + return new CellConfigLegacy(new CellConfig(is), StorageChannel.ITEMS); + } + + @Override + public IAEStackInventory getConfigAEInventory(ItemStack is) { return new CellConfig(is); } @@ -97,4 +108,9 @@ public class ItemVoidStorageCell extends AEBaseItem implements ICellWorkbenchIte public void setOreFilter(ItemStack is, String filter) { Platform.openNbtData(is).setString("OreFilter", filter); } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } } diff --git a/src/main/java/appeng/items/tools/ToolNetworkTool.java b/src/main/java/appeng/items/tools/ToolNetworkTool.java index ac3c79606..1473f3e0a 100644 --- a/src/main/java/appeng/items/tools/ToolNetworkTool.java +++ b/src/main/java/appeng/items/tools/ToolNetworkTool.java @@ -67,7 +67,8 @@ public class ToolNetworkTool extends AEBaseItem } @Override - public IGuiItemObject getGuiObject(final ItemStack is, final World world, final int x, final int y, final int z) { + public IGuiItemObject getGuiObject(final ItemStack is, final World world, final EntityPlayer p, final int x, + final int y, final int z) { final TileEntity te = world.getTileEntity(x, y, z); return new NetworkToolViewer(is, (IGridHost) (te instanceof IGridHost ? te : null), getInventorySize()); } diff --git a/src/main/java/appeng/items/tools/ToolPriorityCard.java b/src/main/java/appeng/items/tools/ToolPriorityCard.java index 30587ec3c..ff35f2005 100644 --- a/src/main/java/appeng/items/tools/ToolPriorityCard.java +++ b/src/main/java/appeng/items/tools/ToolPriorityCard.java @@ -67,7 +67,8 @@ public class ToolPriorityCard extends AEBaseItem implements IGuiItem { } @Override - public IGuiItemObject getGuiObject(final ItemStack is, final World world, final int x, final int y, final int z) { + public IGuiItemObject getGuiObject(final ItemStack is, final World world, EntityPlayer p, final int x, final int y, + final int z) { return new PriorityCardObject(is, x); } diff --git a/src/main/java/appeng/items/tools/powered/ToolColorApplicator.java b/src/main/java/appeng/items/tools/powered/ToolColorApplicator.java index 82b91b2ea..7c3444787 100644 --- a/src/main/java/appeng/items/tools/powered/ToolColorApplicator.java +++ b/src/main/java/appeng/items/tools/powered/ToolColorApplicator.java @@ -45,6 +45,7 @@ import appeng.api.storage.ICellInventoryHandler; import appeng.api.storage.IMEInventory; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.api.util.AEColor; import appeng.api.util.DimensionalCoord; @@ -58,10 +59,12 @@ import appeng.helpers.IMouseWheelItem; import appeng.hooks.DispenserBlockTool; import appeng.hooks.IBlockTool; import appeng.items.contents.CellConfig; +import appeng.items.contents.CellConfigLegacy; import appeng.items.contents.CellUpgrades; import appeng.items.misc.ItemPaintBall; import appeng.items.tools.powered.powersink.AEBasePoweredItem; import appeng.me.storage.CellInventoryHandler; +import appeng.tile.inventory.IAEStackInventory; import appeng.tile.misc.TilePaint; import appeng.util.ItemSorters; import appeng.util.IterationCounter; @@ -420,9 +423,9 @@ public class ToolColorApplicator extends AEBasePoweredItem } @Override - public boolean isBlackListed(final ItemStack cellItem, final IAEItemStack requestedAddition) { - if (requestedAddition != null) { - final int[] id = OreDictionary.getOreIDs(requestedAddition.getItemStack()); + public boolean isBlackListed(final IAEStack requestedAddition) { + if (requestedAddition instanceof IAEItemStack ais) { + final int[] id = OreDictionary.getOreIDs(ais.getItemStack()); for (final int x : id) { if (ORE_TO_COLOR.containsKey(x)) { @@ -430,11 +433,11 @@ public class ToolColorApplicator extends AEBasePoweredItem } } - if (requestedAddition.getItem() instanceof ItemSnowball) { + if (ais.getItem() instanceof ItemSnowball) { return false; } - return !(requestedAddition.getItem() instanceof ItemPaintBall && requestedAddition.getItemDamage() < 20); + return !(ais.getItem() instanceof ItemPaintBall && ais.getItemDamage() < 20); } return true; } @@ -470,7 +473,13 @@ public class ToolColorApplicator extends AEBasePoweredItem } @Override + @Deprecated public IInventory getConfigInventory(final ItemStack is) { + return new CellConfigLegacy(new CellConfig(is), StorageChannel.ITEMS); + } + + @Override + public IAEStackInventory getConfigAEInventory(ItemStack is) { return new CellConfig(is); } @@ -498,4 +507,9 @@ public class ToolColorApplicator extends AEBasePoweredItem public void setOreFilter(ItemStack is, String filter) { Platform.openNbtData(is).setString("OreFilter", filter); } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } } diff --git a/src/main/java/appeng/items/tools/powered/ToolMassCannon.java b/src/main/java/appeng/items/tools/powered/ToolMassCannon.java index 68f396dd9..25ca2c2ec 100644 --- a/src/main/java/appeng/items/tools/powered/ToolMassCannon.java +++ b/src/main/java/appeng/items/tools/powered/ToolMassCannon.java @@ -63,10 +63,12 @@ import appeng.hooks.DispenserMatterCannon; import appeng.hooks.TickHandler; import appeng.hooks.TickHandler.PlayerColor; import appeng.items.contents.CellConfig; +import appeng.items.contents.CellConfigLegacy; import appeng.items.contents.CellUpgrades; import appeng.items.misc.ItemPaintBall; import appeng.items.tools.powered.powersink.AEBasePoweredItem; import appeng.me.storage.CellInventoryHandler; +import appeng.tile.inventory.IAEStackInventory; import appeng.tile.misc.TilePaint; import appeng.util.IterationCounter; import appeng.util.Platform; @@ -442,6 +444,11 @@ public class ToolMassCannon extends AEBasePoweredItem implements IStorageCell { @Override public IInventory getConfigInventory(final ItemStack is) { + return new CellConfigLegacy(new CellConfig(is), StorageChannel.ITEMS); + } + + @Override + public IAEStackInventory getConfigAEInventory(ItemStack is) { return new CellConfig(is); } @@ -476,13 +483,15 @@ public class ToolMassCannon extends AEBasePoweredItem implements IStorageCell { } @Override - public boolean isBlackListed(final ItemStack cellItem, final IAEItemStack requestedAddition) { - final float pen = AEApi.instance().registries().matterCannon().getPenetration(requestedAddition.getItemStack()); - if (pen > 0) { - return false; + public boolean isBlackListed(final IAEStack requestedAddition) { + if (requestedAddition instanceof IAEItemStack ais) { + final float pen = AEApi.instance().registries().matterCannon().getPenetration(ais.getItemStack()); + if (pen > 0) { + return false; + } + return !(ais.getItem() instanceof ItemPaintBall); } - - return !(requestedAddition.getItem() instanceof ItemPaintBall); + return false; } @Override @@ -509,4 +518,9 @@ public class ToolMassCannon extends AEBasePoweredItem implements IStorageCell { public void setOreFilter(ItemStack is, String filter) { Platform.openNbtData(is).setString("OreFilter", filter); } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } } diff --git a/src/main/java/appeng/items/tools/powered/ToolPortableCell.java b/src/main/java/appeng/items/tools/powered/ToolPortableCell.java index cc5e8a19a..24232c533 100644 --- a/src/main/java/appeng/items/tools/powered/ToolPortableCell.java +++ b/src/main/java/appeng/items/tools/powered/ToolPortableCell.java @@ -10,176 +10,13 @@ package appeng.items.tools.powered; -import java.util.EnumSet; -import java.util.List; -import java.util.Set; - -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.IInventory; -import net.minecraft.item.ItemStack; -import net.minecraft.world.World; -import net.minecraftforge.common.util.ForgeDirection; - -import com.google.common.base.Optional; - -import appeng.api.AEApi; -import appeng.api.config.FuzzyMode; -import appeng.api.implementations.guiobjects.IGuiItem; -import appeng.api.implementations.guiobjects.IGuiItemObject; -import appeng.api.implementations.items.IItemGroup; -import appeng.api.implementations.items.IStorageCell; -import appeng.api.storage.ICellInventory; -import appeng.api.storage.ICellInventoryHandler; -import appeng.api.storage.IMEInventory; import appeng.api.storage.StorageChannel; -import appeng.api.storage.data.IAEItemStack; -import appeng.core.AEConfig; -import appeng.core.features.AEFeature; -import appeng.core.localization.GuiText; -import appeng.core.sync.GuiBridge; -import appeng.items.contents.CellConfig; -import appeng.items.contents.CellUpgrades; -import appeng.items.contents.PortableCellViewer; -import appeng.items.tools.powered.powersink.AEBasePoweredItem; -import appeng.me.storage.CellInventoryHandler; -import appeng.util.Platform; -import cpw.mods.fml.relauncher.Side; -import cpw.mods.fml.relauncher.SideOnly; +import appeng.items.AEBasePortableCell; -public class ToolPortableCell extends AEBasePoweredItem implements IStorageCell, IGuiItem, IItemGroup { - - public ToolPortableCell() { - super(AEConfig.instance.portableCellBattery, Optional.absent()); - this.setFeature(EnumSet.of(AEFeature.PortableCell, AEFeature.StorageCells, AEFeature.PoweredTools)); - } +public class ToolPortableCell extends AEBasePortableCell { @Override - public ItemStack onItemRightClick(final ItemStack item, final World w, final EntityPlayer player) { - Platform.openGUI(player, null, ForgeDirection.UNKNOWN, GuiBridge.GUI_PORTABLE_CELL); - return item; - } - - @SideOnly(Side.CLIENT) - @Override - public boolean isFull3D() { - return false; - } - - @SideOnly(Side.CLIENT) - @Override - public void addCheckedInformation(final ItemStack stack, final EntityPlayer player, final List lines, - final boolean displayMoreInfo) { - super.addCheckedInformation(stack, player, lines, displayMoreInfo); - - final IMEInventory cdi = AEApi.instance().registries().cell() - .getCellInventory(stack, null, StorageChannel.ITEMS); - - if (cdi instanceof CellInventoryHandler) { - final ICellInventory cd = ((ICellInventoryHandler) cdi).getCellInv(); - if (cd != null) { - lines.add( - cd.getUsedBytes() + " " - + GuiText.Of.getLocal() - + ' ' - + cd.getTotalBytes() - + ' ' - + GuiText.BytesUsed.getLocal()); - lines.add( - cd.getStoredItemTypes() + " " - + GuiText.Of.getLocal() - + ' ' - + cd.getTotalItemTypes() - + ' ' - + GuiText.Types.getLocal()); - if (((CellInventoryHandler) cdi).getSticky()) { - lines.add(GuiText.Sticky.getLocal()); - } - } - } - } - - @Override - public int getBytes(final ItemStack cellItem) { - return 512; - } - - @Override - public int BytePerType(final ItemStack cell) { - return 8; - } - - @Override - public int getBytesPerType(final ItemStack cellItem) { - return 8; - } - - @Override - public int getTotalTypes(final ItemStack cellItem) { - return 27; - } - - @Override - public boolean isBlackListed(final ItemStack cellItem, final IAEItemStack requestedAddition) { - return false; - } - - @Override - public boolean storableInStorageCell() { - return false; - } - - @Override - public boolean isStorageCell(final ItemStack i) { - return true; - } - - @Override - public double getIdleDrain() { - return 0.5; - } - - @Override - public String getUnlocalizedGroupName(final Set others, final ItemStack is) { - return GuiText.StorageCells.getUnlocalized(); - } - - @Override - public boolean isEditable(final ItemStack is) { - return true; - } - - @Override - public IInventory getUpgradesInventory(final ItemStack is) { - return new CellUpgrades(is, 2); - } - - @Override - public IInventory getConfigInventory(final ItemStack is) { - return new CellConfig(is); - } - - @Override - public FuzzyMode getFuzzyMode(final ItemStack is) { - return FuzzyMode.fromItemStack(is); - } - - @Override - public void setFuzzyMode(final ItemStack is, final FuzzyMode fzMode) { - Platform.openNbtData(is).setString("FuzzyMode", fzMode.name()); - } - - @Override - public IGuiItemObject getGuiObject(final ItemStack is, final World w, final int x, final int y, final int z) { - return new PortableCellViewer(is, x); - } - - @Override - public String getOreFilter(ItemStack is) { - return Platform.openNbtData(is).getString("OreFilter"); - } - - @Override - public void setOreFilter(ItemStack is, String filter) { - Platform.openNbtData(is).setString("OreFilter", filter); + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; } } diff --git a/src/main/java/appeng/items/tools/powered/ToolWirelessTerminal.java b/src/main/java/appeng/items/tools/powered/ToolWirelessTerminal.java index bf30a8b25..23de4a462 100644 --- a/src/main/java/appeng/items/tools/powered/ToolWirelessTerminal.java +++ b/src/main/java/appeng/items/tools/powered/ToolWirelessTerminal.java @@ -35,6 +35,7 @@ import appeng.core.AEConfig; import appeng.core.AppEng; import appeng.core.features.AEFeature; import appeng.core.localization.GuiText; +import appeng.core.sync.GuiBridge; import appeng.items.tools.powered.powersink.AEBasePoweredItem; import appeng.util.ConfigManager; import appeng.util.Platform; @@ -51,6 +52,9 @@ import cpw.mods.fml.relauncher.SideOnly; modid = "Baubles|Expanded") }) public class ToolWirelessTerminal extends AEBasePoweredItem implements IWirelessTermHandler, IBauble, IBaubleExpanded { + public static String infinityBoosterCard = "infinityBoosterCard"; + public static String infinityEnergyCard = "InfinityEnergyCard"; + public ToolWirelessTerminal() { super(AEConfig.instance.wirelessTerminalBattery, Optional.absent()); this.setFeature(EnumSet.of(AEFeature.WirelessAccessTerminal, AEFeature.PoweredTools)); @@ -140,6 +144,10 @@ public class ToolWirelessTerminal extends AEBasePoweredItem implements IWireless return new String[] { AppEng.BAUBLESLOT }; } + public void openGui(final ItemStack is, final World w, final EntityPlayer player, final Object mode) { + Platform.openGUI(player, null, null, GuiBridge.GUI_ME); + } + @Override @cpw.mods.fml.common.Optional.Method(modid = "Baubles") public BaubleType getBaubleType(ItemStack itemStack) { diff --git a/src/main/java/appeng/items/tools/quartz/ToolQuartzCuttingKnife.java b/src/main/java/appeng/items/tools/quartz/ToolQuartzCuttingKnife.java index f0a6a2f20..a3288d943 100644 --- a/src/main/java/appeng/items/tools/quartz/ToolQuartzCuttingKnife.java +++ b/src/main/java/appeng/items/tools/quartz/ToolQuartzCuttingKnife.java @@ -91,7 +91,8 @@ public class ToolQuartzCuttingKnife extends AEBaseItem implements IGuiItem { } @Override - public IGuiItemObject getGuiObject(final ItemStack is, final World world, final int x, final int y, final int z) { + public IGuiItemObject getGuiObject(final ItemStack is, final World world, final EntityPlayer p, final int x, + final int y, final int z) { return new QuartzKnifeObj(is); } } diff --git a/src/main/java/appeng/me/cache/CraftingGridCache.java b/src/main/java/appeng/me/cache/CraftingGridCache.java index 3e206a24f..85010e4bb 100644 --- a/src/main/java/appeng/me/cache/CraftingGridCache.java +++ b/src/main/java/appeng/me/cache/CraftingGridCache.java @@ -10,6 +10,9 @@ package appeng.me.cache; +import static appeng.api.storage.data.IItemList.LIST_FLUID; +import static appeng.api.storage.data.IItemList.LIST_ITEM; +import static appeng.api.storage.data.IItemList.LIST_MIXED; import static appeng.util.Platform.convertStack; import static appeng.util.Platform.stackConvert; @@ -74,6 +77,7 @@ import appeng.api.networking.storage.IStorageGrid; import appeng.api.storage.ICellProvider; import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; @@ -86,8 +90,6 @@ import appeng.me.helpers.GenericInterestManager; import appeng.tile.crafting.TileCraftingStorageTile; import appeng.tile.crafting.TileCraftingTile; import appeng.util.ItemSorters; -import appeng.util.Platform; -import appeng.util.item.FluidList; import appeng.util.item.OreListMultiMap; public class CraftingGridCache @@ -365,6 +367,11 @@ public class CraftingGridCache this.emitableItems.add(someItem.copy()); } + @Override + public void setEmitable(final IAEStack someItem) { + this.emitableItems.add(someItem.copy()); + } + @Override public List getCellArray(final StorageChannel channel) { return Arrays.asList(this); @@ -428,15 +435,30 @@ public class CraftingGridCache @Override public IItemList getAvailableItems(final IItemList out, int iteration) { - if (out.getClass().equals(FluidList.class)) return out; // add craftable items! for (final IAEStack stack : this.craftableItems.keySet()) { - out.addCrafting(Platform.stackConvert(stack)); + if (stack instanceof IAEFluidStack afs) { + if (out.getStackType() == LIST_MIXED || out.getStackType() == LIST_FLUID) { + out.addCrafting(afs); + } + } else { + if (out.getStackType() == LIST_MIXED || out.getStackType() == LIST_ITEM) { + out.addCrafting(stack); + } + } } - for (final IAEStack st : this.emitableItems) { - out.addCrafting(Platform.stackConvert(st)); + for (final IAEStack stack : emitableItems) { + if (stack instanceof IAEFluidStack afs) { + if (out.getStackType() == LIST_MIXED || out.getStackType() == LIST_FLUID) { + out.addCrafting(afs); + } + } else { + if (out.getStackType() == LIST_MIXED || out.getStackType() == LIST_ITEM) { + out.addCrafting(stack); + } + } } return out; @@ -505,16 +527,22 @@ public class CraftingGridCache @Override public Future beginCraftingJob(final World world, final IGrid grid, final BaseActionSource actionSrc, final IAEItemStack slotItem, final ICraftingCallback cb) { - return beginCraftingJob(world, grid, actionSrc, slotItem, CraftingMode.STANDARD, cb); + return beginCraftingJob(world, grid, actionSrc, convertStack(slotItem), CraftingMode.STANDARD, cb); + } + + @Override + public Future beginCraftingJob(final World world, final IGrid grid, final BaseActionSource actionSrc, + final IAEStack stack, final ICraftingCallback cb) { + return beginCraftingJob(world, grid, actionSrc, stack, CraftingMode.STANDARD, cb); } public Future beginCraftingJob(final World world, final IGrid grid, final BaseActionSource actionSrc, - final IAEItemStack slotItem, final CraftingMode craftingMode, final ICraftingCallback cb) { - if (world == null || grid == null || actionSrc == null || slotItem == null) { + final IAEStack stack, final CraftingMode craftingMode, final ICraftingCallback cb) { + if (world == null || grid == null || actionSrc == null || stack == null) { throw new IllegalArgumentException("Invalid Crafting Job Request"); } - final ICraftingJob job = new CraftingJobV2<>(world, grid, actionSrc, convertStack(slotItem), craftingMode, cb); + final ICraftingJob job = new CraftingJobV2<>(world, grid, actionSrc, (IAEStack) stack, craftingMode, cb); return job.schedule(); } diff --git a/src/main/java/appeng/me/cache/GridStorageCache.java b/src/main/java/appeng/me/cache/GridStorageCache.java index bf10f6bd5..0ccddbe41 100644 --- a/src/main/java/appeng/me/cache/GridStorageCache.java +++ b/src/main/java/appeng/me/cache/GridStorageCache.java @@ -304,12 +304,12 @@ public class GridStorageCache implements IStorageGrid { } @Override - public void postAlterationOfStoredItems(final StorageChannel chan, final Iterable input, + public void postAlterationOfStoredItems(final StorageChannel chan, final Iterable> input, final BaseActionSource src) { if (chan == StorageChannel.ITEMS) { - this.itemMonitor.postChange(true, (Iterable) input, src); + this.itemMonitor.postChange(true, (Iterable>) input, src); } else if (chan == StorageChannel.FLUIDS) { - this.fluidMonitor.postChange(true, (Iterable) input, src); + this.fluidMonitor.postChange(true, (Iterable>) input, src); } } diff --git a/src/main/java/appeng/me/cache/NetworkMonitor.java b/src/main/java/appeng/me/cache/NetworkMonitor.java index 15c9547bb..595a7e691 100644 --- a/src/main/java/appeng/me/cache/NetworkMonitor.java +++ b/src/main/java/appeng/me/cache/NetworkMonitor.java @@ -57,7 +57,7 @@ public class NetworkMonitor> implements IMEMonitor { private final IItemList cachedList; @Nonnull - private final Map, Object> listeners; + private final Map listeners; private boolean sendEvent = false; private boolean hasChanged = false; @@ -73,7 +73,7 @@ public class NetworkMonitor> implements IMEMonitor { } @Override - public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { + public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { this.listeners.put(l, verificationToken); } @@ -170,7 +170,7 @@ public class NetworkMonitor> implements IMEMonitor { } @Override - public void removeListener(final IMEMonitorHandlerReceiver l) { + public void removeListener(final IMEMonitorHandlerReceiver l) { this.listeners.remove(l); } @@ -208,7 +208,7 @@ public class NetworkMonitor> implements IMEMonitor { return this.myGridCache.getGrid(); } - private Iterator, Object>> getListeners() { + private Iterator> getListeners() { return this.listeners.entrySet().iterator(); } @@ -229,13 +229,13 @@ public class NetworkMonitor> implements IMEMonitor { return leftOvers; } - private void notifyListenersOfChange(final Iterable diff, final BaseActionSource src) { + private void notifyListenersOfChange(final Iterable> diff, final BaseActionSource src) { this.hasChanged = true; - final Iterator, Object>> i = this.getListeners(); + final Iterator> i = this.getListeners(); while (i.hasNext()) { - final Entry, Object> o = i.next(); - final IMEMonitorHandlerReceiver receiver = o.getKey(); + final Entry o = i.next(); + final IMEMonitorHandlerReceiver receiver = o.getKey(); if (receiver.isValid(o.getValue())) { receiver.postChange(this, diff, src); } else { @@ -244,11 +244,11 @@ public class NetworkMonitor> implements IMEMonitor { } } - private void postChangesToListeners(final Iterable changes, final BaseActionSource src) { + private void postChangesToListeners(final Iterable> changes, final BaseActionSource src) { this.postChange(true, changes, src); } - protected void postChange(final boolean add, final Iterable changes, final BaseActionSource src) { + protected void postChange(final boolean add, final Iterable> changes, final BaseActionSource src) { if (localDepthSemaphore > 0 || GLOBAL_DEPTH.contains(this)) { return; } @@ -260,15 +260,15 @@ public class NetworkMonitor> implements IMEMonitor { this.notifyListenersOfChange(changes, src); - for (final T changedItem : changes) { + for (final IAEStack changedItem : changes) { if (changedItem == null) { continue; } - T difference = changedItem; + T difference = (T) changedItem; if (!add) { - difference = changedItem.copy(); + difference = (T) changedItem.copy(); difference.setStackSize(-changedItem.getStackSize()); } @@ -277,7 +277,7 @@ public class NetworkMonitor> implements IMEMonitor { if (!list.isEmpty()) { IAEStack fullStack = this.getHandler() - .getAvailableItem(changedItem, IterationCounter.fetchNewId()); + .getAvailableItem((T) changedItem, IterationCounter.fetchNewId()); if (fullStack == null) { fullStack = changedItem.copy(); @@ -307,10 +307,10 @@ public class NetworkMonitor> implements IMEMonitor { void forceUpdate() { this.hasChanged = true; - final Iterator, Object>> i = this.getListeners(); + final Iterator> i = this.getListeners(); while (i.hasNext()) { - final Entry, Object> o = i.next(); - final IMEMonitorHandlerReceiver receiver = o.getKey(); + final Entry o = i.next(); + final IMEMonitorHandlerReceiver receiver = o.getKey(); if (receiver.isValid(o.getValue())) { receiver.onListUpdate(); diff --git a/src/main/java/appeng/me/cluster/implementations/CraftingCPUCluster.java b/src/main/java/appeng/me/cluster/implementations/CraftingCPUCluster.java index 1d6b64940..f44a6d851 100644 --- a/src/main/java/appeng/me/cluster/implementations/CraftingCPUCluster.java +++ b/src/main/java/appeng/me/cluster/implementations/CraftingCPUCluster.java @@ -146,7 +146,7 @@ public final class CraftingCPUCluster implements IAECluster, ICraftingCPU { private final LinkedList tiles = new LinkedList<>(); private final LinkedList storage = new LinkedList<>(); private final LinkedList status = new LinkedList<>(); - private final HashMap>, Object> listeners = new HashMap<>(); + private final HashMap listeners = new HashMap<>(); private final HashMap, List> providers = new HashMap<>(); private ICraftingLink myLastLink; private String myName = ""; @@ -479,15 +479,15 @@ public final class CraftingCPUCluster implements IAECluster, ICraftingCPU { } private void postChange(final IAEStack diff, final BaseActionSource src) { - final Iterator>, Object>> i = this.getListeners(); + final Iterator> i = this.getListeners(); // protect integrity if (i.hasNext()) { final ImmutableList> single = ImmutableList.of(diff.copy()); while (i.hasNext()) { - final Entry>, Object> o = i.next(); - final IMEMonitorHandlerReceiver> receiver = o.getKey(); + final Entry o = i.next(); + final IMEMonitorHandlerReceiver receiver = o.getKey(); if (receiver.isValid(o.getValue())) { receiver.postChange(null, single, src); @@ -567,7 +567,7 @@ public final class CraftingCPUCluster implements IAECluster, ICraftingCPU { } } - private Iterator>, Object>> getListeners() { + private Iterator> getListeners() { return this.listeners.entrySet().iterator(); } @@ -812,8 +812,7 @@ public final class CraftingCPUCluster implements IAECluster, ICraftingCPU { for (final IAEStack anInput : input) { if (anInput != null) { - if (anInput.isItem()) sum += anInput.getStackSize(); - else sum += anInput.getStackSize() / 1000D; + sum += (double) anInput.getStackSize() / anInput.getPowerMultiplier(); } } // upgraded interface uses more power @@ -1736,7 +1735,7 @@ public final class CraftingCPUCluster implements IAECluster, ICraftingCPU { this.playersFollowingCurrentCraft.add(name); } - final Iterator>, Object>> i = this.getListeners(); + final Iterator> i = this.getListeners(); while (i.hasNext()) { if (i.next().getKey() instanceof ContainerCraftingCPU cccpu) { cccpu.sendUpdateFollowPacket(playersFollowingCurrentCraft); @@ -1745,13 +1744,13 @@ public final class CraftingCPUCluster implements IAECluster, ICraftingCPU { } @SuppressWarnings("unchecked") - public List getProviders(IAEItemStack is) { - return this.providers.getOrDefault(convertStack(is), Collections.EMPTY_LIST); + public List getProviders(IAEStack is) { + return this.providers.getOrDefault(is, Collections.EMPTY_LIST); } - public ScheduledReason getScheduledReason(IAEItemStack is) { + public ScheduledReason getScheduledReason(IAEStack is) { for (final Entry t : this.tasks.entrySet()) { - for (final IAEItemStack ais : t.getKey().getCondensedOutputs()) { + for (final IAEStack ais : t.getKey().getCondensedAEOutputs()) { if (Objects.equals(ais, is)) { return reasonProvider.getOrDefault(t.getKey(), ScheduledReason.UNDEFINED); } diff --git a/src/main/java/appeng/me/storage/CellInventory.java b/src/main/java/appeng/me/storage/CellInventory.java index 664366e16..94a82adc9 100644 --- a/src/main/java/appeng/me/storage/CellInventory.java +++ b/src/main/java/appeng/me/storage/CellInventory.java @@ -11,9 +11,7 @@ package appeng.me.storage; import java.util.Arrays; -import java.util.HashSet; import java.util.List; -import java.util.Set; import javax.annotation.Nonnull; @@ -22,9 +20,7 @@ import net.minecraft.item.Item; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTBase; import net.minecraft.nbt.NBTTagCompound; -import net.minecraftforge.oredict.OreDictionary; -import appeng.api.AEApi; import appeng.api.config.Actionable; import appeng.api.config.FuzzyMode; import appeng.api.config.Upgrades; @@ -38,57 +34,52 @@ import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.ISaveProvider; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.IterationCounter; import appeng.util.Platform; -import appeng.util.item.AEItemStack; -public class CellInventory implements ICellInventory { +public abstract class CellInventory> implements ICellInventory { - private static final String ITEM_TYPE_TAG = "it"; - private static final String ITEM_COUNT_TAG = "ic"; - private static final String ITEM_SLOT = "#"; - private static final String ITEM_SLOT_COUNT = "@"; - private static final Set BLACK_LIST = new HashSet<>(); - private static String[] itemSlots; - private static String[] itemSlotCount; + private static final String STACK_SLOT = "#"; + private static final String STACK_SLOT_COUNT = "@"; + private final String[] slots; + private final String[] slotCount; private final NBTTagCompound tagCompound; private final ISaveProvider container; - private int maxItemTypes = 63; - private short storedItemTypes = 0; - private long storedItemCount = 0; - private IItemList cellItems; + private int maxTypes = 63; + private short storedTypes = 0; + private long storedCount = 0; + private IItemList cellStacks; private final ItemStack cellItem; - private IStorageCell cellType; + private final IStorageCell cellType; private boolean cardVoidOverflow = false; private boolean cardDistribution = false; private byte restrictionTypes = 0; private long restrictionLong = 0; + private int typeWeight = 8; + private final int distTypesCount; - private CellInventory(final ItemStack o, final ISaveProvider container) throws AppEngException { - if (itemSlots == null) { - itemSlots = new String[this.maxItemTypes]; - itemSlotCount = new String[this.maxItemTypes]; + protected CellInventory(final ItemStack o, final ISaveProvider container) throws AppEngException { + slots = new String[this.maxTypes]; + slotCount = new String[this.maxTypes]; - for (int x = 0; x < this.maxItemTypes; x++) { - itemSlots[x] = ITEM_SLOT + x; - itemSlotCount[x] = ITEM_SLOT_COUNT + x; - } + for (int x = 0; x < this.maxTypes; x++) { + slots[x] = STACK_SLOT + x; + slotCount[x] = STACK_SLOT_COUNT + x; } if (o == null) { throw new AppEngException("ItemStack was used as a cell, but was not a cell!"); } - this.cellType = null; this.cellItem = o; - final Item type = this.cellItem.getItem(); - - if (type instanceof IStorageCell) { - this.cellType = (IStorageCell) this.cellItem.getItem(); - this.maxItemTypes = this.cellType.getTotalTypes(this.cellItem); - } + if (this.cellItem.getItem() instanceof IStorageCell type) { + this.cellType = type; + this.maxTypes = this.cellType.getTotalTypes(this.cellItem); + } else this.cellType = null; if (this.cellType == null) { throw new AppEngException("ItemStack was used as a cell, but was not a cell!"); @@ -98,11 +89,11 @@ public class CellInventory implements ICellInventory { throw new AppEngException("ItemStack was used as a cell, but was not a cell!"); } - if (this.maxItemTypes > 63) { - this.maxItemTypes = 63; + if (this.maxTypes > 63) { + this.maxTypes = 63; } - if (this.maxItemTypes < 1) { - this.maxItemTypes = 1; + if (this.maxTypes < 1) { + this.maxTypes = 1; } final IInventory upgrades = this.getUpgradesInventory(); @@ -122,31 +113,34 @@ public class CellInventory implements ICellInventory { this.container = container; this.tagCompound = Platform.openNbtData(o); - this.storedItemTypes = this.tagCompound.getShort(ITEM_TYPE_TAG); - this.storedItemCount = this.tagCompound.getLong(ITEM_COUNT_TAG); + this.storedTypes = this.tagCompound.getShort(getStackTypeTag()); + this.storedCount = this.tagCompound.getLong(getStackCountTag()); this.restrictionTypes = this.tagCompound.getByte("cellRestrictionTypes"); this.restrictionLong = this.tagCompound.getLong("cellRestrictionAmount"); - this.cellItems = null; - } + this.cellStacks = null; - public static IMEInventoryHandler getCell(final ItemStack o, final ISaveProvider container2) { - try { - return new CellInventoryHandler(new CellInventory(o, container2)); - } catch (final AppEngException e) { - return null; + if (this.restrictionTypes > 0) this.distTypesCount = this.restrictionTypes; + else { + int types = 0; + final IAEStackInventory config = this.getConfigAEInventory(); + for (int i = 0; i < config.getSizeInventory(); i++) { + if (config.getAEStackInSlot(i) != null) types++; + } + + this.distTypesCount = types == 0 ? this.maxTypes : Math.min(types, this.maxTypes); } } - private static boolean isStorageCell(final IAEItemStack itemStack) { - if (itemStack == null) { + private static boolean isStorageCell(final IAEStack itemStack) { + if (!(itemStack instanceof IAEItemStack ais)) { return false; } try { - final Item type = itemStack.getItem(); + final Item type = ais.getItem(); - if (type instanceof IStorageCell) { - return !((IStorageCell) type).storableInStorageCell(); + if (type instanceof IStorageCell sc) { + return !sc.storableInStorageCell(); } } catch (final Throwable err) { return true; @@ -162,34 +156,29 @@ public class CellInventory implements ICellInventory { final Item type = itemStack.getItem(); - if (type instanceof IStorageCell) { - return ((IStorageCell) type).isStorageCell(itemStack); + if (type instanceof IStorageCell cell) { + return cell.isStorageCell(itemStack); } return false; } - public static void addBasicBlackList(final int itemID, final int meta) { - BLACK_LIST.add((meta << Platform.DEF_OFFSET) | itemID); + public static IMEInventoryHandler getCell(final ItemStack o, final ISaveProvider container2, StorageChannel sc) { + try { + if (sc == StorageChannel.ITEMS) return new ItemCellInventoryHandler(new ItemCellInventory(o, container2)); + if (sc == StorageChannel.FLUIDS) + return new FluidCellInventoryHandler(new FluidCellInventory(o, container2)); + } catch (final AppEngException ignored) {} + return null; } - private static boolean isBlackListed(final IAEItemStack input) { - if (BLACK_LIST.contains( - (OreDictionary.WILDCARD_VALUE << Platform.DEF_OFFSET) | Item.getIdFromItem(input.getItem()))) { - return true; - } - - return BLACK_LIST - .contains((input.getItemDamage() << Platform.DEF_OFFSET) | Item.getIdFromItem(input.getItem())); - } - - private boolean isEmpty(final IMEInventory meInventory) { - return meInventory.getAvailableItems(AEApi.instance().storage().createItemList(), IterationCounter.fetchNewId()) - .isEmpty(); + private boolean isEmpty(final IMEInventory meInventory) { + return ((IMEInventory) meInventory) + .getAvailableItems(this.getChannel().createPrimitiveList(), IterationCounter.fetchNewId()).isEmpty(); } @Override - public IAEItemStack injectItems(final IAEItemStack input, final Actionable mode, final BaseActionSource src) { + public StackType injectItems(final StackType input, final Actionable mode, final BaseActionSource src) { if (input == null) { return null; } @@ -198,14 +187,19 @@ public class CellInventory implements ICellInventory { return null; } - if (isBlackListed(input) || this.cellType.isBlackListed(this.cellItem, input)) { + if (this.cellType.isBlackListed(input)) { return input; } if (CellInventory.isStorageCell(input)) { - final IMEInventory meInventory = getCell(input.getItemStack(), null); + final ItemStack cellStack = ((IAEItemStack) input).getItemStack(); + final CellInventoryHandler cellInventory = (CellInventoryHandler) getCell( + cellStack, + null, + ((IStorageCell) cellStack.getItem()).getStorageChannel()); - if (meInventory != null && !this.isEmpty(meInventory)) { + // same as isEmpty but less effort + if (cellInventory != null && cellInventory.getUsedBytes() > 0) { return input; } } @@ -214,7 +208,7 @@ public class CellInventory implements ICellInventory { input.setCraftable(false); } - final IAEItemStack l = this.getCellItems().findPrecise(input); + final StackType l = this.getCellStacks().findPrecise(input); if (l != null) { long remainingItemSlots; @@ -232,7 +226,7 @@ public class CellInventory implements ICellInventory { } if (input.getStackSize() > remainingItemSlots) { - final IAEItemStack r = input.copy(); + final StackType r = input.copy(); r.setStackSize(r.getStackSize() - remainingItemSlots); if (mode == Actionable.MODULATE) { @@ -262,20 +256,20 @@ public class CellInventory implements ICellInventory { if (restrictionLong > 0) { remainingItemCount = this.getRemainingItemCount(); } else { - remainingItemCount = this.getRemainingItemCount() - this.getBytesPerType() * 8L; + remainingItemCount = this.getRemainingItemCount() - this.getBytesPerType() * (long) this.typeWeight; } } if (remainingItemCount > 0) { if (input.getStackSize() > remainingItemCount) { - final IAEItemStack toReturn = input.copy(); + final StackType toReturn = input.copy(); toReturn.decStackSize(remainingItemCount); if (mode == Actionable.MODULATE) { - final IAEItemStack toWrite = input.copy(); + final StackType toWrite = input.copy(); toWrite.setStackSize(remainingItemCount); - this.cellItems.add(toWrite); + this.cellStacks.add(toWrite); this.updateItemCount(toWrite.getStackSize()); this.saveChanges(); } @@ -284,7 +278,7 @@ public class CellInventory implements ICellInventory { if (mode == Actionable.MODULATE) { this.updateItemCount(input.getStackSize()); - this.cellItems.add(input); + this.cellStacks.add(input); this.saveChanges(); } @@ -296,16 +290,16 @@ public class CellInventory implements ICellInventory { } @Override - public IAEItemStack extractItems(final IAEItemStack request, final Actionable mode, final BaseActionSource src) { + public StackType extractItems(final StackType request, final Actionable mode, final BaseActionSource src) { if (request == null) { return null; } final long size = request.getStackSize(); - IAEItemStack results = null; + StackType results = null; - final IAEItemStack l = this.getCellItems().findPrecise(request); + final StackType l = this.getCellStacks().findPrecise(request); if (l != null) { results = l.copy(); @@ -332,17 +326,17 @@ public class CellInventory implements ICellInventory { return results; } - private IItemList getCellItems() { - if (this.cellItems == null) { + private IItemList getCellStacks() { + if (this.cellStacks == null) { this.loadCellItems(); } - return this.cellItems; + return this.cellStacks; } private void updateItemCount(final long delta) { - this.storedItemCount += delta; - this.tagCompound.setLong(ITEM_COUNT_TAG, this.storedItemCount); + this.storedCount += delta; + this.tagCompound.setLong(getStackCountTag(), this.storedCount); } private void saveChanges() { @@ -352,59 +346,59 @@ public class CellInventory implements ICellInventory { // add new pretty stuff... int x = 0; - for (final IAEItemStack v : this.cellItems) { + for (final StackType v : this.cellStacks) { itemCount += v.getStackSize(); - final NBTBase c = this.tagCompound.getTag(itemSlots[x]); + final NBTBase c = this.tagCompound.getTag(slots[x]); - if (c instanceof NBTTagCompound) { - v.writeToNBT((NBTTagCompound) c); + if (c instanceof NBTTagCompound nbt) { + v.writeToNBT(nbt); } else { final NBTTagCompound g = new NBTTagCompound(); v.writeToNBT(g); - this.tagCompound.setTag(itemSlots[x], g); + this.tagCompound.setTag(slots[x], g); } /* * NBTBase tagSlotCount = tagCompound.getTag( itemSlotCount[x] ); if ( tagSlotCount instanceof NBTTagInt ) * ((NBTTagInt) tagSlotCount).data = (int) v.getStackSize(); else */ - this.tagCompound.setLong(itemSlotCount[x], v.getStackSize()); + this.tagCompound.setLong(slotCount[x], v.getStackSize()); x++; } // NBTBase tagType = tagCompound.getTag( ITEM_TYPE_TAG ); // NBTBase tagCount = tagCompound.getTag( ITEM_COUNT_TAG ); - final short oldStoredItems = this.storedItemTypes; + final short oldStoredItems = this.storedTypes; /* * if ( tagType instanceof NBTTagShort ) ((NBTTagShort) tagType).data = storedItems = (short) cellItems.size(); * else */ - this.storedItemTypes = (short) this.cellItems.size(); + this.storedTypes = (short) this.cellStacks.size(); - if (this.cellItems.isEmpty()) { - this.tagCompound.removeTag(ITEM_TYPE_TAG); + if (this.cellStacks.isEmpty()) { + this.tagCompound.removeTag(getStackTypeTag()); } else { - this.tagCompound.setShort(ITEM_TYPE_TAG, this.storedItemTypes); + this.tagCompound.setShort(getStackTypeTag(), this.storedTypes); } /* * if ( tagCount instanceof NBTTagInt ) ((NBTTagInt) tagCount).data = storedItemCount = itemCount; else */ - this.storedItemCount = itemCount; + this.storedCount = itemCount; if (itemCount == 0) { - this.tagCompound.removeTag(ITEM_COUNT_TAG); + this.tagCompound.removeTag(getStackCountTag()); } else { - this.tagCompound.setLong(ITEM_COUNT_TAG, itemCount); + this.tagCompound.setLong(getStackCountTag(), itemCount); } // clean any old crusty stuff... - for (; x < oldStoredItems && x < this.maxItemTypes; x++) { - this.tagCompound.removeTag(itemSlots[x]); - this.tagCompound.removeTag(itemSlotCount[x]); + for (; x < oldStoredItems && x < this.maxTypes; x++) { + this.tagCompound.removeTag(slots[x]); + this.tagCompound.removeTag(slotCount[x]); } if (this.container != null) { @@ -413,40 +407,41 @@ public class CellInventory implements ICellInventory { } private void loadCellItems() { - if (this.cellItems == null) { - this.cellItems = AEApi.instance().storage().createPrimitiveItemList(); + if (this.cellStacks == null) { + this.cellStacks = this.getChannel().createPrimitiveList(); } - this.cellItems.resetStatus(); // clears totals and stuff. + this.cellStacks.resetStatus(); // clears totals and stuff. final int types = (int) this.getStoredItemTypes(); for (int x = 0; x < types; x++) { - final ItemStack t = ItemStack.loadItemStackFromNBT(this.tagCompound.getCompoundTag(itemSlots[x])); - final IAEItemStack ias = AEItemStack.create(t); - if (t != null) { - ias.setStackSize(this.tagCompound.getLong(itemSlotCount[x])); + final StackType ias = readStack(this.tagCompound.getCompoundTag(slots[x])); + if (ias != null) { + ias.setStackSize(this.tagCompound.getLong(slotCount[x])); if (ias.getStackSize() > 0) { - this.cellItems.add(ias); + this.cellStacks.add(ias); } else { // Dirty Compact for EC2 - ias.setStackSize(this.tagCompound.getCompoundTag(itemSlots[x]).getLong("Cnt")); + ias.setStackSize(this.tagCompound.getCompoundTag(slots[x]).getLong("Cnt")); if (ias.getStackSize() > 0) { - this.cellItems.add(ias); + this.cellStacks.add(ias); } } } } - if (this.cellItems.size() != types) { + if (this.cellStacks.size() != types) { // fix broken singularity cells this.saveChanges(); } } + protected abstract StackType readStack(NBTTagCompound tag); + @Override - public IItemList getAvailableItems(final IItemList out, int iteration) { - for (final IAEItemStack i : this.getCellItems()) { + public IItemList getAvailableItems(final IItemList out, int iteration) { + for (final StackType i : this.getCellStacks()) { out.add(i); } @@ -454,9 +449,9 @@ public class CellInventory implements ICellInventory { } @Override - public IAEItemStack getAvailableItem(@Nonnull IAEItemStack request, int iteration) { + public StackType getAvailableItem(@Nonnull StackType request, int iteration) { long count = 0; - for (final IAEItemStack is : this.getCellItems()) { + for (final StackType is : this.getCellStacks()) { if (is != null && is.getStackSize() > 0 && is.isSameType(request)) { count += is.getStackSize(); if (count < 0) { @@ -469,11 +464,6 @@ public class CellInventory implements ICellInventory { return count == 0 ? null : request.copy().setStackSize(count); } - @Override - public StorageChannel getChannel() { - return StorageChannel.ITEMS; - } - @Override public ItemStack getItemStack() { return this.cellItem; @@ -495,10 +485,16 @@ public class CellInventory implements ICellInventory { } @Override + @Deprecated public IInventory getConfigInventory() { return this.cellType.getConfigInventory(this.cellItem); } + @Override + public IAEStackInventory getConfigAEInventory() { + return this.cellType.getConfigAEInventory(this.cellItem); + } + @Override public IInventory getUpgradesInventory() { return this.cellType.getUpgradesInventory(this.cellItem); @@ -531,7 +527,7 @@ public class CellInventory implements ICellInventory { @Override public long getUsedBytes() { - final long bytesForItemCount = (this.getStoredItemCount() + this.getUnusedItemCount()) / 8; + final long bytesForItemCount = (this.getStoredItemCount() + this.getUnusedItemCount()) / this.typeWeight; return this.getStoredItemTypes() * this.getBytesPerType() + bytesForItemCount; } @@ -539,21 +535,21 @@ public class CellInventory implements ICellInventory { @Override public long getTotalItemTypes() { if (restrictionTypes > 0) return restrictionTypes; - return this.maxItemTypes; + return this.maxTypes; } - public long getMaxItemTypes() { - return this.maxItemTypes; + public long getMaxTypes() { + return this.maxTypes; } @Override public long getStoredItemCount() { - return this.storedItemCount; + return this.storedCount; } @Override public long getStoredItemTypes() { - return this.storedItemTypes; + return this.storedTypes; } @Override @@ -561,31 +557,30 @@ public class CellInventory implements ICellInventory { final long basedOnStorage = this.getFreeBytes() / this.getBytesPerType(); final long baseOnTotal = this.getTotalItemTypes() - this.getStoredItemTypes(); - return basedOnStorage > baseOnTotal ? baseOnTotal : basedOnStorage; + return Math.min(basedOnStorage, baseOnTotal); } @Override - public long getRemainingItemsCountDist(IAEItemStack l) { + public long getRemainingItemsCountDist(StackType l) { long remaining; - long types = 0; - for (int i = 0; i < this.getTotalItemTypes(); i++) { - if (this.getConfigInventory().getStackInSlot(i) != null) { - types++; - } - } - if (types == 0) types = this.getTotalItemTypes(); + if (l != null) { if (restrictionLong > 0) { - remaining = Math.min((restrictionLong / types) - l.getStackSize(), getRemainingItemCount()); + remaining = Math + .min((restrictionLong / this.distTypesCount) - l.getStackSize(), getRemainingItemCount()); } else { - remaining = (((getTotalBytes() / types) - getBytesPerType()) * 8) - l.getStackSize(); + remaining = (((getTotalBytes() / this.distTypesCount) - getBytesPerType()) * this.typeWeight) + - l.getStackSize(); } } else { if (restrictionLong > 0) { - remaining = Math - .min(restrictionLong / types, ((this.getTotalBytes() / types) - this.getBytesPerType()) * 8L); + remaining = Math.min( + restrictionLong / this.distTypesCount, + ((this.getTotalBytes() / this.distTypesCount) - this.getBytesPerType()) + * (long) this.typeWeight); } else { - remaining = ((this.getTotalBytes() / types) - this.getBytesPerType()) * 8L; + remaining = ((this.getTotalBytes() / this.distTypesCount) - this.getBytesPerType()) + * (long) this.typeWeight; } } return remaining > 0 ? remaining : 0; @@ -596,22 +591,22 @@ public class CellInventory implements ICellInventory { if (restrictionLong > 0) { return Math.min( restrictionLong - this.getStoredItemCount(), - this.getFreeBytes() * 8 + this.getUnusedItemCount()); + this.getFreeBytes() * this.typeWeight + this.getUnusedItemCount()); } - final long remaining = this.getFreeBytes() * 8 + this.getUnusedItemCount(); + final long remaining = this.getFreeBytes() * this.typeWeight + this.getUnusedItemCount(); return remaining > 0 ? remaining : 0; } @Override public int getUnusedItemCount() { - final long div = this.getStoredItemCount() % 8; + final long div = this.getStoredItemCount() % this.typeWeight; if (div == 0) { return 0; } - return (int) (8 - div); + return (int) (this.typeWeight - div); } @Override @@ -631,4 +626,17 @@ public class CellInventory implements ICellInventory { public List getRestriction() { return Arrays.asList(restrictionLong, restrictionTypes); } + + protected void setTypeWeight(int typeWeight) { + this.typeWeight = typeWeight; + } + + @Override + public StorageChannel getChannel() { + return this.cellType.getStorageChannel(); + } + + protected abstract String getStackTypeTag(); + + protected abstract String getStackCountTag(); } diff --git a/src/main/java/appeng/me/storage/CellInventoryHandler.java b/src/main/java/appeng/me/storage/CellInventoryHandler.java index e8991ed40..b5f2c6a12 100644 --- a/src/main/java/appeng/me/storage/CellInventoryHandler.java +++ b/src/main/java/appeng/me/storage/CellInventoryHandler.java @@ -15,7 +15,6 @@ import java.util.List; import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; -import appeng.api.AEApi; import appeng.api.config.FuzzyMode; import appeng.api.config.IncludeExclude; import appeng.api.config.Upgrades; @@ -25,24 +24,21 @@ import appeng.api.storage.ICellInventory; import appeng.api.storage.ICellInventoryHandler; import appeng.api.storage.IMEInventory; import appeng.api.storage.StorageChannel; -import appeng.api.storage.data.IAEItemStack; -import appeng.api.storage.data.IItemList; -import appeng.util.item.AEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.prioitylist.FuzzyPriorityList; -import appeng.util.prioitylist.OreFilteredList; -import appeng.util.prioitylist.PrecisePriorityList; -public class CellInventoryHandler extends MEInventoryHandler - implements ICellInventoryHandler, ICellCacheRegistry { +public abstract class CellInventoryHandler> extends MEInventoryHandler + implements ICellInventoryHandler, ICellCacheRegistry { - CellInventoryHandler(final IMEInventory c) { - super(c, StorageChannel.ITEMS); + CellInventoryHandler(final IMEInventory c, final StorageChannel sc) { + super(c, sc); - final ICellInventory ci = this.getCellInv(); + final ICellInventory ci = this.getCellInv(); if (ci != null) { final IInventory upgrades = ci.getUpgradesInventory(); - final IInventory config = ci.getConfigInventory(); + final IAEStackInventory config = ci.getConfigAEInventory(); final FuzzyMode fzMode = ci.getFuzzyMode(); final String filter = ci.getOreFilter(); @@ -66,6 +62,7 @@ public class CellInventoryHandler extends MEInventoryHandler } } } + this.setWhitelist(hasInverter ? IncludeExclude.BLACKLIST : IncludeExclude.WHITELIST); if (hasSticky) { @@ -73,33 +70,24 @@ public class CellInventoryHandler extends MEInventoryHandler } if (hasOreFilter && !filter.isEmpty()) { - this.setPartitionList(new OreFilteredList(filter)); + setOreFilteredList(filter); } else { - final IItemList priorityList = AEApi.instance().storage().createItemList(); - for (int x = 0; x < config.getSizeInventory(); x++) { - final ItemStack is = config.getStackInSlot(x); - if (is != null) { - priorityList.add(AEItemStack.create(is)); - } - } - if (!priorityList.isEmpty()) { - if (hasFuzzy) { - this.setPartitionList(new FuzzyPriorityList<>(priorityList, fzMode)); - } else { - this.setPartitionList(new PrecisePriorityList<>(priorityList)); - } - } + setPriorityList(hasFuzzy, config, fzMode); } } } + protected void setOreFilteredList(String filter) {} + + protected void setPriorityList(boolean hasFuzzy, IAEStackInventory config, FuzzyMode fzMode) {} + @Override - public ICellInventory getCellInv() { + public ICellInventory getCellInv() { Object o = this.getInternal(); if (o instanceof MEPassThrough) { o = ((MEPassThrough) o).getInternal(); } - return (ICellInventory) (o instanceof ICellInventory ? o : null); + return o instanceof ICellInventory ici ? ici : null; } @Override @@ -169,12 +157,12 @@ public class CellInventoryHandler extends MEInventoryHandler @Override public TYPE getCellType() { - return TYPE.ITEM; + return this.getStorageChannel() == StorageChannel.FLUIDS ? TYPE.FLUID : TYPE.ITEM; } public List getRestricted() { - ICellInventory cellInventory = this.getCellInv(); - if (cellInventory instanceof CellInventory ci) { + ICellInventory cellInventory = this.getCellInv(); + if (cellInventory instanceof CellInventoryci) { return ci.getRestriction(); } diff --git a/src/main/java/appeng/me/storage/CreativeCellInventory.java b/src/main/java/appeng/me/storage/CreativeCellInventory.java index 151597afd..74f9afc53 100644 --- a/src/main/java/appeng/me/storage/CreativeCellInventory.java +++ b/src/main/java/appeng/me/storage/CreativeCellInventory.java @@ -12,41 +12,61 @@ package appeng.me.storage; import javax.annotation.Nonnull; +import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; -import appeng.api.AEApi; +import com.glodblock.github.util.Util; + import appeng.api.config.AccessRestriction; import appeng.api.config.Actionable; +import appeng.api.config.FuzzyMode; +import appeng.api.implementations.items.IStorageCell; import appeng.api.networking.security.BaseActionSource; +import appeng.api.storage.ICellInventory; import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.items.contents.CellConfig; -import appeng.util.item.AEItemStack; +import appeng.tile.inventory.IAEStackInventory; -public class CreativeCellInventory implements IMEInventoryHandler { +public class CreativeCellInventory> + implements IMEInventoryHandler, ICellInventory { - private final IItemList itemListCache = AEApi.instance().storage().createItemList(); + private final IItemList listCache; + private final ItemStack cellItem; + private final IStorageCell cellType; protected CreativeCellInventory(final ItemStack o) { - final CellConfig cc = new CellConfig(o); - for (final ItemStack is : cc) { - if (is != null) { - final IAEItemStack i = AEItemStack.create(is); - i.setStackSize((long) (Math.pow(2, 52) - 1)); - this.itemListCache.add(i); + this.cellItem = o; + this.cellType = (IStorageCell) o.getItem(); + this.listCache = getChannel().createPrimitiveList(); + + final IAEStackInventory cc = o.getItem() instanceof IStorageCell sc ? sc.getConfigAEInventory(o) + : new IAEStackInventory(null, 0); + for (int i = 0; i < cc.getSizeInventory(); i++) { + IAEStack aes = cc.getAEStackInSlot(i); + if (aes != null) { + if (getChannel() == StorageChannel.FLUIDS && aes instanceof IAEItemStack ais) { + aes = Util.getAEFluidFromItem(ais.getItemStack()); + } + + aes.setStackSize((long) (Math.pow(2, 52) - 1)); + this.listCache.add((StackType) aes); } } } - public static IMEInventoryHandler getCell(final ItemStack o) { - return new CellInventoryHandler(new CreativeCellInventory(o)); + public static IMEInventoryHandler getCell(final ItemStack o, StorageChannel sc) { + if (sc == StorageChannel.ITEMS) return new ItemCellInventoryHandler(new CreativeCellInventory<>(o)); + if (sc == StorageChannel.FLUIDS) return new FluidCellInventoryHandler(new CreativeCellInventory<>(o)); + return null; } @Override - public IAEItemStack injectItems(final IAEItemStack input, final Actionable mode, final BaseActionSource src) { - final IAEItemStack local = this.itemListCache.findPrecise(input); + public StackType injectItems(final StackType input, final Actionable mode, final BaseActionSource src) { + final StackType local = this.listCache.findPrecise(input); if (local == null) { return input; } @@ -55,8 +75,8 @@ public class CreativeCellInventory implements IMEInventoryHandler } @Override - public IAEItemStack extractItems(final IAEItemStack request, final Actionable mode, final BaseActionSource src) { - final IAEItemStack local = this.itemListCache.findPrecise(request); + public StackType extractItems(final StackType request, final Actionable mode, final BaseActionSource src) { + final StackType local = this.listCache.findPrecise(request); if (local == null) { return null; } @@ -65,16 +85,16 @@ public class CreativeCellInventory implements IMEInventoryHandler } @Override - public IItemList getAvailableItems(final IItemList out, int iteration) { - for (final IAEItemStack ais : this.itemListCache) { + public IItemList getAvailableItems(final IItemList out, int iteration) { + for (final StackType ais : this.listCache) { out.add(ais); } return out; } @Override - public IAEItemStack getAvailableItem(@Nonnull IAEItemStack request, int iteration) { - final IAEItemStack local = this.itemListCache.findPrecise(request); + public StackType getAvailableItem(@Nonnull StackType request, int iteration) { + final StackType local = this.listCache.findPrecise(request); if (local == null) { return null; } @@ -84,7 +104,7 @@ public class CreativeCellInventory implements IMEInventoryHandler @Override public StorageChannel getChannel() { - return StorageChannel.ITEMS; + return this.cellType.getStorageChannel(); } @Override @@ -93,13 +113,13 @@ public class CreativeCellInventory implements IMEInventoryHandler } @Override - public boolean isPrioritized(final IAEItemStack input) { - return this.itemListCache.findPrecise(input) != null; + public boolean isPrioritized(final StackType input) { + return this.listCache.findPrecise(input) != null; } @Override - public boolean canAccept(final IAEItemStack input) { - return this.itemListCache.findPrecise(input) != null; + public boolean canAccept(final StackType input) { + return this.listCache.findPrecise(input) != null; } @Override @@ -116,4 +136,99 @@ public class CreativeCellInventory implements IMEInventoryHandler public boolean validForPass(final int i) { return true; } + + @Override + public IAEStackInventory getConfigAEInventory() { + return new CellConfig(this.cellItem); + } + + @Override + public ItemStack getItemStack() { + return this.cellItem; + } + + @Override + public double getIdleDrain() { + return this.cellType.getIdleDrain(); + } + + @Override + public FuzzyMode getFuzzyMode() { + return FuzzyMode.IGNORE_ALL; + } + + @Override + public IInventory getUpgradesInventory() { + return this.cellType.getUpgradesInventory(this.cellItem); + } + + @Override + public int getBytesPerType() { + return 0; + } + + @Override + public boolean canHoldNewItem() { + return false; + } + + @Override + public long getTotalBytes() { + return 0; + } + + @Override + public long getFreeBytes() { + return 0; + } + + @Override + public long getUsedBytes() { + return 0; + } + + @Override + public long getTotalItemTypes() { + return 0; + } + + @Override + public long getStoredItemCount() { + return 0; + } + + @Override + public long getStoredItemTypes() { + return 0; + } + + @Override + public long getRemainingItemTypes() { + return 0; + } + + @Override + public long getRemainingItemCount() { + return 0; + } + + @Override + public long getRemainingItemsCountDist(StackType l) { + return 0; + } + + @Override + public int getUnusedItemCount() { + return 0; + } + + @Override + public int getStatusForCell() { + return 0; + } + + @Override + public String getOreFilter() { + return ""; + } } diff --git a/src/main/java/appeng/me/storage/FluidCellInventory.java b/src/main/java/appeng/me/storage/FluidCellInventory.java new file mode 100644 index 000000000..9eca7436b --- /dev/null +++ b/src/main/java/appeng/me/storage/FluidCellInventory.java @@ -0,0 +1,33 @@ +package appeng.me.storage; + +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; + +import appeng.api.exceptions.AppEngException; +import appeng.api.storage.ISaveProvider; +import appeng.api.storage.data.IAEFluidStack; +import appeng.util.item.AEFluidStack; + +public class FluidCellInventory extends CellInventory { + + public FluidCellInventory(ItemStack o, ISaveProvider container2) throws AppEngException { + super(o, container2); + + this.setTypeWeight(256 * 8); + } + + @Override + protected IAEFluidStack readStack(NBTTagCompound tag) { + return AEFluidStack.loadFluidStackFromNBT(tag); + } + + @Override + protected String getStackTypeTag() { + return "ft"; + } + + @Override + protected String getStackCountTag() { + return "fc"; + } +} diff --git a/src/main/java/appeng/me/storage/FluidCellInventoryHandler.java b/src/main/java/appeng/me/storage/FluidCellInventoryHandler.java new file mode 100644 index 000000000..d136be239 --- /dev/null +++ b/src/main/java/appeng/me/storage/FluidCellInventoryHandler.java @@ -0,0 +1,56 @@ +package appeng.me.storage; + +import com.glodblock.github.util.Util; + +import appeng.api.AEApi; +import appeng.api.config.FuzzyMode; +import appeng.api.storage.IMEInventory; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEFluidStack; +import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.api.storage.data.IItemList; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.item.AEFluidStack; +import appeng.util.prioitylist.PrecisePriorityList; + +public class FluidCellInventoryHandler extends CellInventoryHandler { + + public FluidCellInventoryHandler(IMEInventory c) { + super(c, StorageChannel.FLUIDS); + } + + @Override + protected void setOreFilteredList(String filter) { + // no ore dict + } + + @Override + protected void setPriorityList(boolean hasFuzzy, IAEStackInventory config, FuzzyMode fzMode) { + final IItemList priorityList = AEApi.instance().storage().createFluidList(); + for (int x = 0; x < config.getSizeInventory(); x++) { + final IAEStack aes = config.getAEStackInSlot(x); + final IAEFluidStack fluid = aes instanceof IAEFluidStack afs ? afs + : aes instanceof IAEItemStack ais ? AEFluidStack.create(Util.getFluidFromItem(ais.getItemStack())) + : null; + if (fluid != null) { + fluid.setStackSize(1); + priorityList.add(fluid); + + // convert partition on cells in network + if (aes instanceof IAEItemStack) { + config.putAEStackInSlot(x, fluid); + config.markDirty(); + } + } + } + if (!priorityList.isEmpty()) { + this.setPartitionList(new PrecisePriorityList<>(priorityList)); + } + } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.FLUIDS; + } +} diff --git a/src/main/java/appeng/me/storage/ItemCellInventory.java b/src/main/java/appeng/me/storage/ItemCellInventory.java new file mode 100644 index 000000000..8fdb79c15 --- /dev/null +++ b/src/main/java/appeng/me/storage/ItemCellInventory.java @@ -0,0 +1,33 @@ +package appeng.me.storage; + +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; + +import appeng.api.exceptions.AppEngException; +import appeng.api.storage.ISaveProvider; +import appeng.api.storage.data.IAEItemStack; +import appeng.util.item.AEItemStack; + +public class ItemCellInventory extends CellInventory { + + public ItemCellInventory(ItemStack o, ISaveProvider container2) throws AppEngException { + super(o, container2); + + this.setTypeWeight(8); + } + + @Override + protected IAEItemStack readStack(NBTTagCompound tag) { + return AEItemStack.loadItemStackFromNBT(tag); + } + + @Override + protected String getStackTypeTag() { + return "it"; + } + + @Override + protected String getStackCountTag() { + return "ic"; + } +} diff --git a/src/main/java/appeng/me/storage/ItemCellInventoryHandler.java b/src/main/java/appeng/me/storage/ItemCellInventoryHandler.java new file mode 100644 index 000000000..2770b3014 --- /dev/null +++ b/src/main/java/appeng/me/storage/ItemCellInventoryHandler.java @@ -0,0 +1,48 @@ +package appeng.me.storage; + +import appeng.api.AEApi; +import appeng.api.config.FuzzyMode; +import appeng.api.storage.IMEInventory; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.api.storage.data.IItemList; +import appeng.tile.inventory.IAEStackInventory; +import appeng.util.prioitylist.FuzzyPriorityList; +import appeng.util.prioitylist.OreFilteredList; +import appeng.util.prioitylist.PrecisePriorityList; + +public class ItemCellInventoryHandler extends CellInventoryHandler { + + public ItemCellInventoryHandler(IMEInventory c) { + super(c, StorageChannel.ITEMS); + } + + @Override + protected void setOreFilteredList(String filter) { + this.setPartitionList(new OreFilteredList(filter)); + } + + @Override + protected void setPriorityList(boolean hasFuzzy, IAEStackInventory config, FuzzyMode fzMode) { + final IItemList priorityList = AEApi.instance().storage().createItemList(); + for (int x = 0; x < config.getSizeInventory(); x++) { + final IAEStack aes = config.getAEStackInSlot(x); + if (aes != null) { + priorityList.add((IAEItemStack) aes); + } + } + if (!priorityList.isEmpty()) { + if (hasFuzzy) { + this.setPartitionList(new FuzzyPriorityList<>(priorityList, fzMode)); + } else { + this.setPartitionList(new PrecisePriorityList<>(priorityList)); + } + } + } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } +} diff --git a/src/main/java/appeng/me/storage/MEMonitorIInventory.java b/src/main/java/appeng/me/storage/MEMonitorIInventory.java index 6b480a6a7..637fb58e1 100644 --- a/src/main/java/appeng/me/storage/MEMonitorIInventory.java +++ b/src/main/java/appeng/me/storage/MEMonitorIInventory.java @@ -31,6 +31,7 @@ import appeng.api.storage.IMEMonitor; import appeng.api.storage.IMEMonitorHandlerReceiver; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.util.InventoryAdaptor; import appeng.util.Platform; @@ -41,7 +42,7 @@ public class MEMonitorIInventory implements IMEMonitor { private final InventoryAdaptor adaptor; private final IItemList list = AEApi.instance().storage().createItemList(); - private final HashMap, Object> listeners = new HashMap<>(); + private final HashMap listeners = new HashMap<>(); private final NavigableMap memory; private BaseActionSource mySource; private StorageFilter mode = StorageFilter.EXTRACTABLE_ONLY; @@ -53,12 +54,12 @@ public class MEMonitorIInventory implements IMEMonitor { } @Override - public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { + public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { this.listeners.put(l, verificationToken); } @Override - public void removeListener(final IMEMonitorHandlerReceiver l) { + public void removeListener(final IMEMonitorHandlerReceiver l) { this.listeners.remove(l); } @@ -119,7 +120,7 @@ public class MEMonitorIInventory implements IMEMonitor { public TickRateModulation onTick() { - final LinkedList changes = new LinkedList<>(); + final LinkedList> changes = new LinkedList<>(); this.list.resetStatus(); int high = 0; @@ -204,14 +205,13 @@ public class MEMonitorIInventory implements IMEMonitor { return !Platform.isSameItemPrecise(a, b); } - private void postDifference(final Iterable a) { + private void postDifference(final Iterable> a) { // AELog.info( a.getItemStack().getUnlocalizedName() + " @ " + a.getStackSize() ); if (a != null) { - final Iterator, Object>> i = this.listeners.entrySet() - .iterator(); + final Iterator> i = this.listeners.entrySet().iterator(); while (i.hasNext()) { - final Entry, Object> l = i.next(); - final IMEMonitorHandlerReceiver key = l.getKey(); + final Entry l = i.next(); + final IMEMonitorHandlerReceiver key = l.getKey(); if (key.isValid(l.getValue())) { key.postChange(this, a, this.getActionSource()); } else { diff --git a/src/main/java/appeng/me/storage/MEMonitorPassThrough.java b/src/main/java/appeng/me/storage/MEMonitorPassThrough.java index ee043e240..9af295e06 100644 --- a/src/main/java/appeng/me/storage/MEMonitorPassThrough.java +++ b/src/main/java/appeng/me/storage/MEMonitorPassThrough.java @@ -31,7 +31,7 @@ import appeng.util.item.ItemFilterList; public class MEMonitorPassThrough> extends MEPassThrough implements IMEMonitor, IMEMonitorHandlerReceiver { - private final HashMap, Object> listeners = new HashMap<>(); + private final HashMap listeners = new HashMap<>(); private BaseActionSource changeSource; private IMEMonitor monitor; private StorageFilter mode = StorageFilter.EXTRACTABLE_ONLY; @@ -86,12 +86,12 @@ public class MEMonitorPassThrough> extends MEPassThrough l, final Object verificationToken) { + public void addListener(final IMEMonitorHandlerReceiver l, final Object verificationToken) { this.listeners.put(l, verificationToken); } @Override - public void removeListener(final IMEMonitorHandlerReceiver l) { + public void removeListener(final IMEMonitorHandlerReceiver l) { this.listeners.remove(l); } @@ -112,10 +112,10 @@ public class MEMonitorPassThrough> extends MEPassThrough monitor, final Iterable change, final BaseActionSource source) { - final Iterator, Object>> i = this.listeners.entrySet().iterator(); + final Iterator> i = this.listeners.entrySet().iterator(); while (i.hasNext()) { - final Entry, Object> e = i.next(); - final IMEMonitorHandlerReceiver receiver = e.getKey(); + final Entry e = i.next(); + final IMEMonitorHandlerReceiver receiver = e.getKey(); if (receiver.isValid(e.getValue())) { receiver.postChange(this, change, source); } else { @@ -126,10 +126,10 @@ public class MEMonitorPassThrough> extends MEPassThrough, Object>> i = this.listeners.entrySet().iterator(); + final Iterator> i = this.listeners.entrySet().iterator(); while (i.hasNext()) { - final Entry, Object> e = i.next(); - final IMEMonitorHandlerReceiver receiver = e.getKey(); + final Entry e = i.next(); + final IMEMonitorHandlerReceiver receiver = e.getKey(); if (receiver.isValid(e.getValue())) { receiver.onListUpdate(); } else { diff --git a/src/main/java/appeng/me/storage/VoidCellInventory.java b/src/main/java/appeng/me/storage/VoidCellInventory.java index bf2fd2d75..23d7ed954 100644 --- a/src/main/java/appeng/me/storage/VoidCellInventory.java +++ b/src/main/java/appeng/me/storage/VoidCellInventory.java @@ -5,138 +5,160 @@ import javax.annotation.Nonnull; import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; -import appeng.api.AEApi; -import appeng.api.config.AccessRestriction; import appeng.api.config.Actionable; import appeng.api.config.FuzzyMode; -import appeng.api.config.IncludeExclude; -import appeng.api.config.Upgrades; -import appeng.api.exceptions.AppEngException; -import appeng.api.implementations.items.IUpgradeModule; import appeng.api.networking.security.BaseActionSource; +import appeng.api.storage.ICellInventory; import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.StorageChannel; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.items.storage.ItemVoidStorageCell; -import appeng.util.item.AEItemStack; -import appeng.util.prioitylist.FuzzyPriorityList; -import appeng.util.prioitylist.OreFilteredList; -import appeng.util.prioitylist.PrecisePriorityList; +import appeng.tile.inventory.IAEStackInventory; -public class VoidCellInventory extends MEInventoryHandler { +public class VoidCellInventory> implements ICellInventory { - private final boolean fuzzy; + private final ItemStack cellItem; + private final ItemVoidStorageCell cellType; - protected VoidCellInventory(final ItemStack o) throws AppEngException { - super(new NullInventory<>(), StorageChannel.ITEMS); - if (o == null || !(o.getItem() instanceof ItemVoidStorageCell cell)) { - throw new AppEngException("ItemStack was used as a void cell, but was not a void cell!"); - } - final IInventory upgrades = cell.getUpgradesInventory(o); - final IInventory config = cell.getConfigInventory(o); - final FuzzyMode fzMode = cell.getFuzzyMode(o); - final String filter = cell.getOreFilter(o); - boolean hasInverter = false; - boolean hasFuzzy = false; - boolean hasOreFilter = false; - boolean hasSticky = false; + protected VoidCellInventory(ItemStack is) { + super(); - for (int x = 0; x < upgrades.getSizeInventory(); x++) { - final ItemStack is = upgrades.getStackInSlot(x); - if (is != null && is.getItem() instanceof IUpgradeModule) { - final Upgrades u = ((IUpgradeModule) is.getItem()).getType(is); - if (u != null) { - switch (u) { - case FUZZY -> hasFuzzy = true; - case INVERTER -> hasInverter = true; - case ORE_FILTER -> hasOreFilter = true; - case STICKY -> hasSticky = true; - default -> {} - } - } - } - } - if (hasSticky) { - setSticky(true); - } - this.fuzzy = hasFuzzy; - this.setWhitelist(hasInverter ? IncludeExclude.BLACKLIST : IncludeExclude.WHITELIST); - if (hasOreFilter && !filter.isEmpty()) { - this.setPartitionList(new OreFilteredList(filter)); - } else { - final IItemList priorityList = AEApi.instance().storage().createItemList(); - for (int x = 0; x < config.getSizeInventory(); x++) { - final ItemStack is = config.getStackInSlot(x); - if (is != null) { - priorityList.add(AEItemStack.create(is)); - } - } - if (!priorityList.isEmpty()) { - if (hasFuzzy) { - this.setPartitionList(new FuzzyPriorityList<>(priorityList, fzMode)); - } else { - this.setPartitionList(new PrecisePriorityList<>(priorityList)); - } - } - } + this.cellItem = is; + if (this.cellItem.getItem() instanceof ItemVoidStorageCell type) { + this.cellType = type; + } else this.cellType = null; } - public static IMEInventoryHandler getCell(final ItemStack o) { - try { - return new VoidCellInventory(o); - } catch (final AppEngException e) { - return null; - } - } - - @Override - public IAEItemStack injectItems(IAEItemStack input, Actionable type, BaseActionSource src) { - return this.canAccept(input) ? null : input; - } - - @Override - public IAEItemStack extractItems(IAEItemStack request, Actionable mode, BaseActionSource src) { + public static IMEInventoryHandler getCell(final ItemStack o, final StorageChannel sc) { + if (sc == StorageChannel.ITEMS) return new ItemCellInventoryHandler(new VoidCellInventory<>(o)); + if (sc == StorageChannel.FLUIDS) return new FluidCellInventoryHandler(new VoidCellInventory<>(o)); return null; } @Override - public IItemList getAvailableItems(IItemList out, int iteration) { + public StackType injectItems(StackType input, Actionable type, BaseActionSource src) { + return null; + } + + @Override + public StackType extractItems(StackType request, Actionable mode, BaseActionSource src) { + return null; + } + + @Override + public IItemList getAvailableItems(IItemList out, int iteration) { return out; } @Override - public IAEItemStack getAvailableItem(@Nonnull IAEItemStack request, int iteration) { + public StackType getAvailableItem(@Nonnull StackType request, int iteration) { return null; } @Override - public AccessRestriction getAccess() { - // you shouldn't try to read anything in void cell. - return AccessRestriction.WRITE; + public StorageChannel getChannel() { + return this.cellType.getStorageChannel(); } @Override - public boolean canAccept(IAEItemStack input) { - if (this.getWhitelist() == IncludeExclude.BLACKLIST && this.getPartitionList().isListed(input)) { - return false; - } - if (this.getPartitionList().isEmpty() || this.getWhitelist() == IncludeExclude.BLACKLIST) { - return true; - } - return this.getPartitionList().isListed(input); + public ItemStack getItemStack() { + return this.cellItem; } @Override - public int getSlot() { + public double getIdleDrain() { return 0; } - public boolean isPreformatted() { - return !this.getPartitionList().isEmpty(); + @Override + public FuzzyMode getFuzzyMode() { + return this.cellType.getFuzzyMode(this.cellItem); } - public boolean isFuzzy() { - return this.fuzzy; + @Override + @Deprecated + public IInventory getConfigInventory() { + return this.cellType.getConfigInventory(this.cellItem); + } + + @Override + public IAEStackInventory getConfigAEInventory() { + return this.cellType.getConfigAEInventory(this.cellItem); + } + + @Override + public IInventory getUpgradesInventory() { + return this.cellType.getUpgradesInventory(this.cellItem); + } + + @Override + public int getBytesPerType() { + return 0; + } + + @Override + public boolean canHoldNewItem() { + return true; + } + + @Override + public long getTotalBytes() { + return 0; + } + + @Override + public long getFreeBytes() { + return 0; + } + + @Override + public long getUsedBytes() { + return 0; + } + + @Override + public long getTotalItemTypes() { + return Long.MAX_VALUE; + } + + @Override + public long getStoredItemCount() { + return 0; + } + + @Override + public long getStoredItemTypes() { + return 0; + } + + @Override + public long getRemainingItemTypes() { + return Long.MAX_VALUE; + } + + @Override + public long getRemainingItemCount() { + return 0; + } + + @Override + public long getRemainingItemsCountDist(StackType l) { + return 0; + } + + @Override + public int getUnusedItemCount() { + return 0; + } + + @Override + public int getStatusForCell() { + return 1; + } + + @Override + public String getOreFilter() { + return this.cellType.getOreFilter(this.cellItem); } } diff --git a/src/main/java/appeng/parts/automation/PartBaseExportBus.java b/src/main/java/appeng/parts/automation/PartBaseExportBus.java new file mode 100644 index 000000000..c637e5be5 --- /dev/null +++ b/src/main/java/appeng/parts/automation/PartBaseExportBus.java @@ -0,0 +1,311 @@ +package appeng.parts.automation; + +import net.minecraft.client.renderer.RenderBlocks; +import net.minecraft.item.ItemStack; +import net.minecraft.nbt.NBTTagCompound; + +import com.google.common.collect.ImmutableSet; + +import appeng.api.config.Actionable; +import appeng.api.config.FuzzyMode; +import appeng.api.config.InsertionMode; +import appeng.api.config.PowerMultiplier; +import appeng.api.config.SchedulingMode; +import appeng.api.config.Settings; +import appeng.api.config.Upgrades; +import appeng.api.config.YesNo; +import appeng.api.networking.IGridNode; +import appeng.api.networking.crafting.ICraftingGrid; +import appeng.api.networking.crafting.ICraftingLink; +import appeng.api.networking.crafting.ICraftingRequester; +import appeng.api.networking.energy.IEnergyGrid; +import appeng.api.networking.ticking.TickRateModulation; +import appeng.api.networking.ticking.TickingRequest; +import appeng.api.parts.IPartCollisionHelper; +import appeng.api.parts.IPartRenderHelper; +import appeng.api.storage.IMEInventory; +import appeng.api.storage.IMEMonitor; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.client.texture.CableBusTextures; +import appeng.core.AELog; +import appeng.core.settings.TickRates; +import appeng.helpers.MultiCraftingTracker; +import appeng.helpers.Reflected; +import appeng.me.GridAccessException; +import appeng.util.InventoryAdaptor; +import appeng.util.Platform; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public abstract class PartBaseExportBus> extends PartSharedItemBus + implements ICraftingRequester { + + private final MultiCraftingTracker craftingTracker = new MultiCraftingTracker(this, 9); + protected long itemToSend = 1; + private boolean didSomething = false; + private int nextSlot = 0; + + @Reflected + public PartBaseExportBus(final ItemStack is) { + super(is); + + this.getConfigManager().registerSetting(Settings.CRAFT_ONLY, YesNo.NO); + this.getConfigManager().registerSetting(Settings.SCHEDULING_MODE, SchedulingMode.DEFAULT); + } + + @Override + public void readFromNBT(final NBTTagCompound extra) { + super.readFromNBT(extra); + this.craftingTracker.readFromNBT(extra); + this.nextSlot = extra.getInteger("nextSlot"); + } + + @Override + public void writeToNBT(final NBTTagCompound extra) { + super.writeToNBT(extra); + this.craftingTracker.writeToNBT(extra); + extra.setInteger("nextSlot", this.nextSlot); + } + + @Override + protected TickRateModulation doBusWork() { + if (!this.getProxy().isActive() || !this.canDoBusWork()) { + return TickRateModulation.IDLE; + } + + this.itemToSend = this.calculateAmountToSend(); + this.didSomething = false; + + try { + final InventoryAdaptor destination = this.getHandler(); + final IMEMonitor gridInv = this.getMonitor(); + final IEnergyGrid energy = this.getProxy().getEnergy(); + final ICraftingGrid cg = this.getProxy().getCrafting(); + final FuzzyMode fuzzyMode = supportFuzzy() + ? (FuzzyMode) this.getConfigManager().getSetting(Settings.FUZZY_MODE) + : null; + final SchedulingMode schedulingMode = (SchedulingMode) this.getConfigManager() + .getSetting(Settings.SCHEDULING_MODE); + + if (destination != null) { + if (this.getInstalledUpgrades(Upgrades.ORE_FILTER) == 0) { + int x = 0; + + for (x = 0; x < this.availableSlots() && this.itemToSend > 0; x++) { + final int slotToExport = slotSequence[this.getStartingSlot(schedulingMode, x)]; + + final StackType aes = (StackType) this.getAEInventoryByName(StorageName.NONE) + .getAEStackInSlot(slotToExport); + + if (aes == null || this.itemToSend <= 0 || this.craftOnly()) { + if (this.isCraftingEnabled()) { + this.didSomething = this.craftingTracker.handleCrafting( + slotToExport, + this.itemToSend, + aes, + destination, + this.getTile().getWorldObj(), + this.getProxy().getGrid(), + cg, + this.mySrc) || this.didSomething; + } + continue; + } + + final long before = this.itemToSend; + + if (supportFuzzy() && this.getInstalledUpgrades(Upgrades.FUZZY) > 0) { + doFuzzy(aes, fuzzyMode, destination, energy, gridInv); + } else { + this.pushItemIntoTarget(destination, energy, gridInv, aes); + } + + if (this.itemToSend == before && this.isCraftingEnabled()) { + this.didSomething = this.craftingTracker.handleCrafting( + slotToExport, + this.itemToSend, + aes, + destination, + this.getTile().getWorldObj(), + this.getProxy().getGrid(), + cg, + this.mySrc) || this.didSomething; + } + } + + this.updateSchedulingMode(schedulingMode, x); + } else if (supportOreDict()) { + doOreDict(destination, energy, gridInv); + } + } else { + return TickRateModulation.SLEEP; + } + } catch (final GridAccessException e) { + // :P + } + + return this.didSomething ? TickRateModulation.FASTER : TickRateModulation.SLOWER; + } + + @Override + public void getBoxes(final IPartCollisionHelper bch) { + bch.addBox(4, 4, 12, 12, 12, 14); + bch.addBox(5, 5, 14, 11, 11, 15); + bch.addBox(6, 6, 15, 10, 10, 16); + bch.addBox(6, 6, 11, 10, 10, 12); + } + + @Override + @SideOnly(Side.CLIENT) + public void renderInventory(final IPartRenderHelper rh, final RenderBlocks renderer) { + rh.setTexture( + CableBusTextures.PartExportSides.getIcon(), + CableBusTextures.PartExportSides.getIcon(), + CableBusTextures.PartMonitorBack.getIcon(), + this.getFaceIcon(), + CableBusTextures.PartExportSides.getIcon(), + CableBusTextures.PartExportSides.getIcon()); + + rh.setBounds(4, 4, 12, 12, 12, 14); + rh.renderInventoryBox(renderer); + + rh.setBounds(5, 5, 14, 11, 11, 15); + rh.renderInventoryBox(renderer); + + rh.setBounds(6, 6, 15, 10, 10, 16); + rh.renderInventoryBox(renderer); + } + + @Override + @SideOnly(Side.CLIENT) + public void renderStatic(final int x, final int y, final int z, final IPartRenderHelper rh, + final RenderBlocks renderer) { + this.setRenderCache(rh.useSimplifiedRendering(x, y, z, this, this.getRenderCache())); + rh.setTexture( + CableBusTextures.PartExportSides.getIcon(), + CableBusTextures.PartExportSides.getIcon(), + CableBusTextures.PartMonitorBack.getIcon(), + this.getFaceIcon(), + CableBusTextures.PartExportSides.getIcon(), + CableBusTextures.PartExportSides.getIcon()); + + rh.setBounds(4, 4, 12, 12, 12, 14); + rh.renderBlock(x, y, z, renderer); + + rh.setBounds(5, 5, 14, 11, 11, 15); + rh.renderBlock(x, y, z, renderer); + + rh.setBounds(6, 6, 15, 10, 10, 16); + rh.renderBlock(x, y, z, renderer); + + rh.setTexture( + CableBusTextures.PartMonitorSidesStatus.getIcon(), + CableBusTextures.PartMonitorSidesStatus.getIcon(), + CableBusTextures.PartMonitorBack.getIcon(), + this.getFaceIcon(), + CableBusTextures.PartMonitorSidesStatus.getIcon(), + CableBusTextures.PartMonitorSidesStatus.getIcon()); + + rh.setBounds(6, 6, 11, 10, 10, 12); + rh.renderBlock(x, y, z, renderer); + + this.renderLights(x, y, z, rh, renderer); + } + + @Override + public TickingRequest getTickingRequest(final IGridNode node) { + return new TickingRequest(TickRates.ExportBus.getMin(), TickRates.ExportBus.getMax(), this.isSleeping(), false); + } + + @Override + public ImmutableSet getRequestedJobs() { + return this.craftingTracker.getRequestedJobs(); + } + + @Override + public IAEStack injectCraftedItems(final ICraftingLink link, final IAEStack items, final Actionable mode) { + final InventoryAdaptor d = this.getHandler(); + + try { + if (d != null && this.getProxy().isActive()) { + final IEnergyGrid energy = this.getProxy().getEnergy(); + final double power = (double) items.getStackSize() / items.getPowerMultiplier(); + + if (energy.extractAEPower(power, mode, PowerMultiplier.CONFIG) > power - 0.01) { + if (mode == Actionable.MODULATE) { + return d.addStack(items, InsertionMode.DEFAULT); + } + return d.simulateAddStack(items, InsertionMode.DEFAULT); + } + } + } catch (final GridAccessException e) { + AELog.debug(e); + } + + return items; + } + + @Override + public void jobStateChange(final ICraftingLink link) { + this.craftingTracker.jobStateChange(link); + } + + private boolean craftOnly() { + return this.getConfigManager().getSetting(Settings.CRAFT_ONLY) == YesNo.YES; + } + + private boolean isCraftingEnabled() { + return this.getInstalledUpgrades(Upgrades.CRAFTING) > 0; + } + + protected void pushItemIntoTarget(final InventoryAdaptor d, final IEnergyGrid energy, + final IMEInventory inv, StackType aes) { + final StackType ins = aes.copy(); + ins.setStackSize(this.itemToSend); + + final StackType o = (StackType) d.simulateAddStack(ins, InsertionMode.DEFAULT); + final long canFit = o == null ? this.itemToSend : this.itemToSend - o.getStackSize(); + + if (canFit > 0) { + aes = aes.copy(); + aes.setStackSize(canFit); + final StackType itemsToAdd = Platform.poweredExtraction(energy, inv, aes, this.mySrc); + + if (itemsToAdd != null) { + this.itemToSend -= itemsToAdd.getStackSize(); + + final StackType failed = (StackType) d.addStack(itemsToAdd, InsertionMode.DEFAULT); + if (failed != null) { + aes.setStackSize(failed.getStackSize()); + inv.injectItems(aes, Actionable.MODULATE, this.mySrc); + } else { + this.didSomething = true; + } + } + } + } + + private int getStartingSlot(final SchedulingMode schedulingMode, final int x) { + if (schedulingMode == SchedulingMode.RANDOM) { + return Platform.getRandom().nextInt(this.availableSlots()); + } + + if (schedulingMode == SchedulingMode.ROUNDROBIN) { + return (this.nextSlot + x) % this.availableSlots(); + } + + return x; + } + + private void updateSchedulingMode(final SchedulingMode schedulingMode, final int x) { + if (schedulingMode == SchedulingMode.ROUNDROBIN) { + this.nextSlot = (this.nextSlot + x) % this.availableSlots(); + } + } + + protected abstract void doFuzzy(StackType aes, FuzzyMode fzMode, InventoryAdaptor destination, IEnergyGrid energy, + IMEMonitor gridInv); + + protected abstract void doOreDict(InventoryAdaptor destination, IEnergyGrid energy, IMEMonitor gridInv); +} diff --git a/src/main/java/appeng/parts/automation/PartBaseImportBus.java b/src/main/java/appeng/parts/automation/PartBaseImportBus.java new file mode 100644 index 000000000..8db153d37 --- /dev/null +++ b/src/main/java/appeng/parts/automation/PartBaseImportBus.java @@ -0,0 +1,178 @@ +package appeng.parts.automation; + +import net.minecraft.client.renderer.RenderBlocks; +import net.minecraft.item.ItemStack; + +import appeng.api.config.Actionable; +import appeng.api.config.FuzzyMode; +import appeng.api.config.PowerMultiplier; +import appeng.api.config.Settings; +import appeng.api.config.Upgrades; +import appeng.api.networking.IGridNode; +import appeng.api.networking.energy.IEnergyGrid; +import appeng.api.networking.energy.IEnergySource; +import appeng.api.networking.ticking.TickRateModulation; +import appeng.api.networking.ticking.TickingRequest; +import appeng.api.parts.IPartCollisionHelper; +import appeng.api.parts.IPartRenderHelper; +import appeng.api.storage.IMEInventory; +import appeng.api.storage.IMEMonitor; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.client.texture.CableBusTextures; +import appeng.core.settings.TickRates; +import appeng.me.GridAccessException; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; + +public abstract class PartBaseImportBus> extends PartSharedItemBus { + + protected IMEInventory destination = null; + protected StackType lastItemChecked = null; + protected int itemToSend; // used in tickingRequest + protected boolean worked; // used in tickingRequest + + public PartBaseImportBus(final ItemStack is) { + super(is); + } + + @Override + public void getBoxes(final IPartCollisionHelper bch) { + bch.addBox(6, 6, 11, 10, 10, 13); + bch.addBox(5, 5, 13, 11, 11, 14); + bch.addBox(4, 4, 14, 12, 12, 16); + } + + @Override + @SideOnly(Side.CLIENT) + public void renderInventory(final IPartRenderHelper rh, final RenderBlocks renderer) { + rh.setTexture( + CableBusTextures.PartImportSides.getIcon(), + CableBusTextures.PartImportSides.getIcon(), + CableBusTextures.PartMonitorBack.getIcon(), + this.getFaceIcon(), + CableBusTextures.PartImportSides.getIcon(), + CableBusTextures.PartImportSides.getIcon()); + + rh.setBounds(3, 3, 15, 13, 13, 16); + rh.renderInventoryBox(renderer); + + rh.setBounds(4, 4, 14, 12, 12, 15); + rh.renderInventoryBox(renderer); + + rh.setBounds(5, 5, 13, 11, 11, 14); + rh.renderInventoryBox(renderer); + } + + @Override + @SideOnly(Side.CLIENT) + public void renderStatic(final int x, final int y, final int z, final IPartRenderHelper rh, + final RenderBlocks renderer) { + this.setRenderCache(rh.useSimplifiedRendering(x, y, z, this, this.getRenderCache())); + rh.setTexture( + CableBusTextures.PartImportSides.getIcon(), + CableBusTextures.PartImportSides.getIcon(), + CableBusTextures.PartMonitorBack.getIcon(), + this.getFaceIcon(), + CableBusTextures.PartImportSides.getIcon(), + CableBusTextures.PartImportSides.getIcon()); + + rh.setBounds(4, 4, 14, 12, 12, 16); + rh.renderBlock(x, y, z, renderer); + + rh.setBounds(5, 5, 13, 11, 11, 14); + rh.renderBlock(x, y, z, renderer); + + rh.setBounds(6, 6, 12, 10, 10, 13); + rh.renderBlock(x, y, z, renderer); + rh.setTexture( + CableBusTextures.PartMonitorSidesStatus.getIcon(), + CableBusTextures.PartMonitorSidesStatus.getIcon(), + CableBusTextures.PartMonitorBack.getIcon(), + this.getFaceIcon(), + CableBusTextures.PartMonitorSidesStatus.getIcon(), + CableBusTextures.PartMonitorSidesStatus.getIcon()); + + rh.setBounds(6, 6, 11, 10, 10, 12); + rh.renderBlock(x, y, z, renderer); + + this.renderLights(x, y, z, rh, renderer); + } + + @Override + public TickingRequest getTickingRequest(final IGridNode node) { + return new TickingRequest( + TickRates.ImportBus.getMin(), + TickRates.ImportBus.getMax(), + this.getHandler() == null, + false); + } + + @Override + protected TickRateModulation doBusWork() { + if (!this.getProxy().isActive() || !this.canDoBusWork()) { + return TickRateModulation.IDLE; + } + + this.worked = false; + + final Object myTarget = this.getTarget(); + final FuzzyMode fzMode = (FuzzyMode) this.getConfigManager().getSetting(Settings.FUZZY_MODE); + + if (myTarget != null) { + try { + this.itemToSend = this.calculateAmountToSend(); + this.itemToSend = Math.min( + this.itemToSend, + (int) (0.01 + this.getProxy().getEnergy().extractAEPower( + this.itemToSend / getPowerMultiplier(), + Actionable.SIMULATE, + PowerMultiplier.CONFIG))); + + final IMEMonitor inv = this.getMonitor(); + final IEnergyGrid energy = this.getProxy().getEnergy(); + + boolean configured = false; + if (this.getInstalledUpgrades(Upgrades.ORE_FILTER) == 0) { + for (int x = 0; x < this.availableSlots(); x++) { + final int slotToExport = slotSequence[x]; + final StackType ais = (StackType) this.getAEInventoryByName(StorageName.NONE) + .getAEStackInSlot(slotToExport); + if (ais != null && this.itemToSend > 0) { + configured = true; + while (this.itemToSend > 0) { + if (this.importStuff(myTarget, ais, inv, energy, fzMode)) { + break; + } + } + } + } + } else if (supportOreDict()) configured = doOreDict(myTarget, inv, energy, fzMode); + + if (!configured) { + while (this.itemToSend > 0) { + if (this.importStuff(myTarget, null, inv, energy, fzMode)) { + break; + } + } + } + } catch (final GridAccessException e) { + // :3 + } + } else { + return TickRateModulation.SLEEP; + } + + return this.worked ? TickRateModulation.FASTER : TickRateModulation.SLOWER; + } + + protected abstract Object getTarget(); + + protected abstract boolean importStuff(final Object myTarget, final StackType whatToImport, + final IMEMonitor inv, final IEnergySource energy, final FuzzyMode fzMode); + + protected abstract boolean doOreDict(final Object myTarget, IMEMonitor inv, final IEnergyGrid energy, + final FuzzyMode fzMode); + + protected abstract int getPowerMultiplier(); +} diff --git a/src/main/java/appeng/parts/automation/PartExportBus.java b/src/main/java/appeng/parts/automation/PartExportBus.java index cb9e2baf2..10dae82e1 100644 --- a/src/main/java/appeng/parts/automation/PartExportBus.java +++ b/src/main/java/appeng/parts/automation/PartExportBus.java @@ -13,376 +13,104 @@ package appeng.parts.automation; import java.util.ArrayList; import java.util.Collection; -import net.minecraft.client.renderer.RenderBlocks; -import net.minecraft.entity.player.EntityPlayer; import net.minecraft.item.ItemStack; -import net.minecraft.nbt.NBTTagCompound; -import net.minecraft.util.Vec3; -import com.google.common.collect.ImmutableSet; - -import appeng.api.config.Actionable; import appeng.api.config.FuzzyMode; -import appeng.api.config.PowerMultiplier; -import appeng.api.config.RedstoneMode; -import appeng.api.config.SchedulingMode; import appeng.api.config.Settings; import appeng.api.config.Upgrades; -import appeng.api.config.YesNo; -import appeng.api.networking.IGridNode; -import appeng.api.networking.crafting.ICraftingGrid; -import appeng.api.networking.crafting.ICraftingLink; import appeng.api.networking.crafting.ICraftingRequester; import appeng.api.networking.energy.IEnergyGrid; -import appeng.api.networking.security.BaseActionSource; -import appeng.api.networking.security.MachineSource; -import appeng.api.networking.ticking.TickRateModulation; -import appeng.api.networking.ticking.TickingRequest; -import appeng.api.parts.IPartCollisionHelper; -import appeng.api.parts.IPartRenderHelper; -import appeng.api.storage.IMEInventory; import appeng.api.storage.IMEMonitor; import appeng.api.storage.data.IAEItemStack; -import appeng.client.texture.CableBusTextures; -import appeng.core.AELog; -import appeng.core.settings.TickRates; -import appeng.core.sync.GuiBridge; -import appeng.helpers.MultiCraftingTracker; import appeng.helpers.Reflected; import appeng.me.GridAccessException; import appeng.me.cache.NetworkMonitor; import appeng.util.InventoryAdaptor; import appeng.util.IterationCounter; -import appeng.util.Platform; -import appeng.util.item.AEItemStack; import appeng.util.prioitylist.OreFilteredList; -import cpw.mods.fml.relauncher.Side; -import cpw.mods.fml.relauncher.SideOnly; -public class PartExportBus extends PartSharedItemBus implements ICraftingRequester { - - private final MultiCraftingTracker craftingTracker = new MultiCraftingTracker(this, 9); - private final BaseActionSource mySrc; - private long itemToSend = 1; - private boolean didSomething = false; - private int nextSlot = 0; +public class PartExportBus extends PartBaseExportBus implements ICraftingRequester { @Reflected public PartExportBus(final ItemStack is) { super(is); - this.getConfigManager().registerSetting(Settings.REDSTONE_CONTROLLED, RedstoneMode.IGNORE); this.getConfigManager().registerSetting(Settings.FUZZY_MODE, FuzzyMode.IGNORE_ALL); - this.getConfigManager().registerSetting(Settings.CRAFT_ONLY, YesNo.NO); - this.getConfigManager().registerSetting(Settings.SCHEDULING_MODE, SchedulingMode.DEFAULT); - this.mySrc = new MachineSource(this); } @Override - public void readFromNBT(final NBTTagCompound extra) { - super.readFromNBT(extra); - this.craftingTracker.readFromNBT(extra); - this.nextSlot = extra.getInteger("nextSlot"); - } + public int calculateAmountToSend() { + int toSend = switch (this.getInstalledUpgrades(Upgrades.SPEED)) { + case 1 -> 8; + case 2 -> 32; + case 3 -> 64; + case 4 -> 96; + default -> 1; + }; - @Override - public void writeToNBT(final NBTTagCompound extra) { - super.writeToNBT(extra); - this.craftingTracker.writeToNBT(extra); - extra.setInteger("nextSlot", this.nextSlot); - } - - @Override - protected TickRateModulation doBusWork() { - if (!this.getProxy().isActive() || !this.canDoBusWork()) { - return TickRateModulation.IDLE; + switch (this.getInstalledUpgrades(Upgrades.SUPERSPEED)) { + case 1 -> toSend += 16; + case 2 -> toSend += 16 * 8; + case 3 -> toSend += 16 * 8 * 8; + case 4 -> toSend += 16 * 8 * 8 * 8; } - this.itemToSend = this.calculateItemsToSend(); - this.didSomething = false; + switch (this.getInstalledUpgrades(Upgrades.SUPERLUMINALSPEED)) { + case 1 -> toSend += 131_072; + case 2 -> toSend += 131_072 * 8; + case 3 -> toSend += 131_072 * 8 * 8; + case 4 -> toSend += 131_072 * 8 * 8 * 8; + } + return toSend; + } + + @Override + protected boolean supportFuzzy() { + return true; + } + + @Override + protected boolean supportOreDict() { + return true; + } + + @Override + protected IMEMonitor getMonitor() { try { - final InventoryAdaptor destination = this.getHandler(); - final IMEMonitor gridInv = this.getProxy().getStorage().getItemInventory(); - final IEnergyGrid energy = this.getProxy().getEnergy(); - final ICraftingGrid cg = this.getProxy().getCrafting(); - final FuzzyMode fzMode = (FuzzyMode) this.getConfigManager().getSetting(Settings.FUZZY_MODE); - final SchedulingMode schedulingMode = (SchedulingMode) this.getConfigManager() - .getSetting(Settings.SCHEDULING_MODE); - - if (destination != null) { - if (this.getInstalledUpgrades(Upgrades.ORE_FILTER) == 0) { - int x = 0; - - for (x = 0; x < this.availableSlots() && this.itemToSend > 0; x++) { - final int slotToExport = this.getStartingSlot(schedulingMode, x); - - final IAEItemStack ais = this.getConfig().getAEStackInSlot(slotToExport); - - if (ais == null || this.itemToSend <= 0 || this.craftOnly()) { - if (this.isCraftingEnabled()) { - this.didSomething = this.craftingTracker.handleCrafting( - slotToExport, - this.itemToSend, - ais, - destination, - this.getTile().getWorldObj(), - this.getProxy().getGrid(), - cg, - this.mySrc) || this.didSomething; - } - continue; - } - - final long before = this.itemToSend; - - if (this.getInstalledUpgrades(Upgrades.FUZZY) > 0) { - - /* - * This actually returns a NetworkInventoryHandler object. The method .getSortedFuzzyItems() - * used is the overriden one found in the .java file. - */ - - if (gridInv instanceof NetworkMonitor) { - final Collection fzlist = ((NetworkMonitor) gridInv) - .getHandler().getSortedFuzzyItems( - new ArrayList<>(), - ais, - fzMode, - IterationCounter.fetchNewId()); - - for (final IAEItemStack o : fzlist) { - this.pushItemIntoTarget(destination, energy, gridInv, o); - } - if (this.itemToSend <= 0) { - break; - } - } - - } else { - this.pushItemIntoTarget(destination, energy, gridInv, ais); - } - - if (this.itemToSend == before && this.isCraftingEnabled()) { - this.didSomething = this.craftingTracker.handleCrafting( - slotToExport, - this.itemToSend, - ais, - destination, - this.getTile().getWorldObj(), - this.getProxy().getGrid(), - cg, - this.mySrc) || this.didSomething; - } - } - - this.updateSchedulingMode(schedulingMode, x); - } else if (!oreFilterString.isEmpty()) { - if (filterPredicate == null) filterPredicate = OreFilteredList.makeFilter(oreFilterString); - - for (IAEItemStack stack : gridInv.getStorageList()) { - if (stack == null || filterPredicate == null || !this.filterPredicate.test(stack)) continue; - this.pushItemIntoTarget(destination, energy, gridInv, stack); - if (this.itemToSend <= 0) break; - } - } - } else { - return TickRateModulation.SLEEP; - } + return this.getProxy().getStorage().getItemInventory(); } catch (final GridAccessException e) { - // :P + return null; } - - return this.didSomething ? TickRateModulation.FASTER : TickRateModulation.SLOWER; } @Override - public void getBoxes(final IPartCollisionHelper bch) { - bch.addBox(4, 4, 12, 12, 12, 14); - bch.addBox(5, 5, 14, 11, 11, 15); - bch.addBox(6, 6, 15, 10, 10, 16); - bch.addBox(6, 6, 11, 10, 10, 12); - } + protected void doFuzzy(IAEItemStack aes, FuzzyMode fzMode, InventoryAdaptor destination, IEnergyGrid energy, + IMEMonitor gridInv) { + /* + * This actually returns a NetworkInventoryHandler object. The method .getSortedFuzzyItems() used is the + * overriden one found in the .java file. + */ + if (gridInv instanceof NetworkMonitor) { + final Collection fzlist = ((NetworkMonitor) gridInv).getHandler() + .getSortedFuzzyItems(new ArrayList<>(), aes, fzMode, IterationCounter.fetchNewId()); - @Override - @SideOnly(Side.CLIENT) - public void renderInventory(final IPartRenderHelper rh, final RenderBlocks renderer) { - rh.setTexture( - CableBusTextures.PartExportSides.getIcon(), - CableBusTextures.PartExportSides.getIcon(), - CableBusTextures.PartMonitorBack.getIcon(), - this.getItemStack().getIconIndex(), - CableBusTextures.PartExportSides.getIcon(), - CableBusTextures.PartExportSides.getIcon()); - - rh.setBounds(4, 4, 12, 12, 12, 14); - rh.renderInventoryBox(renderer); - - rh.setBounds(5, 5, 14, 11, 11, 15); - rh.renderInventoryBox(renderer); - - rh.setBounds(6, 6, 15, 10, 10, 16); - rh.renderInventoryBox(renderer); - } - - @Override - @SideOnly(Side.CLIENT) - public void renderStatic(final int x, final int y, final int z, final IPartRenderHelper rh, - final RenderBlocks renderer) { - this.setRenderCache(rh.useSimplifiedRendering(x, y, z, this, this.getRenderCache())); - rh.setTexture( - CableBusTextures.PartExportSides.getIcon(), - CableBusTextures.PartExportSides.getIcon(), - CableBusTextures.PartMonitorBack.getIcon(), - this.getItemStack().getIconIndex(), - CableBusTextures.PartExportSides.getIcon(), - CableBusTextures.PartExportSides.getIcon()); - - rh.setBounds(4, 4, 12, 12, 12, 14); - rh.renderBlock(x, y, z, renderer); - - rh.setBounds(5, 5, 14, 11, 11, 15); - rh.renderBlock(x, y, z, renderer); - - rh.setBounds(6, 6, 15, 10, 10, 16); - rh.renderBlock(x, y, z, renderer); - - rh.setTexture( - CableBusTextures.PartMonitorSidesStatus.getIcon(), - CableBusTextures.PartMonitorSidesStatus.getIcon(), - CableBusTextures.PartMonitorBack.getIcon(), - this.getItemStack().getIconIndex(), - CableBusTextures.PartMonitorSidesStatus.getIcon(), - CableBusTextures.PartMonitorSidesStatus.getIcon()); - - rh.setBounds(6, 6, 11, 10, 10, 12); - rh.renderBlock(x, y, z, renderer); - - this.renderLights(x, y, z, rh, renderer); - } - - @Override - public int cableConnectionRenderTo() { - return 5; - } - - @Override - public boolean onPartActivate(final EntityPlayer player, final Vec3 pos) { - if (!player.isSneaking()) { - if (Platform.isClient()) { - return true; - } - - Platform.openGUI(player, this.getHost().getTile(), this.getSide(), GuiBridge.GUI_BUS); - return true; - } - - return false; - } - - @Override - public TickingRequest getTickingRequest(final IGridNode node) { - return new TickingRequest(TickRates.ExportBus.getMin(), TickRates.ExportBus.getMax(), this.isSleeping(), false); - } - - @Override - public RedstoneMode getRSMode() { - return (RedstoneMode) this.getConfigManager().getSetting(Settings.REDSTONE_CONTROLLED); - } - - @Override - public TickRateModulation tickingRequest(final IGridNode node, final int ticksSinceLastCall) { - return this.doBusWork(); - } - - @Override - public ImmutableSet getRequestedJobs() { - return this.craftingTracker.getRequestedJobs(); - } - - @Override - public IAEItemStack injectCraftedItems(final ICraftingLink link, final IAEItemStack items, final Actionable mode) { - final InventoryAdaptor d = this.getHandler(); - - try { - if (d != null && this.getProxy().isActive()) { - final IEnergyGrid energy = this.getProxy().getEnergy(); - final double power = items.getStackSize(); - - if (energy.extractAEPower(power, mode, PowerMultiplier.CONFIG) > power - 0.01) { - if (mode == Actionable.MODULATE) { - return AEItemStack.create(d.addItems(items.getItemStack())); - } - return AEItemStack.create(d.simulateAdd(items.getItemStack())); - } - } - } catch (final GridAccessException e) { - AELog.debug(e); - } - - return items; - } - - @Override - public void jobStateChange(final ICraftingLink link) { - this.craftingTracker.jobStateChange(link); - } - - @Override - protected boolean isSleeping() { - return this.getHandler() == null || super.isSleeping(); - } - - private boolean craftOnly() { - return this.getConfigManager().getSetting(Settings.CRAFT_ONLY) == YesNo.YES; - } - - private boolean isCraftingEnabled() { - return this.getInstalledUpgrades(Upgrades.CRAFTING) > 0; - } - - private void pushItemIntoTarget(final InventoryAdaptor d, final IEnergyGrid energy, - final IMEInventory inv, IAEItemStack ais) { - final ItemStack is = ais.getItemStack(); - is.stackSize = (int) this.itemToSend; - - final ItemStack o = d.simulateAdd(is); - final long canFit = o == null ? this.itemToSend : this.itemToSend - o.stackSize; - - if (canFit > 0) { - ais = ais.copy(); - ais.setStackSize(canFit); - final IAEItemStack itemsToAdd = Platform.poweredExtraction(energy, inv, ais, this.mySrc); - - if (itemsToAdd != null) { - this.itemToSend -= itemsToAdd.getStackSize(); - - final ItemStack failed = d.addItems(itemsToAdd.getItemStack()); - if (failed != null) { - ais.setStackSize(failed.stackSize); - inv.injectItems(ais, Actionable.MODULATE, this.mySrc); - } else { - this.didSomething = true; - } + for (final IAEItemStack o : fzlist) { + this.pushItemIntoTarget(destination, energy, gridInv, o); } } } - private int getStartingSlot(final SchedulingMode schedulingMode, final int x) { - if (schedulingMode == SchedulingMode.RANDOM) { - return Platform.getRandom().nextInt(this.availableSlots()); - } + @Override + protected void doOreDict(InventoryAdaptor destination, IEnergyGrid energy, IMEMonitor gridInv) { + if (!oreFilterString.isEmpty()) { + if (filterPredicate == null) filterPredicate = OreFilteredList.makeFilter(oreFilterString); - if (schedulingMode == SchedulingMode.ROUNDROBIN) { - return (this.nextSlot + x) % this.availableSlots(); - } - - return x; - } - - private void updateSchedulingMode(final SchedulingMode schedulingMode, final int x) { - if (schedulingMode == SchedulingMode.ROUNDROBIN) { - this.nextSlot = (this.nextSlot + x) % this.availableSlots(); + for (IAEItemStack stack : gridInv.getStorageList()) { + if (stack == null || filterPredicate == null || !this.filterPredicate.test(stack)) continue; + this.pushItemIntoTarget(destination, energy, gridInv, stack); + if (this.itemToSend <= 0) break; + } } } diff --git a/src/main/java/appeng/parts/automation/PartFormationPlane.java b/src/main/java/appeng/parts/automation/PartFormationPlane.java index e43f250e4..81b10f421 100644 --- a/src/main/java/appeng/parts/automation/PartFormationPlane.java +++ b/src/main/java/appeng/parts/automation/PartFormationPlane.java @@ -66,6 +66,7 @@ import appeng.api.util.IConfigManager; import appeng.client.texture.CableBusTextures; import appeng.core.AEConfig; import appeng.core.sync.GuiBridge; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.IPriorityHost; import appeng.me.GridAccessException; import appeng.me.storage.MEInventoryHandler; @@ -79,7 +80,7 @@ import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; public class PartFormationPlane extends PartUpgradeable - implements ICellContainer, IPriorityHost, IMEInventory { + implements ICellContainer, IPriorityHost, IMEInventory, IPrimaryGuiIconProvider { private final MEInventoryHandler myHandler = new MEInventoryHandler(this, StorageChannel.ITEMS); private final AppEngInternalAEInventory Config = new AppEngInternalAEInventory(this, 63); @@ -646,4 +647,9 @@ public class PartFormationPlane extends PartUpgradeable public void saveChanges(final IMEInventory cellInventory) { // nope! } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().formationPlane().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/parts/automation/PartImportBus.java b/src/main/java/appeng/parts/automation/PartImportBus.java index 28ccaafe9..6f9155b2a 100644 --- a/src/main/java/appeng/parts/automation/PartImportBus.java +++ b/src/main/java/appeng/parts/automation/PartImportBus.java @@ -10,33 +10,17 @@ package appeng.parts.automation; -import net.minecraft.client.renderer.RenderBlocks; -import net.minecraft.entity.player.EntityPlayer; import net.minecraft.item.ItemStack; -import net.minecraft.util.Vec3; import appeng.api.AEApi; import appeng.api.config.Actionable; import appeng.api.config.FuzzyMode; import appeng.api.config.PowerMultiplier; -import appeng.api.config.RedstoneMode; -import appeng.api.config.Settings; import appeng.api.config.Upgrades; -import appeng.api.networking.IGridNode; import appeng.api.networking.energy.IEnergyGrid; import appeng.api.networking.energy.IEnergySource; -import appeng.api.networking.security.BaseActionSource; -import appeng.api.networking.security.MachineSource; -import appeng.api.networking.ticking.TickRateModulation; -import appeng.api.networking.ticking.TickingRequest; -import appeng.api.parts.IPartCollisionHelper; -import appeng.api.parts.IPartRenderHelper; -import appeng.api.storage.IMEInventory; import appeng.api.storage.IMEMonitor; import appeng.api.storage.data.IAEItemStack; -import appeng.client.texture.CableBusTextures; -import appeng.core.settings.TickRates; -import appeng.core.sync.GuiBridge; import appeng.helpers.Reflected; import appeng.me.GridAccessException; import appeng.util.InventoryAdaptor; @@ -45,24 +29,12 @@ import appeng.util.inv.IInventoryDestination; import appeng.util.inv.ItemSlot; import appeng.util.item.AEItemStack; import appeng.util.prioitylist.OreFilteredList; -import cpw.mods.fml.relauncher.Side; -import cpw.mods.fml.relauncher.SideOnly; -public class PartImportBus extends PartSharedItemBus implements IInventoryDestination { - - private final BaseActionSource source; - private IMEInventory destination = null; - private IAEItemStack lastItemChecked = null; - private int itemToSend; // used in tickingRequest - private boolean worked; // used in tickingRequest +public class PartImportBus extends PartBaseImportBus implements IInventoryDestination { @Reflected public PartImportBus(final ItemStack is) { super(is); - - this.getConfigManager().registerSetting(Settings.REDSTONE_CONTROLLED, RedstoneMode.IGNORE); - this.getConfigManager().registerSetting(Settings.FUZZY_MODE, FuzzyMode.IGNORE_ALL); - this.source = new MachineSource(this); } @Override @@ -74,7 +46,7 @@ public class PartImportBus extends PartSharedItemBus implements IInventoryDestin final IAEItemStack out = this.destination.injectItems( this.lastItemChecked = AEApi.instance().storage().createItemStack(stack), Actionable.SIMULATE, - this.source); + this.mySrc); if (out == null) { return true; } @@ -82,169 +54,65 @@ public class PartImportBus extends PartSharedItemBus implements IInventoryDestin } @Override - public void getBoxes(final IPartCollisionHelper bch) { - bch.addBox(6, 6, 11, 10, 10, 13); - bch.addBox(5, 5, 13, 11, 11, 14); - bch.addBox(4, 4, 14, 12, 12, 16); + protected Object getTarget() { + return this.getHandler(); } @Override - @SideOnly(Side.CLIENT) - public void renderInventory(final IPartRenderHelper rh, final RenderBlocks renderer) { - rh.setTexture( - CableBusTextures.PartImportSides.getIcon(), - CableBusTextures.PartImportSides.getIcon(), - CableBusTextures.PartMonitorBack.getIcon(), - this.getItemStack().getIconIndex(), - CableBusTextures.PartImportSides.getIcon(), - CableBusTextures.PartImportSides.getIcon()); - - rh.setBounds(3, 3, 15, 13, 13, 16); - rh.renderInventoryBox(renderer); - - rh.setBounds(4, 4, 14, 12, 12, 15); - rh.renderInventoryBox(renderer); - - rh.setBounds(5, 5, 13, 11, 11, 14); - rh.renderInventoryBox(renderer); + protected int getPowerMultiplier() { + return 1; } @Override - @SideOnly(Side.CLIENT) - public void renderStatic(final int x, final int y, final int z, final IPartRenderHelper rh, - final RenderBlocks renderer) { - this.setRenderCache(rh.useSimplifiedRendering(x, y, z, this, this.getRenderCache())); - rh.setTexture( - CableBusTextures.PartImportSides.getIcon(), - CableBusTextures.PartImportSides.getIcon(), - CableBusTextures.PartMonitorBack.getIcon(), - this.getItemStack().getIconIndex(), - CableBusTextures.PartImportSides.getIcon(), - CableBusTextures.PartImportSides.getIcon()); - - rh.setBounds(4, 4, 14, 12, 12, 16); - rh.renderBlock(x, y, z, renderer); - - rh.setBounds(5, 5, 13, 11, 11, 14); - rh.renderBlock(x, y, z, renderer); - - rh.setBounds(6, 6, 12, 10, 10, 13); - rh.renderBlock(x, y, z, renderer); - rh.setTexture( - CableBusTextures.PartMonitorSidesStatus.getIcon(), - CableBusTextures.PartMonitorSidesStatus.getIcon(), - CableBusTextures.PartMonitorBack.getIcon(), - this.getItemStack().getIconIndex(), - CableBusTextures.PartMonitorSidesStatus.getIcon(), - CableBusTextures.PartMonitorSidesStatus.getIcon()); - - rh.setBounds(6, 6, 11, 10, 10, 12); - rh.renderBlock(x, y, z, renderer); - - this.renderLights(x, y, z, rh, renderer); + protected boolean supportFuzzy() { + return true; } @Override - public int cableConnectionRenderTo() { - return 5; + protected boolean supportOreDict() { + return true; } @Override - public boolean onPartActivate(final EntityPlayer player, final Vec3 pos) { - if (!player.isSneaking()) { - if (Platform.isClient()) { - return true; - } + protected IMEMonitor getMonitor() { + try { + return this.getProxy().getStorage().getItemInventory(); + } catch (final GridAccessException e) { + return null; + } + } - Platform.openGUI(player, this.getHost().getTile(), this.getSide(), GuiBridge.GUI_BUS); - return true; + @Override + public int calculateAmountToSend() { + int toSend = switch (this.getInstalledUpgrades(Upgrades.SPEED)) { + case 1 -> 8; + case 2 -> 32; + case 3 -> 64; + case 4 -> 96; + default -> 1; + }; + + switch (this.getInstalledUpgrades(Upgrades.SUPERSPEED)) { + case 1 -> toSend += 16; + case 2 -> toSend += 16 * 8; + case 3 -> toSend += 16 * 8 * 8; + case 4 -> toSend += 16 * 8 * 8 * 8; } - return false; - } - - @Override - public TickingRequest getTickingRequest(final IGridNode node) { - return new TickingRequest( - TickRates.ImportBus.getMin(), - TickRates.ImportBus.getMax(), - this.getHandler() == null, - false); - } - - @Override - public TickRateModulation tickingRequest(final IGridNode node, final int ticksSinceLastCall) { - return this.doBusWork(); - } - - @Override - protected TickRateModulation doBusWork() { - if (!this.getProxy().isActive() || !this.canDoBusWork()) { - return TickRateModulation.IDLE; + switch (this.getInstalledUpgrades(Upgrades.SUPERLUMINALSPEED)) { + case 1 -> toSend += 131_072; + case 2 -> toSend += 131_072 * 8; + case 3 -> toSend += 131_072 * 8 * 8; + case 4 -> toSend += 131_072 * 8 * 8 * 8; } - this.worked = false; - - final InventoryAdaptor myAdaptor = this.getHandler(); - final FuzzyMode fzMode = (FuzzyMode) this.getConfigManager().getSetting(Settings.FUZZY_MODE); - - if (myAdaptor != null) { - try { - this.itemToSend = this.calculateItemsToSend(); - this.itemToSend = Math.min( - this.itemToSend, - (int) (0.01 + this.getProxy().getEnergy() - .extractAEPower(this.itemToSend, Actionable.SIMULATE, PowerMultiplier.CONFIG))); - - final IMEMonitor inv = this.getProxy().getStorage().getItemInventory(); - final IEnergyGrid energy = this.getProxy().getEnergy(); - - boolean configured = false; - if (this.getInstalledUpgrades(Upgrades.ORE_FILTER) == 0) { - for (int x = 0; x < this.availableSlots(); x++) { - final IAEItemStack ais = this.getConfig().getAEStackInSlot(x); - if (ais != null && this.itemToSend > 0) { - configured = true; - while (this.itemToSend > 0) { - if (this.importStuff(myAdaptor, ais, inv, energy, fzMode)) { - break; - } - } - } - } - } else if (!oreFilterString.isEmpty()) { - configured = true; - if (filterPredicate == null) filterPredicate = OreFilteredList.makeFilter(oreFilterString); - for (ItemSlot slot : myAdaptor) { - if (this.itemToSend <= 0) break; - if (slot.isExtractable() && filterPredicate != null - && filterPredicate.test(slot.getAEItemStack())) { - while (this.itemToSend > 0) { - if (this.importStuff(myAdaptor, slot.getAEItemStack(), inv, energy, fzMode)) break; - } - } - } - } - - if (!configured) { - while (this.itemToSend > 0) { - if (this.importStuff(myAdaptor, null, inv, energy, fzMode)) { - break; - } - } - } - } catch (final GridAccessException e) { - // :3 - } - } else { - return TickRateModulation.SLEEP; - } - - return this.worked ? TickRateModulation.FASTER : TickRateModulation.SLOWER; + return toSend; } - private boolean importStuff(final InventoryAdaptor myAdaptor, final IAEItemStack whatToImport, + @Override + protected boolean importStuff(final Object myTarget, final IAEItemStack whatToImport, final IMEMonitor inv, final IEnergySource energy, final FuzzyMode fzMode) { + if (!(myTarget instanceof InventoryAdaptor myAdaptor)) return true; final int toSend = this.calculateMaximumAmountToImport(myAdaptor, whatToImport, inv, fzMode); final ItemStack newItems; @@ -274,7 +142,7 @@ public class PartImportBus extends PartSharedItemBus implements IInventoryDestin } final IAEItemStack failed = Platform - .poweredInsert(energy, this.destination, this.lastItemChecked, this.source); + .poweredInsert(energy, this.destination, this.lastItemChecked, this.mySrc); if (failed != null) { myAdaptor.addItems(failed.getItemStack()); @@ -308,7 +176,7 @@ public class PartImportBus extends PartSharedItemBus implements IInventoryDestin simResult = myAdaptor.simulateRemove(toSend, itemStackToImport, this.configDestination(inv)); } itemAmountNotStorable = this.destination - .injectItems(AEItemStack.create(simResult), Actionable.SIMULATE, this.source); + .injectItems(AEItemStack.create(simResult), Actionable.SIMULATE, this.mySrc); if (itemAmountNotStorable != null) { return (int) Math.min(simResult.stackSize - itemAmountNotStorable.getStackSize(), toSend); @@ -323,13 +191,22 @@ public class PartImportBus extends PartSharedItemBus implements IInventoryDestin } @Override - protected boolean isSleeping() { - return this.getHandler() == null || super.isSleeping(); - } - - @Override - public RedstoneMode getRSMode() { - return (RedstoneMode) this.getConfigManager().getSetting(Settings.REDSTONE_CONTROLLED); + protected boolean doOreDict(final Object myTarget, IMEMonitor inv, final IEnergyGrid energy, + final FuzzyMode fzMode) { + if (!(myTarget instanceof InventoryAdaptor myAdaptor)) return false; + if (!oreFilterString.isEmpty()) { + if (filterPredicate == null) filterPredicate = OreFilteredList.makeFilter(oreFilterString); + for (ItemSlot slot : myAdaptor) { + if (this.itemToSend <= 0) break; + if (slot.isExtractable() && filterPredicate != null && filterPredicate.test(slot.getAEItemStack())) { + while (this.itemToSend > 0) { + if (this.importStuff(myAdaptor, slot.getAEItemStack(), inv, energy, fzMode)) break; + } + } + } + return true; + } + return false; } @Override diff --git a/src/main/java/appeng/parts/automation/PartLevelEmitter.java b/src/main/java/appeng/parts/automation/PartLevelEmitter.java index d089ce9b0..90d40554c 100644 --- a/src/main/java/appeng/parts/automation/PartLevelEmitter.java +++ b/src/main/java/appeng/parts/automation/PartLevelEmitter.java @@ -16,7 +16,6 @@ import java.util.Random; import net.minecraft.client.renderer.RenderBlocks; import net.minecraft.client.renderer.Tessellator; import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.IInventory; import net.minecraft.inventory.InventoryCrafting; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; @@ -33,16 +32,15 @@ import appeng.api.config.RedstoneMode; import appeng.api.config.Settings; import appeng.api.config.Upgrades; import appeng.api.config.YesNo; +import appeng.api.features.LevelItemInfo; +import appeng.api.features.LevelState; import appeng.api.networking.IGridNode; import appeng.api.networking.crafting.ICraftingGrid; import appeng.api.networking.crafting.ICraftingPatternDetails; -import appeng.api.networking.crafting.ICraftingProvider; import appeng.api.networking.crafting.ICraftingProviderHelper; import appeng.api.networking.crafting.ICraftingWatcher; -import appeng.api.networking.crafting.ICraftingWatcherHost; import appeng.api.networking.energy.IEnergyGrid; import appeng.api.networking.energy.IEnergyWatcher; -import appeng.api.networking.energy.IEnergyWatcherHost; import appeng.api.networking.events.MENetworkChannelsChanged; import appeng.api.networking.events.MENetworkCraftingPatternChange; import appeng.api.networking.events.MENetworkEventSubscribe; @@ -50,15 +48,15 @@ import appeng.api.networking.events.MENetworkPowerStatusChange; import appeng.api.networking.security.BaseActionSource; import appeng.api.networking.storage.IBaseMonitor; import appeng.api.networking.storage.IStackWatcher; -import appeng.api.networking.storage.IStackWatcherHost; -import appeng.api.networking.ticking.IGridTickable; import appeng.api.networking.ticking.TickRateModulation; import appeng.api.networking.ticking.TickingRequest; +import appeng.api.parts.ILevelEmitter; import appeng.api.parts.IPartCollisionHelper; import appeng.api.parts.IPartRenderHelper; import appeng.api.storage.IMEMonitor; -import appeng.api.storage.IMEMonitorHandlerReceiver; import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; @@ -70,18 +68,16 @@ import appeng.core.AELog; import appeng.core.sync.GuiBridge; import appeng.helpers.Reflected; import appeng.me.GridAccessException; -import appeng.tile.inventory.AppEngInternalAEInventory; -import appeng.tile.inventory.InvOperation; +import appeng.tile.inventory.IAEStackInventory; import appeng.util.Platform; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherHost, IStackWatcherHost, - ICraftingWatcherHost, IMEMonitorHandlerReceiver, ICraftingProvider, IGridTickable { +public class PartLevelEmitter extends PartUpgradeable implements ILevelEmitter { private static final int FLAG_ON = 8; - private final AppEngInternalAEInventory config = new AppEngInternalAEInventory(this, 1); + private final IAEStackInventory config = new IAEStackInventory(this, 1); private boolean prevState = false; @@ -91,6 +87,7 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH private IStackWatcher myWatcher; private IEnergyWatcher myEnergyWatcher; private ICraftingWatcher myCraftingWatcher; + private double centerX; private double centerY; private double centerZ; @@ -200,7 +197,7 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH // update the system... private void configureWatchers() { - final IAEItemStack myStack = this.config.getAEStackInSlot(0); + final IAEStack myStack = this.config.getAEStackInSlot(0); if (this.myWatcher != null) { this.myWatcher.clear(); @@ -240,6 +237,7 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH // no more item stuff.. this.getProxy().getStorage().getItemInventory().removeListener(this); + this.getProxy().getStorage().getFluidInventory().removeListener(this); } catch (final GridAccessException e) { // :P } @@ -252,35 +250,43 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH this.getProxy().getStorage().getItemInventory().addListener(this, this.getProxy().getGrid()); } else { this.getProxy().getStorage().getItemInventory().removeListener(this); + this.getProxy().getStorage().getFluidInventory().removeListener(this); if (this.myWatcher != null) { this.myWatcher.add(myStack); } } - this.updateReportingValue(this.getProxy().getStorage().getItemInventory()); + if (myStack instanceof IAEFluidStack) { + this.updateReportingValue(this.getProxy().getStorage().getFluidInventory()); + } else { + this.updateReportingValue(this.getProxy().getStorage().getItemInventory()); + } + } catch (final GridAccessException e) { // >.> } } - private void updateReportingValue(final IMEMonitor monitor) { - final IAEItemStack myStack = this.config.getAEStackInSlot(0); + private void updateReportingValue(final IMEMonitor monitor) { + final IAEStack myStack = this.config.getAEStackInSlot(0); if (myStack == null) { this.lastReportedValue = 0; - for (final IAEItemStack st : monitor.getStorageList()) { + for (final IAEStack st : ((IMEMonitor) monitor).getStorageList()) { this.lastReportedValue += st.getStackSize(); } - } else if (this.getInstalledUpgrades(Upgrades.FUZZY) > 0) { + } else if (myStack.getChannel() != monitor.getChannel()) { + return; + } else if (myStack instanceof IAEItemStack ais && this.getInstalledUpgrades(Upgrades.FUZZY) > 0) { this.lastReportedValue = 0; final FuzzyMode fzMode = (FuzzyMode) this.getConfigManager().getSetting(Settings.FUZZY_MODE); - final Collection fuzzyList = monitor.getStorageList().findFuzzy(myStack, fzMode); + final Collection fuzzyList = monitor.getStorageList().findFuzzy(ais, fzMode); for (final IAEItemStack st : fuzzyList) { this.lastReportedValue += st.getStackSize(); } } else { - final IAEItemStack r = monitor.getStorageList().findPrecise(myStack); + final IAEStack r = monitor.getStorageList().findPrecise(myStack); if (r == null) { this.lastReportedValue = 0; } else { @@ -300,8 +306,10 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH @Override public void onStackChange(final IItemList o, final IAEStack fullStack, final IAEStack diffStack, final BaseActionSource src, final StorageChannel chan) { - if (chan == StorageChannel.ITEMS && fullStack.equals(this.config.getAEStackInSlot(0)) - && this.getInstalledUpgrades(Upgrades.FUZZY) == 0) { + IAEStack myStack = this.config.getAEStackInSlot(0); + if (myStack == null) return; + + if (fullStack.equals(myStack)) { this.lastReportedValue = fullStack.getStackSize(); this.updateState(); } @@ -353,7 +361,7 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH } @Override - public void postChange(final IBaseMonitor monitor, final Iterable change, + public void postChange(final IBaseMonitor> monitor, final Iterable> change, final BaseActionSource actionSource) { // todo use change if (canDoWork()) { @@ -366,7 +374,7 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH } } lastWorkingTick = MinecraftServer.getServer().getTickCounter(); - this.updateReportingValue((IMEMonitor) monitor); + this.updateReportingValue((IMEMonitor>) monitor); } else if (!delayedUpdatesQueued) { delayedUpdatesQueued = true; try { @@ -380,7 +388,9 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH @Override public void onListUpdate() { try { - this.updateReportingValue(this.getProxy().getStorage().getItemInventory()); + if (this.config.getAEStackInSlot(0) instanceof IAEFluidStack) + this.updateReportingValue(this.getProxy().getStorage().getFluidInventory()); + else this.updateReportingValue(this.getProxy().getStorage().getItemInventory()); } catch (final GridAccessException e) { // ;P } @@ -674,16 +684,6 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH this.configureWatchers(); } - @Override - public void onChangeInventory(final IInventory inv, final int slot, final InvOperation mc, - final ItemStack removedStack, final ItemStack newStack) { - if (inv == this.config) { - this.configureWatchers(); - } - - super.onChangeInventory(inv, slot, mc, removedStack, newStack); - } - @Override public void upgradesChanged() { this.configureWatchers(); @@ -712,15 +712,6 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH this.config.writeToNBT(data, "config"); } - @Override - public IInventory getInventoryByName(final String name) { - if (name.equals("config")) { - return this.config; - } - - return super.getInventoryByName(name); - } - @Override public boolean pushPattern(final ICraftingPatternDetails patternDetails, final InventoryCrafting table) { return false; @@ -735,11 +726,32 @@ public class PartLevelEmitter extends PartUpgradeable implements IEnergyWatcherH public void provideCrafting(final ICraftingProviderHelper craftingTracker) { if (this.getInstalledUpgrades(Upgrades.CRAFTING) > 0) { if (this.getConfigManager().getSetting(Settings.CRAFT_VIA_REDSTONE) == YesNo.YES) { - final IAEItemStack what = this.config.getAEStackInSlot(0); + final IAEStack what = this.config.getAEStackInSlot(0); if (what != null) { craftingTracker.setEmitable(what); } } } } + + @Override + public LevelItemInfo[] getLevelItemInfoList() { + IAEStack stack = this.config.getAEStackInSlot(0); + if (stack == null) return new LevelItemInfo[] { null }; + return new LevelItemInfo[] { new LevelItemInfo( + stack, + this.getReportingValue(), + -1, + this.isProvidingStrongPower() > 0 ? LevelState.Craft : LevelState.Idle) }; + } + + @Override + public void saveAEStackInv() { + this.configureWatchers(); + } + + @Override + public IAEStackInventory getAEInventoryByName(StorageName name) { + return this.config; + } } diff --git a/src/main/java/appeng/parts/automation/PartSharedItemBus.java b/src/main/java/appeng/parts/automation/PartSharedItemBus.java index 1e35346e9..d8ac08a44 100644 --- a/src/main/java/appeng/parts/automation/PartSharedItemBus.java +++ b/src/main/java/appeng/parts/automation/PartSharedItemBus.java @@ -12,33 +12,58 @@ package appeng.parts.automation; import java.util.function.Predicate; -import net.minecraft.inventory.IInventory; +import net.minecraft.entity.player.EntityPlayer; import net.minecraft.item.ItemStack; import net.minecraft.tileentity.TileEntity; +import net.minecraft.util.IIcon; +import net.minecraft.util.Vec3; import net.minecraft.world.World; +import appeng.api.config.FuzzyMode; import appeng.api.config.RedstoneMode; +import appeng.api.config.Settings; import appeng.api.config.Upgrades; +import appeng.api.networking.IGridNode; +import appeng.api.networking.security.BaseActionSource; +import appeng.api.networking.security.MachineSource; import appeng.api.networking.ticking.IGridTickable; import appeng.api.networking.ticking.TickRateModulation; +import appeng.api.storage.IMEMonitor; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; +import appeng.core.sync.GuiBridge; import appeng.helpers.IOreFilterable; import appeng.me.GridAccessException; -import appeng.tile.inventory.AppEngInternalAEInventory; +import appeng.tile.inventory.IAEStackInventory; +import appeng.tile.inventory.IIAEStackInventory; import appeng.util.InventoryAdaptor; import appeng.util.Platform; -public abstract class PartSharedItemBus extends PartUpgradeable implements IGridTickable, IOreFilterable { +public abstract class PartSharedItemBus> extends PartUpgradeable + implements IGridTickable, IOreFilterable, IIAEStackInventory { - private final AppEngInternalAEInventory config = new AppEngInternalAEInventory(this, 9); + private final IAEStackInventory config = new IAEStackInventory(this, 9); private int adaptorHash = 0; private InventoryAdaptor adaptor; private boolean lastRedstone = false; protected String oreFilterString = ""; protected Predicate filterPredicate = null; + protected final BaseActionSource mySrc; + private final StorageChannel channel; + + // XD + protected final int[] slotSequence = new int[] { 4, 1, 3, 5, 7, 0, 2, 6, 8 }; public PartSharedItemBus(final ItemStack is) { super(is); + + this.getConfigManager().registerSetting(Settings.REDSTONE_CONTROLLED, RedstoneMode.IGNORE); + this.getConfigManager().registerSetting(Settings.FUZZY_MODE, FuzzyMode.IGNORE_ALL); + + this.mySrc = new MachineSource(this); + this.channel = StorageChannel.getStorageChannelByParametrizedClass(this.getClass()); } @Override @@ -53,26 +78,17 @@ public abstract class PartSharedItemBus extends PartUpgradeable implements IGrid @Override public void readFromNBT(final net.minecraft.nbt.NBTTagCompound extra) { super.readFromNBT(extra); - this.getConfig().readFromNBT(extra, "config"); + this.config.readFromNBT(extra, "config"); this.oreFilterString = extra.getString("filter"); } @Override public void writeToNBT(final net.minecraft.nbt.NBTTagCompound extra) { super.writeToNBT(extra); - this.getConfig().writeToNBT(extra, "config"); + this.config.writeToNBT(extra, "config"); extra.setString("filter", this.oreFilterString); } - @Override - public IInventory getInventoryByName(final String name) { - if (name.equals("config")) { - return this.getConfig(); - } - - return super.getInventoryByName(name); - } - @Override public void onNeighborChanged() { this.updateState(); @@ -110,33 +126,13 @@ public abstract class PartSharedItemBus extends PartUpgradeable implements IGrid } protected int availableSlots() { - return Math.min(1 + this.getInstalledUpgrades(Upgrades.CAPACITY) * 4, this.getConfig().getSizeInventory()); + return Math.min(1 + this.getInstalledUpgrades(Upgrades.CAPACITY) * 4, this.config.getSizeInventory()); } - protected int calculateItemsToSend() { - int toSend = switch (this.getInstalledUpgrades(Upgrades.SPEED)) { - default -> 1; - case 1 -> 8; - case 2 -> 32; - case 3 -> 64; - case 4 -> 96; - }; + public abstract int calculateAmountToSend(); - switch (this.getInstalledUpgrades(Upgrades.SUPERSPEED)) { - case 1 -> toSend += 16; - case 2 -> toSend += 16 * 8; - case 3 -> toSend += 16 * 8 * 8; - case 4 -> toSend += 16 * 8 * 8 * 8; - } - - switch (this.getInstalledUpgrades(Upgrades.SUPERLUMINALSPEED)) { - case 1 -> toSend += 131_072; - case 2 -> toSend += 131_072 * 8; - case 3 -> toSend += 131_072 * 8 * 8; - case 4 -> toSend += 131_072 * 8 * 8 * 8; - } - - return toSend; + public IIcon getFaceIcon() { + return this.getItemStack().getIconIndex(); } /** @@ -179,10 +175,6 @@ public abstract class PartSharedItemBus extends PartUpgradeable implements IGrid protected abstract TickRateModulation doBusWork(); - AppEngInternalAEInventory getConfig() { - return this.config; - } - @Override public String getFilter() { return oreFilterString; @@ -193,4 +185,60 @@ public abstract class PartSharedItemBus extends PartUpgradeable implements IGrid oreFilterString = filter; filterPredicate = null; } + + @Override + protected boolean isSleeping() { + return this.getHandler() == null || super.isSleeping(); + } + + @Override + public TickRateModulation tickingRequest(final IGridNode node, final int ticksSinceLastCall) { + return this.doBusWork(); + } + + @Override + public boolean onPartActivate(final EntityPlayer player, final Vec3 pos) { + if (!player.isSneaking()) { + if (Platform.isClient()) { + return true; + } + + Platform.openGUI(player, this.getHost().getTile(), this.getSide(), GuiBridge.GUI_BUS); + return true; + } + + return false; + } + + @Override + public RedstoneMode getRSMode() { + return (RedstoneMode) this.getConfigManager().getSetting(Settings.REDSTONE_CONTROLLED); + } + + @Override + public int cableConnectionRenderTo() { + return 5; + } + + @Override + public void saveAEStackInv() {} + + @Override + public IAEStackInventory getAEInventoryByName(StorageName name) { + return this.config; + } + + public StorageChannel getStorageChannel() { + return this.channel; + } + + protected abstract IMEMonitor getMonitor(); + + protected boolean supportFuzzy() { + return false; + } + + protected boolean supportOreDict() { + return false; + } } diff --git a/src/main/java/appeng/parts/misc/PartInterface.java b/src/main/java/appeng/parts/misc/PartInterface.java index 0bea43ab0..13bfe17ce 100644 --- a/src/main/java/appeng/parts/misc/PartInterface.java +++ b/src/main/java/appeng/parts/misc/PartInterface.java @@ -33,6 +33,7 @@ import com.gtnewhorizon.gtnhlib.capability.item.ItemIO; import com.gtnewhorizon.gtnhlib.capability.item.ItemSink; import com.gtnewhorizon.gtnhlib.capability.item.ItemSource; +import appeng.api.AEApi; import appeng.api.config.Actionable; import appeng.api.config.Upgrades; import appeng.api.implementations.tiles.ITileStorageMonitorable; @@ -60,6 +61,7 @@ import appeng.client.texture.CableBusTextures; import appeng.core.sync.GuiBridge; import appeng.helpers.DualityInterface; import appeng.helpers.IInterfaceHost; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.IPriorityHost; import appeng.helpers.Reflected; import appeng.me.GridAccessException; @@ -71,8 +73,9 @@ import appeng.util.inv.IInventoryDestination; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -public class PartInterface extends PartBasicState implements IGridTickable, IStorageMonitorable, IInventoryDestination, - IInterfaceHost, ISidedInventory, IAEAppEngInventory, ITileStorageMonitorable, IPriorityHost { +public class PartInterface extends PartBasicState + implements IGridTickable, IStorageMonitorable, IInventoryDestination, IInterfaceHost, ISidedInventory, + IAEAppEngInventory, ITileStorageMonitorable, IPriorityHost, IPrimaryGuiIconProvider { private final DualityInterface duality = new DualityInterface(this.getProxy(), this); @@ -411,6 +414,11 @@ public class PartInterface extends PartBasicState implements IGridTickable, ISto return this.getItemStack(); } + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().iface().maybeStack(1).orNull(); + } + private MEItemIO getItemIO() { try { return new MEItemIO(this); diff --git a/src/main/java/appeng/parts/misc/PartStorageBus.java b/src/main/java/appeng/parts/misc/PartStorageBus.java index 7d4666c4a..94176eb4c 100644 --- a/src/main/java/appeng/parts/misc/PartStorageBus.java +++ b/src/main/java/appeng/parts/misc/PartStorageBus.java @@ -10,6 +10,10 @@ package appeng.parts.misc; +import static appeng.util.Platform.isAE2FCLoaded; +import static appeng.util.Platform.readStackNBT; +import static appeng.util.Platform.writeStackNBT; + import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; @@ -20,13 +24,15 @@ import javax.annotation.Nullable; import net.minecraft.client.renderer.RenderBlocks; import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.tileentity.TileEntity; import net.minecraft.util.Vec3; import net.minecraftforge.common.util.ForgeDirection; +import com.glodblock.github.common.item.ItemFluidPacket; +import com.glodblock.github.inventory.MEMonitorIFluidHandler; + import appeng.api.AEApi; import appeng.api.config.AccessRestriction; import appeng.api.config.FuzzyMode; @@ -44,22 +50,22 @@ import appeng.api.networking.events.MENetworkPowerStatusChange; import appeng.api.networking.security.BaseActionSource; import appeng.api.networking.security.MachineSource; import appeng.api.networking.storage.IBaseMonitor; -import appeng.api.networking.ticking.IGridTickable; import appeng.api.networking.ticking.ITickManager; import appeng.api.networking.ticking.TickRateModulation; import appeng.api.networking.ticking.TickingRequest; import appeng.api.parts.IPartCollisionHelper; import appeng.api.parts.IPartHost; import appeng.api.parts.IPartRenderHelper; +import appeng.api.parts.IStorageBus; import appeng.api.parts.PartItemStack; -import appeng.api.storage.ICellContainer; import appeng.api.storage.IExternalStorageHandler; import appeng.api.storage.IMEInventory; import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.IMEMonitor; -import appeng.api.storage.IMEMonitorHandlerReceiver; import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IItemList; import appeng.api.util.IConfigManager; import appeng.client.texture.CableBusTextures; @@ -67,8 +73,6 @@ import appeng.core.settings.TickRates; import appeng.core.stats.Achievements; import appeng.core.sync.GuiBridge; import appeng.helpers.IInterfaceHost; -import appeng.helpers.IOreFilterable; -import appeng.helpers.IPriorityHost; import appeng.helpers.Reflected; import appeng.integration.IntegrationType; import appeng.me.GridAccessException; @@ -78,33 +82,41 @@ import appeng.me.storage.MEMonitorPassThrough; import appeng.me.storage.MEPassThrough; import appeng.me.storage.StorageBusInventoryHandler; import appeng.parts.automation.PartUpgradeable; -import appeng.tile.inventory.AppEngInternalAEInventory; -import appeng.tile.inventory.InvOperation; -import appeng.transformer.annotations.Integration.Interface; +import appeng.tile.inventory.IAEStackInventory; import appeng.transformer.annotations.Integration.Method; import appeng.util.IterationCounter; import appeng.util.Platform; import appeng.util.prioitylist.FuzzyPriorityList; import appeng.util.prioitylist.OreFilteredList; import appeng.util.prioitylist.PrecisePriorityList; -import buildcraft.api.transport.IPipeConnection; import buildcraft.api.transport.IPipeTile.PipeType; import cpw.mods.fml.relauncher.Side; import cpw.mods.fml.relauncher.SideOnly; -@Interface(iname = IntegrationType.BuildCraftTransport, iface = "buildcraft.api.transport.IPipeConnection") -public class PartStorageBus extends PartUpgradeable implements IGridTickable, ICellContainer, - IMEMonitorHandlerReceiver, IPipeConnection, IPriorityHost, IOreFilterable { +public class PartStorageBus extends PartUpgradeable implements IStorageBus { private final BaseActionSource mySrc; - private final AppEngInternalAEInventory Config = new AppEngInternalAEInventory(this, 63); - public boolean needSyncGUI = false; + private final IAEStackInventory Config = new IAEStackInventory(this, 63) { + + @Override + public void putAEStackInSlot(int n, IAEStack aes) { + super.putAEStackInSlot(n, aes); + + if (n >= 18 && (n < (18 + getInstalledUpgrades(Upgrades.CAPACITY) * 9))) { + filterCache[n - 18] = aes; + } + + resetCache(true); + } + }; + + private boolean needSyncGUI = false; // represents the 45 optional slots unlockable with a Storage Card - private final ItemStack[] filterCache = new ItemStack[63 - 18]; + private final IAEStack[] filterCache = new IAEStack[63 - 18]; private int priority = 0; private boolean cached = false; - private MEMonitorIInventory monitor = null; - private MEInventoryHandler handler = null; + private IMEMonitor monitor = null; + private MEInventoryHandler handler = null; private int handlerHash = 0; private boolean wasActive = false; private byte resetCacheLogic = 0; @@ -189,6 +201,12 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC this.updateStatus(); } + @Override + @MENetworkEventSubscribe + public void chanRender(final MENetworkChannelsChanged changedChannels) { + this.updateStatus(); + } + private void updateStatus() { final boolean currentActive = this.getProxy().isActive(); if (this.wasActive != currentActive) { @@ -218,20 +236,6 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC this.getHost().markForSave(); } - @Override - public void onChangeInventory(final IInventory inv, final int slot, final InvOperation mc, - final ItemStack removedStack, final ItemStack newStack) { - super.onChangeInventory(inv, slot, mc, removedStack, newStack); - - if (inv == this.Config) { - if ((removedStack != null || newStack != null) && slot >= 18 - && (slot < (18 + this.getInstalledUpgrades(Upgrades.CAPACITY) * 9))) - this.filterCache[slot - 18] = newStack; - - this.resetCache(true); - } - } - @Override public void upgradesChanged() { super.upgradesChanged(); @@ -239,19 +243,29 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC else if (this.oreFilterString.isEmpty()) this.oreFilterString = previousOreFilterString; for (int x = 0; x < (this.getInstalledUpgrades(Upgrades.CAPACITY) * 9); x++) { - final ItemStack is = filterCache[x]; - if (is != null) this.Config.setInventorySlotContents(x + 18, is); + final IAEStack aes = filterCache[x]; + if (aes != null) this.Config.putAEStackInSlot(x + 18, aes); } needSyncGUI = true; this.resetCache(true); } + @Override + public boolean needSyncGUI() { + return this.needSyncGUI; + } + + @Override + public void setNeedSyncGUI(boolean needSyncGUI) { + this.needSyncGUI = needSyncGUI; + } + private void readFilterCache(NBTTagCompound tagCompound) { for (int x = 0; x < filterCache.length; x++) { if (tagCompound.hasKey("#" + x)) { NBTTagCompound isTag = tagCompound.getCompoundTag("#" + x); - filterCache[x] = ItemStack.loadItemStackFromNBT(isTag); + filterCache[x] = readStackNBT(isTag, true); } else { filterCache[x] = null; } @@ -262,7 +276,7 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC for (int x = 0; x < filterCache.length; x++) { if (filterCache[x] != null) { NBTTagCompound isTag = new NBTTagCompound(); - filterCache[x].writeToNBT(isTag); + writeStackNBT(filterCache[x], isTag, true); tagCompound.setTag("#" + x, isTag); } } @@ -291,15 +305,6 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC data.setTag("filterCache", tagCompound); } - @Override - public IInventory getInventoryByName(final String name) { - if (name.equals("config")) { - return this.Config; - } - - return super.getInventoryByName(name); - } - private void resetCache(final boolean fullReset) { if (this.getHost() == null || this.getHost().getTile() == null || this.getHost().getTile().getWorldObj() == null @@ -326,7 +331,7 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC } @Override - public void postChange(final IBaseMonitor monitor, final Iterable change, + public void postChange(final IBaseMonitor> monitor, final Iterable> change, final BaseActionSource source) { try { if (this.getProxy().isActive()) { @@ -338,11 +343,11 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC return; } } - Iterable filteredChanges = this.filterChanges(change, this.readOncePass); + Iterable> filteredChanges = this.filterChanges(change, this.readOncePass); this.readOncePass = false; if (filteredChanges == null) return; this.getProxy().getStorage() - .postAlterationOfStoredItems(StorageChannel.ITEMS, filteredChanges, this.mySrc); + .postAlterationOfStoredItems(getStorageChannel(), filteredChanges, this.mySrc); } } catch (final GridAccessException e) { // :( @@ -354,16 +359,16 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC * changes match the filter. */ @Nullable - private Iterable filterChanges(final Iterable change, final boolean readOncePass) { + private Iterable> filterChanges(final Iterable> change, final boolean readOncePass) { if (readOncePass) { return change; } if (this.handler != null && this.handler.isExtractFilterActive() && !this.handler.getExtractPartitionList().isEmpty()) { - List filteredChanges = new ArrayList<>(); - Predicate extractFilterCondition = this.handler.getExtractFilterCondition(); - for (final IAEItemStack changedItem : change) { + List> filteredChanges = new ArrayList<>(); + Predicate> extractFilterCondition = this.handler.getExtractFilterCondition(); + for (final IAEStack changedItem : change) { if (extractFilterCondition.test(changedItem)) { filteredChanges.add(changedItem); } @@ -490,7 +495,8 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC } if (this.monitor != null) { - return this.monitor.onTick(); + if (getStorageChannel() == StorageChannel.ITEMS) return ((MEMonitorIInventory) this.monitor).onTick(); + else return ((MEMonitorIFluidHandler) this.monitor).onTick(); } return TickRateModulation.SLEEP; @@ -500,8 +506,10 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC final boolean fullReset = this.resetCacheLogic == 2; this.resetCacheLogic = 0; - final IMEInventory in = this.getInternalHandler(); - IItemList before = AEApi.instance().storage().createItemList(); + final IMEInventory in = this.getInternalHandler(); + + IItemList before = getItemList(); + if (in != null) { before = in.getAvailableItems(before, IterationCounter.fetchNewId()); } @@ -511,13 +519,15 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC this.handlerHash = 0; } - final IMEInventory out = this.getInternalHandler(); + final IMEInventory out = this.getInternalHandler(); if (this.monitor != null) { - this.monitor.onTick(); + if (getStorageChannel() == StorageChannel.ITEMS) ((MEMonitorIInventory) this.monitor).onTick(); + else((MEMonitorIFluidHandler) this.monitor).onTick(); } - IItemList after = AEApi.instance().storage().createItemList(); + IItemList after = getItemList(); + if (out != null) { after = out.getAvailableItems(after, IterationCounter.fetchNewId()); } @@ -552,15 +562,15 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC if (target != null) { final IExternalStorageHandler esh = AEApi.instance().registries().externalStorage() - .getHandler(target, this.getSide().getOpposite(), StorageChannel.ITEMS, this.mySrc); + .getHandler(target, this.getSide().getOpposite(), getStorageChannel(), this.mySrc); if (esh != null) { - return esh.getInventory(target, this.getSide().getOpposite(), StorageChannel.ITEMS, this.mySrc); + return esh.getInventory(target, this.getSide().getOpposite(), getStorageChannel(), this.mySrc); } } return null; } - public MEInventoryHandler getInternalHandler() { + public MEInventoryHandler getInternalHandler() { if (this.cached) { return this.handler; } @@ -569,10 +579,9 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC this.cached = true; final TileEntity self = this.getHost().getTile(); - final TileEntity target = self.getWorldObj().getTileEntity( - self.xCoord + this.getSide().offsetX, - self.yCoord + this.getSide().offsetY, - self.zCoord + this.getSide().offsetZ); + + ForgeDirection side = this.getSide(); + final TileEntity target = self.getWorldObj().getTileEntity(self.xCoord + side.offsetX, self.yCoord + side.offsetY, self.zCoord + side.offsetZ); final int newHandlerHash = Platform.generateTileHash(target); @@ -586,16 +595,21 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC this.readOncePass = true; if (target != null) { final IExternalStorageHandler esh = AEApi.instance().registries().externalStorage() - .getHandler(target, this.getSide().getOpposite(), StorageChannel.ITEMS, this.mySrc); + .getHandler(target, this.getSide().getOpposite(), getStorageChannel(), this.mySrc); if (esh != null) { final IMEInventory inv = esh - .getInventory(target, this.getSide().getOpposite(), StorageChannel.ITEMS, this.mySrc); + .getInventory(target, this.getSide().getOpposite(), getStorageChannel(), this.mySrc); if (inv instanceof MEMonitorIInventory h) { h.setMode((StorageFilter) this.getConfigManager().getSetting(Settings.STORAGE_FILTER)); h.setActionSource(new MachineSource(this)); this.monitor = h; + } else if (inv instanceof final MEMonitorIFluidHandler h) { + h.setMode((StorageFilter) this.getConfigManager().getSetting(Settings.STORAGE_FILTER)); + h.setActionSource(new MachineSource(this)); + this.monitor = h; } + if (inv instanceof MEMonitorPassThroughh) { h.setMode((StorageFilter) this.getConfigManager().getSetting(Settings.STORAGE_FILTER)); } @@ -603,7 +617,7 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC if (inv != null) { this.checkInterfaceVsStorageBus(target, this.getSide().getOpposite()); - this.handler = new StorageBusInventoryHandler<>(inv, StorageChannel.ITEMS); + this.handler = new StorageBusInventoryHandler<>(inv, getStorageChannel()); AccessRestriction currentAccess = (AccessRestriction) this.getConfigManager() .getSetting(Settings.ACCESS); @@ -621,22 +635,29 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC } if (this.oreFilterString.isEmpty()) { - final IItemList priorityList = AEApi.instance().storage().createItemList(); + final IItemList priorityList = getItemList(); final int slotsToUse = 18 + this.getInstalledUpgrades(Upgrades.CAPACITY) * 9; for (int x = 0; x < this.Config.getSizeInventory() && x < slotsToUse; x++) { - final IAEItemStack is = this.Config.getAEStackInSlot(x); - if (is != null) priorityList.add(is); + IAEStack is = this.Config.getAEStackInSlot(x); + + if (getStorageChannel() == StorageChannel.FLUIDS && isAE2FCLoaded && is instanceof IAEItemStack ais && ais.getItem() instanceof ItemFluidPacket) { + is = ItemFluidPacket.getFluidAEStack(ais); + } + if (is != null) { + priorityList.add(is); + } } - if (this.getInstalledUpgrades(Upgrades.FUZZY) > 0) { + if (getStorageChannel() == StorageChannel.ITEMS + && this.getInstalledUpgrades(Upgrades.FUZZY) > 0) { FuzzyPriorityList partitionList = new FuzzyPriorityList<>( priorityList, (FuzzyMode) this.getConfigManager().getSetting(Settings.FUZZY_MODE)); this.handler.setPartitionList(partitionList); this.handler.setExtractPartitionList(partitionList); } else { - PrecisePriorityList partitionList = new PrecisePriorityList<>(priorityList); + PrecisePriorityList partitionList = new PrecisePriorityList<>(priorityList); this.handler.setPartitionList(partitionList); this.handler.setExtractPartitionList(partitionList); } @@ -700,12 +721,13 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC @Override public List getCellArray(final StorageChannel channel) { - if (channel == StorageChannel.ITEMS) { - final IMEInventoryHandler out = this.getProxy().isActive() ? this.getInternalHandler() : null; + if (channel == getStorageChannel()) { + final IMEInventoryHandler out = this.getProxy().isActive() ? this.getInternalHandler() : null; if (out != null) { return Collections.singletonList(out); } } + return Arrays.asList(new IMEInventoryHandler[] {}); } @@ -743,4 +765,22 @@ public class PartStorageBus extends PartUpgradeable implements IGridTickable, IC previousOreFilterString = filter; resetCache(true); } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().storageBus().maybeStack(1).orNull(); + } + + @Override + public StorageChannel getStorageChannel() { + return StorageChannel.ITEMS; + } + + @Override + public void saveAEStackInv() {} + + @Override + public IAEStackInventory getAEInventoryByName(StorageName name) { + return this.Config; + } } diff --git a/src/main/java/appeng/parts/p2p/PartP2PInterface.java b/src/main/java/appeng/parts/p2p/PartP2PInterface.java index ac7e9db19..fc05f2b23 100644 --- a/src/main/java/appeng/parts/p2p/PartP2PInterface.java +++ b/src/main/java/appeng/parts/p2p/PartP2PInterface.java @@ -46,6 +46,7 @@ import appeng.api.util.IConfigManager; import appeng.core.sync.GuiBridge; import appeng.helpers.DualityInterface; import appeng.helpers.IInterfaceHost; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.IPriorityHost; import appeng.helpers.Reflected; import appeng.me.GridAccessException; @@ -62,14 +63,14 @@ import cpw.mods.fml.relauncher.SideOnly; public class PartP2PInterface extends PartP2PTunnelStatic implements IGridTickable, IStorageMonitorable, IInventoryDestination, IInterfaceHost, ISidedInventory, - IAEAppEngInventory, ITileStorageMonitorable, IPriorityHost { + IAEAppEngInventory, ITileStorageMonitorable, IPriorityHost, IPrimaryGuiIconProvider { @Reflected public PartP2PInterface(ItemStack is) { super(is); } - private final DualityInterface duality = new DualityInterface(this.getProxy(), this) { + protected final DualityInterface duality = new DualityInterface(this.getProxy(), this) { @Override public void updateCraftingList() { @@ -601,4 +602,9 @@ public class PartP2PInterface extends PartP2PTunnelStatic public ItemStack getSelfRep() { return this.getItemStack(); } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().p2PTunnelMEInterface().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/parts/reporting/AbstractPartTerminal.java b/src/main/java/appeng/parts/reporting/AbstractPartTerminal.java index 5ec6522c3..508a7b01a 100644 --- a/src/main/java/appeng/parts/reporting/AbstractPartTerminal.java +++ b/src/main/java/appeng/parts/reporting/AbstractPartTerminal.java @@ -33,6 +33,7 @@ import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEItemStack; import appeng.api.util.IConfigManager; import appeng.core.sync.GuiBridge; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.items.contents.PinsHandler; import appeng.items.contents.PinsHolder; import appeng.me.GridAccessException; @@ -54,8 +55,8 @@ import appeng.util.Platform; * @version rv3 * @since rv3 */ -public abstract class AbstractPartTerminal extends AbstractPartDisplay - implements ITerminalHost, IConfigManagerHost, IViewCellStorage, IAEAppEngInventory, ITerminalPins { +public abstract class AbstractPartTerminal extends AbstractPartDisplay implements ITerminalHost, IConfigManagerHost, + IViewCellStorage, IAEAppEngInventory, ITerminalPins, IPrimaryGuiIconProvider { private final IConfigManager cm = new ConfigManager(this); private final AppEngInternalInventory viewCell = new AppEngInternalInventory(this, 5); @@ -195,4 +196,6 @@ public abstract class AbstractPartTerminal extends AbstractPartDisplay && AEApi.instance().definitions().materials().cardPatternRefiller().isSameAs(itemstack); } } + + public abstract ItemStack getPrimaryGuiIcon(); } diff --git a/src/main/java/appeng/parts/reporting/PartCraftingTerminal.java b/src/main/java/appeng/parts/reporting/PartCraftingTerminal.java index 7645bea65..f8435dfd0 100644 --- a/src/main/java/appeng/parts/reporting/PartCraftingTerminal.java +++ b/src/main/java/appeng/parts/reporting/PartCraftingTerminal.java @@ -17,12 +17,14 @@ import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; +import appeng.api.AEApi; +import appeng.api.parts.ICraftingTerminal; import appeng.client.texture.CableBusTextures; import appeng.core.sync.GuiBridge; import appeng.helpers.Reflected; import appeng.tile.inventory.AppEngInternalInventory; -public class PartCraftingTerminal extends AbstractPartTerminal { +public class PartCraftingTerminal extends AbstractPartTerminal implements ICraftingTerminal { private static final CableBusTextures FRONT_BRIGHT_ICON = CableBusTextures.PartCraftingTerm_Bright; private static final CableBusTextures FRONT_DARK_ICON = CableBusTextures.PartCraftingTerm_Dark; @@ -97,4 +99,9 @@ public class PartCraftingTerminal extends AbstractPartTerminal { public CableBusTextures getFrontDark() { return FRONT_DARK_ICON; } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().craftingTerminal().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/parts/reporting/PartInterfaceTerminal.java b/src/main/java/appeng/parts/reporting/PartInterfaceTerminal.java index d3f1744f6..f5f6adb8a 100644 --- a/src/main/java/appeng/parts/reporting/PartInterfaceTerminal.java +++ b/src/main/java/appeng/parts/reporting/PartInterfaceTerminal.java @@ -16,11 +16,12 @@ import net.minecraft.util.Vec3; import appeng.api.networking.events.MENetworkBootingStatusChange; import appeng.api.networking.events.MENetworkEventSubscribe; +import appeng.api.parts.IInterfaceTerminal; import appeng.client.texture.CableBusTextures; import appeng.core.sync.GuiBridge; import appeng.util.Platform; -public class PartInterfaceTerminal extends AbstractPartDisplay { +public class PartInterfaceTerminal extends AbstractPartDisplay implements IInterfaceTerminal { private static final CableBusTextures FRONT_BRIGHT_ICON = CableBusTextures.PartInterfaceTerm_Bright; private static final CableBusTextures FRONT_DARK_ICON = CableBusTextures.PartInterfaceTerm_Dark; diff --git a/src/main/java/appeng/parts/reporting/PartPatternTerminal.java b/src/main/java/appeng/parts/reporting/PartPatternTerminal.java index e9cb25084..76c05d23d 100644 --- a/src/main/java/appeng/parts/reporting/PartPatternTerminal.java +++ b/src/main/java/appeng/parts/reporting/PartPatternTerminal.java @@ -17,27 +17,40 @@ import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; -import appeng.api.implementations.ICraftingPatternItem; -import appeng.api.networking.crafting.ICraftingPatternDetails; -import appeng.api.storage.data.IAEItemStack; +import appeng.api.AEApi; +import appeng.api.parts.IPatternTerminal; +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; import appeng.client.texture.CableBusTextures; import appeng.core.sync.GuiBridge; -import appeng.helpers.PatternHelper; import appeng.helpers.Reflected; import appeng.tile.inventory.AppEngInternalInventory; -import appeng.tile.inventory.BiggerAppEngInventory; +import appeng.tile.inventory.IAEStackInventory; +import appeng.tile.inventory.IIAEStackInventory; import appeng.tile.inventory.InvOperation; -public class PartPatternTerminal extends AbstractPartTerminal { +public class PartPatternTerminal extends AbstractPartTerminal implements IIAEStackInventory, IPatternTerminal { private static final CableBusTextures FRONT_BRIGHT_ICON = CableBusTextures.PartPatternTerm_Bright; private static final CableBusTextures FRONT_DARK_ICON = CableBusTextures.PartPatternTerm_Dark; private static final CableBusTextures FRONT_COLORED_ICON = CableBusTextures.PartPatternTerm_Colored; - private final AppEngInternalInventory crafting = new BiggerAppEngInventory(this, 9) {}; + public static final int patternInputsWidth = 3; + public static final int patternInputsHeigh = 3; + public static final int patternInputsPages = 1; - private final AppEngInternalInventory output = new BiggerAppEngInventory(this, 3) {}; + public static final int patternOutputsWidth = 1; + public static final int patternOutputsHeigh = 3; + public static final int patternOutputPages = 1; + private final IAEStackInventory crafting = new IAEStackInventory( + this, + getPatternInputsWidth() * getPatternInputsHeigh() * getPatternInputPages(), + StorageName.CRAFTING_INPUT); + private final IAEStackInventory output = new IAEStackInventory( + this, + getPatternOutputsWidth() * getPatternOutputsHeigh() * getPatternOutputPages(), + StorageName.CRAFTING_OUTPUT); private final AppEngInternalInventory pattern = new AppEngInternalInventory(this, 2); private boolean craftingMode = true; @@ -93,90 +106,41 @@ public class PartPatternTerminal extends AbstractPartTerminal { z = this.getTile().zCoord; } - if (GuiBridge.GUI_PATTERN_TERMINAL.hasPermissions(this.getHost().getTile(), x, y, z, this.getSide(), p)) { - return GuiBridge.GUI_PATTERN_TERMINAL; + if (getPatternGui().hasPermissions(this.getHost().getTile(), x, y, z, this.getSide(), p)) { + return getPatternGui(); } return GuiBridge.GUI_ME; } + protected GuiBridge getPatternGui() { + return GuiBridge.GUI_PATTERN_TERMINAL; + } + @Override public void onChangeInventory(final IInventory inv, final int slot, final InvOperation mc, final ItemStack removedStack, final ItemStack newStack) { if (inv == this.pattern && slot == 1) { - final ItemStack stack = this.pattern.getStackInSlot(1); - - if (stack != null && stack.getItem() instanceof ICraftingPatternItem pattern) { - final NBTTagCompound encodedValue = stack.getTagCompound(); - - if (encodedValue != null) { - final ICraftingPatternDetails details = pattern - .getPatternForItem(stack, this.getHost().getTile().getWorldObj()); - final boolean substitute = encodedValue.getBoolean("substitute"); - final boolean beSubstitute = encodedValue.getBoolean("beSubstitute"); - final boolean isCrafting = encodedValue.getBoolean("crafting"); - final IAEItemStack[] inItems; - final IAEItemStack[] outItems; - - if (details == null) { - inItems = PatternHelper.loadIAEItemStackFromNBT(encodedValue.getTagList("in", 10), true, null); - outItems = PatternHelper - .loadIAEItemStackFromNBT(encodedValue.getTagList("out", 10), true, null); - } else { - inItems = details.getInputs(); - outItems = details.getOutputs(); - } - - this.setCraftingRecipe(isCrafting); - this.setSubstitution(substitute); - this.setCanBeSubstitution(beSubstitute); - - for (int x = 0; x < this.crafting.getSizeInventory(); x++) { - this.crafting.setInventorySlotContents(x, null); - } - - for (int x = 0; x < this.output.getSizeInventory(); x++) { - this.output.setInventorySlotContents(x, null); - } - - for (int x = 0; x < this.crafting.getSizeInventory() && x < inItems.length; x++) { - if (inItems[x] != null) { - this.crafting.setInventorySlotContents(x, inItems[x].getItemStack()); - } - } - - for (int x = 0; x < this.output.getSizeInventory() && x < outItems.length; x++) { - if (outItems[x] != null) { - this.output.setInventorySlotContents(x, outItems[x].getItemStack()); - } - } - } - } - } else if (inv == this.crafting) { - this.fixCraftingRecipes(); + loadPatternFromItem(stack, this.host.getTile().getWorldObj(), this.crafting, this.output); } this.getHost().markForSave(); } - private void fixCraftingRecipes() { - if (this.craftingMode) { - for (int x = 0; x < this.crafting.getSizeInventory(); x++) { - final ItemStack is = this.crafting.getStackInSlot(x); - if (is != null) { - is.stackSize = 1; - } - } - } + @Override + public void saveAEStackInv() { + this.getHost().markForSave(); } + public void exPatternTerminalCall(IAEStack[] in, IAEStack[] out) {} + + @Override public boolean isCraftingRecipe() { return this.craftingMode; } public void setCraftingRecipe(final boolean craftingMode) { this.craftingMode = craftingMode; - this.fixCraftingRecipes(); } public boolean isSubstitution() { @@ -197,14 +161,6 @@ public class PartPatternTerminal extends AbstractPartTerminal { @Override public IInventory getInventoryByName(final String name) { - if (name.equals("crafting")) { - return this.crafting; - } - - if (name.equals("output")) { - return this.output; - } - if (name.equals("pattern")) { return this.pattern; } @@ -212,6 +168,19 @@ public class PartPatternTerminal extends AbstractPartTerminal { return super.getInventoryByName(name); } + @Override + public IAEStackInventory getAEInventoryByName(StorageName name) { + switch (name) { + case CRAFTING_INPUT -> { + return this.crafting; + } + case CRAFTING_OUTPUT -> { + return this.output; + } + } + return null; + } + @Override public CableBusTextures getFrontBright() { return FRONT_BRIGHT_ICON; @@ -226,4 +195,33 @@ public class PartPatternTerminal extends AbstractPartTerminal { public CableBusTextures getFrontDark() { return FRONT_DARK_ICON; } + + protected int getPatternInputsWidth() { + return patternInputsWidth; + } + + protected int getPatternInputsHeigh() { + return patternInputsHeigh; + } + + protected int getPatternInputPages() { + return patternInputsPages; + } + + protected int getPatternOutputsWidth() { + return patternOutputsWidth; + } + + protected int getPatternOutputsHeigh() { + return patternOutputsHeigh; + } + + protected int getPatternOutputPages() { + return patternOutputPages; + } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().patternTerminal().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/parts/reporting/PartPatternTerminalEx.java b/src/main/java/appeng/parts/reporting/PartPatternTerminalEx.java index 106b83a50..347f5c27d 100644 --- a/src/main/java/appeng/parts/reporting/PartPatternTerminalEx.java +++ b/src/main/java/appeng/parts/reporting/PartPatternTerminalEx.java @@ -1,64 +1,36 @@ package appeng.parts.reporting; -import java.util.List; - -import net.minecraft.entity.player.EntityPlayer; -import net.minecraft.inventory.IInventory; import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; -import appeng.api.implementations.ICraftingPatternItem; -import appeng.api.networking.crafting.ICraftingPatternDetails; -import appeng.api.storage.data.IAEItemStack; -import appeng.client.texture.CableBusTextures; +import appeng.api.AEApi; +import appeng.api.parts.IPatternTerminalEx; +import appeng.api.storage.data.IAEStack; import appeng.core.sync.GuiBridge; -import appeng.helpers.PatternHelper; import appeng.helpers.Reflected; -import appeng.tile.inventory.AppEngInternalInventory; -import appeng.tile.inventory.BiggerAppEngInventory; -import appeng.tile.inventory.InvOperation; -public class PartPatternTerminalEx extends AbstractPartTerminal { +public class PartPatternTerminalEx extends PartPatternTerminal implements IPatternTerminalEx { - private static final CableBusTextures FRONT_BRIGHT_ICON = CableBusTextures.PartPatternTerm_Bright; - private static final CableBusTextures FRONT_DARK_ICON = CableBusTextures.PartPatternTerm_Dark; - private static final CableBusTextures FRONT_COLORED_ICON = CableBusTextures.PartPatternTerm_Colored; + public static final int exPatternInputsWidth = 4; + public static final int exPatternInputsHeigh = 4; + public static final int exPatternInputsPages = 2; - private final AppEngInternalInventory crafting = new BiggerAppEngInventory(this, 32); - private final AppEngInternalInventory output = new BiggerAppEngInventory(this, 32); - private final AppEngInternalInventory pattern = new AppEngInternalInventory(this, 2); + public static final int exPatternOutputsWidth = 1; + public static final int exPatternOutputsHeigh = 4; + public static final int exPatternOutputPages = 2; - private boolean substitute = false; - private boolean beSubstitute = false; private boolean inverted = false; private int activePage = 0; @Reflected public PartPatternTerminalEx(final ItemStack is) { super(is); - } - - @Override - public void getDrops(final List drops, final boolean wrenched) { - super.getDrops(drops, wrenched); - - for (final ItemStack is : this.pattern) { - if (is != null) { - drops.add(is); - } - } + setCraftingRecipe(false); } @Override public void readFromNBT(final NBTTagCompound data) { super.readFromNBT(data); - - this.pattern.readFromNBT(data, "pattern"); - this.output.readFromNBT(data, "outputList"); - this.crafting.readFromNBT(data, "craftingGrid"); - - this.setSubstitution(data.getBoolean("substitute")); - this.setCanBeSubstitution(data.getBoolean("beSubstitute")); this.setInverted(data.getBoolean("inverted")); this.setActivePage(data.getInteger("activePage")); } @@ -66,155 +38,34 @@ public class PartPatternTerminalEx extends AbstractPartTerminal { @Override public void writeToNBT(final NBTTagCompound data) { super.writeToNBT(data); - - this.pattern.writeToNBT(data, "pattern"); - this.output.writeToNBT(data, "outputList"); - this.crafting.writeToNBT(data, "craftingGrid"); - - data.setBoolean("substitute", this.substitute); - data.setBoolean("beSubstitute", this.beSubstitute); data.setBoolean("inverted", this.inverted); data.setInteger("activePage", this.activePage); } @Override - public GuiBridge getGui(final EntityPlayer p) { - int x = (int) p.posX; - int y = (int) p.posY; - int z = (int) p.posZ; - if (this.getHost().getTile() != null) { - x = this.getTile().xCoord; - y = this.getTile().yCoord; - z = this.getTile().zCoord; - } - - if (GuiBridge.GUI_PATTERN_TERMINAL_EX.hasPermissions(this.getHost().getTile(), x, y, z, this.getSide(), p)) { - return GuiBridge.GUI_PATTERN_TERMINAL_EX; - } - return GuiBridge.GUI_ME; + protected GuiBridge getPatternGui() { + return GuiBridge.GUI_PATTERN_TERMINAL_EX; } @Override - public void onChangeInventory(final IInventory inv, final int slot, final InvOperation mc, - final ItemStack removedStack, final ItemStack newStack) { - if (inv == this.pattern && slot == 1) { - final ItemStack stack = this.pattern.getStackInSlot(1); + public void exPatternTerminalCall(IAEStack[] in, IAEStack[] out) { + int inputsCount = 0; + int outputCount = 0; - if (stack != null && stack.getItem() instanceof ICraftingPatternItem pattern) { - final NBTTagCompound encodedValue = stack.getTagCompound(); - - if (encodedValue != null) { - final ICraftingPatternDetails details = pattern - .getPatternForItem(stack, this.getHost().getTile().getWorldObj()); - final boolean substitute = encodedValue.getBoolean("substitute"); - final IAEItemStack[] inItems; - final IAEItemStack[] outItems; - int inputsCount = 0; - int outputCount = 0; - - if (details == null) { - inItems = PatternHelper.loadIAEItemStackFromNBT(encodedValue.getTagList("in", 10), true, null); - outItems = PatternHelper - .loadIAEItemStackFromNBT(encodedValue.getTagList("out", 10), false, null); - } else { - inItems = details.getInputs(); - outItems = details.getOutputs(); - } - - for (IAEItemStack inItem : inItems) { - if (inItem != null) { - inputsCount++; - } - } - - for (IAEItemStack outItem : outItems) { - if (outItem != null) { - outputCount++; - } - } - - this.setSubstitution(substitute); - this.setInverted(inputsCount <= 8 && outputCount >= 8); - this.setActivePage(0); - - for (int x = 0; x < this.crafting.getSizeInventory(); x++) { - this.crafting.setInventorySlotContents(x, null); - } - - for (int x = 0; x < this.output.getSizeInventory(); x++) { - this.output.setInventorySlotContents(x, null); - } - - for (int x = 0; x < this.crafting.getSizeInventory() && x < inItems.length; x++) { - if (inItems[x] != null) { - this.crafting.setInventorySlotContents(x, inItems[x].getItemStack()); - } - } - - if (inverted) { - for (int x = 0; x < this.output.getSizeInventory() && x < outItems.length; x++) { - if (outItems[x] != null) { - this.output.setInventorySlotContents(x, outItems[x].getItemStack()); - } - } - } else { - for (int x = 0; x < outItems.length && x < 8; x++) { - this.output.setInventorySlotContents(x >= 4 ? 12 + x : x, outItems[x].getItemStack()); - } - } - } + for (IAEStack inItem : in) { + if (inItem != null) { + inputsCount++; } } - this.getHost().markForSave(); - } - - public boolean isSubstitution() { - return this.substitute; - } - - public boolean canBeSubstitution() { - return this.beSubstitute; - } - - public void setSubstitution(boolean canSubstitute) { - this.substitute = canSubstitute; - } - - public void setCanBeSubstitution(boolean beSubstitute) { - this.beSubstitute = beSubstitute; - } - - @Override - public IInventory getInventoryByName(final String name) { - if (name.equals("crafting")) { - return this.crafting; + for (IAEStack outItem : out) { + if (outItem != null) { + outputCount++; + } } - if (name.equals("output")) { - return this.output; - } - - if (name.equals("pattern")) { - return this.pattern; - } - - return super.getInventoryByName(name); - } - - @Override - public CableBusTextures getFrontBright() { - return FRONT_BRIGHT_ICON; - } - - @Override - public CableBusTextures getFrontColored() { - return FRONT_COLORED_ICON; - } - - @Override - public CableBusTextures getFrontDark() { - return FRONT_DARK_ICON; + this.setInverted(inputsCount <= 8 && outputCount >= 8); + this.setActivePage(0); } public boolean isInverted() { @@ -232,4 +83,44 @@ public class PartPatternTerminalEx extends AbstractPartTerminal { public void setActivePage(int activePage) { this.activePage = activePage; } + + @Override + public void setCraftingRecipe(boolean craftingMode) { + super.setCraftingRecipe(false); + } + + @Override + protected int getPatternInputsWidth() { + return exPatternInputsWidth; + } + + @Override + protected int getPatternInputsHeigh() { + return exPatternInputsHeigh; + } + + @Override + protected int getPatternInputPages() { + return exPatternInputsPages; + } + + @Override + protected int getPatternOutputsWidth() { + return exPatternOutputsWidth; + } + + @Override + protected int getPatternOutputsHeigh() { + return exPatternOutputsHeigh; + } + + @Override + protected int getPatternOutputPages() { + return exPatternOutputPages; + } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().patternTerminalEx().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/parts/reporting/PartTerminal.java b/src/main/java/appeng/parts/reporting/PartTerminal.java index 2b2cf281c..7e970a400 100644 --- a/src/main/java/appeng/parts/reporting/PartTerminal.java +++ b/src/main/java/appeng/parts/reporting/PartTerminal.java @@ -12,6 +12,7 @@ package appeng.parts.reporting; import net.minecraft.item.ItemStack; +import appeng.api.AEApi; import appeng.client.texture.CableBusTextures; public class PartTerminal extends AbstractPartTerminal { @@ -38,4 +39,9 @@ public class PartTerminal extends AbstractPartTerminal { public CableBusTextures getFrontDark() { return FRONT_DARK_ICON; } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().parts().terminal().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/tile/inventory/IAEStackInventory.java b/src/main/java/appeng/tile/inventory/IAEStackInventory.java new file mode 100644 index 000000000..664f1ab30 --- /dev/null +++ b/src/main/java/appeng/tile/inventory/IAEStackInventory.java @@ -0,0 +1,109 @@ +package appeng.tile.inventory; + +import static appeng.util.Platform.readStackNBT; +import static appeng.util.Platform.writeStackNBT; + +import net.minecraft.nbt.NBTTagCompound; + +import appeng.api.storage.StorageName; +import appeng.api.storage.data.IAEStack; +import appeng.core.AELog; +import appeng.util.Platform; + +public class IAEStackInventory { + + private final IIAEStackInventory aesInventory; + private final IAEStack[] inv; + private final int size; + private final StorageName storageName; + + public IAEStackInventory(final IIAEStackInventory te, final int size, StorageName storageName) { + this.aesInventory = te; + this.size = size; + this.inv = new IAEStack[size]; + this.storageName = storageName; + } + + public IAEStackInventory(final IIAEStackInventory te, final int size) { + this.aesInventory = te; + this.size = size; + this.inv = new IAEStack[size]; + this.storageName = StorageName.NONE; + } + + public boolean isEmpty() { + for (int x = 0; x < this.size; x++) { + if (this.getAEStackInSlot(x) != null) { + return false; + } + } + return true; + } + + public IAEStack getAEStackInSlot(final int n) { + return this.inv[n]; + } + + public void putAEStackInSlot(final int n, IAEStack aes) { + this.inv[n] = aes; + markDirty(); + } + + public void writeToNBT(final NBTTagCompound data, final String name) { + final NBTTagCompound c = new NBTTagCompound(); + this.writeToNBT(c); + data.setTag(name, c); + } + + private void writeToNBT(final NBTTagCompound target) { + for (int x = 0; x < this.size; x++) { + try { + final NBTTagCompound c = new NBTTagCompound(); + final IAEStack tmp = this.inv[x]; + + if (tmp != null) { + writeStackNBT(tmp, c, true); + } + + target.setTag("#" + x, c); + } catch (final Exception ignored) {} + } + } + + public void readFromNBT(final NBTTagCompound data, final String name) { + final NBTTagCompound c = data.getCompoundTag(name); + if (c != null) { + this.readFromNBT(c); + } + } + + private void readFromNBT(final NBTTagCompound target) { + for (int x = 0; x < this.size; x++) { + try { + final NBTTagCompound c = target.getCompoundTag("#" + x); + + if (c != null) { + final IAEStack stack = readStackNBT(c, false); + if (stack != null && stack.getStackSize() == 0) stack.setStackSize(c.getInteger("Count")); + this.inv[x] = stack; + } + } catch (final Exception e) { + AELog.debug(e); + } + } + } + + public int getSizeInventory() { + return this.size; + } + + public void markDirty() { + if (this.aesInventory != null && Platform.isServer()) { + this.aesInventory.saveAEStackInv(); + } + } + + public StorageName getStorageName() { + return storageName; + } +} diff --git a/src/main/java/appeng/tile/inventory/IIAEStackInventory.java b/src/main/java/appeng/tile/inventory/IIAEStackInventory.java new file mode 100644 index 000000000..1ac5f15c1 --- /dev/null +++ b/src/main/java/appeng/tile/inventory/IIAEStackInventory.java @@ -0,0 +1,10 @@ +package appeng.tile.inventory; + +import appeng.api.storage.StorageName; + +public interface IIAEStackInventory { + + void saveAEStackInv(); + + IAEStackInventory getAEInventoryByName(StorageName name); +} diff --git a/src/main/java/appeng/tile/misc/TileCellWorkbench.java b/src/main/java/appeng/tile/misc/TileCellWorkbench.java index 7d8ec54c6..e03fc6750 100644 --- a/src/main/java/appeng/tile/misc/TileCellWorkbench.java +++ b/src/main/java/appeng/tile/misc/TileCellWorkbench.java @@ -17,37 +17,38 @@ import net.minecraft.item.ItemStack; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.world.World; +import appeng.api.AEApi; import appeng.api.config.CopyMode; import appeng.api.config.Settings; import appeng.api.config.Upgrades; -import appeng.api.implementations.IUpgradeableHost; import appeng.api.implementations.items.IUpgradeModule; +import appeng.api.implementations.tiles.ICellWorkbench; import appeng.api.storage.ICellWorkbenchItem; +import appeng.api.storage.StorageChannel; +import appeng.api.storage.StorageName; import appeng.api.util.IConfigManager; import appeng.helpers.ICellRestriction; -import appeng.helpers.IOreFilterable; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.tile.AEBaseTile; import appeng.tile.TileEvent; import appeng.tile.events.TileEventType; -import appeng.tile.inventory.AppEngInternalAEInventory; import appeng.tile.inventory.AppEngInternalInventory; -import appeng.tile.inventory.IAEAppEngInventory; +import appeng.tile.inventory.IAEStackInventory; import appeng.tile.inventory.InvOperation; import appeng.util.ConfigManager; -import appeng.util.IConfigManagerHost; -public class TileCellWorkbench extends AEBaseTile - implements IUpgradeableHost, IAEAppEngInventory, IConfigManagerHost, IOreFilterable, ICellRestriction { +public class TileCellWorkbench extends AEBaseTile implements ICellWorkbench, IPrimaryGuiIconProvider { private final AppEngInternalInventory cell = new AppEngInternalInventory(this, 1); - private final AppEngInternalAEInventory config = new AppEngInternalAEInventory(this, 63); + private final IAEStackInventory config = new IAEStackInventory(this, 63); private final ConfigManager manager = new ConfigManager(this); private IInventory cacheUpgrades = null; - private IInventory cacheConfig = null; + private IAEStackInventory cacheConfig = null; private boolean locked = false; private long cellRestrictAmount; private byte cellRestrictTypes; + private StorageChannel storageChannel; public TileCellWorkbench() { this.manager.registerSetting(Settings.COPY_MODE, CopyMode.CLEAR_ON_REMOVE); @@ -104,10 +105,6 @@ public class TileCellWorkbench extends AEBaseTile @Override public IInventory getInventoryByName(final String name) { - if (name.equals("config")) { - return this.config; - } - if (name.equals("cell")) { return this.cell; } @@ -138,17 +135,27 @@ public class TileCellWorkbench extends AEBaseTile this.cacheUpgrades = null; this.cacheConfig = null; + ItemStack is = this.cell.getStackInSlot(0); if (this.manager.getSetting(Settings.COPY_MODE) == CopyMode.KEEP_ON_REMOVE) { - ItemStack is = this.cell.getStackInSlot(0); if (is != null && is.getItem() instanceof ICellRestriction icr) icr.setCellRestriction(is, cellRestrictTypes + "," + cellRestrictAmount); } - final IInventory configInventory = this.getCellConfigInventory(); + if (is != null && is.getItem() instanceof ICellWorkbenchItem wi) { + if (wi.getStorageChannel() != this.storageChannel) { + this.storageChannel = wi.getStorageChannel(); + + for (int x = 0; x < this.config.getSizeInventory(); x++) { + this.config.putAEStackInSlot(x, null); + } + } + } + + final IAEStackInventory configInventory = this.getCellConfigInventory(); if (configInventory != null) { boolean cellHasConfig = false; for (int x = 0; x < configInventory.getSizeInventory(); x++) { - if (configInventory.getStackInSlot(x) != null) { + if (configInventory.getAEStackInSlot(x) != null) { cellHasConfig = true; break; } @@ -156,39 +163,30 @@ public class TileCellWorkbench extends AEBaseTile if (cellHasConfig) { for (int x = 0; x < this.config.getSizeInventory(); x++) { - this.config.setInventorySlotContents(x, configInventory.getStackInSlot(x)); + this.config.putAEStackInSlot(x, configInventory.getAEStackInSlot(x)); } } else { for (int x = 0; x < this.config.getSizeInventory(); x++) { - configInventory.setInventorySlotContents(x, this.config.getStackInSlot(x)); + configInventory.putAEStackInSlot(x, this.config.getAEStackInSlot(x)); } configInventory.markDirty(); } } else if (this.manager.getSetting(Settings.COPY_MODE) == CopyMode.CLEAR_ON_REMOVE) { for (int x = 0; x < this.config.getSizeInventory(); x++) { - this.config.setInventorySlotContents(x, null); + this.config.putAEStackInSlot(x, null); } this.markDirty(); } this.locked = false; - } else if (inv == this.config && !this.locked) { - final IInventory c = this.getCellConfigInventory(); - if (c != null) { - for (int x = 0; x < this.config.getSizeInventory(); x++) { - c.setInventorySlotContents(x, this.config.getStackInSlot(x)); - } - - c.markDirty(); - } } else if (inv == cacheUpgrades) { if (getInstalledUpgrades(Upgrades.ORE_FILTER) == 0) setFilter(""); } } - private IInventory getCellConfigInventory() { + private IAEStackInventory getCellConfigInventory() { if (this.cacheConfig == null) { final ICellWorkbenchItem cell = this.getCell(); if (cell == null) { @@ -200,7 +198,7 @@ public class TileCellWorkbench extends AEBaseTile return null; } - final IInventory inv = cell.getConfigInventory(is); + final IAEStackInventory inv = cell.getConfigAEInventory(is); if (inv == null) { return null; } @@ -262,4 +260,37 @@ public class TileCellWorkbench extends AEBaseTile ItemStack is = this.cell.getStackInSlot(0); if (is != null && is.getItem() instanceof ICellRestriction icr) icr.setCellRestriction(is, newData); } + + @Override + public boolean isSame(ICellWorkbench cellWorkbench) { + return this == getWorldObj().getTileEntity(xCoord, yCoord, zCoord); + } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().blocks().cellWorkbench().maybeStack(1).orNull(); + } + + @Override + public void saveAEStackInv() { + if (!this.locked) { + final IAEStackInventory c = this.getCellConfigInventory(); + if (c != null) { + for (int x = 0; x < this.config.getSizeInventory(); x++) { + c.putAEStackInSlot(x, this.config.getAEStackInSlot(x)); + } + + c.markDirty(); + } + } + } + + @Override + public IAEStackInventory getAEInventoryByName(StorageName name) { + return this.config; + } + + public StorageChannel getStorageChannel() { + return this.storageChannel; + } } diff --git a/src/main/java/appeng/tile/misc/TileInterface.java b/src/main/java/appeng/tile/misc/TileInterface.java index a40c06678..a4c00a1f0 100644 --- a/src/main/java/appeng/tile/misc/TileInterface.java +++ b/src/main/java/appeng/tile/misc/TileInterface.java @@ -29,6 +29,7 @@ import com.gtnewhorizon.gtnhlib.capability.item.ItemIO; import com.gtnewhorizon.gtnhlib.capability.item.ItemSink; import com.gtnewhorizon.gtnhlib.capability.item.ItemSource; +import appeng.api.AEApi; import appeng.api.config.Actionable; import appeng.api.config.Upgrades; import appeng.api.implementations.IPowerChannelState; @@ -54,6 +55,7 @@ import appeng.api.util.IConfigManager; import appeng.capabilities.MEItemIO; import appeng.helpers.DualityInterface; import appeng.helpers.IInterfaceHost; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.IPriorityHost; import appeng.me.GridAccessException; import appeng.tile.TileEvent; @@ -64,8 +66,9 @@ import appeng.util.Platform; import appeng.util.inv.IInventoryDestination; import io.netty.buffer.ByteBuf; -public class TileInterface extends AENetworkInvTile implements IGridTickable, ITileStorageMonitorable, - IStorageMonitorable, IInventoryDestination, IInterfaceHost, IPriorityHost, IPowerChannelState { +public class TileInterface extends AENetworkInvTile + implements IGridTickable, ITileStorageMonitorable, IStorageMonitorable, IInventoryDestination, IInterfaceHost, + IPriorityHost, IPowerChannelState, IPrimaryGuiIconProvider { private final DualityInterface duality = new DualityInterface(this.getProxy(), this); private ForgeDirection pointAt = ForgeDirection.UNKNOWN; @@ -338,6 +341,11 @@ public class TileInterface extends AENetworkInvTile implements IGridTickable, IT return this.getItemFromTile(this); } + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().blocks().iface().maybeStack(1).orNull(); + } + private MEItemIO getItemIO() { try { return new MEItemIO(this); diff --git a/src/main/java/appeng/tile/misc/TileSecurity.java b/src/main/java/appeng/tile/misc/TileSecurity.java index e921b4b7e..dd143a840 100644 --- a/src/main/java/appeng/tile/misc/TileSecurity.java +++ b/src/main/java/appeng/tile/misc/TileSecurity.java @@ -52,6 +52,7 @@ import appeng.api.util.AECableType; import appeng.api.util.AEColor; import appeng.api.util.DimensionalCoord; import appeng.api.util.IConfigManager; +import appeng.core.localization.GuiText; import appeng.helpers.PlayerSecurityWrapper; import appeng.me.GridAccessException; import appeng.me.storage.SecurityInventory; @@ -306,4 +307,9 @@ public class TileSecurity extends AENetworkTile implements ITerminalHost, IAEApp public AppEngInternalInventory getConfigSlot() { return this.configSlot; } + + @Override + public GuiText getName() { + return GuiText.Security; + } } diff --git a/src/main/java/appeng/tile/storage/TileChest.java b/src/main/java/appeng/tile/storage/TileChest.java index 517aa2177..76a03decd 100644 --- a/src/main/java/appeng/tile/storage/TileChest.java +++ b/src/main/java/appeng/tile/storage/TileChest.java @@ -74,6 +74,8 @@ import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; import appeng.api.util.AEColor; import appeng.api.util.IConfigManager; +import appeng.core.localization.GuiText; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.IPriorityHost; import appeng.items.storage.ItemBasicStorageCell; import appeng.me.GridAccessException; @@ -90,7 +92,7 @@ import appeng.util.item.AEFluidStack; import io.netty.buffer.ByteBuf; public class TileChest extends AENetworkPowerTile implements IMEChest, IFluidHandler, ITerminalHost, IPriorityHost, - IConfigManagerHost, IColorableTile, IGridTickable { + IConfigManagerHost, IColorableTile, IGridTickable, IPrimaryGuiIconProvider { private static final ChestNoHandler NO_HANDLER = new ChestNoHandler(); private static final int[] SIDES = { 0 }; @@ -247,7 +249,7 @@ public class TileChest extends AENetworkPowerTile implements IMEChest, IFluidHan return null; } - private MEMonitorHandler wrap(final IMEInventoryHandler h) { + private > MEMonitorHandler wrap(final IMEInventoryHandler h) { if (h == null) { return null; } @@ -784,7 +786,7 @@ public class TileChest extends AENetworkPowerTile implements IMEChest, IFluidHan private static final long serialVersionUID = 7995805326136526631L; } - private class ChestNetNotifier> implements IMEMonitorHandlerReceiver { + private class ChestNetNotifier implements IMEMonitorHandlerReceiver> { private final StorageChannel chan; @@ -804,7 +806,8 @@ public class TileChest extends AENetworkPowerTile implements IMEChest, IFluidHan } @Override - public void postChange(final IBaseMonitor monitor, final Iterable change, final BaseActionSource source) { + public void postChange(final IBaseMonitor> monitor, final Iterable> change, + final BaseActionSource source) { try { if (TileChest.this.getProxy().isActive()) { TileChest.this.getProxy().getStorage() @@ -823,7 +826,7 @@ public class TileChest extends AENetworkPowerTile implements IMEChest, IFluidHan } } - private class ChestMonitorHandler extends MEMonitorHandler { + private class ChestMonitorHandler> extends MEMonitorHandler { public ChestMonitorHandler(final IMEInventoryHandler t) { super(t); @@ -879,4 +882,14 @@ public class TileChest extends AENetworkPowerTile implements IMEChest, IFluidHan return super.extractItems(request, mode, src); } } + + @Override + public GuiText getName() { + return GuiText.Chest; + } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().blocks().chest().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/tile/storage/TileDrive.java b/src/main/java/appeng/tile/storage/TileDrive.java index a516f90d4..e2a21220e 100644 --- a/src/main/java/appeng/tile/storage/TileDrive.java +++ b/src/main/java/appeng/tile/storage/TileDrive.java @@ -48,10 +48,13 @@ import appeng.api.storage.IMEInventoryHandler; import appeng.api.storage.ISaveProvider; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; +import appeng.api.storage.data.IAEStack; import appeng.api.util.AECableType; import appeng.api.util.AEColor; import appeng.api.util.DimensionalCoord; +import appeng.helpers.IPrimaryGuiIconProvider; import appeng.helpers.IPriorityHost; +import appeng.items.AEBaseCell; import appeng.items.materials.ItemMultiMaterial; import appeng.items.storage.ItemBasicStorageCell; import appeng.me.GridAccessException; @@ -63,10 +66,10 @@ import appeng.tile.inventory.AppEngInternalInventory; import appeng.tile.inventory.InvOperation; import appeng.util.IterationCounter; import appeng.util.Platform; -import appeng.util.item.ItemList; import io.netty.buffer.ByteBuf; -public class TileDrive extends AENetworkInvTile implements IChestOrDrive, IPriorityHost, IGridTickable, IColorableTile { +public class TileDrive extends AENetworkInvTile + implements IChestOrDrive, IPriorityHost, IGridTickable, IColorableTile, IPrimaryGuiIconProvider { private static final int INV_SIZE = 10; /** @@ -394,13 +397,14 @@ public class TileDrive extends AENetworkInvTile implements IChestOrDrive, IPrior if (cellInventory != null) { if (cellInventory.getStoredItemTypes() != 0) { int idx = 0; - for (IAEItemStack partitionAEItemStack : handler - .getAvailableItems(new ItemList(), IterationCounter.fetchNewId())) { - ItemStack partition = partitionAEItemStack.getItemStack().copy(); - partition.stackSize = 1; - cellInventory.getConfigInventory().setInventorySlotContents(idx++, partition); + for (Object partitionStack : (handler.getAvailableItems( + cellInventory.getChannel().createPrimitiveList(), + IterationCounter.fetchNewId()))) { + final IAEStack aes = ((IAEStack) partitionStack).copy(); + aes.setStackSize(1); + cellInventory.getConfigAEInventory().putAEStackInSlot(idx++, aes); } - cellInventory.getConfigInventory().markDirty(); + cellInventory.getConfigAEInventory().markDirty(); } } } @@ -408,16 +412,19 @@ public class TileDrive extends AENetworkInvTile implements IChestOrDrive, IPrior public static void unpartitionStorageCell(ICellInventoryHandler handler) { ICellInventory cellInventory = handler.getCellInv(); if (cellInventory != null) { - for (int i = 0; i < cellInventory.getConfigInventory().getSizeInventory(); i++) { - cellInventory.getConfigInventory().setInventorySlotContents(i, null); + for (int i = 0; i < cellInventory.getConfigAEInventory().getSizeInventory(); i++) { + cellInventory.getConfigAEInventory().putAEStackInSlot(i, null); } - cellInventory.getConfigInventory().markDirty(); + cellInventory.getConfigAEInventory().markDirty(); } } public static boolean applyStickyCardToItemStorageCell(ICellHandler cellHandler, ItemStack cell, ISaveProvider host, ICellWorkbenchItem cellItem) { - final IMEInventoryHandler inv = cellHandler.getCellInventory(cell, host, StorageChannel.ITEMS); + final IMEInventoryHandler inv = cellHandler.getCellInventory( + cell, + host, + cell.getItem() instanceof AEBaseCell abc ? abc.getStorageChannel() : StorageChannel.ITEMS); if (inv instanceof ICellInventoryHandler handler) { final ICellInventory cellInventory = handler.getCellInv(); if (cellInventory != null && cellInventory.getStoredItemTypes() > 0) { @@ -457,7 +464,10 @@ public class TileDrive extends AENetworkInvTile implements IChestOrDrive, IPrior if (ItemBasicStorageCell.checkInvalidForLockingAndStickyCarding(cell, cellHandler)) { continue; } - final IMEInventoryHandler inv = cellHandler.getCellInventory(cell, this, StorageChannel.ITEMS); + final IMEInventoryHandler inv = cellHandler.getCellInventory( + cell, + this, + cell.getItem() instanceof AEBaseCell abc ? abc.getStorageChannel() : StorageChannel.ITEMS); if (inv instanceof ICellInventoryHandler handler) { if (ItemBasicStorageCell.cellIsPartitioned(handler)) { unpartitionStorageCell(handler); @@ -520,4 +530,9 @@ public class TileDrive extends AENetworkInvTile implements IChestOrDrive, IPrior this.markForUpdate(); return true; } + + @Override + public ItemStack getPrimaryGuiIcon() { + return AEApi.instance().definitions().blocks().drive().maybeStack(1).orNull(); + } } diff --git a/src/main/java/appeng/util/FluidUtils.java b/src/main/java/appeng/util/FluidUtils.java new file mode 100644 index 000000000..9c499cea4 --- /dev/null +++ b/src/main/java/appeng/util/FluidUtils.java @@ -0,0 +1,95 @@ +package appeng.util; + +import javax.annotation.Nullable; + +import net.minecraft.item.Item; +import net.minecraft.item.ItemStack; +import net.minecraftforge.fluids.FluidContainerRegistry; +import net.minecraftforge.fluids.FluidStack; +import net.minecraftforge.fluids.IFluidContainerItem; + +import codechicken.nei.recipe.StackInfo; +import it.unimi.dsi.fastutil.objects.ObjectIntMutablePair; +import it.unimi.dsi.fastutil.objects.ObjectIntPair; + +public class FluidUtils { + + public static boolean isFluidContainer(@Nullable ItemStack itemStack) { + if (itemStack == null) return false; + Item item = itemStack.getItem(); + if (item instanceof IFluidContainerItem) return true; + return FluidContainerRegistry.isContainer(itemStack); + } + + public static boolean isFilledFluidContainer(@Nullable ItemStack itemStack) { + if (itemStack == null) return false; + Item item = itemStack.getItem(); + if (item instanceof IFluidContainerItem container) { + FluidStack content = container.getFluid(itemStack); + return content != null && content.amount > 0; + } + return FluidContainerRegistry.isFilledContainer(itemStack); + } + + public static int getFluidContainerCapacity(@Nullable ItemStack itemStack, FluidStack fluidStack) { + if (itemStack == null) return 0; + if (itemStack.getItem() instanceof IFluidContainerItem container) { + return container.getCapacity(itemStack); + } else if (FluidContainerRegistry.isContainer(itemStack)) { + return FluidContainerRegistry.getContainerCapacity(fluidStack, itemStack); + } + return 0; + } + + public static ItemStack getFilledFluidContainer(@Nullable ItemStack itemStack, FluidStack fluidStack) { + if (itemStack == null) return null; + + fluidStack = fluidStack.copy(); + itemStack = itemStack.copy(); + fluidStack.amount = Integer.MAX_VALUE; + if (itemStack.getItem() instanceof IFluidContainerItem container) { + container.fill(itemStack, fluidStack, true); + return itemStack; + } else if (FluidContainerRegistry.isContainer(itemStack)) { + return FluidContainerRegistry.fillFluidContainer(fluidStack, itemStack); + } + return null; + } + + public static ItemStack clearFluidContainer(ItemStack itemStack) { + if (itemStack == null) return null; + if (itemStack.getItem() instanceof IFluidContainerItem container) { + container.drain(itemStack, container.getFluid(itemStack).amount, true); + return itemStack; + } else if (FluidContainerRegistry.isContainer(itemStack)) { + return FluidContainerRegistry.drainFluidContainer(itemStack); + } + return null; + } + + public static FluidStack getFluidFromContainer(ItemStack itemStack) { + if (itemStack == null) return null; + + if (itemStack.getItem() instanceof IFluidContainerItem container) { + return container.getFluid(itemStack); + } else if (FluidContainerRegistry.isContainer(itemStack)) { + return FluidContainerRegistry.getFluidForFilledItem(itemStack); + } else { + return StackInfo.getFluid(Platform.copyStackWithSize(itemStack, 1)); + } + } + + public static ObjectIntPair fillFluidContainer(@Nullable ItemStack itemStack, FluidStack fluidStack) { + if (itemStack == null) return new ObjectIntMutablePair<>(null, 0); + + if (itemStack.getItem() instanceof IFluidContainerItem container) { + return new ObjectIntMutablePair<>(itemStack, container.fill(itemStack, fluidStack, true)); + } else if (FluidContainerRegistry.isContainer(itemStack)) { + ItemStack filledContainer = FluidContainerRegistry.fillFluidContainer(fluidStack, itemStack); + FluidStack filled = FluidContainerRegistry.getFluidForFilledItem(filledContainer); + return new ObjectIntMutablePair<>(filledContainer, filled != null ? filled.amount : 0); + } + + return new ObjectIntMutablePair<>(null, 0); + } +} diff --git a/src/main/java/appeng/util/ItemSorters.java b/src/main/java/appeng/util/ItemSorters.java index c51e8d6da..0a0d7fc65 100644 --- a/src/main/java/appeng/util/ItemSorters.java +++ b/src/main/java/appeng/util/ItemSorters.java @@ -13,32 +13,32 @@ package appeng.util; import java.util.Comparator; import appeng.api.config.SortDir; -import appeng.api.storage.data.IAEItemStack; import appeng.api.storage.data.IAEStack; public class ItemSorters { private static SortDir direction = SortDir.ASCENDING; - public static final Comparator CONFIG_BASED_SORT_BY_NAME = Comparator - .comparing(Platform::getItemDisplayName, (a, b) -> a.compareToIgnoreCase(b) * direction.sortHint); + public static final Comparator> CONFIG_BASED_SORT_BY_NAME = Comparator + .comparing(IAEStack::getDisplayName, (a, b) -> a.compareToIgnoreCase(b) * direction.sortHint); - public static final Comparator CONFIG_BASED_SORT_BY_MOD = Comparator - .comparing(Platform::getModId, (a, b) -> a.compareToIgnoreCase(b) * direction.sortHint) - .thenComparing(Platform::getItemDisplayName); + public static final Comparator> CONFIG_BASED_SORT_BY_MOD = Comparator + .comparing((IAEStack stack) -> stack.getModId(), (a, b) -> a.compareToIgnoreCase(b) * direction.sortHint) + .thenComparing(IAEStack::getDisplayName); - public static final Comparator CONFIG_BASED_SORT_BY_SIZE = Comparator + public static final Comparator> CONFIG_BASED_SORT_BY_SIZE = Comparator .comparing(IAEStack::getStackSize, (a, b) -> Long.compare(b, a) * direction.sortHint); - public static final Comparator CONFIG_BASED_SORT_BY_INV_TWEAKS = new Comparator<>() { + public static final Comparator> CONFIG_BASED_SORT_BY_INV_TWEAKS = new Comparator<>() { @Override - public int compare(final IAEItemStack o1, final IAEItemStack o2) { + public int compare(final IAEStack o1, final IAEStack o2) { if (!InvTweakSortingModule.isLoaded()) { return CONFIG_BASED_SORT_BY_NAME.compare(o1, o2); } - return InvTweakSortingModule.compareItems(o1.getItemStack(), o2.getItemStack()) * direction.sortHint; + return InvTweakSortingModule.compareItems(o1.getItemStackForNEI(), o2.getItemStackForNEI()) + * direction.sortHint; } }; diff --git a/src/main/java/appeng/util/Platform.java b/src/main/java/appeng/util/Platform.java index 230b135a0..9f01b72a1 100644 --- a/src/main/java/appeng/util/Platform.java +++ b/src/main/java/appeng/util/Platform.java @@ -112,7 +112,7 @@ import appeng.api.storage.data.IAETagCompound; import appeng.api.storage.data.IItemList; import appeng.api.util.AEColor; import appeng.api.util.DimensionalCoord; -import appeng.client.me.SlotME; +import appeng.container.AEBaseContainer; import appeng.container.slot.SlotFake; import appeng.core.AEConfig; import appeng.core.AELog; @@ -135,6 +135,7 @@ import appeng.util.item.AEStack; import appeng.util.item.OreHelper; import appeng.util.item.OreReference; import appeng.util.prioitylist.IPartitionList; +import baubles.api.BaublesApi; import buildcraft.api.tools.IToolWrench; import cofh.api.item.IToolHammer; import cpw.mods.fml.common.FMLCommonHandler; @@ -176,6 +177,7 @@ public class Platform { private static final DecimalFormat df = new DecimalFormat("#.##"); public static final boolean isAE2FCLoaded = Loader.isModLoaded("ae2fc"); public static final boolean isEIOLoaded = Loader.isModLoaded("EnderIO"); + public static boolean isBaublesLoaded = Loader.isModLoaded("Baubles"); static { BYTE_LIMIT = new double[10]; @@ -339,8 +341,16 @@ public class Platform { return e == SearchBoxMode.NEI_MANUAL_SEARCH && !IntegrationRegistry.INSTANCE.isEnabled(IntegrationType.NEI); } + // xCord game limit + public final static int itemGuiSlotOffset = 30_000_001; + public static void openGUI(@Nonnull final EntityPlayer p, @Nullable final TileEntity tile, @Nullable final ForgeDirection side, @Nonnull final GuiBridge type) { + openGUI(p, tile, side, type, Integer.MIN_VALUE); + } + + public static void openGUI(@Nonnull final EntityPlayer p, @Nullable final TileEntity tile, + @Nullable final ForgeDirection side, @Nonnull final GuiBridge type, final int slotIndex) { if (isClient()) { return; } @@ -355,13 +365,13 @@ public class Platform { } if ((type.getType().isItem() && tile == null) || type.hasPermissions(tile, x, y, z, side, p)) { - if (tile == null && type.getType() == GuiHostType.ITEM) { + if (tile == null && type.getType() != GuiHostType.WORLD) { p.openGui( AppEng.instance(), type.ordinal() << 5 | (1 << 4), p.getEntityWorld(), - p.inventory.currentItem, - 0, + itemGuiSlotOffset + (slotIndex == Integer.MIN_VALUE ? p.inventory.currentItem : slotIndex), + p.openContainer instanceof AEBaseContainer abc ? abc.getSwitchAbleGuiNext() : Integer.MIN_VALUE, 0); } else if (tile == null || type.getType() == GuiHostType.ITEM) { p.openGui(AppEng.instance(), type.ordinal() << 5 | (1 << 3), p.getEntityWorld(), x, y, z); @@ -792,7 +802,7 @@ public class Platform { return "** Null"; } - final String n = ((AEItemStack) is).getModID(); + final String n = ((AEItemStack) is).getModId(); return n == null ? "** Null" : n; } @@ -1257,13 +1267,20 @@ public class Platform { if (possible != null) { retrieved = possible.getStackSize(); } + final int typeMultiplier = request.getPowerMultiplier(); - final double availablePower = energy.extractAEPower(retrieved, Actionable.SIMULATE, PowerMultiplier.CONFIG); + final double availablePower = energy.extractAEPower( + Platform.ceilDiv(retrieved, typeMultiplier), + Actionable.SIMULATE, + PowerMultiplier.CONFIG); - final long itemToExtract = Math.min((long) (availablePower + 0.9), retrieved); + final long itemToExtract = Math.min((long) (availablePower * typeMultiplier + 0.9), retrieved); if (itemToExtract > 0) { - energy.extractAEPower(retrieved, Actionable.MODULATE, PowerMultiplier.CONFIG); + energy.extractAEPower( + Platform.ceilDiv(retrieved, typeMultiplier), + Actionable.MODULATE, + PowerMultiplier.CONFIG); possible.setStackSize(itemToExtract); final StackType ret = cell.extractItems(possible, Actionable.MODULATE, src); @@ -1286,7 +1303,7 @@ public class Platform { if (possible != null) { stored -= possible.getStackSize(); } - long typeMultiplier = input instanceof IAEFluidStack ? 1000 : 1; + final int typeMultiplier = input.getPowerMultiplier(); final double availablePower = energy .extractAEPower(Platform.ceilDiv(stored, typeMultiplier), Actionable.SIMULATE, PowerMultiplier.CONFIG); @@ -1373,8 +1390,8 @@ public class Platform { } public static > void postListChanges(final IItemList before, final IItemList after, - final IMEMonitorHandlerReceiver meMonitorPassthrough, final BaseActionSource source) { - final LinkedList changes = new LinkedList<>(); + final IMEMonitorHandlerReceiver meMonitorPassthrough, final BaseActionSource source) { + final LinkedList> changes = new LinkedList<>(); for (final T is : before) { is.setStackSize(-is.getStackSize()); @@ -1846,10 +1863,6 @@ public class Platform { return null; } - if (slot instanceof SlotME) { - return ((SlotME) slot).getAEStack(); - } - if (slot instanceof SlotFake) { return ((SlotFake) slot).getAEStack(); } @@ -2000,6 +2013,7 @@ public class Platform { } public static IAEStack readStackNBT(NBTTagCompound tag, boolean convert) { + if (tag == null) return null; if (tag.hasKey("StackType", 1)) { // For old experimental compatibility final byte stackType = tag.getByte("StackType"); @@ -2090,7 +2104,44 @@ public class Platform { return AEItemStack.create(stack); } + public static boolean isStacksIdentical(IAEStack a, IAEStack b) { + if (a == null && b == null) return true; + if (a == null || b == null) return false; + if (a.equals(b)) return a.getStackSize() == b.getStackSize(); + return false; + } + + public final static int baublesSlotsOffset = 100_012; + + public static ItemStack getItemFromPlayerInventoryBySlotIndex(final EntityPlayer p, final int slotIndex) { + if (slotIndex < 0) { + return p.inventory.getCurrentItem(); + } else if (isBaublesLoaded && slotIndex >= baublesSlotsOffset) { + return BaublesApi.getBaubles(p).getStackInSlot(slotIndex - baublesSlotsOffset); + } else if (slotIndex < p.inventory.getSizeInventory()) { + return p.inventory.getStackInSlot(slotIndex); + } + + return null; + } + + public static void setPlayerInventorySlotByIndex(final EntityPlayer p, final int slotIndex, final ItemStack is) { + if (isBaublesLoaded && slotIndex >= baublesSlotsOffset) { + BaublesApi.getBaubles(p).setInventorySlotContents(slotIndex, is); + } else p.inventory.setInventorySlotContents(slotIndex, is); + } + public static int longToInt(long number) { return (int) Math.min(Integer.MAX_VALUE, number); } + + public static ItemStack copyStackWithSize(ItemStack itemStack, int size) { + if (size != 0 && itemStack != null) { + ItemStack copy = itemStack.copy(); + copy.stackSize = size; + return copy; + } else { + return null; + } + } } diff --git a/src/main/java/appeng/util/item/AEFluidStack.java b/src/main/java/appeng/util/item/AEFluidStack.java index 27f986c81..9256ab12c 100644 --- a/src/main/java/appeng/util/item/AEFluidStack.java +++ b/src/main/java/appeng/util/item/AEFluidStack.java @@ -10,6 +10,8 @@ package appeng.util.item; +import static appeng.util.Platform.stackConvertPacket; + import java.io.ByteArrayInputStream; import java.io.ByteArrayOutputStream; import java.io.DataInputStream; @@ -18,19 +20,31 @@ import java.io.IOException; import java.nio.charset.StandardCharsets; import javax.annotation.Nonnull; +import javax.annotation.Nullable; +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.Tessellator; +import net.minecraft.client.renderer.texture.TextureMap; +import net.minecraft.item.ItemStack; import net.minecraft.nbt.CompressedStreamTools; import net.minecraft.nbt.NBTBase; import net.minecraft.nbt.NBTTagCompound; +import net.minecraft.util.IIcon; import net.minecraftforge.fluids.Fluid; +import net.minecraftforge.fluids.FluidRegistry; import net.minecraftforge.fluids.FluidStack; +import org.lwjgl.opengl.GL11; + import appeng.api.config.FuzzyMode; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEFluidStack; import appeng.api.storage.data.IAEStack; import appeng.api.storage.data.IAETagCompound; import appeng.util.Platform; +import codechicken.nei.recipe.StackInfo; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; import io.netty.buffer.ByteBuf; public final class AEFluidStack extends AEStack implements IAEFluidStack, Comparable { @@ -383,6 +397,54 @@ public final class AEFluidStack extends AEStack implements IAEFlu return fluid.getUnlocalizedName(); } + @Override + public String getModId() { + String name = FluidRegistry.getDefaultFluidName(this.fluid); + try { + return name.split(":")[0]; + } catch (Exception e) { + return ""; + } + } + @Override public void setTagCompound(NBTTagCompound tagCompound) {} + + @Nullable + @Override + public ItemStack getItemStackForNEI() { + IAEFluidStack ifs = this.copy(); + if (ifs.getStackSize() <= 0) ifs.setStackSize(1); + ItemStack stack = stackConvertPacket(ifs).getItemStack(); + return StackInfo.loadFromNBT(StackInfo.itemStackToNBT(stack), 0); + } + + @Override + @SideOnly(Side.CLIENT) + public void drawInGui(Minecraft mc, int x, int y) { + final IIcon icon = this.fluid.getIcon(); + final int color = this.fluid.getColor(); + final Tessellator tessellator = Tessellator.instance; + + mc.renderEngine.bindTexture(TextureMap.locationBlocksTexture); + GL11.glPushAttrib(GL11.GL_ENABLE_BIT); + GL11.glDisable(GL11.GL_LIGHTING); + GL11.glEnable(GL11.GL_BLEND); + GL11.glBlendFunc(GL11.GL_SRC_ALPHA, GL11.GL_ONE_MINUS_SRC_ALPHA); + tessellator.startDrawingQuads(); + + tessellator.setColorRGBA(color >> 16 & 0xFF, color >> 8 & 0xFF, color & 0xFF, 0xFF); + tessellator.addVertexWithUV(x + 16, y, 0, icon.getMaxU(), icon.getMinV()); + tessellator.addVertexWithUV(x, y, 0, icon.getMinU(), icon.getMinV()); + tessellator.addVertexWithUV(x, y + 16, 0, icon.getMinU(), icon.getMaxV()); + tessellator.addVertexWithUV(x + 16, y + 16, 0, icon.getMaxU(), icon.getMaxV()); + + tessellator.draw(); + GL11.glPopAttrib(); + } + + @Override + public int getPowerMultiplier() { + return 1000; + } } diff --git a/src/main/java/appeng/util/item/AEItemStack.java b/src/main/java/appeng/util/item/AEItemStack.java index 6bb9d0e61..21d4000db 100644 --- a/src/main/java/appeng/util/item/AEItemStack.java +++ b/src/main/java/appeng/util/item/AEItemStack.java @@ -20,12 +20,16 @@ import java.util.List; import javax.annotation.Nullable; +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.entity.RenderItem; import net.minecraft.item.Item; import net.minecraft.item.ItemStack; import net.minecraft.nbt.CompressedStreamTools; import net.minecraft.nbt.NBTTagCompound; import net.minecraft.util.StatCollector; +import org.lwjgl.opengl.GL11; + import appeng.api.config.FuzzyMode; import appeng.api.storage.StorageChannel; import appeng.api.storage.data.IAEItemStack; @@ -536,7 +540,13 @@ public final class AEItemStack extends AEStack implements IAEItemS return getItem().getUnlocalizedName(); } + // addon... public String getModID() { + return this.getModId(); + } + + @Override + public String getModId() { if (this.getDefinition().getUniqueID() != null) { return this.getModName(this.getDefinition().getUniqueID()); } @@ -666,4 +676,31 @@ public final class AEItemStack extends AEStack implements IAEItemS .setTagCompound((AESharedNBT) AESharedNBT.getSharedTagCompound(tagCompound, getItemStack())); } } + + @Override + public ItemStack getItemStackForNEI() { + return this.getItemStack(); + } + + @Override + @SideOnly(Side.CLIENT) + public void drawInGui(Minecraft mc, int x, int y) { + ItemStack itemStack = this.getItemStack(); + RenderItem itemRender = RenderItem.getInstance(); + itemRender.renderItemAndEffectIntoGUI(mc.fontRenderer, mc.getTextureManager(), itemStack, x, y); + + GL11.glTranslatef(0.0f, 0.0f, 200.0f); + + int stackSize = itemStack.stackSize; + itemStack.stackSize = 1; + itemRender.renderItemOverlayIntoGUI(mc.fontRenderer, mc.getTextureManager(), itemStack, x, y); + itemStack.stackSize = stackSize; + + GL11.glTranslatef(0.0f, 0.0f, -200.0f); + } + + @Override + public int getPowerMultiplier() { + return 1; + } } diff --git a/src/main/java/appeng/util/item/AEStack.java b/src/main/java/appeng/util/item/AEStack.java index 91587bc50..f2c20eaa6 100644 --- a/src/main/java/appeng/util/item/AEStack.java +++ b/src/main/java/appeng/util/item/AEStack.java @@ -12,7 +12,20 @@ package appeng.util.item; import java.io.IOException; +import net.minecraft.client.Minecraft; +import net.minecraft.client.renderer.entity.RenderItem; +import net.minecraft.item.ItemStack; + +import org.lwjgl.opengl.GL11; + +import appeng.api.AEApi; +import appeng.api.config.TerminalFontSize; import appeng.api.storage.data.IAEStack; +import appeng.client.render.StackSizeRenderer; +import appeng.core.AEConfig; +import appeng.core.localization.GuiText; +import cpw.mods.fml.relauncher.Side; +import cpw.mods.fml.relauncher.SideOnly; import io.netty.buffer.ByteBuf; public abstract class AEStack> implements IAEStack { @@ -181,4 +194,53 @@ public abstract class AEStack> implements tag.writeLong(num); } } + + private static final ItemStack PATTERN = AEApi.instance().definitions().items().encodedPattern().maybeStack(1) + .orNull(); + + @Override + @SideOnly(Side.CLIENT) + public void drawOverlayInGui(Minecraft mc, int x, int y, boolean showAmount, boolean showAmountAlways, + boolean showCraftableText, boolean showCraftableIcon) { + final TerminalFontSize fontSize = AEConfig.instance.getTerminalFontSize(); + + GL11.glTranslatef(0.0f, 0.0f, 200.0f); + GL11.glDisable(GL11.GL_LIGHTING); + + if (showCraftableText && this.isCraftable()) { + if (this.stackSize == 0) { + final String craftLabelText = fontSize == TerminalFontSize.SMALL ? GuiText.SmallFontCraft.getLocal() + : GuiText.LargeFontCraft.getLocal(); + + GL11.glPushMatrix(); + StackSizeRenderer.drawStackSize(x, y, craftLabelText, mc.fontRenderer, fontSize); + GL11.glPopMatrix(); + } else { + if (showCraftableIcon) { + GL11.glPushMatrix(); + GL11.glScalef(0.4f, 0.4f, 0.4f); + RenderItem itemRender = new RenderItem(); + itemRender.renderItemIntoGUI( + mc.fontRenderer, + mc.renderEngine, + PATTERN, + (int) ((x + 10) * 2.5), + (int) (y * 2.5)); + GL11.glScalef(2.5f, 2.5f, 2.5f); + GL11.glPopMatrix(); + + } + } + } + + if (showAmount && (this.stackSize > 1 + || (showAmountAlways && (this.stackSize > 0 || !showCraftableText || !this.isCraftable)))) { + GL11.glPushMatrix(); + StackSizeRenderer.drawStackSize(x, y, this.stackSize, mc.fontRenderer, fontSize); + GL11.glPopMatrix(); + } + + GL11.glEnable(GL11.GL_LIGHTING); + GL11.glTranslatef(0.0f, 0.0f, -200.0f); + } } diff --git a/src/main/java/appeng/util/item/FluidList.java b/src/main/java/appeng/util/item/FluidList.java index 111b7fde9..8c11ef7ab 100644 --- a/src/main/java/appeng/util/item/FluidList.java +++ b/src/main/java/appeng/util/item/FluidList.java @@ -56,7 +56,12 @@ public final class FluidList implements IItemList { return Collections.emptyList(); } - return Collections.singletonList(this.findPrecise(filter)); + IAEFluidStack found = this.findPrecise(filter); + if (found == null) { + return Collections.emptyList(); + } + + return Collections.singletonList(found); } @Override diff --git a/src/main/java/appeng/util/item/IAEStackList.java b/src/main/java/appeng/util/item/IAEStackList.java index b8dbdd952..2adce75a9 100644 --- a/src/main/java/appeng/util/item/IAEStackList.java +++ b/src/main/java/appeng/util/item/IAEStackList.java @@ -1,7 +1,6 @@ package appeng.util.item; import java.util.Collection; -import java.util.Collections; import java.util.Iterator; import javax.annotation.Nonnull; @@ -42,12 +41,13 @@ public final class IAEStackList implements IItemList> { } @Override + @SuppressWarnings({ "unchecked", "rawtypes" }) public Collection> findFuzzy(final IAEStack filter, final FuzzyMode fuzzy) { if (filter != null) { if (filter.isItem()) { - return Collections.singleton((IAEStack) itemList.findFuzzy((IAEItemStack) filter, fuzzy)); + return (Collection) itemList.findFuzzy((IAEItemStack) filter, fuzzy); } else { - return Collections.singleton((IAEStack) fluidList.findFuzzy((IAEFluidStack) filter, fuzzy)); + return (Collection) fluidList.findFuzzy((IAEFluidStack) filter, fuzzy); } } return null; diff --git a/src/main/resources/assets/appliedenergistics2/lang/en_US.lang b/src/main/resources/assets/appliedenergistics2/lang/en_US.lang index ac05cff43..dee1e15f7 100644 --- a/src/main/resources/assets/appliedenergistics2/lang/en_US.lang +++ b/src/main/resources/assets/appliedenergistics2/lang/en_US.lang @@ -499,7 +499,7 @@ gui.tooltips.appliedenergistics2.ReportInaccessibleItemsNo=No: Only extractable gui.tooltips.appliedenergistics2.TypeFilter=Filter Types gui.tooltips.appliedenergistics2.TypeFilterShowAll=Show All gui.tooltips.appliedenergistics2.TypeFilterShowItemsOnly=Show Items only -gui.tooltips.appliedenergistics2.TypeFilterShowFluidsOnly=Show Fluid Drops only +gui.tooltips.appliedenergistics2.TypeFilterShowFluidsOnly=Show Fluids only gui.tooltips.appliedenergistics2.BlockPlacement=Block Placement gui.tooltips.appliedenergistics2.BlockPlacementYes=Blocks will be placed as block. @@ -510,8 +510,8 @@ gui.tooltips.appliedenergistics2.SchedulingModeDefault=Export the first item unt gui.tooltips.appliedenergistics2.SchedulingModeRoundRobin=Export using round robin mode. gui.tooltips.appliedenergistics2.SchedulingModeRandom=Export items in random mode. -gui.tooltips.appliedenergistics2.ItemsStored=Items Stored: %s -gui.tooltips.appliedenergistics2.ItemCount=Items Count: %s +gui.tooltips.appliedenergistics2.ItemsStored=Stored: %s +gui.tooltips.appliedenergistics2.ItemCount=Count: %s gui.tooltips.appliedenergistics2.ItemsRequestable=Items Requestable: %s gui.tooltips.appliedenergistics2.P2PFrequency=Frequency: %s gui.tooltips.appliedenergistics2.OreFilterHint=Filter items using ore dictionary names @@ -944,3 +944,4 @@ stat.ae2.TurnedCranks=Turned Cranks key.appliedenergistics2.category=Applied Energistics 2 key.toggle_focus.desc=Toggle search box focus key.search_connected_inventories.desc=Search network inventories for item +key.control_operation.desc=Control operation