Added fluid autocrafting, not finished yet. #461

This commit is contained in:
raoulvdberge
2018-07-22 17:07:48 +02:00
parent 5a595c9120
commit 26d36b0d65
81 changed files with 1680 additions and 409 deletions

View File

@@ -1,5 +1,8 @@
# Refined Storage Changelog # Refined Storage Changelog
### 1.6.1
- Added fluid autocrafting (raoulvdberge)
### 1.6 ### 1.6
NOTE: Worlds that used Refined Storage 1.5.x are fully compatible with Refined Storage 1.6.x and are getting converted upon loading the world. It is however not possible to revert back to Refined Storage 1.5.x when a world has already been converted to Refined Storage 1.6.x. NOTE: Worlds that used Refined Storage 1.5.x are fully compatible with Refined Storage 1.6.x and are getting converted upon loading the world. It is however not possible to revert back to Refined Storage 1.5.x when a world has already been converted to Refined Storage 1.6.x.

View File

@@ -5,6 +5,8 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftin
import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElementRegistry; import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElementRegistry;
import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElementRegistry; import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElementRegistry;
import com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskRegistry; import com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskRegistry;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.network.grid.wireless.IWirelessGridFactory; import com.raoulvdberge.refinedstorage.api.network.grid.wireless.IWirelessGridFactory;
import com.raoulvdberge.refinedstorage.api.network.grid.wireless.IWirelessGridRegistry; import com.raoulvdberge.refinedstorage.api.network.grid.wireless.IWirelessGridRegistry;
@@ -25,6 +27,7 @@ import com.raoulvdberge.refinedstorage.api.util.IQuantityFormatter;
import com.raoulvdberge.refinedstorage.api.util.IStackList; import com.raoulvdberge.refinedstorage.api.util.IStackList;
import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.util.EnumHand; import net.minecraft.util.EnumHand;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World; import net.minecraft.world.World;
@@ -171,6 +174,30 @@ public interface IRSAPI {
@Nonnull @Nonnull
IStorageDisk<FluidStack> createDefaultFluidDisk(World world, int capacity); IStorageDisk<FluidStack> createDefaultFluidDisk(World world, int capacity);
/**
* Creates crafting request info for an item.
*
* @param stack the stack
* @return the request info
*/
ICraftingRequestInfo createCraftingRequestInfo(ItemStack stack);
/**
* Creates crafting request info for a fluid.
*
* @param stack the stack
* @return the request info
*/
ICraftingRequestInfo createCraftingRequestInfo(FluidStack stack);
/**
* Creates crafting request info from NBT.
*
* @param tag the nbt tag
* @return the request info
*/
ICraftingRequestInfo createCraftingRequestInfo(NBTTagCompound tag) throws CraftingTaskReadException;
/** /**
* Returns a helper for the 1.6.x migration. * Returns a helper for the 1.6.x migration.
* Will be removed in 1.7.x! * Will be removed in 1.7.x!

View File

@@ -4,6 +4,7 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftin
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask; import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagCompound;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.items.IItemHandlerModifiable; import net.minecraftforge.items.IItemHandlerModifiable;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@@ -60,6 +61,16 @@ public interface ICraftingManager {
@Nullable @Nullable
ICraftingTask create(ItemStack stack, int quantity); ICraftingTask create(ItemStack stack, int quantity);
/**
* Creates a crafting task for a given stack, but doesn't add it to the list.
*
* @param stack the stack to craft
* @param quantity the quantity to craft
* @return the crafting task, or null if no pattern was found for the given stack
*/
@Nullable
ICraftingTask create(FluidStack stack, int quantity);
/** /**
* @return a new pattern chain list * @return a new pattern chain list
*/ */
@@ -82,6 +93,13 @@ public interface ICraftingManager {
*/ */
void track(ItemStack stack, int size); void track(ItemStack stack, int size);
/**
* Tracks an incoming stack.
*
* @param stack the stack
*/
void track(FluidStack stack, int size);
/** /**
* @return a list of crafting patterns in this network, do NOT modify this list * @return a list of crafting patterns in this network, do NOT modify this list
*/ */
@@ -101,6 +119,15 @@ public interface ICraftingManager {
@Nullable @Nullable
ICraftingPattern getPattern(ItemStack pattern); ICraftingPattern getPattern(ItemStack pattern);
/**
* Return a crafting pattern from a fluid stack.
*
* @param pattern the stack to get a pattern for
* @return the crafting pattern, or null if none is found
*/
@Nullable
ICraftingPattern getPattern(FluidStack pattern);
/** /**
* Updates the tasks in this manager. * Updates the tasks in this manager.
*/ */

View File

@@ -2,6 +2,7 @@ package com.raoulvdberge.refinedstorage.api.autocrafting;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.util.NonNullList; import net.minecraft.util.NonNullList;
import net.minecraftforge.fluids.FluidStack;
import java.util.List; import java.util.List;
@@ -61,6 +62,10 @@ public interface ICraftingPattern {
*/ */
NonNullList<ItemStack> getByproducts(NonNullList<ItemStack> took); NonNullList<ItemStack> getByproducts(NonNullList<ItemStack> took);
NonNullList<FluidStack> getFluidInputs();
NonNullList<FluidStack> getFluidOutputs();
/** /**
* @return the id of the factory that creates a crafting task for this pattern, as defined in the {@link com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskRegistry} * @return the id of the factory that creates a crafting task for this pattern, as defined in the {@link com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskRegistry}
*/ */

View File

@@ -3,6 +3,7 @@ package com.raoulvdberge.refinedstorage.api.autocrafting;
import net.minecraft.tileentity.TileEntity; import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.EnumFacing; import net.minecraft.util.EnumFacing;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import net.minecraftforge.fluids.capability.IFluidHandler;
import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.IItemHandler;
import net.minecraftforge.items.IItemHandlerModifiable; import net.minecraftforge.items.IItemHandlerModifiable;
@@ -25,6 +26,9 @@ public interface ICraftingPatternContainer {
@Nullable @Nullable
IItemHandler getConnectedInventory(); IItemHandler getConnectedInventory();
@Nullable
IFluidHandler getConnectedFluidInventory();
/** /**
* @return the tile that this container is connected to, or null if no tile is present * @return the tile that this container is connected to, or null if no tile is present
*/ */

View File

@@ -2,9 +2,9 @@ package com.raoulvdberge.refinedstorage.api.autocrafting.registry;
import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern; import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException; import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask; import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagCompound;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@@ -18,13 +18,13 @@ public interface ICraftingTaskFactory {
* Returns a crafting task for a given pattern. * Returns a crafting task for a given pattern.
* *
* @param network the network * @param network the network
* @param stack the stack to create a task for * @param requested the request info
* @param pattern the pattern * @param pattern the pattern
* @param quantity the quantity * @param quantity the quantity
* @return the crafting task * @return the crafting task
*/ */
@Nonnull @Nonnull
ICraftingTask create(INetwork network, ItemStack stack, int quantity, ICraftingPattern pattern); ICraftingTask create(INetwork network, ICraftingRequestInfo requested, int quantity, ICraftingPattern pattern);
/** /**
* Returns a crafting task for a given NBT tag. * Returns a crafting task for a given NBT tag.

View File

@@ -0,0 +1,29 @@
package com.raoulvdberge.refinedstorage.api.autocrafting.task;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraftforge.fluids.FluidStack;
import javax.annotation.Nullable;
/**
* Contains information about a crafting request.
*/
public interface ICraftingRequestInfo {
/**
* @return the item requested, or null if no item was requested
*/
@Nullable
ItemStack getItem();
/**
* @return the fluid requested, or null if no fluid was requested
*/
@Nullable
FluidStack getFluid();
/**
* @return the written tag
*/
NBTTagCompound writeToNbt();
}

View File

@@ -6,6 +6,7 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreview
import com.raoulvdberge.refinedstorage.api.util.IStackList; import com.raoulvdberge.refinedstorage.api.util.IStackList;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagCompound;
import net.minecraftforge.fluids.FluidStack;
import javax.annotation.Nullable; import javax.annotation.Nullable;
import java.util.List; import java.util.List;
@@ -44,7 +45,7 @@ public interface ICraftingTask {
/** /**
* @return the stack requested * @return the stack requested
*/ */
ItemStack getRequested(); ICraftingRequestInfo getRequested();
/** /**
* Called when a stack is inserted into the system through {@link com.raoulvdberge.refinedstorage.api.network.INetwork#insertItemTracked(ItemStack, int)}. * Called when a stack is inserted into the system through {@link com.raoulvdberge.refinedstorage.api.network.INetwork#insertItemTracked(ItemStack, int)}.
@@ -52,7 +53,15 @@ public interface ICraftingTask {
* @param stack the stack * @param stack the stack
* @return the size remaining, decremented by the crafting task when it was relevant to it * @return the size remaining, decremented by the crafting task when it was relevant to it
*/ */
int onTrackedItemInserted(ItemStack stack, int size); int onTrackedInsert(ItemStack stack, int size);
/**
* Called when a stack is inserted into the system through {@link com.raoulvdberge.refinedstorage.api.network.INetwork#insertFluidTracked(FluidStack, int)}.
*
* @param stack the stack
* @return the size remaining, decremented by the crafting task when it was relevant to it
*/
int onTrackedInsert(FluidStack stack, int size);
/** /**
* Writes this task to NBT. * Writes this task to NBT.

View File

@@ -167,6 +167,16 @@ public interface INetwork {
@Nullable @Nullable
FluidStack insertFluid(@Nonnull FluidStack stack, int size, Action action); FluidStack insertFluid(@Nonnull FluidStack stack, int size, Action action);
default FluidStack insertFluidTracked(@Nonnull FluidStack stack, int size) {
FluidStack remainder = insertFluid(stack, size, Action.PERFORM);
int inserted = remainder == null ? size : (size - remainder.amount);
getCraftingManager().track(stack, inserted);
return remainder;
}
/** /**
* Extracts a fluid from this network. * Extracts a fluid from this network.
* *

View File

@@ -47,7 +47,7 @@ public interface IGrid {
/** /**
* @return the grid type * @return the grid type
*/ */
GridType getType(); GridType getGridType();
/** /**
* @param player the player to create a listener for * @param player the player to create a listener for

View File

@@ -1,8 +1,10 @@
package com.raoulvdberge.refinedstorage.api.network.grid; package com.raoulvdberge.refinedstorage.api.network.grid;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawer;
import com.raoulvdberge.refinedstorage.api.util.IFilter; import com.raoulvdberge.refinedstorage.api.util.IFilter;
import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.gui.FontRenderer;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraftforge.fluids.FluidStack;
import java.util.List; import java.util.List;
@@ -30,7 +32,10 @@ public interface IGridTab {
void drawTooltip(int x, int y, int screenWidth, int screenHeight, FontRenderer fontRenderer); void drawTooltip(int x, int y, int screenWidth, int screenHeight, FontRenderer fontRenderer);
/** /**
* @return the icon * Draws the icon.
*
* @param x the x position
* @param y the y position
*/ */
ItemStack getIcon(); void drawIcon(int x, int y, IElementDrawer<ItemStack> itemDrawer, IElementDrawer<FluidStack> fluidDrawer);
} }

View File

@@ -45,4 +45,24 @@ public interface IFluidGridHandler {
* @return the remainder container * @return the remainder container
*/ */
ItemStack onShiftClick(EntityPlayerMP player, ItemStack container); ItemStack onShiftClick(EntityPlayerMP player, ItemStack container);
/**
* Called when a player requests the crafting preview window to be opened.
*
* @param player the player
* @param hash the item stack hash
* @param quantity the amount of that item that we need a preview for
* @param noPreview true if the crafting preview window shouldn't be shown, false otherwise
*/
void onCraftingPreviewRequested(EntityPlayerMP player, int hash, int quantity, boolean noPreview);
/**
* Called when a player requested crafting for an item.
*
* @param player the player that is requesting the crafting
* @param hash the hash of the item to request a craft for
* @param quantity the amount of the item that has to be crafted
*/
void onCraftingRequested(EntityPlayerMP player, int hash, int quantity);
} }

View File

@@ -24,4 +24,20 @@ public interface IQuantityFormatter {
* @return the formatted quantity * @return the formatted quantity
*/ */
String format(int qty); String format(int qty);
/**
* Divides quantity by 1000 and appends "B".
*
* @param qty the quantity
* @return the formatted quantity
*/
String formatInBucketForm(int qty);
/**
* Used in Fluid Grid.
*
* @param qty the quantity
* @return the formatted quantity
*/
String formatInBucketFormWithOnlyTrailingDigitsIfZero(int qty);
} }

View File

@@ -9,6 +9,8 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftin
import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElementRegistry; import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElementRegistry;
import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElementRegistry; import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElementRegistry;
import com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskRegistry; import com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskRegistry;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.network.grid.wireless.IWirelessGridRegistry; import com.raoulvdberge.refinedstorage.api.network.grid.wireless.IWirelessGridRegistry;
import com.raoulvdberge.refinedstorage.api.network.node.INetworkNode; import com.raoulvdberge.refinedstorage.api.network.node.INetworkNode;
@@ -27,6 +29,7 @@ import com.raoulvdberge.refinedstorage.api.util.IComparer;
import com.raoulvdberge.refinedstorage.api.util.IOneSixMigrationHelper; import com.raoulvdberge.refinedstorage.api.util.IOneSixMigrationHelper;
import com.raoulvdberge.refinedstorage.api.util.IQuantityFormatter; import com.raoulvdberge.refinedstorage.api.util.IQuantityFormatter;
import com.raoulvdberge.refinedstorage.api.util.IStackList; import com.raoulvdberge.refinedstorage.api.util.IStackList;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.CraftingRequestInfo;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementList; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementList;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementRegistry; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementRegistry;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview.CraftingPreviewElementRegistry; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview.CraftingPreviewElementRegistry;
@@ -246,6 +249,21 @@ public class API implements IRSAPI {
return new StorageDiskFluid(world, capacity); return new StorageDiskFluid(world, capacity);
} }
@Override
public ICraftingRequestInfo createCraftingRequestInfo(ItemStack stack) {
return new CraftingRequestInfo(stack);
}
@Override
public ICraftingRequestInfo createCraftingRequestInfo(FluidStack stack) {
return new CraftingRequestInfo(stack);
}
@Override
public ICraftingRequestInfo createCraftingRequestInfo(NBTTagCompound tag) throws CraftingTaskReadException {
return new CraftingRequestInfo(tag);
}
@Override @Override
@Nonnull @Nonnull
public IOneSixMigrationHelper getOneSixMigrationHelper() { public IOneSixMigrationHelper getOneSixMigrationHelper() {

View File

@@ -10,12 +10,14 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadExc
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask; import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTaskError; import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTaskError;
import com.raoulvdberge.refinedstorage.api.network.node.INetworkNode; import com.raoulvdberge.refinedstorage.api.network.node.INetworkNode;
import com.raoulvdberge.refinedstorage.api.util.IComparer;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.tile.TileController; import com.raoulvdberge.refinedstorage.tile.TileController;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList; import net.minecraft.nbt.NBTTagList;
import net.minecraftforge.common.util.Constants; import net.minecraftforge.common.util.Constants;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.items.IItemHandlerModifiable; import net.minecraftforge.items.IItemHandlerModifiable;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@@ -91,7 +93,23 @@ public class CraftingManager implements ICraftingManager {
return null; return null;
} }
return factory.create(network, stack, quantity, pattern); return factory.create(network, API.instance().createCraftingRequestInfo(stack), quantity, pattern);
}
@Nullable
@Override
public ICraftingTask create(FluidStack stack, int quantity) {
ICraftingPattern pattern = getPattern(stack);
if (pattern == null) {
return null;
}
ICraftingTaskFactory factory = API.instance().getCraftingTaskRegistry().get(pattern.getId());
if (factory == null) {
return null;
}
return factory.create(network, API.instance().createCraftingRequestInfo(stack), quantity, pattern);
} }
@Override @Override
@@ -200,14 +218,17 @@ public class CraftingManager implements ICraftingManager {
listeners.forEach(ICraftingMonitorListener::onChanged); listeners.forEach(ICraftingMonitorListener::onChanged);
} }
//TODO: Make fluid version
@Override @Override
@Nullable @Nullable
public ICraftingTask request(ItemStack stack, int amount) { public ICraftingTask request(ItemStack stack, int amount) {
for (ICraftingTask task : getTasks()) { for (ICraftingTask task : getTasks()) {
if (API.instance().getComparer().isEqualNoQuantity(task.getRequested(), stack)) { if (task.getRequested().getItem() != null) {
if (API.instance().getComparer().isEqualNoQuantity(task.getRequested().getItem(), stack)) {
amount -= task.getQuantity(); amount -= task.getQuantity();
} }
} }
}
if (amount > 0) { if (amount > 0) {
ICraftingTask task = create(stack, amount); ICraftingTask task = create(stack, amount);
@@ -231,7 +252,24 @@ public class CraftingManager implements ICraftingManager {
int initialSize = size; int initialSize = size;
for (ICraftingTask task : tasks.values()) { for (ICraftingTask task : tasks.values()) {
size = task.onTrackedItemInserted(stack, size); size = task.onTrackedInsert(stack, size);
if (size == 0) {
break;
}
}
if (size != initialSize) {
this.onTaskChanged();
}
}
@Override
public void track(FluidStack stack, int size) {
int initialSize = size;
for (ICraftingTask task : tasks.values()) {
size = task.onTrackedInsert(stack, size);
if (size == 0) { if (size == 0) {
break; break;
@@ -286,4 +324,18 @@ public class CraftingManager implements ICraftingManager {
return null; return null;
} }
@Nullable
@Override
public ICraftingPattern getPattern(FluidStack pattern) {
for (ICraftingPattern patternInList : patterns) {
for (FluidStack output : patternInList.getFluidOutputs()) {
if (API.instance().getComparer().isEqual(output, pattern, IComparer.COMPARE_NBT)) {
return patternInList;
}
}
}
return null;
}
} }

View File

@@ -2,6 +2,7 @@ package com.raoulvdberge.refinedstorage.apiimpl.autocrafting;
import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern; import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPatternContainer; import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPatternContainer;
import com.raoulvdberge.refinedstorage.api.util.IComparer;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.registry.CraftingTaskFactory; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.registry.CraftingTaskFactory;
import com.raoulvdberge.refinedstorage.apiimpl.util.OneSixMigrationHelper; import com.raoulvdberge.refinedstorage.apiimpl.util.OneSixMigrationHelper;
@@ -15,6 +16,7 @@ import net.minecraft.item.crafting.CraftingManager;
import net.minecraft.item.crafting.IRecipe; import net.minecraft.item.crafting.IRecipe;
import net.minecraft.util.NonNullList; import net.minecraft.util.NonNullList;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.oredict.OreDictionary; import net.minecraftforge.oredict.OreDictionary;
import java.util.ArrayList; import java.util.ArrayList;
@@ -30,6 +32,8 @@ public class CraftingPattern implements ICraftingPattern {
private List<NonNullList<ItemStack>> inputs = new ArrayList<>(); private List<NonNullList<ItemStack>> inputs = new ArrayList<>();
private NonNullList<ItemStack> outputs = NonNullList.create(); private NonNullList<ItemStack> outputs = NonNullList.create();
private NonNullList<ItemStack> byproducts = NonNullList.create(); private NonNullList<ItemStack> byproducts = NonNullList.create();
private NonNullList<FluidStack> fluidInputs = NonNullList.create();
private NonNullList<FluidStack> fluidOutputs = NonNullList.create();
public CraftingPattern(World world, ICraftingPatternContainer container, ItemStack stack) { public CraftingPattern(World world, ICraftingPatternContainer container, ItemStack stack) {
if (!OneSixMigrationHelper.isValidOneSixPattern(stack)) { if (!OneSixMigrationHelper.isValidOneSixPattern(stack)) {
@@ -77,6 +81,20 @@ public class CraftingPattern implements ICraftingPattern {
outputs.add(output); outputs.add(output);
} }
FluidStack fluidInput = ItemPattern.getFluidInputSlot(stack, i);
if (fluidInput != null) {
this.valid = true;
fluidInputs.add(fluidInput);
}
FluidStack fluidOutput = ItemPattern.getFluidOutputSlot(stack, i);
if (fluidOutput != null) {
this.valid = true;
fluidOutputs.add(fluidOutput);
}
} }
} else { } else {
InventoryCrafting inv = new InventoryCraftingDummy(); InventoryCrafting inv = new InventoryCraftingDummy();
@@ -218,6 +236,16 @@ public class CraftingPattern implements ICraftingPattern {
return sanitized; return sanitized;
} }
@Override
public NonNullList<FluidStack> getFluidInputs() {
return fluidInputs;
}
@Override
public NonNullList<FluidStack> getFluidOutputs() {
return fluidOutputs;
}
@Override @Override
public String getId() { public String getId() {
return CraftingTaskFactory.ID; return CraftingTaskFactory.ID;
@@ -229,7 +257,10 @@ public class CraftingPattern implements ICraftingPattern {
return false; return false;
} }
if ((other.getInputs().size() != inputs.size()) || (other.getOutputs().size() != outputs.size())) { if ((other.getInputs().size() != inputs.size()) ||
(other.getFluidInputs().size() != fluidInputs.size()) ||
(other.getOutputs().size() != outputs.size()) ||
(other.getFluidOutputs().size() != fluidOutputs.size())) {
return false; return false;
} }
@@ -252,12 +283,24 @@ public class CraftingPattern implements ICraftingPattern {
} }
} }
for (int i = 0; i < fluidInputs.size(); ++i) {
if (!API.instance().getComparer().isEqual(fluidInputs.get(i), other.getFluidInputs().get(i), IComparer.COMPARE_NBT | IComparer.COMPARE_QUANTITY)) {
return false;
}
}
for (int i = 0; i < outputs.size(); ++i) { for (int i = 0; i < outputs.size(); ++i) {
if (!API.instance().getComparer().isEqual(outputs.get(i), other.getOutputs().get(i))) { if (!API.instance().getComparer().isEqual(outputs.get(i), other.getOutputs().get(i))) {
return false; return false;
} }
} }
for (int i = 0; i < fluidOutputs.size(); ++i) {
if (!API.instance().getComparer().isEqual(fluidOutputs.get(i), other.getFluidOutputs().get(i), IComparer.COMPARE_NBT | IComparer.COMPARE_QUANTITY)) {
return false;
}
}
if (!processing) { if (!processing) {
for (int i = 0; i < byproducts.size(); ++i) { for (int i = 0; i < byproducts.size(); ++i) {
if (!API.instance().getComparer().isEqual(byproducts.get(i), other.getByproducts().get(i))) { if (!API.instance().getComparer().isEqual(byproducts.get(i), other.getByproducts().get(i))) {
@@ -282,10 +325,18 @@ public class CraftingPattern implements ICraftingPattern {
} }
} }
for (FluidStack input : this.fluidInputs) {
result = 31 * result + API.instance().getFluidStackHashCode(input);
}
for (ItemStack output : this.outputs) { for (ItemStack output : this.outputs) {
result = 31 * result + API.instance().getItemStackHashCode(output); result = 31 * result + API.instance().getItemStackHashCode(output);
} }
for (FluidStack output : this.fluidOutputs) {
result = 31 * result + API.instance().getFluidStackHashCode(output);
}
for (ItemStack byproduct : this.byproducts) { for (ItemStack byproduct : this.byproducts) {
result = 31 * result + API.instance().getItemStackHashCode(byproduct); result = 31 * result + API.instance().getItemStackHashCode(byproduct);
} }

View File

@@ -0,0 +1,69 @@
package com.raoulvdberge.refinedstorage.apiimpl.autocrafting;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.util.StackUtils;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraftforge.fluids.FluidStack;
import javax.annotation.Nullable;
public class CraftingRequestInfo implements ICraftingRequestInfo {
private static final String NBT_FLUID = "Fluid";
private static final String NBT_STACK = "Stack";
private ItemStack item;
private FluidStack fluid;
public CraftingRequestInfo(NBTTagCompound tag) throws CraftingTaskReadException {
if (!tag.getBoolean(NBT_FLUID)) {
item = StackUtils.deserializeStackFromNbt(tag.getCompoundTag(NBT_STACK));
if (item.isEmpty()) {
throw new CraftingTaskReadException("Extractor stack is empty");
}
} else {
fluid = FluidStack.loadFluidStackFromNBT(tag.getCompoundTag(NBT_STACK));
if (fluid == null) {
throw new CraftingTaskReadException("Extractor fluid stack is emty");
}
}
}
public CraftingRequestInfo(ItemStack item) {
this.item = item;
}
public CraftingRequestInfo(FluidStack fluid) {
this.fluid = fluid;
}
@Nullable
@Override
public ItemStack getItem() {
return item;
}
@Nullable
@Override
public FluidStack getFluid() {
return fluid;
}
@Override
public NBTTagCompound writeToNbt() {
NBTTagCompound tag = new NBTTagCompound();
tag.setBoolean(NBT_FLUID, fluid != null);
if (fluid != null) {
tag.setTag(NBT_STACK, fluid.writeToNBT(new NBTTagCompound()));
} else {
tag.setTag(NBT_STACK, StackUtils.serializeStackToNbt(item));
}
return tag;
}
}

View File

@@ -15,10 +15,12 @@ public class CraftingMonitorElementFluidRender implements ICraftingMonitorElemen
public static final String ID = "fluid_render"; public static final String ID = "fluid_render";
private FluidStack stack; private FluidStack stack;
private int quantity;
private int offset; private int offset;
public CraftingMonitorElementFluidRender(FluidStack stack, int offset) { public CraftingMonitorElementFluidRender(FluidStack stack, int quantity, int offset) {
this.stack = stack; this.stack = stack;
this.quantity = quantity;
this.offset = offset; this.offset = offset;
} }
@@ -36,7 +38,7 @@ public class CraftingMonitorElementFluidRender implements ICraftingMonitorElemen
GlStateManager.pushMatrix(); GlStateManager.pushMatrix();
GlStateManager.scale(scale, scale, 1); GlStateManager.scale(scale, scale, 1);
drawers.getStringDrawer().draw(RenderUtils.getOffsetOnScale(x + 21 + offset, scale), RenderUtils.getOffsetOnScale(y + 7, scale), API.instance().getQuantityFormatter().format(stack.amount) + " mB " + stack.getLocalizedName()); drawers.getStringDrawer().draw(RenderUtils.getOffsetOnScale(x + 21 + offset, scale), RenderUtils.getOffsetOnScale(y + 7, scale), API.instance().getQuantityFormatter().formatInBucketForm(quantity) + " " + stack.getLocalizedName());
GlStateManager.popMatrix(); GlStateManager.popMatrix();
} }
@@ -49,13 +51,14 @@ public class CraftingMonitorElementFluidRender implements ICraftingMonitorElemen
@Override @Override
public void write(ByteBuf buf) { public void write(ByteBuf buf) {
StackUtils.writeFluidStack(buf, stack); StackUtils.writeFluidStack(buf, stack);
buf.writeInt(quantity);
buf.writeInt(offset); buf.writeInt(offset);
} }
@Override @Override
public boolean merge(ICraftingMonitorElement element) { public boolean merge(ICraftingMonitorElement element) {
if (element.getId().equals(getId()) && elementHashCode() == element.elementHashCode()) { if (element.getId().equals(getId()) && elementHashCode() == element.elementHashCode()) {
this.stack.amount += ((CraftingMonitorElementFluidRender) element).stack.amount; this.quantity += ((CraftingMonitorElementFluidRender) element).quantity;
return true; return true;
} }

View File

@@ -2,6 +2,7 @@ package com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview;
import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElement; import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElement;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawers; import com.raoulvdberge.refinedstorage.api.render.IElementDrawers;
import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.gui.GuiBase; import com.raoulvdberge.refinedstorage.gui.GuiBase;
import com.raoulvdberge.refinedstorage.util.RenderUtils; import com.raoulvdberge.refinedstorage.util.RenderUtils;
import io.netty.buffer.ByteBuf; import io.netty.buffer.ByteBuf;
@@ -25,7 +26,6 @@ public class CraftingPreviewElementFluidStack implements ICraftingPreviewElement
public CraftingPreviewElementFluidStack(FluidStack stack) { public CraftingPreviewElementFluidStack(FluidStack stack) {
this.stack = stack.copy(); this.stack = stack.copy();
this.available = stack.amount;
} }
public CraftingPreviewElementFluidStack(FluidStack stack, int available, boolean missing, int toCraft) { public CraftingPreviewElementFluidStack(FluidStack stack, int available, boolean missing, int toCraft) {
@@ -73,11 +73,21 @@ public class CraftingPreviewElementFluidStack implements ICraftingPreviewElement
float scale = drawers.getFontRenderer().getUnicodeFlag() ? 1F : 0.5F; float scale = drawers.getFontRenderer().getUnicodeFlag() ? 1F : 0.5F;
y += 2;
GlStateManager.pushMatrix(); GlStateManager.pushMatrix();
GlStateManager.scale(scale, scale, 1); GlStateManager.scale(scale, scale, 1);
drawers.getStringDrawer().draw(RenderUtils.getOffsetOnScale(x + 23, scale), RenderUtils.getOffsetOnScale(y + 3, scale), GuiBase.t("gui.refinedstorage:crafting_preview.available", "")); if (getToCraft() > 0) {
drawers.getStringDrawer().draw(RenderUtils.getOffsetOnScale(x + 23, scale), RenderUtils.getOffsetOnScale(y + 9, scale), getAvailable() + " mB"); String format = hasMissing() ? "gui.refinedstorage:crafting_preview.missing" : "gui.refinedstorage:crafting_preview.to_craft";
drawers.getStringDrawer().draw(RenderUtils.getOffsetOnScale(x + 23, scale), RenderUtils.getOffsetOnScale(y, scale), GuiBase.t(format, API.instance().getQuantityFormatter().formatInBucketForm(getToCraft())));
y += 7;
}
if (getAvailable() > 0) {
drawers.getStringDrawer().draw(RenderUtils.getOffsetOnScale(x + 23, scale), RenderUtils.getOffsetOnScale(y, scale), GuiBase.t("gui.refinedstorage:crafting_preview.available", API.instance().getQuantityFormatter().formatInBucketForm(getAvailable())));
}
GlStateManager.popMatrix(); GlStateManager.popMatrix();
} }

View File

@@ -3,10 +3,10 @@ package com.raoulvdberge.refinedstorage.apiimpl.autocrafting.registry;
import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern; import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
import com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskFactory; import com.raoulvdberge.refinedstorage.api.autocrafting.registry.ICraftingTaskFactory;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException; import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask; import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.CraftingTask; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.CraftingTask;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagCompound;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@@ -16,8 +16,8 @@ public class CraftingTaskFactory implements ICraftingTaskFactory {
@Nonnull @Nonnull
@Override @Override
public ICraftingTask create(INetwork network, ItemStack stack, int quantity, ICraftingPattern pattern) { public ICraftingTask create(INetwork network, ICraftingRequestInfo requested, int quantity, ICraftingPattern pattern) {
return new CraftingTask(network, stack, quantity, pattern); return new CraftingTask(network, requested, quantity, pattern);
} }
@Override @Override

View File

@@ -4,21 +4,21 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.*;
import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElement; import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElement;
import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElementList; import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElementList;
import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElement; import com.raoulvdberge.refinedstorage.api.autocrafting.preview.ICraftingPreviewElement;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskErrorType; import com.raoulvdberge.refinedstorage.api.autocrafting.task.*;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTaskError;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.network.node.INetworkNode; import com.raoulvdberge.refinedstorage.api.network.node.INetworkNode;
import com.raoulvdberge.refinedstorage.api.util.IComparer; import com.raoulvdberge.refinedstorage.api.util.IComparer;
import com.raoulvdberge.refinedstorage.api.util.IStackList; import com.raoulvdberge.refinedstorage.api.util.IStackList;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementColor; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementColor;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementFluidRender;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementItemRender; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementItemRender;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementText; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.craftingmonitor.CraftingMonitorElementText;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview.CraftingPreviewElementFluidStack;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview.CraftingPreviewElementItemStack; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview.CraftingPreviewElementItemStack;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractor; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractor;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractorItemStatus; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractorStack;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractorStatus;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserter; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserter;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserterItem; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserterItem;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserterItemStatus; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserterItemStatus;
@@ -33,6 +33,7 @@ import net.minecraft.util.NonNullList;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.common.util.Constants; import net.minecraftforge.common.util.Constants;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.items.ItemHandlerHelper; import net.minecraftforge.items.ItemHandlerHelper;
import org.apache.commons.lang3.tuple.Pair; import org.apache.commons.lang3.tuple.Pair;
@@ -56,7 +57,7 @@ public class CraftingTask implements ICraftingTask {
private static final String NBT_PATTERN_CONTAINER_POS = "ContainerPos"; private static final String NBT_PATTERN_CONTAINER_POS = "ContainerPos";
private INetwork network; private INetwork network;
private ItemStack requested; private ICraftingRequestInfo requested;
private int quantity; private int quantity;
private ICraftingPattern pattern; private ICraftingPattern pattern;
private List<CraftingStep> steps = new LinkedList<>(); private List<CraftingStep> steps = new LinkedList<>();
@@ -68,10 +69,15 @@ public class CraftingTask implements ICraftingTask {
private UUID id = UUID.randomUUID(); private UUID id = UUID.randomUUID();
private IStackList<ItemStack> toTake = API.instance().createItemStackList(); private IStackList<ItemStack> toTake = API.instance().createItemStackList();
private IStackList<ItemStack> missing = API.instance().createItemStackList(); private IStackList<FluidStack> toTakeFluids = API.instance().createFluidStackList();
private IStackList<ItemStack> toCraft = API.instance().createItemStackList();
public CraftingTask(INetwork network, ItemStack requested, int quantity, ICraftingPattern pattern) { private IStackList<ItemStack> missing = API.instance().createItemStackList();
private IStackList<FluidStack> missingFluids = API.instance().createFluidStackList();
private IStackList<ItemStack> toCraft = API.instance().createItemStackList();
private IStackList<FluidStack> toCraftFluids = API.instance().createFluidStackList();
public CraftingTask(INetwork network, ICraftingRequestInfo requested, int quantity, ICraftingPattern pattern) {
this.network = network; this.network = network;
this.inserter = new CraftingInserter(network); this.inserter = new CraftingInserter(network);
this.requested = requested; this.requested = requested;
@@ -82,11 +88,7 @@ public class CraftingTask implements ICraftingTask {
public CraftingTask(INetwork network, NBTTagCompound tag) throws CraftingTaskReadException { public CraftingTask(INetwork network, NBTTagCompound tag) throws CraftingTaskReadException {
this.network = network; this.network = network;
this.requested = new ItemStack(tag.getCompoundTag(NBT_REQUESTED)); this.requested = API.instance().createCraftingRequestInfo(tag.getCompoundTag(NBT_REQUESTED));
if (requested.isEmpty()) {
throw new CraftingTaskReadException("Requested item doesn't exist anymore");
}
this.quantity = tag.getInteger(NBT_QUANTITY); this.quantity = tag.getInteger(NBT_QUANTITY);
this.pattern = readPatternFromNbt(tag.getCompoundTag(NBT_PATTERN), network.world()); this.pattern = readPatternFromNbt(tag.getCompoundTag(NBT_PATTERN), network.world());
this.inserter = new CraftingInserter(network, tag.getTagList(NBT_INSERTER, Constants.NBT.TAG_COMPOUND)); this.inserter = new CraftingInserter(network, tag.getTagList(NBT_INSERTER, Constants.NBT.TAG_COMPOUND));
@@ -134,7 +136,10 @@ public class CraftingTask implements ICraftingTask {
int crafted = 0; int crafted = 0;
IStackList<ItemStack> results = API.instance().createItemStackList(); IStackList<ItemStack> results = API.instance().createItemStackList();
IStackList<FluidStack> fluidResults = API.instance().createFluidStackList();
IStackList<ItemStack> storage = network.getItemStorageCache().getList().copy(); IStackList<ItemStack> storage = network.getItemStorageCache().getList().copy();
IStackList<FluidStack> fluidStorage = network.getFluidStorageCache().getList().copy();
// Items that are being handled in other tasks aren't available to us. // Items that are being handled in other tasks aren't available to us.
for (ICraftingTask task : network.getCraftingManager().getTasks()) { for (ICraftingTask task : network.getCraftingManager().getTasks()) {
@@ -149,8 +154,20 @@ public class CraftingTask implements ICraftingTask {
} }
if (extractor != null) { if (extractor != null) {
for (ItemStack inUse : extractor.getItems()) { for (CraftingExtractorStack inUse : extractor.getStacks()) {
storage.remove(inUse); ItemStack inUseItem = inUse.getItem();
if (inUseItem != null) {
storage.remove(inUseItem);
} else {
FluidStack inUseFluid = inUse.getFluid();
if (inUseFluid != null) {
fluidStorage.remove(inUseFluid);
} else {
throw new IllegalStateException("Extractor stack is neither a fluid or an item!");
}
}
} }
} }
} }
@@ -162,7 +179,7 @@ public class CraftingTask implements ICraftingTask {
ICraftingPatternChain patternChain = patternChainList.getChain(pattern); ICraftingPatternChain patternChain = patternChainList.getChain(pattern);
while (qty > 0) { while (qty > 0) {
Pair<CraftingStep, ICraftingTaskError> result = calculateInternal(storage, results, patternChainList, patternChain.current()); Pair<CraftingStep, ICraftingTaskError> result = calculateInternal(storage, fluidStorage, results, fluidResults, patternChainList, patternChain.current());
if (result.getRight() != null) { if (result.getRight() != null) {
return result.getRight(); return result.getRight();
@@ -177,12 +194,23 @@ public class CraftingTask implements ICraftingTask {
patternChain.cycle(); patternChain.cycle();
} }
this.toCraft.add(requested, crafted); if (requested.getItem() != null) {
this.toCraft.add(requested.getItem(), crafted);
} else {
this.toCraftFluids.add(requested.getFluid(), crafted);
}
return null; return null;
} }
private Pair<CraftingStep, ICraftingTaskError> calculateInternal(IStackList<ItemStack> mutatedStorage, IStackList<ItemStack> results, ICraftingPatternChainList patternChainList, ICraftingPattern pattern) { private Pair<CraftingStep, ICraftingTaskError> calculateInternal(
IStackList<ItemStack> mutatedStorage,
IStackList<FluidStack> mutatedFluidStorage,
IStackList<ItemStack> results,
IStackList<FluidStack> fluidResults,
ICraftingPatternChainList patternChainList,
ICraftingPattern pattern) {
if (System.currentTimeMillis() - calculationStarted > CALCULATION_TIMEOUT_MS) { if (System.currentTimeMillis() - calculationStarted > CALCULATION_TIMEOUT_MS) {
return Pair.of(null, new CraftingTaskError(CraftingTaskErrorType.TOO_COMPLEX)); return Pair.of(null, new CraftingTaskError(CraftingTaskErrorType.TOO_COMPLEX));
} }
@@ -192,6 +220,7 @@ public class CraftingTask implements ICraftingTask {
} }
IStackList<ItemStack> itemsToExtract = API.instance().createItemStackList(); IStackList<ItemStack> itemsToExtract = API.instance().createItemStackList();
IStackList<FluidStack> fluidsToExtract = API.instance().createFluidStackList();
NonNullList<ItemStack> took = NonNullList.create(); NonNullList<ItemStack> took = NonNullList.create();
@@ -270,7 +299,7 @@ public class CraftingTask implements ICraftingTask {
ICraftingPatternChain subPatternChain = patternChainList.getChain(subPattern); ICraftingPatternChain subPatternChain = patternChainList.getChain(subPattern);
while ((fromSelf == null ? 0 : fromSelf.getCount()) < remaining) { while ((fromSelf == null ? 0 : fromSelf.getCount()) < remaining) {
Pair<CraftingStep, ICraftingTaskError> result = calculateInternal(mutatedStorage, results, patternChainList, subPatternChain.current()); Pair<CraftingStep, ICraftingTaskError> result = calculateInternal(mutatedStorage, mutatedFluidStorage, results, fluidResults, patternChainList, subPatternChain.current());
if (result.getRight() != null) { if (result.getRight() != null) {
return Pair.of(null, result.getRight()); return Pair.of(null, result.getRight());
@@ -301,6 +330,73 @@ public class CraftingTask implements ICraftingTask {
} }
} }
for (FluidStack input : pattern.getFluidInputs()) {
FluidStack fromSelf = fluidResults.get(input, IComparer.COMPARE_NBT);
FluidStack fromNetwork = mutatedFluidStorage.get(input, IComparer.COMPARE_NBT);
int remaining = input.amount;
while (remaining > 0) {
if (fromSelf != null) {
int toTake = Math.min(remaining, fromSelf.amount);
fluidsToExtract.add(input, toTake);
fluidResults.remove(input, toTake);
remaining -= toTake;
fromSelf = fluidResults.get(input, IComparer.COMPARE_NBT);
} else if (fromNetwork != null) {
int toTake = Math.min(remaining, fromNetwork.amount);
this.toTakeFluids.add(input, toTake);
fluidsToExtract.add(input, toTake);
mutatedFluidStorage.remove(fromNetwork, toTake);
remaining -= toTake;
fromNetwork = mutatedFluidStorage.get(input, IComparer.COMPARE_NBT);
} else {
ICraftingPattern subPattern = network.getCraftingManager().getPattern(input);
if (subPattern != null) {
ICraftingPatternChain subPatternChain = patternChainList.getChain(subPattern);
while ((fromSelf == null ? 0 : fromSelf.amount) < remaining) {
Pair<CraftingStep, ICraftingTaskError> result = calculateInternal(mutatedStorage, mutatedFluidStorage, results, fluidResults, patternChainList, subPatternChain.current());
if (result.getRight() != null) {
return Pair.of(null, result.getRight());
}
this.steps.add(result.getLeft());
fromSelf = fluidResults.get(input, IComparer.COMPARE_NBT);
if (fromSelf == null) {
throw new IllegalStateException("Recursive fluid calculation didn't yield anything");
}
fromNetwork = mutatedFluidStorage.get(input, IComparer.COMPARE_NBT);
subPatternChain.cycle();
}
// fromSelf contains the amount crafted after the loop.
this.toCraftFluids.add(input, fromSelf.amount);
} else {
this.missingFluids.add(input, remaining);
fluidsToExtract.add(input, remaining);
remaining = 0;
}
}
}
}
patternsUsed.remove(pattern); patternsUsed.remove(pattern);
if (pattern.isProcessing()) { if (pattern.isProcessing()) {
@@ -308,8 +404,16 @@ public class CraftingTask implements ICraftingTask {
results.add(output); results.add(output);
} }
return Pair.of(new CraftingStepProcess(pattern, network, new ArrayList<>(itemsToExtract.getStacks())), null); for (FluidStack output : pattern.getFluidOutputs()) {
fluidResults.add(output);
}
return Pair.of(new CraftingStepProcess(pattern, network, new ArrayList<>(itemsToExtract.getStacks()), new ArrayList<>(fluidsToExtract.getStacks())), null);
} else { } else {
if (!fluidsToExtract.isEmpty()) {
throw new IllegalStateException("Cannot extract fluids in normal pattern!");
}
results.add(pattern.getOutput(took)); results.add(pattern.getOutput(took));
for (ItemStack byproduct : pattern.getByproducts(took)) { for (ItemStack byproduct : pattern.getByproducts(took)) {
@@ -320,11 +424,12 @@ public class CraftingTask implements ICraftingTask {
} }
} }
private int getQuantityPerCraft(ICraftingPattern pattern, ItemStack requested) { private int getQuantityPerCraft(ICraftingPattern pattern, ICraftingRequestInfo requested) {
int qty = 0; int qty = 0;
if (requested.getItem() != null) {
for (ItemStack output : pattern.getOutputs()) { for (ItemStack output : pattern.getOutputs()) {
if (API.instance().getComparer().isEqualNoQuantity(output, requested)) { if (API.instance().getComparer().isEqualNoQuantity(output, requested.getItem())) {
qty += output.getCount(); qty += output.getCount();
if (!pattern.isProcessing()) { if (!pattern.isProcessing()) {
@@ -332,6 +437,13 @@ public class CraftingTask implements ICraftingTask {
} }
} }
} }
} else {
for (FluidStack output : pattern.getFluidOutputs()) {
if (API.instance().getComparer().isEqual(output, requested.getFluid(), IComparer.COMPARE_NBT)) {
qty += output.amount;
}
}
}
return qty; return qty;
} }
@@ -376,12 +488,12 @@ public class CraftingTask implements ICraftingTask {
} }
@Override @Override
public ItemStack getRequested() { public ICraftingRequestInfo getRequested() {
return requested; return requested;
} }
@Override @Override
public int onTrackedItemInserted(ItemStack stack, int size) { public int onTrackedInsert(ItemStack stack, int size) {
for (CraftingStep step : steps) { for (CraftingStep step : steps) {
if (step instanceof CraftingStepProcess) { if (step instanceof CraftingStepProcess) {
size = ((CraftingStepProcess) step).onTrackedItemInserted(stack, size); size = ((CraftingStepProcess) step).onTrackedItemInserted(stack, size);
@@ -395,13 +507,31 @@ public class CraftingTask implements ICraftingTask {
return size; return size;
} }
@Override
public int onTrackedInsert(FluidStack stack, int size) {
for (CraftingStep step : steps) {
if (step instanceof CraftingStepProcess) {
size = ((CraftingStepProcess) step).onTrackedFluidInserted(stack, size);
if (size == 0) {
break;
}
}
}
return size;
}
// TODO: Fix lang keys.
@Override @Override
public List<ICraftingMonitorElement> getCraftingMonitorElements() { public List<ICraftingMonitorElement> getCraftingMonitorElements() {
ICraftingMonitorElementList elements = API.instance().createCraftingMonitorElementList(); ICraftingMonitorElementList elements = API.instance().createCraftingMonitorElementList();
if (!missing.isEmpty()) { if (!missing.isEmpty() || !missingFluids.isEmpty()) {
elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_missing", 5)); elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_missing", 5));
}
if (!missing.isEmpty()) {
for (ItemStack missing : this.missing.getStacks()) { for (ItemStack missing : this.missing.getStacks()) {
elements.add(new CraftingMonitorElementColor(new CraftingMonitorElementItemRender(missing, missing.getCount(), 0), "", CraftingMonitorElementColor.COLOR_ERROR)); elements.add(new CraftingMonitorElementColor(new CraftingMonitorElementItemRender(missing, missing.getCount(), 0), "", CraftingMonitorElementColor.COLOR_ERROR));
} }
@@ -409,6 +539,14 @@ public class CraftingTask implements ICraftingTask {
elements.commit(); elements.commit();
} }
if (!missingFluids.isEmpty()) {
for (FluidStack missing : this.missingFluids.getStacks()) {
elements.add(new CraftingMonitorElementColor(new CraftingMonitorElementFluidRender(missing, missing.amount, 0), "", CraftingMonitorElementColor.COLOR_ERROR));
}
elements.commit();
}
if (!inserter.getItems().isEmpty()) { if (!inserter.getItems().isEmpty()) {
elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_inserting", 5)); elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_inserting", 5));
@@ -425,20 +563,20 @@ public class CraftingTask implements ICraftingTask {
elements.commit(); elements.commit();
} }
if (steps.stream().anyMatch(s -> s instanceof CraftingStepCraft && !s.isCompleted() && !((CraftingStepCraft) s).getExtractor().getItems().isEmpty())) { if (steps.stream().anyMatch(s -> s instanceof CraftingStepCraft && !s.isCompleted() && !((CraftingStepCraft) s).getExtractor().getStacks().isEmpty())) {
elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_crafting", 5)); elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_crafting", 5));
for (CraftingStep step : steps) { for (CraftingStep step : steps) {
if (step instanceof CraftingStepCraft && !step.isCompleted()) { if (step instanceof CraftingStepCraft && !step.isCompleted()) {
CraftingExtractor extractor = ((CraftingStepCraft) step).getExtractor(); CraftingExtractor extractor = ((CraftingStepCraft) step).getExtractor();
for (int i = 0; i < extractor.getItems().size(); ++i) { for (int i = 0; i < extractor.getStacks().size(); ++i) {
ItemStack item = extractor.getItems().get(i); // Assume we have an item here.
CraftingExtractorItemStatus status = extractor.getStatus().get(i); CraftingExtractorStack stack = extractor.getStacks().get(i);
ICraftingMonitorElement element = new CraftingMonitorElementItemRender(item, item.getCount(), 0); ICraftingMonitorElement element = new CraftingMonitorElementItemRender(stack.getItem(), stack.getItem().getCount(), 0);
if (status == CraftingExtractorItemStatus.MISSING) { if (stack.getStatus() == CraftingExtractorStatus.MISSING) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.waiting_for_items", CraftingMonitorElementColor.COLOR_INFO); element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.waiting_for_items", CraftingMonitorElementColor.COLOR_INFO);
} }
@@ -450,6 +588,7 @@ public class CraftingTask implements ICraftingTask {
elements.commit(); elements.commit();
} }
// TODO: Make better?
if (steps.stream().anyMatch(s -> s instanceof CraftingStepProcess && !s.isCompleted())) { if (steps.stream().anyMatch(s -> s instanceof CraftingStepProcess && !s.isCompleted())) {
elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_processing", 5)); elements.directAdd(new CraftingMonitorElementText("gui.refinedstorage:crafting_monitor.items_processing", 5));
@@ -457,19 +596,54 @@ public class CraftingTask implements ICraftingTask {
if (step instanceof CraftingStepProcess && !step.isCompleted()) { if (step instanceof CraftingStepProcess && !step.isCompleted()) {
CraftingExtractor extractor = ((CraftingStepProcess) step).getExtractor(); CraftingExtractor extractor = ((CraftingStepProcess) step).getExtractor();
for (int i = 0; i < extractor.getItems().size(); ++i) { for (int i = 0; i < extractor.getStacks().size(); ++i) {
ItemStack item = extractor.getItems().get(i); CraftingExtractorStack stack = extractor.getStacks().get(i);
CraftingExtractorItemStatus status = extractor.getStatus().get(i);
ICraftingMonitorElement element = new CraftingMonitorElementItemRender(item, item.getCount(), 0); if (stack.getItem() == null) {
continue;
}
if (status == CraftingExtractorItemStatus.MISSING) { ICraftingMonitorElement element = new CraftingMonitorElementItemRender(stack.getItem(), stack.getItem().getCount(), 0);
if (stack.getStatus() == CraftingExtractorStatus.MISSING) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.waiting_for_items", CraftingMonitorElementColor.COLOR_INFO); element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.waiting_for_items", CraftingMonitorElementColor.COLOR_INFO);
} else if (status == CraftingExtractorItemStatus.MACHINE_DOES_NOT_ACCEPT) { } else if (stack.getStatus() == CraftingExtractorStatus.MACHINE_DOES_NOT_ACCEPT) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.machine_does_not_accept", CraftingMonitorElementColor.COLOR_ERROR); element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.machine_does_not_accept", CraftingMonitorElementColor.COLOR_ERROR);
} else if (status == CraftingExtractorItemStatus.MACHINE_NONE) { } else if (stack.getStatus() == CraftingExtractorStatus.MACHINE_NONE) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.machine_none", CraftingMonitorElementColor.COLOR_ERROR); element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.machine_none", CraftingMonitorElementColor.COLOR_ERROR);
} else if (status == CraftingExtractorItemStatus.EXTRACTED) { } else if (stack.getStatus() == CraftingExtractorStatus.EXTRACTED) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.item_inserted_into_machine", CraftingMonitorElementColor.COLOR_SUCCESS);
}
elements.add(element);
}
}
}
elements.commit();
for (CraftingStep step : steps) {
if (step instanceof CraftingStepProcess && !step.isCompleted()) {
CraftingExtractor extractor = ((CraftingStepProcess) step).getExtractor();
for (int i = 0; i < extractor.getStacks().size(); ++i) {
CraftingExtractorStack stack = extractor.getStacks().get(i);
ICraftingMonitorElement element;
if (stack.getItem() != null) {
continue;
}
element = new CraftingMonitorElementFluidRender(stack.getFluid(), stack.getFluid().amount, 0);
if (stack.getStatus() == CraftingExtractorStatus.MISSING) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.waiting_for_items", CraftingMonitorElementColor.COLOR_INFO);
} else if (stack.getStatus() == CraftingExtractorStatus.MACHINE_DOES_NOT_ACCEPT) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.machine_does_not_accept", CraftingMonitorElementColor.COLOR_ERROR);
} else if (stack.getStatus() == CraftingExtractorStatus.MACHINE_NONE) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.machine_none", CraftingMonitorElementColor.COLOR_ERROR);
} else if (stack.getStatus() == CraftingExtractorStatus.EXTRACTED) {
element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.item_inserted_into_machine", CraftingMonitorElementColor.COLOR_SUCCESS); element = new CraftingMonitorElementColor(element, "gui.refinedstorage:crafting_monitor.item_inserted_into_machine", CraftingMonitorElementColor.COLOR_SUCCESS);
} }
@@ -487,6 +661,7 @@ public class CraftingTask implements ICraftingTask {
@Override @Override
public List<ICraftingPreviewElement> getPreviewStacks() { public List<ICraftingPreviewElement> getPreviewStacks() {
Map<Integer, CraftingPreviewElementItemStack> map = new LinkedHashMap<>(); Map<Integer, CraftingPreviewElementItemStack> map = new LinkedHashMap<>();
Map<Integer, CraftingPreviewElementFluidStack> mapFluids = new LinkedHashMap<>();
for (ItemStack stack : toCraft.getStacks()) { for (ItemStack stack : toCraft.getStacks()) {
int hash = API.instance().getItemStackHashCode(stack); int hash = API.instance().getItemStackHashCode(stack);
@@ -502,6 +677,20 @@ public class CraftingTask implements ICraftingTask {
map.put(hash, previewStack); map.put(hash, previewStack);
} }
for (FluidStack stack : toCraftFluids.getStacks()) {
int hash = API.instance().getFluidStackHashCode(stack);
CraftingPreviewElementFluidStack previewStack = mapFluids.get(hash);
if (previewStack == null) {
previewStack = new CraftingPreviewElementFluidStack(stack);
}
previewStack.addToCraft(stack.amount);
mapFluids.put(hash, previewStack);
}
for (ItemStack stack : missing.getStacks()) { for (ItemStack stack : missing.getStacks()) {
int hash = API.instance().getItemStackHashCode(stack); int hash = API.instance().getItemStackHashCode(stack);
@@ -517,6 +706,21 @@ public class CraftingTask implements ICraftingTask {
map.put(hash, previewStack); map.put(hash, previewStack);
} }
for (FluidStack stack : missingFluids.getStacks()) {
int hash = API.instance().getFluidStackHashCode(stack);
CraftingPreviewElementFluidStack previewStack = mapFluids.get(hash);
if (previewStack == null) {
previewStack = new CraftingPreviewElementFluidStack(stack);
}
previewStack.setMissing(true);
previewStack.addToCraft(stack.amount);
mapFluids.put(hash, previewStack);
}
for (ItemStack stack : toTake.getStacks()) { for (ItemStack stack : toTake.getStacks()) {
int hash = API.instance().getItemStackHashCode(stack); int hash = API.instance().getItemStackHashCode(stack);
@@ -531,7 +735,26 @@ public class CraftingTask implements ICraftingTask {
map.put(hash, previewStack); map.put(hash, previewStack);
} }
return new ArrayList<>(map.values()); for (FluidStack stack : toTakeFluids.getStacks()) {
int hash = API.instance().getFluidStackHashCode(stack);
CraftingPreviewElementFluidStack previewStack = mapFluids.get(hash);
if (previewStack == null) {
previewStack = new CraftingPreviewElementFluidStack(stack);
}
previewStack.addAvailable(stack.amount);
mapFluids.put(hash, previewStack);
}
List<ICraftingPreviewElement> elements = new ArrayList<>();
elements.addAll(map.values());
elements.addAll(mapFluids.values());
return elements;
} }
@Override @Override
@@ -561,7 +784,7 @@ public class CraftingTask implements ICraftingTask {
@Override @Override
public NBTTagCompound writeToNbt(NBTTagCompound tag) { public NBTTagCompound writeToNbt(NBTTagCompound tag) {
tag.setTag(NBT_REQUESTED, requested.serializeNBT()); tag.setTag(NBT_REQUESTED, requested.writeToNbt());
tag.setInteger(NBT_QUANTITY, quantity); tag.setInteger(NBT_QUANTITY, quantity);
tag.setTag(NBT_PATTERN, writePatternToNbt(pattern)); tag.setTag(NBT_PATTERN, writePatternToNbt(pattern));
tag.setTag(NBT_INSERTER, inserter.writeToNbt()); tag.setTag(NBT_INSERTER, inserter.writeToNbt());

View File

@@ -3,11 +3,12 @@ package com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException; import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.util.Action; import com.raoulvdberge.refinedstorage.api.util.Action;
import com.raoulvdberge.refinedstorage.api.util.IComparer;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.CraftingTask; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.CraftingTask;
import com.raoulvdberge.refinedstorage.util.StackUtils;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList; import net.minecraft.nbt.NBTTagList;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fluids.capability.IFluidHandler;
import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.IItemHandler;
import net.minecraftforge.items.ItemHandlerHelper; import net.minecraftforge.items.ItemHandlerHelper;
@@ -16,80 +17,75 @@ import java.util.ArrayList;
import java.util.List; import java.util.List;
public class CraftingExtractor { public class CraftingExtractor {
private static final String NBT_ITEM = "Item";
private static final String NBT_STATUS = "Status";
private INetwork network; private INetwork network;
private List<ItemStack> items; private List<CraftingExtractorStack> stacks;
private List<CraftingExtractorItemStatus> status = new ArrayList<>();
private boolean processing; private boolean processing;
public CraftingExtractor(INetwork network, List<ItemStack> items, boolean processing) { public CraftingExtractor(INetwork network, List<CraftingExtractorStack> stacks, boolean processing) {
this.network = network; this.network = network;
this.items = items; this.stacks = stacks;
this.processing = processing; this.processing = processing;
for (int i = 0; i < items.size(); ++i) {
status.add(CraftingExtractorItemStatus.MISSING);
}
} }
public CraftingExtractor(INetwork network, NBTTagList tag, boolean processing) throws CraftingTaskReadException { public CraftingExtractor(INetwork network, NBTTagList tag, boolean processing) throws CraftingTaskReadException {
this.network = network; this.network = network;
this.processing = processing; this.processing = processing;
this.items = new ArrayList<>(); this.stacks = new ArrayList<>();
for (int i = 0; i < tag.tagCount(); ++i) { for (int i = 0; i < tag.tagCount(); ++i) {
NBTTagCompound itemTag = tag.getCompoundTagAt(i); this.stacks.add(new CraftingExtractorStack(tag.getCompoundTagAt(i)));
ItemStack stack = StackUtils.deserializeStackFromNbt(itemTag.getCompoundTag(NBT_ITEM));
if (stack.isEmpty()) {
throw new CraftingTaskReadException("Extractor stack is empty");
}
CraftingExtractorItemStatus status = CraftingExtractorItemStatus.values()[itemTag.getInteger(NBT_STATUS)];
this.items.add(stack);
this.status.add(status);
} }
} }
public List<ItemStack> getItems() { public List<CraftingExtractorStack> getStacks() {
return items; return stacks;
} }
public List<CraftingExtractorItemStatus> getStatus() { public void updateStatus(@Nullable IItemHandler processingInventory, @Nullable IFluidHandler processingFluidInventory) {
return status;
}
public void updateStatus(@Nullable IItemHandler processingInventory) {
boolean updated = false; boolean updated = false;
for (int i = 0; i < items.size(); ++i) { for (CraftingExtractorStack stack : stacks) {
if (status.get(i) != CraftingExtractorItemStatus.EXTRACTED) { if (stack.getStatus() != CraftingExtractorStatus.EXTRACTED) {
ItemStack stack = items.get(i); CraftingExtractorStatus previousStatus = stack.getStatus();
ItemStack inNetwork = network.extractItem(stack, stack.getCount(), CraftingTask.getFlags(stack), Action.SIMULATE); if (stack.getItem() != null) {
ItemStack item = stack.getItem();
CraftingExtractorItemStatus previousStatus = status.get(i); ItemStack inNetwork = network.extractItem(item, item.getCount(), CraftingTask.getFlags(item), Action.SIMULATE);
if (inNetwork == null || inNetwork.getCount() < stack.getCount()) { if (inNetwork == null || inNetwork.getCount() < item.getCount()) {
status.set(i, CraftingExtractorItemStatus.MISSING); stack.setStatus(CraftingExtractorStatus.MISSING);
} else { } else {
status.set(i, CraftingExtractorItemStatus.AVAILABLE); stack.setStatus(CraftingExtractorStatus.AVAILABLE);
if (processing) { if (processing) {
if (processingInventory == null) { if (processingInventory == null) {
status.set(i, CraftingExtractorItemStatus.MACHINE_NONE); stack.setStatus(CraftingExtractorStatus.MACHINE_NONE);
} else if (!ItemHandlerHelper.insertItem(processingInventory, stack, true).isEmpty()) { } else if (!ItemHandlerHelper.insertItem(processingInventory, item, true).isEmpty()) {
status.set(i, CraftingExtractorItemStatus.MACHINE_DOES_NOT_ACCEPT); stack.setStatus(CraftingExtractorStatus.MACHINE_DOES_NOT_ACCEPT);
}
}
}
} else {
FluidStack fluid = stack.getFluid();
FluidStack inNetwork = network.extractFluid(fluid, fluid.amount, IComparer.COMPARE_NBT, Action.SIMULATE);
if (inNetwork == null || inNetwork.amount < fluid.amount) {
stack.setStatus(CraftingExtractorStatus.MISSING);
} else {
stack.setStatus(CraftingExtractorStatus.AVAILABLE);
if (processingFluidInventory == null) {
stack.setStatus(CraftingExtractorStatus.MACHINE_NONE);
} else if (processingFluidInventory.fill(fluid, false) != fluid.amount) {
stack.setStatus(CraftingExtractorStatus.MACHINE_DOES_NOT_ACCEPT);
} }
} }
} }
if (previousStatus != status.get(i)) { if (previousStatus != stack.getStatus()) {
updated = true; updated = true;
} }
} }
@@ -101,19 +97,22 @@ public class CraftingExtractor {
} }
public boolean isAllAvailable() { public boolean isAllAvailable() {
return !items.isEmpty() && status.stream().allMatch(s -> s == CraftingExtractorItemStatus.AVAILABLE || s == CraftingExtractorItemStatus.EXTRACTED); return !stacks.isEmpty() && stacks.stream().allMatch(s -> s.getStatus() == CraftingExtractorStatus.AVAILABLE || s.getStatus() == CraftingExtractorStatus.EXTRACTED);
} }
public boolean isAllExtracted() { public boolean isAllExtracted() {
return !items.isEmpty() && status.stream().allMatch(s -> s == CraftingExtractorItemStatus.EXTRACTED); return !stacks.isEmpty() && stacks.stream().allMatch(s -> s.getStatus() == CraftingExtractorStatus.EXTRACTED);
} }
public void extractOne(@Nullable IItemHandler processingInventory) { public void extractOne(@Nullable IItemHandler processingInventory, @Nullable IFluidHandler processingFluidInventory) {
boolean changed = false; boolean changed = false;
for (int i = 0; i < items.size(); ++i) { for (CraftingExtractorStack stack : stacks) {
if (status.get(i) == CraftingExtractorItemStatus.AVAILABLE) { if (stack.getStatus() == CraftingExtractorStatus.AVAILABLE) {
ItemStack extracted = network.extractItem(items.get(i), items.get(i).getCount(), CraftingTask.getFlags(items.get(i)), Action.PERFORM); if (stack.getItem() != null) {
ItemStack item = stack.getItem();
ItemStack extracted = network.extractItem(item, item.getCount(), CraftingTask.getFlags(item), Action.PERFORM);
if (extracted == null) { if (extracted == null) {
throw new IllegalStateException("Did not extract anything while available"); throw new IllegalStateException("Did not extract anything while available");
} }
@@ -129,15 +128,36 @@ public class CraftingExtractor {
} }
} }
status.set(i, CraftingExtractorItemStatus.EXTRACTED); stack.setStatus(CraftingExtractorStatus.EXTRACTED);
changed = true; changed = true;
} else {
FluidStack fluid = stack.getFluid();
FluidStack extracted = network.extractFluid(fluid, fluid.amount, IComparer.COMPARE_NBT, Action.PERFORM);
if (extracted == null) {
throw new IllegalStateException("Did not extract any fluids while available");
}
if (processingFluidInventory == null) {
throw new IllegalStateException("Processing fluid inventory is null");
}
int filled = processingFluidInventory.fill(fluid, true);
if (filled != fluid.amount) {
throw new IllegalStateException("The processing fluid inventory gave back a remainder while it previously stated it could handle all");
}
stack.setStatus(CraftingExtractorStatus.EXTRACTED);
changed = true;
}
// For processing patterns we want to insert all items at once to avoid conflicts with other crafting steps. // For processing patterns we want to insert all items at once to avoid conflicts with other crafting steps.
if (!processing) { if (!processing) {
return; return;
} else { } else {
updateStatus(processingInventory); updateStatus(processingInventory, processingFluidInventory);
} }
} }
} }
@@ -150,13 +170,8 @@ public class CraftingExtractor {
public NBTTagList writeToNbt() { public NBTTagList writeToNbt() {
NBTTagList list = new NBTTagList(); NBTTagList list = new NBTTagList();
for (int i = 0; i < items.size(); ++i) { for (CraftingExtractorStack stack : stacks) {
NBTTagCompound tag = new NBTTagCompound(); list.appendTag(stack.writeToNbt());
tag.setTag(NBT_ITEM, StackUtils.serializeStackToNbt(items.get(i)));
tag.setInteger(NBT_STATUS, status.get(i).ordinal());
list.appendTag(tag);
} }
return list; return list;

View File

@@ -0,0 +1,79 @@
package com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.util.StackUtils;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraftforge.fluids.FluidStack;
import javax.annotation.Nullable;
public class CraftingExtractorStack {
private static final String NBT_FLUID = "Fluid";
private static final String NBT_STACK = "Stack";
private static final String NBT_STATUS = "Status";
private ItemStack item;
private FluidStack fluid;
private CraftingExtractorStatus status = CraftingExtractorStatus.MISSING;
public CraftingExtractorStack(ItemStack item) {
this.item = item;
}
public CraftingExtractorStack(FluidStack fluid) {
this.fluid = fluid;
}
public CraftingExtractorStack(NBTTagCompound tag) throws CraftingTaskReadException {
if (!tag.getBoolean(NBT_FLUID)) {
item = StackUtils.deserializeStackFromNbt(tag.getCompoundTag(NBT_STACK));
if (item.isEmpty()) {
throw new CraftingTaskReadException("Extractor stack is empty");
}
} else {
fluid = FluidStack.loadFluidStackFromNBT(tag.getCompoundTag(NBT_STACK));
if (fluid == null) {
throw new CraftingTaskReadException("Extractor fluid stack is empty");
}
}
status = CraftingExtractorStatus.values()[tag.getInteger(NBT_STATUS)];
}
@Nullable
public ItemStack getItem() {
return item;
}
@Nullable
public FluidStack getFluid() {
return fluid;
}
public NBTTagCompound writeToNbt() {
NBTTagCompound tag = new NBTTagCompound();
tag.setBoolean(NBT_FLUID, fluid != null);
if (fluid != null) {
tag.setTag(NBT_STACK, fluid.writeToNBT(new NBTTagCompound()));
} else {
tag.setTag(NBT_STACK, StackUtils.serializeStackToNbt(item));
}
tag.setInteger(NBT_STATUS, status.ordinal());
return tag;
}
public CraftingExtractorStatus getStatus() {
return status;
}
public void setStatus(CraftingExtractorStatus status) {
this.status = status;
}
}

View File

@@ -1,6 +1,6 @@
package com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor; package com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor;
public enum CraftingExtractorItemStatus { public enum CraftingExtractorStatus {
AVAILABLE, AVAILABLE,
MISSING, MISSING,
EXTRACTED, EXTRACTED,

View File

@@ -4,6 +4,7 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException; import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractor; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractor;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractorStack;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserter; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.inserter.CraftingInserter;
import com.raoulvdberge.refinedstorage.util.StackUtils; import com.raoulvdberge.refinedstorage.util.StackUtils;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
@@ -13,6 +14,7 @@ import net.minecraft.util.NonNullList;
import net.minecraftforge.common.util.Constants; import net.minecraftforge.common.util.Constants;
import java.util.List; import java.util.List;
import java.util.stream.Collectors;
public class CraftingStepCraft extends CraftingStep { public class CraftingStepCraft extends CraftingStep {
public static final String TYPE = "craft"; public static final String TYPE = "craft";
@@ -33,7 +35,7 @@ public class CraftingStepCraft extends CraftingStep {
} }
this.inserter = inserter; this.inserter = inserter;
this.extractor = new CraftingExtractor(network, toExtract, false); this.extractor = new CraftingExtractor(network, toExtract.stream().map(CraftingExtractorStack::new).collect(Collectors.toList()), false);
this.took = took; this.took = took;
} }
@@ -57,14 +59,14 @@ public class CraftingStepCraft extends CraftingStep {
@Override @Override
public boolean canExecute() { public boolean canExecute() {
extractor.updateStatus(null); extractor.updateStatus(null, null);
return extractor.isAllAvailable(); return extractor.isAllAvailable();
} }
@Override @Override
public boolean execute() { public boolean execute() {
extractor.extractOne(null); extractor.extractOne(null, null);
boolean allExtracted = extractor.isAllExtracted(); boolean allExtracted = extractor.isAllExtracted();

View File

@@ -6,12 +6,15 @@ import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.util.IStackList; import com.raoulvdberge.refinedstorage.api.util.IStackList;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractor; import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractor;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.task.extractor.CraftingExtractorStack;
import com.raoulvdberge.refinedstorage.util.StackUtils; import com.raoulvdberge.refinedstorage.util.StackUtils;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound; import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.nbt.NBTTagList; import net.minecraft.nbt.NBTTagList;
import net.minecraftforge.common.util.Constants; import net.minecraftforge.common.util.Constants;
import net.minecraftforge.fluids.FluidStack;
import java.util.ArrayList;
import java.util.List; import java.util.List;
public class CraftingStepProcess extends CraftingStep { public class CraftingStepProcess extends CraftingStep {
@@ -19,22 +22,39 @@ public class CraftingStepProcess extends CraftingStep {
private static final String NBT_EXTRACTOR = "Extractor"; private static final String NBT_EXTRACTOR = "Extractor";
private static final String NBT_TO_RECEIVE = "ToReceive"; private static final String NBT_TO_RECEIVE = "ToReceive";
private static final String NBT_TO_RECEIVE_FLUIDS = "ToReceiveFluids";
private CraftingExtractor extractor; private CraftingExtractor extractor;
private IStackList<ItemStack> itemsToReceive = API.instance().createItemStackList();
public CraftingStepProcess(ICraftingPattern pattern, INetwork network, List<ItemStack> toExtract) { private IStackList<ItemStack> itemsToReceive = API.instance().createItemStackList();
private IStackList<FluidStack> fluidsToReceive = API.instance().createFluidStackList();
public CraftingStepProcess(ICraftingPattern pattern, INetwork network, List<ItemStack> toExtract, List<FluidStack> fluidsToExtract) {
super(pattern); super(pattern);
if (!pattern.isProcessing()) { if (!pattern.isProcessing()) {
throw new IllegalArgumentException("Cannot pass non-processing pattern to processing handler"); throw new IllegalArgumentException("Cannot pass non-processing pattern to processing handler");
} }
this.extractor = new CraftingExtractor(network, toExtract, true); List<CraftingExtractorStack> stacks = new ArrayList<>();
for (ItemStack item : toExtract) {
stacks.add(new CraftingExtractorStack(item));
}
for (FluidStack fluid : fluidsToExtract) {
stacks.add(new CraftingExtractorStack(fluid));
}
this.extractor = new CraftingExtractor(network, stacks, true);
for (ItemStack output : pattern.getOutputs()) { for (ItemStack output : pattern.getOutputs()) {
this.itemsToReceive.add(output); this.itemsToReceive.add(output);
} }
for (FluidStack output : pattern.getFluidOutputs()) {
this.fluidsToReceive.add(output);
}
} }
public CraftingStepProcess(ICraftingPattern pattern, INetwork network, NBTTagCompound tag) throws CraftingTaskReadException { public CraftingStepProcess(ICraftingPattern pattern, INetwork network, NBTTagCompound tag) throws CraftingTaskReadException {
@@ -56,11 +76,22 @@ public class CraftingStepProcess extends CraftingStep {
this.itemsToReceive.add(toReceive); this.itemsToReceive.add(toReceive);
} }
NBTTagList toReceiveFluidsList = tag.getTagList(NBT_TO_RECEIVE_FLUIDS, Constants.NBT.TAG_COMPOUND);
for (int i = 0; i < toReceiveFluidsList.tagCount(); ++i) {
FluidStack toReceive = FluidStack.loadFluidStackFromNBT(toReceiveFluidsList.getCompoundTagAt(i));
if (toReceive == null) {
throw new CraftingTaskReadException("Fluid to receive is null");
}
this.fluidsToReceive.add(toReceive);
}
} }
@Override @Override
public boolean canExecute() { public boolean canExecute() {
extractor.updateStatus(pattern.getContainer().getConnectedInventory()); extractor.updateStatus(pattern.getContainer().getConnectedInventory(), pattern.getContainer().getConnectedFluidInventory());
return extractor.isAllAvailable(); return extractor.isAllAvailable();
} }
@@ -82,13 +113,30 @@ public class CraftingStepProcess extends CraftingStep {
return size - toExtract; return size - toExtract;
} }
public int onTrackedFluidInserted(FluidStack stack, int size) {
if (!extractor.isAllExtracted()) {
return size;
}
FluidStack inList = fluidsToReceive.get(stack);
if (inList == null) {
return size;
}
int toExtract = Math.min(size, inList.amount);
fluidsToReceive.remove(stack, toExtract);
return size - toExtract;
}
@Override @Override
public boolean execute() { public boolean execute() {
if (!extractor.isAllExtracted()) { if (!extractor.isAllExtracted()) {
extractor.extractOne(pattern.getContainer().getConnectedInventory()); extractor.extractOne(pattern.getContainer().getConnectedInventory(), pattern.getContainer().getConnectedFluidInventory());
} }
return extractor.isAllExtracted() && itemsToReceive.isEmpty(); return extractor.isAllExtracted() && itemsToReceive.isEmpty() && fluidsToReceive.isEmpty();
} }
@Override @Override
@@ -110,6 +158,14 @@ public class CraftingStepProcess extends CraftingStep {
tag.setTag(NBT_TO_RECEIVE, toReceive); tag.setTag(NBT_TO_RECEIVE, toReceive);
NBTTagList toReceiveFluids = new NBTTagList();
for (FluidStack toReceiveStack : fluidsToReceive.getStacks()) {
toReceiveFluids.appendTag(toReceiveStack.writeToNBT(new NBTTagCompound()));
}
tag.setTag(NBT_TO_RECEIVE_FLUIDS, toReceiveFluids);
return tag; return tag;
} }

View File

@@ -1,9 +1,12 @@
package com.raoulvdberge.refinedstorage.apiimpl.network.grid; package com.raoulvdberge.refinedstorage.apiimpl.network.grid;
import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab; import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawer;
import com.raoulvdberge.refinedstorage.api.util.IFilter; import com.raoulvdberge.refinedstorage.api.util.IFilter;
import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.gui.FontRenderer;
import net.minecraft.client.renderer.RenderHelper;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fml.client.config.GuiUtils; import net.minecraftforge.fml.client.config.GuiUtils;
import java.util.Collections; import java.util.Collections;
@@ -33,7 +36,9 @@ public class GridTab implements IGridTab {
} }
@Override @Override
public ItemStack getIcon() { public void drawIcon(int x, int y, IElementDrawer<ItemStack> itemDrawer, IElementDrawer<FluidStack> fluidDrawer) {
return icon; RenderHelper.enableGUIStandardItemLighting();
itemDrawer.draw(x, y, icon);
} }
} }

View File

@@ -1,12 +1,20 @@
package com.raoulvdberge.refinedstorage.apiimpl.network.grid.handler; package com.raoulvdberge.refinedstorage.apiimpl.network.grid.handler;
import com.raoulvdberge.refinedstorage.RS;
import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTaskError;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.network.grid.handler.IFluidGridHandler; import com.raoulvdberge.refinedstorage.api.network.grid.handler.IFluidGridHandler;
import com.raoulvdberge.refinedstorage.api.network.item.INetworkItem; import com.raoulvdberge.refinedstorage.api.network.item.INetworkItem;
import com.raoulvdberge.refinedstorage.api.network.item.NetworkItemAction; import com.raoulvdberge.refinedstorage.api.network.item.NetworkItemAction;
import com.raoulvdberge.refinedstorage.api.network.security.Permission; import com.raoulvdberge.refinedstorage.api.network.security.Permission;
import com.raoulvdberge.refinedstorage.api.util.Action; import com.raoulvdberge.refinedstorage.api.util.Action;
import com.raoulvdberge.refinedstorage.api.util.IStackList;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.apiimpl.autocrafting.preview.CraftingPreviewElementError;
import com.raoulvdberge.refinedstorage.network.MessageGridCraftingPreviewResponse;
import com.raoulvdberge.refinedstorage.network.MessageGridCraftingStartResponse;
import com.raoulvdberge.refinedstorage.util.StackUtils; import com.raoulvdberge.refinedstorage.util.StackUtils;
import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.inventory.InventoryHelper; import net.minecraft.inventory.InventoryHelper;
@@ -18,6 +26,7 @@ import net.minecraftforge.fluids.capability.IFluidHandlerItem;
import org.apache.commons.lang3.tuple.Pair; import org.apache.commons.lang3.tuple.Pair;
import javax.annotation.Nullable; import javax.annotation.Nullable;
import java.util.Collections;
public class FluidGridHandler implements IFluidGridHandler { public class FluidGridHandler implements IFluidGridHandler {
private INetwork network; private INetwork network;
@@ -116,4 +125,79 @@ public class FluidGridHandler implements IFluidGridHandler {
public ItemStack onShiftClick(EntityPlayerMP player, ItemStack container) { public ItemStack onShiftClick(EntityPlayerMP player, ItemStack container) {
return StackUtils.nullToEmpty(onInsert(player, container)); return StackUtils.nullToEmpty(onInsert(player, container));
} }
@Override
public void onCraftingPreviewRequested(EntityPlayerMP player, int hash, int quantity, boolean noPreview) {
if (!network.getSecurityManager().hasPermission(Permission.AUTOCRAFTING, player)) {
return;
}
IStackList<FluidStack> cache = API.instance().createFluidStackList();
for (ICraftingPattern pattern : network.getCraftingManager().getPatterns()) {
for (FluidStack output : pattern.getFluidOutputs()) {
cache.add(output);
}
}
FluidStack stack = cache.get(hash);
if (stack != null) {
Thread calculationThread = new Thread(() -> {
ICraftingTask task = network.getCraftingManager().create(stack, quantity);
if (task == null) {
return;
}
ICraftingTaskError error = task.calculate();
if (error != null) {
RS.INSTANCE.network.sendTo(new MessageGridCraftingPreviewResponse(Collections.singletonList(new CraftingPreviewElementError(error.getType(), error.getRecursedPattern() == null ? ItemStack.EMPTY : error.getRecursedPattern().getStack())), hash, quantity, true), player);
} else if (noPreview && task.getMissing().isEmpty()) {
network.getCraftingManager().add(task);
RS.INSTANCE.network.sendTo(new MessageGridCraftingStartResponse(), player);
} else {
RS.INSTANCE.network.sendTo(new MessageGridCraftingPreviewResponse(task.getPreviewStacks(), hash, quantity, true), player);
}
}, "RS crafting preview calculation");
calculationThread.start();
}
}
@Override
public void onCraftingRequested(EntityPlayerMP player, int hash, int quantity) {
if (quantity <= 0 || !network.getSecurityManager().hasPermission(Permission.AUTOCRAFTING, player)) {
return;
}
FluidStack stack = null;
for (ICraftingPattern pattern : network.getCraftingManager().getPatterns()) {
for (FluidStack output : pattern.getFluidOutputs()) {
if (API.instance().getFluidStackHashCode(output) == hash) {
stack = output;
break;
}
}
if (stack != null) {
break;
}
}
if (stack != null) {
ICraftingTask task = network.getCraftingManager().create(stack, quantity);
if (task == null) {
return;
}
ICraftingTaskError error = task.calculate();
if (error == null) {
network.getCraftingManager().add(task);
}
}
}
} }

View File

@@ -196,13 +196,13 @@ public class ItemGridHandler implements IItemGridHandler {
ICraftingTaskError error = task.calculate(); ICraftingTaskError error = task.calculate();
if (error != null) { if (error != null) {
RS.INSTANCE.network.sendTo(new MessageGridCraftingPreviewResponse(Collections.singletonList(new CraftingPreviewElementError(error.getType(), error.getRecursedPattern() == null ? ItemStack.EMPTY : error.getRecursedPattern().getStack())), hash, quantity), player); RS.INSTANCE.network.sendTo(new MessageGridCraftingPreviewResponse(Collections.singletonList(new CraftingPreviewElementError(error.getType(), error.getRecursedPattern() == null ? ItemStack.EMPTY : error.getRecursedPattern().getStack())), hash, quantity, false), player);
} else if (noPreview && task.getMissing().isEmpty()) { } else if (noPreview && task.getMissing().isEmpty()) {
network.getCraftingManager().add(task); network.getCraftingManager().add(task);
RS.INSTANCE.network.sendTo(new MessageGridCraftingStartResponse(), player); RS.INSTANCE.network.sendTo(new MessageGridCraftingStartResponse(), player);
} else { } else {
RS.INSTANCE.network.sendTo(new MessageGridCraftingPreviewResponse(task.getPreviewStacks(), hash, quantity), player); RS.INSTANCE.network.sendTo(new MessageGridCraftingPreviewResponse(task.getPreviewStacks(), hash, quantity, false), player);
} }
}, "RS crafting preview calculation"); }, "RS crafting preview calculation");

View File

@@ -48,6 +48,7 @@ import net.minecraftforge.items.wrapper.CombinedInvWrapper;
import javax.annotation.Nullable; import javax.annotation.Nullable;
// TODO: Crafting upgrade for fluids.
public class NetworkNodeConstructor extends NetworkNode implements IComparable, IType, ICoverable { public class NetworkNodeConstructor extends NetworkNode implements IComparable, IType, ICoverable {
public static final String ID = "constructor"; public static final String ID = "constructor";

View File

@@ -19,6 +19,7 @@ import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import net.minecraft.world.IWorldNameable; import net.minecraft.world.IWorldNameable;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.fluids.capability.IFluidHandler;
import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.IItemHandler;
import net.minecraftforge.items.IItemHandlerModifiable; import net.minecraftforge.items.IItemHandlerModifiable;
import net.minecraftforge.items.wrapper.CombinedInvWrapper; import net.minecraftforge.items.wrapper.CombinedInvWrapper;
@@ -187,6 +188,17 @@ public class NetworkNodeCrafter extends NetworkNode implements ICraftingPatternC
return WorldUtils.getItemHandler(proxy.getFacingTile(), proxy.getDirection().getOpposite()); return WorldUtils.getItemHandler(proxy.getFacingTile(), proxy.getDirection().getOpposite());
} }
@Nullable
@Override
public IFluidHandler getConnectedFluidInventory() {
ICraftingPatternContainer proxy = getRootContainer();
if (proxy == null) {
return null;
}
return WorldUtils.getFluidHandler(proxy.getFacingTile(), proxy.getDirection().getOpposite());
}
@Override @Override
@Nullable @Nullable
public TileEntity getConnectedTile() { public TileEntity getConnectedTile() {

View File

@@ -183,7 +183,7 @@ public class NetworkNodeDestructor extends NetworkNode implements IComparable, I
if (stack != null && IFilterable.acceptsFluid(fluidFilters, mode, compare, stack) && network.insertFluid(stack, stack.amount, Action.SIMULATE) == null) { if (stack != null && IFilterable.acceptsFluid(fluidFilters, mode, compare, stack) && network.insertFluid(stack, stack.amount, Action.SIMULATE) == null) {
FluidStack drained = handler.drain(Fluid.BUCKET_VOLUME, true); FluidStack drained = handler.drain(Fluid.BUCKET_VOLUME, true);
network.insertFluid(drained, drained.amount, Action.PERFORM); network.insertFluidTracked(drained, drained.amount);
} }
} }
} }

View File

@@ -29,6 +29,7 @@ import net.minecraftforge.items.wrapper.CombinedInvWrapper;
import javax.annotation.Nullable; import javax.annotation.Nullable;
// TODO: Crafting upgrade for fluids
public class NetworkNodeExporter extends NetworkNode implements IComparable, IType, ICoverable { public class NetworkNodeExporter extends NetworkNode implements IComparable, IType, ICoverable {
public static final String ID = "exporter"; public static final String ID = "exporter";

View File

@@ -19,6 +19,7 @@ import net.minecraftforge.items.IItemHandler;
import net.minecraftforge.items.wrapper.CombinedInvWrapper; import net.minecraftforge.items.wrapper.CombinedInvWrapper;
import org.apache.commons.lang3.tuple.Pair; import org.apache.commons.lang3.tuple.Pair;
// TODO: Crafting upgrade
public class NetworkNodeFluidInterface extends NetworkNode implements IComparable { public class NetworkNodeFluidInterface extends NetworkNode implements IComparable {
public static final String ID = "fluid_interface"; public static final String ID = "fluid_interface";
@@ -96,7 +97,7 @@ public class NetworkNodeFluidInterface extends NetworkNode implements IComparabl
// Drain in tank // Drain in tank
if (drained != null) { if (drained != null) {
FluidStack remainder = network.insertFluid(drained, drained.amount, Action.PERFORM); FluidStack remainder = network.insertFluidTracked(drained, drained.amount);
if (remainder != null) { if (remainder != null) {
tankIn.fillInternal(remainder, true); tankIn.fillInternal(remainder, true);
@@ -112,7 +113,7 @@ public class NetworkNodeFluidInterface extends NetworkNode implements IComparabl
FluidStack remainder = tankOut.drainInternal(Fluid.BUCKET_VOLUME * upgrades.getItemInteractCount(), true); FluidStack remainder = tankOut.drainInternal(Fluid.BUCKET_VOLUME * upgrades.getItemInteractCount(), true);
if (remainder != null) { if (remainder != null) {
network.insertFluid(remainder, remainder.amount, Action.PERFORM); network.insertFluidTracked(remainder, remainder.amount);
} }
} else if (stack != null) { } else if (stack != null) {
// Fill the out fluid // Fill the out fluid

View File

@@ -22,11 +22,9 @@ import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageCacheListenerGridFluid; import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageCacheListenerGridFluid;
import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageCacheListenerGridItem; import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageCacheListenerGridItem;
import com.raoulvdberge.refinedstorage.block.BlockGrid; import com.raoulvdberge.refinedstorage.block.BlockGrid;
import com.raoulvdberge.refinedstorage.inventory.ItemHandlerBase; import com.raoulvdberge.refinedstorage.inventory.*;
import com.raoulvdberge.refinedstorage.inventory.ItemHandlerFilter;
import com.raoulvdberge.refinedstorage.inventory.ItemHandlerListenerNetworkNode;
import com.raoulvdberge.refinedstorage.inventory.ItemValidatorBasic;
import com.raoulvdberge.refinedstorage.item.ItemPattern; import com.raoulvdberge.refinedstorage.item.ItemPattern;
import com.raoulvdberge.refinedstorage.tile.config.IType;
import com.raoulvdberge.refinedstorage.tile.data.TileDataManager; import com.raoulvdberge.refinedstorage.tile.data.TileDataManager;
import com.raoulvdberge.refinedstorage.tile.grid.TileGrid; import com.raoulvdberge.refinedstorage.tile.grid.TileGrid;
import com.raoulvdberge.refinedstorage.util.StackUtils; import com.raoulvdberge.refinedstorage.util.StackUtils;
@@ -41,6 +39,7 @@ import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.util.NonNullList; import net.minecraft.util.NonNullList;
import net.minecraft.util.math.BlockPos; import net.minecraft.util.math.BlockPos;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fml.common.FMLCommonHandler; import net.minecraftforge.fml.common.FMLCommonHandler;
import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.IItemHandler;
import net.minecraftforge.items.IItemHandlerModifiable; import net.minecraftforge.items.IItemHandlerModifiable;
@@ -53,7 +52,7 @@ import javax.annotation.Nullable;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware { public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware, IType {
public static final String ID = "grid"; public static final String ID = "grid";
public static final String NBT_VIEW_TYPE = "ViewType"; public static final String NBT_VIEW_TYPE = "ViewType";
@@ -65,6 +64,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
public static final String NBT_TAB_PAGE = "TabPage"; public static final String NBT_TAB_PAGE = "TabPage";
public static final String NBT_SIZE = "Size"; public static final String NBT_SIZE = "Size";
public static final String NBT_PROCESSING_PATTERN = "ProcessingPattern"; public static final String NBT_PROCESSING_PATTERN = "ProcessingPattern";
public static final String NBT_PROCESSING_TYPE = "ProcessingType";
private Container craftingContainer = new Container() { private Container craftingContainer = new Container() {
@Override @Override
@@ -81,6 +81,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
private InventoryCrafting matrix = new InventoryCrafting(craftingContainer, 3, 3); private InventoryCrafting matrix = new InventoryCrafting(craftingContainer, 3, 3);
private InventoryCraftResult result = new InventoryCraftResult(); private InventoryCraftResult result = new InventoryCraftResult();
private ItemHandlerBase matrixProcessing = new ItemHandlerBase(9 * 2, new ItemHandlerListenerNetworkNode(this)); private ItemHandlerBase matrixProcessing = new ItemHandlerBase(9 * 2, new ItemHandlerListenerNetworkNode(this));
private ItemHandlerFluid matrixProcessingFluids = new ItemHandlerFluid(9 * 2, new ItemHandlerListenerNetworkNode(this));
private ItemHandlerBase patterns = new ItemHandlerBase(2, new ItemHandlerListenerNetworkNode(this), new ItemValidatorBasic(RSItems.PATTERN)) { private ItemHandlerBase patterns = new ItemHandlerBase(2, new ItemHandlerListenerNetworkNode(this), new ItemValidatorBasic(RSItems.PATTERN)) {
@Override @Override
@@ -144,6 +145,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
private boolean oredictPattern = false; private boolean oredictPattern = false;
private boolean processingPattern = false; private boolean processingPattern = false;
private int processingType = IType.ITEMS;
public NetworkNodeGrid(World world, BlockPos pos) { public NetworkNodeGrid(World world, BlockPos pos) {
super(world, pos); super(world, pos);
@@ -151,7 +153,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
@Override @Override
public int getEnergyUsage() { public int getEnergyUsage() {
switch (getType()) { switch (getGridType()) {
case NORMAL: case NORMAL:
return RS.INSTANCE.config.gridUsage; return RS.INSTANCE.config.gridUsage;
case CRAFTING: case CRAFTING:
@@ -209,7 +211,8 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
this.processingPattern = processingPattern; this.processingPattern = processingPattern;
} }
public GridType getType() { @Override
public GridType getGridType() {
if (type == null) { if (type == null) {
IBlockState state = world.getBlockState(pos); IBlockState state = world.getBlockState(pos);
if (state.getBlock() == RSBlocks.GRID) { if (state.getBlock() == RSBlocks.GRID) {
@@ -222,13 +225,13 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
@Override @Override
public IStorageCacheListener createListener(EntityPlayerMP player) { public IStorageCacheListener createListener(EntityPlayerMP player) {
return getType() == GridType.FLUID ? new StorageCacheListenerGridFluid(player, network) : new StorageCacheListenerGridItem(player, network); return getGridType() == GridType.FLUID ? new StorageCacheListenerGridFluid(player, network) : new StorageCacheListenerGridItem(player, network);
} }
@Nullable @Nullable
@Override @Override
public IStorageCache getStorageCache() { public IStorageCache getStorageCache() {
return network != null ? (getType() == GridType.FLUID ? network.getFluidStorageCache() : network.getItemStorageCache()) : null; return network != null ? (getGridType() == GridType.FLUID ? network.getFluidStorageCache() : network.getItemStorageCache()) : null;
} }
@Nullable @Nullable
@@ -245,7 +248,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
@Override @Override
public String getGuiTitle() { public String getGuiTitle() {
GridType type = getType(); GridType type = getGridType();
switch (type) { switch (type) {
case CRAFTING: case CRAFTING:
@@ -292,6 +295,10 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
return matrixProcessing; return matrixProcessing;
} }
public ItemHandlerFluid getMatrixProcessingFluids() {
return matrixProcessingFluids;
}
@Override @Override
public void onCraftingMatrixChanged() { public void onCraftingMatrixChanged() {
if (currentRecipe == null || !currentRecipe.matches(matrix, world)) { if (currentRecipe == null || !currentRecipe.matches(matrix, world)) {
@@ -315,7 +322,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
public static void onRecipeTransfer(IGridNetworkAware grid, EntityPlayer player, ItemStack[][] recipe) { public static void onRecipeTransfer(IGridNetworkAware grid, EntityPlayer player, ItemStack[][] recipe) {
INetwork network = grid.getNetwork(); INetwork network = grid.getNetwork();
if (network != null && grid.getType() == GridType.CRAFTING && !network.getSecurityManager().hasPermission(Permission.EXTRACT, player)) { if (network != null && grid.getGridType() == GridType.CRAFTING && !network.getSecurityManager().hasPermission(Permission.EXTRACT, player)) {
return; return;
} }
@@ -325,7 +332,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
if (!slot.isEmpty()) { if (!slot.isEmpty()) {
// Only if we are a crafting grid. Pattern grids can just be emptied. // Only if we are a crafting grid. Pattern grids can just be emptied.
if (grid.getType() == GridType.CRAFTING) { if (grid.getGridType() == GridType.CRAFTING) {
// If we are connected, try to insert into network. If it fails, stop. // If we are connected, try to insert into network. If it fails, stop.
if (network != null) { if (network != null) {
if (network.insertItem(slot, slot.getCount(), Action.SIMULATE) != null) { if (network.insertItem(slot, slot.getCount(), Action.SIMULATE) != null) {
@@ -351,7 +358,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
ItemStack[] possibilities = recipe[i]; ItemStack[] possibilities = recipe[i];
// If we are a crafting grid // If we are a crafting grid
if (grid.getType() == GridType.CRAFTING) { if (grid.getGridType() == GridType.CRAFTING) {
boolean found = false; boolean found = false;
// If we are connected, first try to get the possibilities from the network // If we are connected, first try to get the possibilities from the network
@@ -389,7 +396,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
} }
} }
} }
} else if (grid.getType() == GridType.PATTERN) { } else if (grid.getGridType() == GridType.PATTERN) {
// If we are a pattern grid we can just set the slot // If we are a pattern grid we can just set the slot
grid.getCraftingMatrix().setInventorySlotContents(i, possibilities.length == 0 ? ItemStack.EMPTY : possibilities[0]); grid.getCraftingMatrix().setInventorySlotContents(i, possibilities.length == 0 ? ItemStack.EMPTY : possibilities[0]);
} }
@@ -402,6 +409,10 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
matrixProcessing.setStackInSlot(i, ItemStack.EMPTY); matrixProcessing.setStackInSlot(i, ItemStack.EMPTY);
} }
for (int i = 0; i < matrixProcessingFluids.getSlots(); ++i) {
matrixProcessingFluids.setStackInSlot(i, ItemStack.EMPTY);
}
for (int i = 0; i < matrix.getSizeInventory(); ++i) { for (int i = 0; i < matrix.getSizeInventory(); ++i) {
matrix.setInventorySlotContents(i, ItemStack.EMPTY); matrix.setInventorySlotContents(i, ItemStack.EMPTY);
} }
@@ -520,6 +531,20 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
ItemPattern.setInputSlot(pattern, i, matrixProcessing.getStackInSlot(i)); ItemPattern.setInputSlot(pattern, i, matrixProcessing.getStackInSlot(i));
} }
} }
if (!matrixProcessingFluids.getStackInSlot(i).isEmpty()) {
if (i >= 9) {
FluidStack fluid = StackUtils.getFluid(ItemHandlerHelper.copyStackWithSize(matrixProcessingFluids.getStackInSlot(i), 1), true).getValue();
if (fluid != null) {
ItemPattern.setFluidOutputSlot(pattern, i - 9, StackUtils.copy(fluid, matrixProcessingFluids.getStackInSlot(i).getCount()));
}
} else {
FluidStack fluid = StackUtils.getFluid(ItemHandlerHelper.copyStackWithSize(matrixProcessingFluids.getStackInSlot(i), 1), true).getValue();
if (fluid != null) {
ItemPattern.setFluidInputSlot(pattern, i, StackUtils.copy(fluid, matrixProcessingFluids.getStackInSlot(i).getCount()));
}
}
}
} }
} else { } else {
for (int i = 0; i < 9; ++i) { for (int i = 0; i < 9; ++i) {
@@ -552,12 +577,20 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
if (!matrixProcessing.getStackInSlot(i).isEmpty()) { if (!matrixProcessing.getStackInSlot(i).isEmpty()) {
inputsFilled++; inputsFilled++;
} }
if (!matrixProcessingFluids.getStackInSlot(i).isEmpty()) {
inputsFilled++;
}
} }
for (int i = 9; i < 18; ++i) { for (int i = 9; i < 18; ++i) {
if (!matrixProcessing.getStackInSlot(i).isEmpty()) { if (!matrixProcessing.getStackInSlot(i).isEmpty()) {
outputsFilled++; outputsFilled++;
} }
if (!matrixProcessingFluids.getStackInSlot(i).isEmpty()) {
outputsFilled++;
}
} }
return inputsFilled > 0 && outputsFilled > 0; return inputsFilled > 0 && outputsFilled > 0;
@@ -643,6 +676,23 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
} }
} }
@Override
public int getType() {
return world.isRemote ? TileGrid.PROCESSING_TYPE.getValue() : processingType;
}
@Override
public void setType(int type) {
this.processingType = type;
this.markDirty();
}
@Override
public IItemHandler getFilterInventory() {
return getType() == IType.FLUIDS ? matrixProcessingFluids : matrixProcessing;
}
@Override @Override
public boolean hasConnectivityState() { public boolean hasConnectivityState() {
return true; return true;
@@ -656,6 +706,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
StackUtils.readItems(patterns, 1, tag); StackUtils.readItems(patterns, 1, tag);
StackUtils.readItems(filter, 2, tag); StackUtils.readItems(filter, 2, tag);
StackUtils.readItems(matrixProcessing, 3, tag); StackUtils.readItems(matrixProcessing, 3, tag);
StackUtils.readItems(matrixProcessingFluids, 4, tag, StackUtils::deserializeStackFromNbt);
if (tag.hasKey(NBT_TAB_SELECTED)) { if (tag.hasKey(NBT_TAB_SELECTED)) {
tabSelected = tag.getInteger(NBT_TAB_SELECTED); tabSelected = tag.getInteger(NBT_TAB_SELECTED);
@@ -679,6 +730,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
StackUtils.writeItems(patterns, 1, tag); StackUtils.writeItems(patterns, 1, tag);
StackUtils.writeItems(filter, 2, tag); StackUtils.writeItems(filter, 2, tag);
StackUtils.writeItems(matrixProcessing, 3, tag); StackUtils.writeItems(matrixProcessing, 3, tag);
StackUtils.writeItems(matrixProcessingFluids, 4, tag, StackUtils::serializeStackToNbt);
tag.setInteger(NBT_TAB_SELECTED, tabSelected); tag.setInteger(NBT_TAB_SELECTED, tabSelected);
tag.setInteger(NBT_TAB_PAGE, tabPage); tag.setInteger(NBT_TAB_PAGE, tabPage);
@@ -698,6 +750,7 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
tag.setBoolean(NBT_OREDICT_PATTERN, oredictPattern); tag.setBoolean(NBT_OREDICT_PATTERN, oredictPattern);
tag.setBoolean(NBT_PROCESSING_PATTERN, processingPattern); tag.setBoolean(NBT_PROCESSING_PATTERN, processingPattern);
tag.setInteger(NBT_PROCESSING_TYPE, processingType);
return tag; return tag;
} }
@@ -733,11 +786,15 @@ public class NetworkNodeGrid extends NetworkNode implements IGridNetworkAware {
if (tag.hasKey(NBT_PROCESSING_PATTERN)) { if (tag.hasKey(NBT_PROCESSING_PATTERN)) {
processingPattern = tag.getBoolean(NBT_PROCESSING_PATTERN); processingPattern = tag.getBoolean(NBT_PROCESSING_PATTERN);
} }
if (tag.hasKey(NBT_PROCESSING_TYPE)) {
processingType = tag.getInteger(NBT_PROCESSING_TYPE);
}
} }
@Override @Override
public IItemHandler getDrops() { public IItemHandler getDrops() {
switch (getType()) { switch (getGridType()) {
case CRAFTING: case CRAFTING:
return new CombinedInvWrapper(filter, new InvWrapper(matrix)); return new CombinedInvWrapper(filter, new InvWrapper(matrix));
case PATTERN: case PATTERN:

View File

@@ -115,7 +115,7 @@ public class NetworkNodeImporter extends NetworkNode implements IComparable, IFi
FluidStack toDrain = handler.drain(Fluid.BUCKET_VOLUME * upgrades.getItemInteractCount(), false); FluidStack toDrain = handler.drain(Fluid.BUCKET_VOLUME * upgrades.getItemInteractCount(), false);
if (toDrain != null) { if (toDrain != null) {
FluidStack remainder = network.insertFluid(toDrain, toDrain.amount, Action.PERFORM); FluidStack remainder = network.insertFluidTracked(toDrain, toDrain.amount);
if (remainder != null) { if (remainder != null) {
toDrain.amount -= remainder.amount; toDrain.amount -= remainder.amount;
} }

View File

@@ -1,6 +1,8 @@
package com.raoulvdberge.refinedstorage.apiimpl.util; package com.raoulvdberge.refinedstorage.apiimpl.util;
import com.raoulvdberge.refinedstorage.api.util.IQuantityFormatter; import com.raoulvdberge.refinedstorage.api.util.IQuantityFormatter;
import com.raoulvdberge.refinedstorage.apiimpl.API;
import net.minecraftforge.fluids.Fluid;
import java.math.RoundingMode; import java.math.RoundingMode;
import java.text.DecimalFormat; import java.text.DecimalFormat;
@@ -10,6 +12,7 @@ import java.util.Locale;
public class QuantityFormatter implements IQuantityFormatter { public class QuantityFormatter implements IQuantityFormatter {
private DecimalFormat formatterWithUnits = new DecimalFormat("####0.#", DecimalFormatSymbols.getInstance(Locale.US)); private DecimalFormat formatterWithUnits = new DecimalFormat("####0.#", DecimalFormatSymbols.getInstance(Locale.US));
private DecimalFormat formatter = new DecimalFormat("#,###", DecimalFormatSymbols.getInstance(Locale.US)); private DecimalFormat formatter = new DecimalFormat("#,###", DecimalFormatSymbols.getInstance(Locale.US));
private DecimalFormat bucketFormatter = new DecimalFormat("####0.###", DecimalFormatSymbols.getInstance(Locale.US));
public QuantityFormatter() { public QuantityFormatter() {
formatterWithUnits.setRoundingMode(RoundingMode.DOWN); formatterWithUnits.setRoundingMode(RoundingMode.DOWN);
@@ -42,4 +45,21 @@ public class QuantityFormatter implements IQuantityFormatter {
public String format(int qty) { public String format(int qty) {
return formatter.format(qty); return formatter.format(qty);
} }
@Override
public String formatInBucketForm(int qty) {
return bucketFormatter.format((float) qty / (float) Fluid.BUCKET_VOLUME) + " B";
}
@Override
public String formatInBucketFormWithOnlyTrailingDigitsIfZero(int qty) {
float amountRaw = ((float) qty / (float) Fluid.BUCKET_VOLUME);
int amount = (int) amountRaw;
if (amount >= 1) {
return API.instance().getQuantityFormatter().formatWithUnits(amount);
} else {
return String.format("%.1f", amountRaw);
}
}
} }

View File

@@ -2,15 +2,22 @@ package com.raoulvdberge.refinedstorage.container;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.container.slot.*; import com.raoulvdberge.refinedstorage.container.slot.*;
import com.raoulvdberge.refinedstorage.gui.GuiBase;
import com.raoulvdberge.refinedstorage.gui.GuiFluidAmount;
import com.raoulvdberge.refinedstorage.tile.TileBase; import com.raoulvdberge.refinedstorage.tile.TileBase;
import com.raoulvdberge.refinedstorage.tile.config.IType;
import com.raoulvdberge.refinedstorage.tile.data.TileDataWatcher; import com.raoulvdberge.refinedstorage.tile.data.TileDataWatcher;
import invtweaks.api.container.InventoryContainer; import invtweaks.api.container.InventoryContainer;
import net.minecraft.client.Minecraft;
import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP; import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.inventory.ClickType; import net.minecraft.inventory.ClickType;
import net.minecraft.inventory.Container; import net.minecraft.inventory.Container;
import net.minecraft.inventory.Slot; import net.minecraft.inventory.Slot;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraftforge.fml.client.FMLClientHandler;
import net.minecraftforge.fml.common.FMLCommonHandler;
import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.items.ItemHandlerHelper; import net.minecraftforge.items.ItemHandlerHelper;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@@ -77,21 +84,21 @@ public abstract class ContainerBase extends Container {
} }
if (slot instanceof SlotFilter) { if (slot instanceof SlotFilter) {
if (((SlotFilter) slot).allowsSize()) { if (((SlotFilter) slot).isSizeAllowed()) {
if (clickType == ClickType.QUICK_MOVE) { if (clickType == ClickType.QUICK_MOVE) {
slot.putStack(ItemStack.EMPTY); slot.putStack(ItemStack.EMPTY);
} else if (!player.inventory.getItemStack().isEmpty()) { } else if (!player.inventory.getItemStack().isEmpty()) {
slot.putStack(player.inventory.getItemStack().copy()); slot.putStack(ItemHandlerHelper.copyStackWithSize(player.inventory.getItemStack(), ((SlotFilter) slot).getInitialAmount(player.inventory.getItemStack())));
} else if (slot.getHasStack()) { } else if (slot.getHasStack()) {
int amount = slot.getStack().getCount(); if (slot instanceof SlotFilterType && ((SlotFilterType) slot).getType().getType() == IType.FLUIDS) {
if (FMLCommonHandler.instance().getSide() == Side.CLIENT) {
if (dragType == 0) { FMLClientHandler.instance().showGuiScreen(new GuiFluidAmount((GuiBase) Minecraft.getMinecraft().currentScreen, player, slot.getSlotIndex(), ((SlotFilterType) slot).getActualStack()));
amount = Math.max(1, amount - 1);
} else if (dragType == 1) {
amount = Math.min(slot.getStack().getMaxStackSize(), amount + 1);
} }
} else {
slot.getStack().setCount(((SlotFilter) slot).getAmountModified(dragType));
slot.getStack().setCount(amount); detectAndSendChanges();
}
} }
} else if (player.inventory.getItemStack().isEmpty()) { } else if (player.inventory.getItemStack().isEmpty()) {
slot.putStack(ItemStack.EMPTY); slot.putStack(ItemStack.EMPTY);
@@ -149,7 +156,7 @@ public abstract class ContainerBase extends Container {
if (slot instanceof SlotFilterFluid) { if (slot instanceof SlotFilterFluid) {
stackInSlot = ((SlotFilterFluid) slot).getRealStack(); stackInSlot = ((SlotFilterFluid) slot).getRealStack();
} else if (slot instanceof SlotFilterType) { } else if (slot instanceof SlotFilterType) {
stackInSlot = ((SlotFilterType) slot).getRealStack(); stackInSlot = ((SlotFilterType) slot).getActualStack();
} }
} }

View File

@@ -1,112 +1,45 @@
package com.raoulvdberge.refinedstorage.container; package com.raoulvdberge.refinedstorage.container;
import com.raoulvdberge.refinedstorage.container.slot.SlotDisabled; import com.raoulvdberge.refinedstorage.gui.grid.stack.GridStackFluid;
import com.raoulvdberge.refinedstorage.gui.grid.stack.GridStackItem;
import com.raoulvdberge.refinedstorage.gui.grid.stack.IGridStack;
import com.raoulvdberge.refinedstorage.inventory.ItemHandlerFluid;
import net.minecraft.entity.player.EntityPlayer; import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.inventory.IInventory;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.util.text.ITextComponent; import net.minecraftforge.items.IItemHandler;
import net.minecraftforge.items.ItemHandlerHelper; import net.minecraftforge.items.ItemHandlerHelper;
import net.minecraftforge.items.ItemStackHandler;
import net.minecraftforge.items.SlotItemHandler;
import javax.annotation.Nullable; import javax.annotation.Nonnull;
public class ContainerCraftingSettings extends ContainerBase { public class ContainerCraftingSettings extends ContainerBase {
public ContainerCraftingSettings(EntityPlayer player, final ItemStack stack) { public ContainerCraftingSettings(EntityPlayer player, IGridStack stack) {
super(null, player); super(null, player);
final ItemStack slot = ItemHandlerHelper.copyStackWithSize(stack, 1); IItemHandler handler = null;
addSlotToContainer(new SlotDisabled(new IInventory() { if (stack instanceof GridStackFluid) {
@Override handler = new ItemHandlerFluid(1, null);
public int getSizeInventory() {
return 1; ((ItemHandlerFluid) handler).setFluidStack(0, ((GridStackFluid) stack).getStack());
} else if (stack instanceof GridStackItem) {
handler = new ItemStackHandler(1);
((ItemStackHandler) handler).setStackInSlot(0, ItemHandlerHelper.copyStackWithSize(((GridStackItem) stack).getStack(), 1));
} }
addSlotToContainer(new SlotItemHandler(handler, 0, 89, 48) {
@Override @Override
public boolean isEmpty() { public boolean isItemValid(@Nonnull ItemStack stack) {
return true;
}
@Nullable
@Override
public ItemStack getStackInSlot(int index) {
return slot;
}
@Nullable
@Override
public ItemStack decrStackSize(int index, int count) {
return null;
}
@Nullable
@Override
public ItemStack removeStackFromSlot(int index) {
return null;
}
@Override
public void setInventorySlotContents(int index, @Nullable ItemStack stack) {
}
@Override
public int getInventoryStackLimit() {
return 0;
}
@Override
public void markDirty() {
}
@Override
public boolean isUsableByPlayer(EntityPlayer player) {
return false; return false;
} }
@Nonnull
@Override @Override
public void openInventory(EntityPlayer player) { public ItemStack getStack() {
return stack instanceof GridStackFluid ? ItemStack.EMPTY : super.getStack();
} }
});
@Override
public void closeInventory(EntityPlayer player) {
}
@Override
public boolean isItemValidForSlot(int index, ItemStack stack) {
return false;
}
@Override
public int getField(int id) {
return 0;
}
@Override
public void setField(int id, int value) {
}
@Override
public int getFieldCount() {
return 0;
}
@Override
public void clear() {
}
@Override
public String getName() {
return null;
}
@Override
public boolean hasCustomName() {
return false;
}
@Override
public ITextComponent getDisplayName() {
return null;
}
}, 0, 89, 48));
} }
} }

View File

@@ -0,0 +1,32 @@
package com.raoulvdberge.refinedstorage.container;
import com.raoulvdberge.refinedstorage.inventory.ItemHandlerFluid;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraftforge.items.ItemHandlerHelper;
import net.minecraftforge.items.SlotItemHandler;
import javax.annotation.Nonnull;
public class ContainerFluidAmount extends ContainerBase {
public ContainerFluidAmount(EntityPlayer player, ItemStack fluidContainer) {
super(null, player);
ItemHandlerFluid handler = new ItemHandlerFluid(1, null);
handler.setStackInSlot(0, ItemHandlerHelper.copyStackWithSize(fluidContainer, 1));
addSlotToContainer(new SlotItemHandler(handler, 0, 89, 48) {
@Override
public boolean isItemValid(@Nonnull ItemStack stack) {
return false;
}
@Nonnull
@Override
public ItemStack getStack() {
return ItemStack.EMPTY;
}
});
}
}

View File

@@ -49,7 +49,7 @@ public class ContainerGrid extends ContainerBase {
int headerAndSlots = getTabDelta() + display.getTopHeight() + (display.getVisibleRows() * 18); int headerAndSlots = getTabDelta() + display.getTopHeight() + (display.getVisibleRows() * 18);
if (grid.getType() != GridType.FLUID) { if (grid.getGridType() != GridType.FLUID) {
int yStart = 6; int yStart = 6;
if (grid instanceof IPortableGrid) { if (grid instanceof IPortableGrid) {
@@ -61,7 +61,7 @@ public class ContainerGrid extends ContainerBase {
} }
} }
if (grid.getType() == GridType.PATTERN) { if (grid.getGridType() == GridType.PATTERN) {
addSlotToContainer(new SlotItemHandler(((NetworkNodeGrid) grid).getPatterns(), 0, 172, headerAndSlots + 4)); addSlotToContainer(new SlotItemHandler(((NetworkNodeGrid) grid).getPatterns(), 0, 172, headerAndSlots + 4));
addSlotToContainer(new SlotItemHandler(((NetworkNodeGrid) grid).getPatterns(), 1, 172, headerAndSlots + 40)); addSlotToContainer(new SlotItemHandler(((NetworkNodeGrid) grid).getPatterns(), 1, 172, headerAndSlots + 40));
} }
@@ -72,7 +72,7 @@ public class ContainerGrid extends ContainerBase {
addPlayerInventory(8, display.getYPlayerInventory()); addPlayerInventory(8, display.getYPlayerInventory());
if (grid.getType() == GridType.CRAFTING) { if (grid.getGridType() == GridType.CRAFTING) {
int x = 26; int x = 26;
int y = headerAndSlots + 4; int y = headerAndSlots + 4;
@@ -88,14 +88,14 @@ public class ContainerGrid extends ContainerBase {
} }
addSlotToContainer(craftingResultSlot = new SlotGridCraftingResult(this, getPlayer(), grid, 0, 130 + 4, headerAndSlots + 22)); addSlotToContainer(craftingResultSlot = new SlotGridCraftingResult(this, getPlayer(), grid, 0, 130 + 4, headerAndSlots + 22));
} else if (grid.getType() == GridType.PATTERN) { } else if (grid.getGridType() == GridType.PATTERN) {
if (((NetworkNodeGrid) grid).isProcessingPattern()) { if (((NetworkNodeGrid) grid).isProcessingPattern()) {
int ox = 8; int ox = 8;
int x = ox; int x = ox;
int y = headerAndSlots + 4; int y = headerAndSlots + 4;
for (int i = 0; i < 9 * 2; ++i) { for (int i = 0; i < 9 * 2; ++i) {
addSlotToContainer(new SlotFilter(((NetworkNodeGrid) grid).getProcessingMatrix(), i, x, y, SlotFilter.FILTER_ALLOW_SIZE)); addSlotToContainer(new SlotFilterType((NetworkNodeGrid) grid, i, x, y, SlotFilter.FILTER_ALLOW_SIZE));
x += 18; x += 18;
@@ -210,7 +210,7 @@ public class ContainerGrid extends ContainerBase {
if (slot.getHasStack()) { if (slot.getHasStack()) {
if (grid instanceof IPortableGrid && slot.slotNumber == 4) { // Prevent moving disk slot into portable grid itself if (grid instanceof IPortableGrid && slot.slotNumber == 4) { // Prevent moving disk slot into portable grid itself
return ItemStack.EMPTY; return ItemStack.EMPTY;
} else if (grid.getType() == GridType.PATTERN && slot.slotNumber == 5) { // From output slot to inventory } else if (grid.getGridType() == GridType.PATTERN && slot.slotNumber == 5) { // From output slot to inventory
ItemStack stack = slot.getStack(); ItemStack stack = slot.getStack();
int startIndex = 5; int startIndex = 5;
@@ -231,7 +231,7 @@ public class ContainerGrid extends ContainerBase {
} else if (slot != patternResultSlot && !(slot instanceof SlotFilterLegacy)) { } else if (slot != patternResultSlot && !(slot instanceof SlotFilterLegacy)) {
ItemStack stack = slot.getStack(); ItemStack stack = slot.getStack();
if (grid.getType() != GridType.FLUID && stack.getItem() == RSItems.FILTER) { if (grid.getGridType() != GridType.FLUID && stack.getItem() == RSItems.FILTER) {
int startIndex = 0; int startIndex = 0;
int endIndex = 4; int endIndex = 4;
@@ -239,7 +239,7 @@ public class ContainerGrid extends ContainerBase {
if (slotIndex < 4) { if (slotIndex < 4) {
startIndex = 4; startIndex = 4;
if (grid.getType() == GridType.PATTERN) { if (grid.getGridType() == GridType.PATTERN) {
startIndex += 2; // Skip the pattern slots startIndex += 2; // Skip the pattern slots
} }
@@ -258,7 +258,7 @@ public class ContainerGrid extends ContainerBase {
return ItemStack.EMPTY; return ItemStack.EMPTY;
} }
} else if ((grid.getType() == GridType.PATTERN && stack.getItem() == RSItems.PATTERN) || (grid instanceof IPortableGrid && stack.getItem() instanceof IStorageDiskFactory)) { } else if ((grid.getGridType() == GridType.PATTERN && stack.getItem() == RSItems.PATTERN) || (grid instanceof IPortableGrid && stack.getItem() instanceof IStorageDiskFactory)) {
int startIndex = 4; int startIndex = 4;
int endIndex = startIndex + 1; int endIndex = startIndex + 1;
@@ -287,7 +287,7 @@ public class ContainerGrid extends ContainerBase {
} }
} }
if (grid.getType() == GridType.FLUID) { if (grid.getGridType() == GridType.FLUID) {
IFluidGridHandler fluidHandler = grid.getFluidHandler(); IFluidGridHandler fluidHandler = grid.getFluidHandler();
if (fluidHandler != null) { if (fluidHandler != null) {

View File

@@ -31,7 +31,7 @@ public class SlotFilter extends SlotItemHandler {
@Override @Override
public boolean isItemValid(@Nonnull ItemStack stack) { public boolean isItemValid(@Nonnull ItemStack stack) {
if (super.isItemValid(stack)) { if (super.isItemValid(stack)) {
if (allowsBlocks()) { if (isBlockAllowed()) {
return stack.getItem() instanceof ItemBlock || stack.getItem() instanceof ItemBlockSpecial || stack.getItem() instanceof IPlantable || stack.getItem() instanceof ItemSkull; return stack.getItem() instanceof ItemBlock || stack.getItem() instanceof ItemBlockSpecial || stack.getItem() instanceof IPlantable || stack.getItem() instanceof ItemSkull;
} }
@@ -43,21 +43,37 @@ public class SlotFilter extends SlotItemHandler {
@Override @Override
public void putStack(@Nonnull ItemStack stack) { public void putStack(@Nonnull ItemStack stack) {
if (!stack.isEmpty() && !allowsSize()) { if (!stack.isEmpty() && !isSizeAllowed()) {
stack.setCount(1); stack.setCount(1);
} }
super.putStack(stack); super.putStack(stack);
} }
public boolean allowsSize() { public boolean isSizeAllowed() {
return (flags & FILTER_ALLOW_SIZE) == FILTER_ALLOW_SIZE; return (flags & FILTER_ALLOW_SIZE) == FILTER_ALLOW_SIZE;
} }
public boolean allowsBlocks() { public boolean isBlockAllowed() {
return (flags & FILTER_ALLOW_BLOCKS) == FILTER_ALLOW_BLOCKS; return (flags & FILTER_ALLOW_BLOCKS) == FILTER_ALLOW_BLOCKS;
} }
public int getAmountModified(int dragType) {
int amount = getStack().getCount();
if (dragType == 0) {
amount = Math.max(1, amount - 1);
} else if (dragType == 1) {
amount = Math.min(getStack().getMaxStackSize(), amount + 1);
}
return amount;
}
public int getInitialAmount(ItemStack stack) {
return stack.getCount();
}
@Nullable @Nullable
public static IBlockState getBlockState(IBlockAccess world, BlockPos pos, @Nullable ItemStack stack) { public static IBlockState getBlockState(IBlockAccess world, BlockPos pos, @Nullable ItemStack stack) {
if (stack != null) { if (stack != null) {

View File

@@ -3,6 +3,7 @@ package com.raoulvdberge.refinedstorage.container.slot;
import com.raoulvdberge.refinedstorage.apiimpl.network.node.NetworkNode; import com.raoulvdberge.refinedstorage.apiimpl.network.node.NetworkNode;
import com.raoulvdberge.refinedstorage.tile.config.IType; import com.raoulvdberge.refinedstorage.tile.config.IType;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraftforge.fluids.Fluid;
import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.IItemHandler;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
@@ -26,13 +27,8 @@ public class SlotFilterType extends SlotFilter {
} }
@Override @Override
public boolean allowsSize() { public boolean isBlockAllowed() {
return super.allowsSize() && type.getType() != IType.FLUIDS; return super.isBlockAllowed() && type.getType() == IType.ITEMS;
}
@Override
public boolean allowsBlocks() {
return super.allowsBlocks() && type.getType() == IType.ITEMS;
} }
@Override @Override
@@ -41,7 +37,20 @@ public class SlotFilterType extends SlotFilter {
return (type.getType() == IType.ITEMS || !((NetworkNode) type).getWorld().isRemote) ? super.getStack() : ItemStack.EMPTY; return (type.getType() == IType.ITEMS || !((NetworkNode) type).getWorld().isRemote) ? super.getStack() : ItemStack.EMPTY;
} }
public ItemStack getRealStack() { public ItemStack getActualStack() {
return super.getStack(); return super.getStack();
} }
public IType getType() {
return type;
}
@Override
public int getInitialAmount(ItemStack stack) {
if (type.getType() == IType.FLUIDS && isSizeAllowed()) {
return Fluid.BUCKET_VOLUME;
}
return super.getInitialAmount(stack);
}
} }

View File

@@ -3,6 +3,7 @@ package com.raoulvdberge.refinedstorage.gui;
import com.raoulvdberge.refinedstorage.RS; import com.raoulvdberge.refinedstorage.RS;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawer; import com.raoulvdberge.refinedstorage.api.render.IElementDrawer;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawers; import com.raoulvdberge.refinedstorage.api.render.IElementDrawers;
import com.raoulvdberge.refinedstorage.container.slot.SlotFilterType;
import com.raoulvdberge.refinedstorage.gui.control.Scrollbar; import com.raoulvdberge.refinedstorage.gui.control.Scrollbar;
import com.raoulvdberge.refinedstorage.gui.control.SideButton; import com.raoulvdberge.refinedstorage.gui.control.SideButton;
import com.raoulvdberge.refinedstorage.integration.jei.IntegrationJEI; import com.raoulvdberge.refinedstorage.integration.jei.IntegrationJEI;
@@ -24,6 +25,7 @@ import net.minecraftforge.fml.client.config.GuiUtils;
import net.minecraftforge.items.SlotItemHandler; import net.minecraftforge.items.SlotItemHandler;
import org.lwjgl.input.Keyboard; import org.lwjgl.input.Keyboard;
import org.lwjgl.input.Mouse; import org.lwjgl.input.Mouse;
import org.lwjgl.opengl.GL11;
import javax.annotation.Nonnull; import javax.annotation.Nonnull;
import javax.annotation.Nullable; import javax.annotation.Nullable;
@@ -187,6 +189,16 @@ public abstract class GuiBase extends GuiContainer {
if (stack != null) { if (stack != null) {
FLUID_RENDERER.draw(mc, guiLeft + slot.xPos, guiTop + slot.yPos, stack); FLUID_RENDERER.draw(mc, guiLeft + slot.xPos, guiTop + slot.yPos, stack);
if (slot instanceof SlotFilterType) {
int count = ((SlotFilterType) slot).getActualStack().getCount();
if (count != 1) {
drawQuantity(guiLeft + slot.xPos, guiTop + slot.yPos, String.valueOf(count));
GL11.glDisable(GL11.GL_LIGHTING);
}
}
if (inBounds(guiLeft + slot.xPos, guiTop + slot.yPos, 18, 18, mouseX, mouseY)) { if (inBounds(guiLeft + slot.xPos, guiTop + slot.yPos, 18, 18, mouseX, mouseY)) {
this.hoveringFluid = stack.getLocalizedName(); this.hoveringFluid = stack.getLocalizedName();
} }

View File

@@ -4,11 +4,13 @@ import com.google.common.base.Optional;
import com.google.common.collect.Lists; import com.google.common.collect.Lists;
import com.raoulvdberge.refinedstorage.RS; import com.raoulvdberge.refinedstorage.RS;
import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElement; import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElement;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.api.network.grid.IGrid; import com.raoulvdberge.refinedstorage.api.network.grid.IGrid;
import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab; import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawer; import com.raoulvdberge.refinedstorage.api.render.IElementDrawer;
import com.raoulvdberge.refinedstorage.api.render.IElementDrawers; import com.raoulvdberge.refinedstorage.api.render.IElementDrawers;
import com.raoulvdberge.refinedstorage.api.util.IFilter; import com.raoulvdberge.refinedstorage.api.util.IFilter;
import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.container.ContainerCraftingMonitor; import com.raoulvdberge.refinedstorage.container.ContainerCraftingMonitor;
import com.raoulvdberge.refinedstorage.gui.control.Scrollbar; import com.raoulvdberge.refinedstorage.gui.control.Scrollbar;
import com.raoulvdberge.refinedstorage.gui.control.SideButtonGridSize; import com.raoulvdberge.refinedstorage.gui.control.SideButtonGridSize;
@@ -23,6 +25,7 @@ import net.minecraft.client.renderer.GlStateManager;
import net.minecraft.client.renderer.RenderHelper; import net.minecraft.client.renderer.RenderHelper;
import net.minecraft.client.resources.I18n; import net.minecraft.client.resources.I18n;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraftforge.fluids.FluidStack;
import javax.annotation.Nullable; import javax.annotation.Nullable;
import java.io.IOException; import java.io.IOException;
@@ -46,12 +49,12 @@ public class GuiCraftingMonitor extends GuiBase implements IResizableDisplay {
public static class CraftingMonitorTask implements IGridTab { public static class CraftingMonitorTask implements IGridTab {
private UUID id; private UUID id;
private ItemStack requested; private ICraftingRequestInfo requested;
private int qty; private int qty;
private long executionStarted; private long executionStarted;
private List<ICraftingMonitorElement> elements; private List<ICraftingMonitorElement> elements;
public CraftingMonitorTask(UUID id, ItemStack requested, int qty, long executionStarted, List<ICraftingMonitorElement> elements) { public CraftingMonitorTask(UUID id, ICraftingRequestInfo requested, int qty, long executionStarted, List<ICraftingMonitorElement> elements) {
this.id = id; this.id = id;
this.requested = requested; this.requested = requested;
this.qty = qty; this.qty = qty;
@@ -66,22 +69,26 @@ public class GuiCraftingMonitor extends GuiBase implements IResizableDisplay {
@Override @Override
public void drawTooltip(int x, int y, int screenWidth, int screenHeight, FontRenderer fontRenderer) { public void drawTooltip(int x, int y, int screenWidth, int screenHeight, FontRenderer fontRenderer) {
List<String> textLines = Lists.newArrayList(requested.getDisplayName()); List<String> textLines = Lists.newArrayList(requested.getItem() != null ? requested.getItem().getDisplayName() : requested.getFluid().getLocalizedName());
List<String> smallTextLines = Lists.newArrayList(); List<String> smallTextLines = Lists.newArrayList();
int totalSecs = (int) (System.currentTimeMillis() - executionStarted) / 1000; int totalSecs = (int) (System.currentTimeMillis() - executionStarted) / 1000;
int minutes = (totalSecs % 3600) / 60; int minutes = (totalSecs % 3600) / 60;
int seconds = totalSecs % 60; int seconds = totalSecs % 60;
smallTextLines.add(I18n.format("gui.refinedstorage:crafting_monitor.tooltip.requested", qty)); smallTextLines.add(I18n.format("gui.refinedstorage:crafting_monitor.tooltip.requested", requested.getFluid() != null ? API.instance().getQuantityFormatter().formatInBucketForm(qty) : API.instance().getQuantityFormatter().format(qty)));
smallTextLines.add(String.format("%02d:%02d", minutes, seconds)); smallTextLines.add(String.format("%02d:%02d", minutes, seconds));
RenderUtils.drawTooltipWithSmallText(textLines, smallTextLines, true, ItemStack.EMPTY, x, y, screenWidth, screenHeight, fontRenderer); RenderUtils.drawTooltipWithSmallText(textLines, smallTextLines, true, ItemStack.EMPTY, x, y, screenWidth, screenHeight, fontRenderer);
} }
@Override @Override
public ItemStack getIcon() { public void drawIcon(int x, int y, IElementDrawer<ItemStack> itemDrawer, IElementDrawer<FluidStack> fluidDrawer) {
return requested; if (requested.getItem() != null) {
itemDrawer.draw(x, y, requested.getItem());
} else {
fluidDrawer.draw(x, y, requested.getFluid());
}
} }
} }
@@ -105,7 +112,7 @@ public class GuiCraftingMonitor extends GuiBase implements IResizableDisplay {
this.craftingMonitor = craftingMonitor; this.craftingMonitor = craftingMonitor;
this.tabs = new TabList(this, () -> tasks, () -> (int) Math.floor((float) Math.max(0, tasks.size() - 1) / (float) ICraftingMonitor.TABS_PER_PAGE), craftingMonitor::getTabPage, () -> { this.tabs = new TabList(this, new ElementDrawers(), () -> tasks, () -> (int) Math.floor((float) Math.max(0, tasks.size() - 1) / (float) ICraftingMonitor.TABS_PER_PAGE), craftingMonitor::getTabPage, () -> {
IGridTab tab = getCurrentTab(); IGridTab tab = getCurrentTab();
if (tab == null) { if (tab == null) {

View File

@@ -31,6 +31,7 @@ import java.io.IOException;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.List; import java.util.List;
// TODO: Make bigger/resizeable and allow more space?
public class GuiCraftingPreview extends GuiBase { public class GuiCraftingPreview extends GuiBase {
public class CraftingPreviewElementDrawers extends ElementDrawers { public class CraftingPreviewElementDrawers extends ElementDrawers {
private IElementDrawer<Integer> overlayDrawer = (x, y, colour) -> { private IElementDrawer<Integer> overlayDrawer = (x, y, colour) -> {
@@ -61,7 +62,9 @@ public class GuiCraftingPreview extends GuiBase {
private IElementDrawers drawers = new CraftingPreviewElementDrawers(); private IElementDrawers drawers = new CraftingPreviewElementDrawers();
public GuiCraftingPreview(GuiScreen parent, List<ICraftingPreviewElement> stacks, int hash, int quantity) { private boolean fluids;
public GuiCraftingPreview(GuiScreen parent, List<ICraftingPreviewElement> stacks, int hash, int quantity, boolean fluids) {
super(new Container() { super(new Container() {
@Override @Override
public boolean canInteractWith(EntityPlayer player) { public boolean canInteractWith(EntityPlayer player) {
@@ -74,6 +77,7 @@ public class GuiCraftingPreview extends GuiBase {
this.hash = hash; this.hash = hash;
this.quantity = quantity; this.quantity = quantity;
this.fluids = fluids;
this.scrollbar = new Scrollbar(149, 20, 12, 119); this.scrollbar = new Scrollbar(149, 20, 12, 119);
} }
@@ -247,7 +251,7 @@ public class GuiCraftingPreview extends GuiBase {
} }
private void startRequest() { private void startRequest() {
RS.INSTANCE.network.sendToServer(new MessageGridCraftingStart(hash, quantity)); RS.INSTANCE.network.sendToServer(new MessageGridCraftingStart(hash, quantity, fluids));
close(); close();
} }

View File

@@ -0,0 +1,66 @@
package com.raoulvdberge.refinedstorage.gui;
import com.google.common.primitives.Ints;
import com.raoulvdberge.refinedstorage.RS;
import com.raoulvdberge.refinedstorage.container.ContainerFluidAmount;
import com.raoulvdberge.refinedstorage.gui.grid.GuiCraftingStart;
import com.raoulvdberge.refinedstorage.network.MessageGridFluidAmount;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraftforge.fluids.Fluid;
public class GuiFluidAmount extends GuiCraftingStart {
private int slot;
private ItemStack fluidContainer;
public GuiFluidAmount(GuiBase parent, EntityPlayer player, int slot, ItemStack fluidContainer) {
super(parent, null, new ContainerFluidAmount(player, fluidContainer), 172, 99);
this.slot = slot;
this.fluidContainer = fluidContainer;
}
@Override
protected int getAmount() {
return fluidContainer.getCount();
}
@Override
protected String getStartButtonText() {
return t("misc.refinedstorage:set");
}
@Override
protected String getTitle() {
return t("gui.refinedstorage:pattern_grid.fluid_amount");
}
@Override
protected boolean canAmountGoNegative() {
return false;
}
@Override
protected int[] getIncrements() {
return new int[]{
10, 50, 100,
-10, -50, -100
};
}
@Override
protected int getMaxAmount() {
return Fluid.BUCKET_VOLUME;
}
@Override
protected void startRequest(boolean noPreview) {
Integer amount = Ints.tryParse(amountField.getText());
if (amount != null && amount > 0 && amount <= Fluid.BUCKET_VOLUME) {
RS.INSTANCE.network.sendToServer(new MessageGridFluidAmount(slot, amount));
close();
}
}
}

View File

@@ -38,7 +38,7 @@ public class SideButtonGridSortingType extends SideButton {
if (type == IGrid.SORTING_TYPE_QUANTITY) { if (type == IGrid.SORTING_TYPE_QUANTITY) {
type = IGrid.SORTING_TYPE_NAME; type = IGrid.SORTING_TYPE_NAME;
} else if (type == IGrid.SORTING_TYPE_NAME) { } else if (type == IGrid.SORTING_TYPE_NAME) {
if (grid.getType() == GridType.FLUID) { if (grid.getGridType() == GridType.FLUID) {
type = IGrid.SORTING_TYPE_LAST_MODIFIED; type = IGrid.SORTING_TYPE_LAST_MODIFIED;
} else { } else {
type = IGrid.SORTING_TYPE_ID; type = IGrid.SORTING_TYPE_ID;
@@ -46,7 +46,7 @@ public class SideButtonGridSortingType extends SideButton {
} else if (type == IGrid.SORTING_TYPE_ID) { } else if (type == IGrid.SORTING_TYPE_ID) {
type = IGrid.SORTING_TYPE_LAST_MODIFIED; type = IGrid.SORTING_TYPE_LAST_MODIFIED;
} else if (type == NetworkNodeGrid.SORTING_TYPE_LAST_MODIFIED) { } else if (type == NetworkNodeGrid.SORTING_TYPE_LAST_MODIFIED) {
if (grid.getType() == GridType.FLUID || !Loader.isModLoaded(GridSorterInventoryTweaks.MOD_ID)) { if (grid.getGridType() == GridType.FLUID || !Loader.isModLoaded(GridSorterInventoryTweaks.MOD_ID)) {
type = IGrid.SORTING_TYPE_QUANTITY; type = IGrid.SORTING_TYPE_QUANTITY;
} else { } else {
type = IGrid.SORTING_TYPE_INVENTORYTWEAKS; type = IGrid.SORTING_TYPE_INVENTORYTWEAKS;

View File

@@ -4,7 +4,6 @@ import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab;
import com.raoulvdberge.refinedstorage.gui.GuiBase; import com.raoulvdberge.refinedstorage.gui.GuiBase;
import net.minecraft.client.gui.FontRenderer; import net.minecraft.client.gui.FontRenderer;
import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiButton;
import net.minecraft.client.renderer.RenderHelper;
import java.util.LinkedList; import java.util.LinkedList;
import java.util.List; import java.util.List;
@@ -18,6 +17,7 @@ public class TabList {
} }
private GuiBase gui; private GuiBase gui;
private GuiBase.ElementDrawers drawers;
private Supplier<List<IGridTab>> tabs; private Supplier<List<IGridTab>> tabs;
private int tabHovering; private int tabHovering;
@@ -34,8 +34,9 @@ public class TabList {
private int width; private int width;
public TabList(GuiBase gui, Supplier<List<IGridTab>> tabs, Supplier<Integer> pages, Supplier<Integer> page, Supplier<Integer> selected, int tabsPerPage) { public TabList(GuiBase gui, GuiBase.ElementDrawers drawers, Supplier<List<IGridTab>> tabs, Supplier<Integer> pages, Supplier<Integer> page, Supplier<Integer> selected, int tabsPerPage) {
this.gui = gui; this.gui = gui;
this.drawers = drawers;
this.tabs = tabs; this.tabs = tabs;
this.pages = pages; this.pages = pages;
this.page = page; this.page = page;
@@ -138,9 +139,7 @@ public class TabList {
gui.drawTexture(tx, ty, uvx, uvy, tbw, IGridTab.TAB_HEIGHT); gui.drawTexture(tx, ty, uvx, uvy, tbw, IGridTab.TAB_HEIGHT);
RenderHelper.enableGUIStandardItemLighting(); tab.drawIcon(otx + 6, ty + 9 - (!isSelected ? 3 : 0), drawers.getItemDrawer(), drawers.getFluidDrawer());
gui.drawItem(otx + 6, ty + 9 - (!isSelected ? 3 : 0), tab.getIcon());
} }
public void drawTooltip(FontRenderer fontRenderer, int mouseX, int mouseY) { public void drawTooltip(FontRenderer fontRenderer, int mouseX, int mouseY) {

View File

@@ -4,7 +4,8 @@ import com.google.common.primitives.Ints;
import com.raoulvdberge.refinedstorage.RS; import com.raoulvdberge.refinedstorage.RS;
import com.raoulvdberge.refinedstorage.container.ContainerCraftingSettings; import com.raoulvdberge.refinedstorage.container.ContainerCraftingSettings;
import com.raoulvdberge.refinedstorage.gui.GuiBase; import com.raoulvdberge.refinedstorage.gui.GuiBase;
import com.raoulvdberge.refinedstorage.gui.grid.stack.GridStackItem; import com.raoulvdberge.refinedstorage.gui.grid.stack.GridStackFluid;
import com.raoulvdberge.refinedstorage.gui.grid.stack.IGridStack;
import com.raoulvdberge.refinedstorage.network.MessageGridCraftingPreview; import com.raoulvdberge.refinedstorage.network.MessageGridCraftingPreview;
import net.minecraft.client.gui.GuiButton; import net.minecraft.client.gui.GuiButton;
import net.minecraft.client.gui.GuiTextField; import net.minecraft.client.gui.GuiTextField;
@@ -16,25 +17,27 @@ import org.lwjgl.input.Keyboard;
import java.io.IOException; import java.io.IOException;
// TODO: Change quantities for fluid craft.
// TODO: Cleanup childclasses.
public class GuiCraftingStart extends GuiBase { public class GuiCraftingStart extends GuiBase {
private static final int DEFAULT_AMOUNT = 1; private static final int DEFAULT_AMOUNT = 1;
protected GuiTextField amountField; protected GuiTextField amountField;
private GuiBase parent; private GuiBase parent;
private GridStackItem stack; private IGridStack stack;
private GuiButton startButton; private GuiButton startButton;
private GuiButton cancelButton; private GuiButton cancelButton;
private GuiButton[] incrementButtons = new GuiButton[6]; private GuiButton[] incrementButtons = new GuiButton[6];
public GuiCraftingStart(GuiBase parent, GridStackItem stack, Container container, int w, int h) { public GuiCraftingStart(GuiBase parent, IGridStack stack, Container container, int w, int h) {
super(container, w, h); super(container, w, h);
this.parent = parent; this.parent = parent;
this.stack = stack; this.stack = stack;
} }
public GuiCraftingStart(GuiGrid parent, EntityPlayer player, GridStackItem stack) { public GuiCraftingStart(GuiGrid parent, EntityPlayer player, IGridStack stack) {
this(parent, stack, new ContainerCraftingSettings(player, stack.getStack()), 172, 99); this(parent, stack, new ContainerCraftingSettings(player, stack), 172, 99);
} }
protected String getStartButtonText() { protected String getStartButtonText() {
@@ -50,14 +53,21 @@ public class GuiCraftingStart extends GuiBase {
} }
protected int[] getIncrements() { protected int[] getIncrements() {
if (stack instanceof GridStackFluid) {
return new int[]{
1, 500, 1000,
-1, -500, -1000
};
} else {
return new int[]{ return new int[]{
1, 10, 64, 1, 10, 64,
-1, -10, -64 -1, -10, -64
}; };
} }
}
protected int getAmount() { protected int getAmount() {
return DEFAULT_AMOUNT; return stack instanceof GridStackFluid ? 1000 : DEFAULT_AMOUNT;
} }
protected Tuple<Integer, Integer> getAmountPos() { protected Tuple<Integer, Integer> getAmountPos() {
@@ -164,6 +174,10 @@ public class GuiCraftingStart extends GuiBase {
newAmount = oldAmount + newAmount; newAmount = oldAmount + newAmount;
} }
if (newAmount > getMaxAmount()) {
newAmount = getMaxAmount();
}
amountField.setText(String.valueOf(newAmount)); amountField.setText(String.valueOf(newAmount));
break; break;
@@ -172,11 +186,15 @@ public class GuiCraftingStart extends GuiBase {
} }
} }
protected int getMaxAmount() {
return Integer.MAX_VALUE;
}
protected void startRequest(boolean noPreview) { protected void startRequest(boolean noPreview) {
Integer quantity = Ints.tryParse(amountField.getText()); Integer quantity = Ints.tryParse(amountField.getText());
if (quantity != null && quantity > 0) { if (quantity != null && quantity > 0) {
RS.INSTANCE.network.sendToServer(new MessageGridCraftingPreview(stack.getHash(), quantity, noPreview)); RS.INSTANCE.network.sendToServer(new MessageGridCraftingPreview(stack.getHash(), quantity, noPreview, stack instanceof GridStackFluid));
startButton.enabled = false; startButton.enabled = false;
} }

View File

@@ -55,7 +55,7 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
private int slotNumber; private int slotNumber;
public GuiGrid(ContainerGrid container, IGrid grid) { public GuiGrid(ContainerGrid container, IGrid grid) {
super(container, grid.getType() == GridType.FLUID ? 193 : 227, 0); super(container, grid.getGridType() == GridType.FLUID ? 193 : 227, 0);
IGridSorter defaultSorter; IGridSorter defaultSorter;
@@ -67,9 +67,9 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
sorters.add(new GridSorterLastModified()); sorters.add(new GridSorterLastModified());
this.grid = grid; this.grid = grid;
this.view = grid.getType() == GridType.FLUID ? new GridViewFluid(this, defaultSorter, sorters) : new GridViewItem(this, defaultSorter, sorters); this.view = grid.getGridType() == GridType.FLUID ? new GridViewFluid(this, defaultSorter, sorters) : new GridViewItem(this, defaultSorter, sorters);
this.wasConnected = this.grid.isActive(); this.wasConnected = this.grid.isActive();
this.tabs = new TabList(this, grid::getTabs, grid::getTotalTabPages, grid::getTabPage, grid::getTabSelected, IGrid.TABS_PER_PAGE); this.tabs = new TabList(this, new ElementDrawers(), grid::getTabs, grid::getTotalTabPages, grid::getTabPage, grid::getTabSelected, IGrid.TABS_PER_PAGE);
this.tabs.addListener(new TabList.ITabListListener() { this.tabs.addListener(new TabList.ITabListListener() {
@Override @Override
public void onSelectionChanged(int tab) { public void onSelectionChanged(int tab) {
@@ -113,12 +113,7 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
searchField.y = sy; searchField.y = sy;
} }
if (grid.getType() == GridType.PATTERN) { if (grid.getGridType() != GridType.FLUID && grid.getViewType() != -1) {
processingPattern = addCheckBox(x + 7, y + tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 60, t("misc.refinedstorage:processing"), TileGrid.PROCESSING_PATTERN.getValue());
oredictPattern = addCheckBox(processingPattern.x + processingPattern.width + 5, y + tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 60, t("misc.refinedstorage:oredict"), TileGrid.OREDICT_PATTERN.getValue());
}
if (grid.getType() != GridType.FLUID && grid.getViewType() != -1) {
addSideButton(new SideButtonGridViewType(this, grid)); addSideButton(new SideButtonGridViewType(this, grid));
} }
@@ -127,6 +122,13 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
addSideButton(new SideButtonGridSearchBoxMode(this)); addSideButton(new SideButtonGridSearchBoxMode(this));
addSideButton(new SideButtonGridSize(this, () -> grid.getSize(), size -> grid.onSizeChanged(size))); addSideButton(new SideButtonGridSize(this, () -> grid.getSize(), size -> grid.onSizeChanged(size)));
if (grid.getGridType() == GridType.PATTERN) {
processingPattern = addCheckBox(x + 7, y + tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 60, t("misc.refinedstorage:processing"), TileGrid.PROCESSING_PATTERN.getValue());
oredictPattern = addCheckBox(processingPattern.x + processingPattern.width + 5, y + tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 60, t("misc.refinedstorage:oredict"), TileGrid.OREDICT_PATTERN.getValue());
addSideButton(new SideButtonType(this, TileGrid.PROCESSING_TYPE));
}
updateScrollbar(); updateScrollbar();
} }
@@ -161,9 +163,9 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
@Override @Override
public int getBottomHeight() { public int getBottomHeight() {
if (grid.getType() == GridType.CRAFTING) { if (grid.getGridType() == GridType.CRAFTING) {
return 156; return 156;
} else if (grid.getType() == GridType.PATTERN) { } else if (grid.getGridType() == GridType.PATTERN) {
return 169; return 169;
} else { } else {
return 99; return 99;
@@ -174,11 +176,11 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
public int getYPlayerInventory() { public int getYPlayerInventory() {
int yp = tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18); int yp = tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18);
if (grid.getType() == GridType.NORMAL || grid.getType() == GridType.FLUID) { if (grid.getGridType() == GridType.NORMAL || grid.getGridType() == GridType.FLUID) {
yp += 16; yp += 16;
} else if (grid.getType() == GridType.CRAFTING) { } else if (grid.getGridType() == GridType.CRAFTING) {
yp += 73; yp += 73;
} else if (grid.getType() == GridType.PATTERN) { } else if (grid.getGridType() == GridType.PATTERN) {
yp += 86; yp += 86;
} }
@@ -237,7 +239,7 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
private boolean isOverClear(int mouseX, int mouseY) { private boolean isOverClear(int mouseX, int mouseY) {
int y = tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 4; int y = tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 4;
switch (grid.getType()) { switch (grid.getGridType()) {
case CRAFTING: case CRAFTING:
return inBounds(82, y, 7, 7, mouseX, mouseY); return inBounds(82, y, 7, 7, mouseX, mouseY);
case PATTERN: case PATTERN:
@@ -252,16 +254,16 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
} }
private boolean isOverCreatePattern(int mouseX, int mouseY) { private boolean isOverCreatePattern(int mouseX, int mouseY) {
return grid.getType() == GridType.PATTERN && inBounds(172, tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 22, 16, 16, mouseX, mouseY) && ((NetworkNodeGrid) grid).canCreatePattern(); return grid.getGridType() == GridType.PATTERN && inBounds(172, tabs.getHeight() + getTopHeight() + (getVisibleRows() * 18) + 22, 16, 16, mouseX, mouseY) && ((NetworkNodeGrid) grid).canCreatePattern();
} }
@Override @Override
public void drawBackground(int x, int y, int mouseX, int mouseY) { public void drawBackground(int x, int y, int mouseX, int mouseY) {
tabs.drawBackground(x, y); tabs.drawBackground(x, y);
if (grid.getType() == GridType.CRAFTING) { if (grid.getGridType() == GridType.CRAFTING) {
bindTexture("gui/crafting_grid.png"); bindTexture("gui/crafting_grid.png");
} else if (grid.getType() == GridType.PATTERN) { } else if (grid.getGridType() == GridType.PATTERN) {
bindTexture("gui/pattern_grid" + (((NetworkNodeGrid) grid).isProcessingPattern() ? "_processing" : "") + ".png"); bindTexture("gui/pattern_grid" + (((NetworkNodeGrid) grid).isProcessingPattern() ? "_processing" : "") + ".png");
} else if (grid instanceof IPortableGrid) { } else if (grid instanceof IPortableGrid) {
bindTexture("gui/portable_grid.png"); bindTexture("gui/portable_grid.png");
@@ -271,9 +273,9 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
int yy = y + tabs.getHeight(); int yy = y + tabs.getHeight();
drawTexture(x, yy, 0, 0, screenWidth - (grid.getType() != GridType.FLUID ? 34 : 0), getTopHeight()); drawTexture(x, yy, 0, 0, screenWidth - (grid.getGridType() != GridType.FLUID ? 34 : 0), getTopHeight());
if (grid.getType() != GridType.FLUID) { if (grid.getGridType() != GridType.FLUID) {
drawTexture(x + screenWidth - 34 + 4, y + tabs.getHeight(), 197, 0, 30, grid instanceof IPortableGrid ? 114 : 82); drawTexture(x + screenWidth - 34 + 4, y + tabs.getHeight(), 197, 0, 30, grid instanceof IPortableGrid ? 114 : 82);
} }
@@ -282,14 +284,14 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
for (int i = 0; i < rows; ++i) { for (int i = 0; i < rows; ++i) {
yy += 18; yy += 18;
drawTexture(x, yy, 0, getTopHeight() + (i > 0 ? (i == rows - 1 ? 18 * 2 : 18) : 0), screenWidth - (grid.getType() != GridType.FLUID ? 34 : 0), 18); drawTexture(x, yy, 0, getTopHeight() + (i > 0 ? (i == rows - 1 ? 18 * 2 : 18) : 0), screenWidth - (grid.getGridType() != GridType.FLUID ? 34 : 0), 18);
} }
yy += 18; yy += 18;
drawTexture(x, yy, 0, getTopHeight() + (18 * 3), screenWidth - (grid.getType() != GridType.FLUID ? 34 : 0), getBottomHeight()); drawTexture(x, yy, 0, getTopHeight() + (18 * 3), screenWidth - (grid.getGridType() != GridType.FLUID ? 34 : 0), getBottomHeight());
if (grid.getType() == GridType.PATTERN) { if (grid.getGridType() == GridType.PATTERN) {
int ty = 0; int ty = 0;
if (isOverCreatePattern(mouseX - guiLeft, mouseY - guiTop)) { if (isOverCreatePattern(mouseX - guiLeft, mouseY - guiTop)) {
@@ -383,7 +385,7 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
List<String> textLines = Lists.newArrayList(gridStack.getTooltip().split("\n")); List<String> textLines = Lists.newArrayList(gridStack.getTooltip().split("\n"));
List<String> smallTextLines = Lists.newArrayList(); List<String> smallTextLines = Lists.newArrayList();
if (!(gridStack instanceof GridStackItem) || !((GridStackItem) gridStack).doesDisplayCraftText()) { if (!gridStack.doesDisplayCraftText()) {
smallTextLines.add(I18n.format("misc.refinedstorage:total", gridStack.getFormattedFullQuantity())); smallTextLines.add(I18n.format("misc.refinedstorage:total", gridStack.getFormattedFullQuantity()));
} }
@@ -439,16 +441,21 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
ItemStack held = ((ContainerGrid) this.inventorySlots).getPlayer().inventory.getItemStack(); ItemStack held = ((ContainerGrid) this.inventorySlots).getPlayer().inventory.getItemStack();
if (isOverSlotArea(mouseX - guiLeft, mouseY - guiTop) && !held.isEmpty() && (clickedButton == 0 || clickedButton == 1)) { if (isOverSlotArea(mouseX - guiLeft, mouseY - guiTop) && !held.isEmpty() && (clickedButton == 0 || clickedButton == 1)) {
RS.INSTANCE.network.sendToServer(grid.getType() == GridType.FLUID ? new MessageGridFluidInsertHeld() : new MessageGridItemInsertHeld(clickedButton == 1)); RS.INSTANCE.network.sendToServer(grid.getGridType() == GridType.FLUID ? new MessageGridFluidInsertHeld() : new MessageGridItemInsertHeld(clickedButton == 1));
} }
if (isOverSlotWithStack()) { if (isOverSlotWithStack()) {
if (grid.getType() != GridType.FLUID && (held.isEmpty() || (!held.isEmpty() && clickedButton == 2))) { boolean isMiddleClickPulling = !held.isEmpty() && clickedButton == 2;
GridStackItem stack = (GridStackItem) view.getStacks().get(slotNumber); boolean isPulling = held.isEmpty() || isMiddleClickPulling;
if (stack.isCraftable() && (stack.doesDisplayCraftText() || (GuiScreen.isShiftKeyDown() && GuiScreen.isCtrlKeyDown())) && view.canCraft()) { IGridStack stack = view.getStacks().get(slotNumber);
if (isPulling) {
if (stack.isCraftable() && view.canCraft() && (stack.doesDisplayCraftText() || (GuiScreen.isShiftKeyDown() && GuiScreen.isCtrlKeyDown()))) {
FMLCommonHandler.instance().showGuiScreen(new GuiCraftingStart(this, ((ContainerGrid) this.inventorySlots).getPlayer(), stack)); FMLCommonHandler.instance().showGuiScreen(new GuiCraftingStart(this, ((ContainerGrid) this.inventorySlots).getPlayer(), stack));
} else { } else if (grid.getGridType() == GridType.FLUID && held.isEmpty()) {
RS.INSTANCE.network.sendToServer(new MessageGridFluidPull(view.getStacks().get(slotNumber).getHash(), GuiScreen.isShiftKeyDown()));
} else if (grid.getGridType() == GridType.NORMAL || grid.getGridType() == GridType.PATTERN) {
int flags = 0; int flags = 0;
if (clickedButton == 1) { if (clickedButton == 1) {
@@ -465,8 +472,6 @@ public class GuiGrid extends GuiBase implements IResizableDisplay {
RS.INSTANCE.network.sendToServer(new MessageGridItemPull(stack.getHash(), flags)); RS.INSTANCE.network.sendToServer(new MessageGridItemPull(stack.getHash(), flags));
} }
} else if (grid.getType() == GridType.FLUID && held.isEmpty()) {
RS.INSTANCE.network.sendToServer(new MessageGridFluidPull(view.getStacks().get(slotNumber).getHash(), GuiScreen.isShiftKeyDown()));
} }
} }
} }

View File

@@ -3,6 +3,7 @@ package com.raoulvdberge.refinedstorage.gui.grid.stack;
import com.raoulvdberge.refinedstorage.api.storage.IStorageTracker; import com.raoulvdberge.refinedstorage.api.storage.IStorageTracker;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import com.raoulvdberge.refinedstorage.gui.GuiBase; import com.raoulvdberge.refinedstorage.gui.GuiBase;
import net.minecraft.client.resources.I18n;
import net.minecraftforge.fluids.FluidStack; import net.minecraftforge.fluids.FluidStack;
import org.apache.commons.lang3.tuple.Pair; import org.apache.commons.lang3.tuple.Pair;
@@ -13,17 +14,36 @@ public class GridStackFluid implements IGridStack {
private FluidStack stack; private FluidStack stack;
@Nullable @Nullable
private IStorageTracker.IStorageTrackerEntry entry; private IStorageTracker.IStorageTrackerEntry entry;
private boolean craftable;
private boolean displayCraftText;
public GridStackFluid(Pair<Integer, FluidStack> data, @Nullable IStorageTracker.IStorageTrackerEntry entry) { public GridStackFluid(Pair<Integer, FluidStack> data, @Nullable IStorageTracker.IStorageTrackerEntry entry, boolean craftable, boolean displayCraftText) {
this.hash = data.getLeft(); this.hash = data.getLeft();
this.stack = data.getRight(); this.stack = data.getRight();
this.entry = entry; this.entry = entry;
this.craftable = craftable;
this.displayCraftText = displayCraftText;
} }
public FluidStack getStack() { public FluidStack getStack() {
return stack; return stack;
} }
@Override
public boolean isCraftable() {
return craftable;
}
@Override
public boolean doesDisplayCraftText() {
return displayCraftText;
}
@Override
public void setDisplayCraftText(boolean displayCraftText) {
this.displayCraftText = displayCraftText;
}
@Override @Override
public int getHash() { public int getHash() {
return hash; return hash;
@@ -63,11 +83,15 @@ public class GridStackFluid implements IGridStack {
public void draw(GuiBase gui, int x, int y) { public void draw(GuiBase gui, int x, int y) {
GuiBase.FLUID_RENDERER.draw(gui.mc, x, y, stack); GuiBase.FLUID_RENDERER.draw(gui.mc, x, y, stack);
float amountRaw = ((float) stack.amount / 1000F); String text;
int amount = (int) amountRaw;
String formattedAmount = amount >= 1 ? API.instance().getQuantityFormatter().formatWithUnits(amount) : String.format("%.1f", amountRaw);
gui.drawQuantity(x, y, formattedAmount); if (displayCraftText) {
text = I18n.format("gui.refinedstorage:grid.craft");
} else {
text = API.instance().getQuantityFormatter().formatInBucketFormWithOnlyTrailingDigitsIfZero(getQuantity());
}
gui.drawQuantity(x, y, text);
} }
@Override @Override

View File

@@ -45,14 +45,17 @@ public class GridStackItem implements IGridStack {
return stack; return stack;
} }
@Override
public boolean isCraftable() { public boolean isCraftable() {
return craftable; return craftable;
} }
@Override
public boolean doesDisplayCraftText() { public boolean doesDisplayCraftText() {
return displayCraftText; return displayCraftText;
} }
@Override
public void setDisplayCraftText(boolean displayCraftText) { public void setDisplayCraftText(boolean displayCraftText) {
this.displayCraftText = displayCraftText; this.displayCraftText = displayCraftText;

View File

@@ -28,4 +28,10 @@ public interface IGridStack {
IStorageTracker.IStorageTrackerEntry getTrackerEntry(); IStorageTracker.IStorageTrackerEntry getTrackerEntry();
void setTrackerEntry(@Nullable IStorageTracker.IStorageTrackerEntry entry); void setTrackerEntry(@Nullable IStorageTracker.IStorageTrackerEntry entry);
boolean isCraftable();
boolean doesDisplayCraftText();
void setDisplayCraftText(boolean displayCraftText);
} }

View File

@@ -17,6 +17,11 @@ public class GridViewFluid extends GridViewBase {
map.clear(); map.clear();
for (IGridStack stack : stacks) { for (IGridStack stack : stacks) {
// Don't let a craftable stack override a normal stack
if (stack.doesDisplayCraftText() && map.containsKey(stack.getHash())) {
continue;
}
map.put(stack.getHash(), stack); map.put(stack.getHash(), stack);
} }
} }
@@ -30,13 +35,25 @@ public class GridViewFluid extends GridViewBase {
GridStackFluid existing = (GridStackFluid) map.get(stack.getHash()); GridStackFluid existing = (GridStackFluid) map.get(stack.getHash());
if (existing == null) { if (existing == null) {
((GridStackFluid) stack).getStack().amount = delta;
map.put(stack.getHash(), stack); map.put(stack.getHash(), stack);
} else { } else {
if (existing.getStack().amount + delta <= 0) { if (existing.getStack().amount + delta <= 0) {
if (existing.isCraftable()) {
existing.setDisplayCraftText(true);
} else {
map.remove(existing.getHash()); map.remove(existing.getHash());
}
} else {
if (existing.doesDisplayCraftText()) {
existing.setDisplayCraftText(false);
existing.getStack().amount = delta;
} else { } else {
existing.getStack().amount += delta; existing.getStack().amount += delta;
} }
}
existing.setTrackerEntry(stack.getTrackerEntry()); existing.setTrackerEntry(stack.getTrackerEntry());
} }

View File

@@ -18,7 +18,7 @@ public class GridViewItem extends GridViewBase {
for (IGridStack stack : stacks) { for (IGridStack stack : stacks) {
// Don't let a craftable stack override a normal stack // Don't let a craftable stack override a normal stack
if (((GridStackItem) stack).doesDisplayCraftText() && map.containsKey(stack.getHash())) { if (stack.doesDisplayCraftText() && map.containsKey(stack.getHash())) {
continue; continue;
} }

View File

@@ -30,7 +30,7 @@ public final class IntegrationCraftingTweaks {
public static class ValidContainerPredicate implements Predicate<ContainerGrid> { public static class ValidContainerPredicate implements Predicate<ContainerGrid> {
@Override @Override
public boolean apply(ContainerGrid containerGrid) { public boolean apply(ContainerGrid containerGrid) {
return containerGrid.getGrid().getType() == GridType.CRAFTING; return containerGrid.getGrid().getGridType() == GridType.CRAFTING;
} }
} }

View File

@@ -50,7 +50,7 @@ public class RecipeTransferHandlerGrid implements IRecipeTransferHandler {
if (doTransfer) { if (doTransfer) {
LAST_TRANSFER = System.currentTimeMillis(); LAST_TRANSFER = System.currentTimeMillis();
if (grid.getType() == GridType.PATTERN && ((NetworkNodeGrid) grid).isProcessingPattern()) { if (grid.getGridType() == GridType.PATTERN && ((NetworkNodeGrid) grid).isProcessingPattern()) {
List<ItemStack> inputs = new LinkedList<>(); List<ItemStack> inputs = new LinkedList<>();
List<ItemStack> outputs = new LinkedList<>(); List<ItemStack> outputs = new LinkedList<>();
@@ -71,7 +71,7 @@ public class RecipeTransferHandlerGrid implements IRecipeTransferHandler {
RS.INSTANCE.network.sendToServer(new MessageGridTransfer(recipeLayout.getItemStacks().getGuiIngredients(), container.inventorySlots.stream().filter(s -> s.inventory instanceof InventoryCrafting).collect(Collectors.toList()))); RS.INSTANCE.network.sendToServer(new MessageGridTransfer(recipeLayout.getItemStacks().getGuiIngredients(), container.inventorySlots.stream().filter(s -> s.inventory instanceof InventoryCrafting).collect(Collectors.toList())));
} }
} else { } else {
if (grid.getType() == GridType.PATTERN && ((NetworkNodeGrid) grid).isProcessingPattern()) { if (grid.getGridType() == GridType.PATTERN && ((NetworkNodeGrid) grid).isProcessingPattern()) {
if (recipeLayout.getRecipeCategory().getUid().equals(VanillaRecipeCategoryUid.CRAFTING)) { if (recipeLayout.getRecipeCategory().getUid().equals(VanillaRecipeCategoryUid.CRAFTING)) {
return ERROR_CANNOT_TRANSFER; return ERROR_CANNOT_TRANSFER;
} }

View File

@@ -150,12 +150,14 @@ public class EnvironmentNetwork extends AbstractManagedEnvironment {
int count = 0; int count = 0;
for (ICraftingTask task : node.getNetwork().getCraftingManager().getTasks()) { for (ICraftingTask task : node.getNetwork().getCraftingManager().getTasks()) {
if (API.instance().getComparer().isEqual(task.getRequested(), stack, COMPARE_NBT | COMPARE_DAMAGE)) { if (task.getRequested().getItem() != null) {
if (API.instance().getComparer().isEqual(task.getRequested().getItem(), stack, COMPARE_NBT | COMPARE_DAMAGE)) {
node.getNetwork().getCraftingManager().cancel(task.getId()); node.getNetwork().getCraftingManager().cancel(task.getId());
count++; count++;
} }
} }
}
return new Object[]{count}; return new Object[]{count};
} }

View File

@@ -24,12 +24,16 @@ public class ItemHandlerFluid extends ItemHandlerBase {
ItemStack stack = getStackInSlot(slot); ItemStack stack = getStackInSlot(slot);
if (stack.isEmpty()) { if (stack.isEmpty()) {
fluids[slot] = null; setFluidStack(slot, null);
} else { } else {
fluids[slot] = StackUtils.getFluid(ItemHandlerHelper.copyStackWithSize(stack, 1), true).getValue(); setFluidStack(slot, StackUtils.getFluid(ItemHandlerHelper.copyStackWithSize(stack, 1), true).getValue());
} }
} }
public void setFluidStack(int slot, @Nullable FluidStack stack) {
fluids[slot] = stack;
}
@Nullable @Nullable
public FluidStack getFluidStackInSlot(int slot) { public FluidStack getFluidStackInSlot(int slot) {
return fluids[slot]; return fluids[slot];

View File

@@ -25,6 +25,7 @@ import net.minecraft.util.EnumActionResult;
import net.minecraft.util.EnumHand; import net.minecraft.util.EnumHand;
import net.minecraft.util.text.TextFormatting; import net.minecraft.util.text.TextFormatting;
import net.minecraft.world.World; import net.minecraft.world.World;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fml.relauncher.Side; import net.minecraftforge.fml.relauncher.Side;
import net.minecraftforge.fml.relauncher.SideOnly; import net.minecraftforge.fml.relauncher.SideOnly;
@@ -41,6 +42,8 @@ public class ItemPattern extends ItemBase implements ICraftingPatternProvider {
private static final String NBT_VERSION = "Version"; private static final String NBT_VERSION = "Version";
public static final String NBT_INPUT_SLOT = "Input_%d"; public static final String NBT_INPUT_SLOT = "Input_%d";
public static final String NBT_OUTPUT_SLOT = "Output_%d"; public static final String NBT_OUTPUT_SLOT = "Output_%d";
private static final String NBT_FLUID_INPUT_SLOT = "FluidInput_%d";
private static final String NBT_FLUID_OUTPUT_SLOT = "FluidOutput_%d";
private static final String NBT_OREDICT = "Oredict"; private static final String NBT_OREDICT = "Oredict";
public static final String NBT_PROCESSING = "Processing"; public static final String NBT_PROCESSING = "Processing";
@@ -81,11 +84,13 @@ public class ItemPattern extends ItemBase implements ICraftingPatternProvider {
tooltip.add(TextFormatting.YELLOW + I18n.format("misc.refinedstorage:pattern.inputs") + TextFormatting.RESET); tooltip.add(TextFormatting.YELLOW + I18n.format("misc.refinedstorage:pattern.inputs") + TextFormatting.RESET);
RenderUtils.addCombinedItemsToTooltip(tooltip, true, pattern.getInputs().stream().map(i -> i.size() > 0 ? i.get(0) : ItemStack.EMPTY).collect(Collectors.toList())); RenderUtils.addCombinedItemsToTooltip(tooltip, true, pattern.getInputs().stream().map(i -> i.size() > 0 ? i.get(0) : ItemStack.EMPTY).collect(Collectors.toList()));
RenderUtils.addCombinedFluidsToTooltip(tooltip, pattern.getFluidInputs());
tooltip.add(TextFormatting.YELLOW + I18n.format("misc.refinedstorage:pattern.outputs") + TextFormatting.RESET); tooltip.add(TextFormatting.YELLOW + I18n.format("misc.refinedstorage:pattern.outputs") + TextFormatting.RESET);
} }
RenderUtils.addCombinedItemsToTooltip(tooltip, true, pattern.getOutputs()); RenderUtils.addCombinedItemsToTooltip(tooltip, true, pattern.getOutputs());
RenderUtils.addCombinedFluidsToTooltip(tooltip, pattern.getFluidOutputs());
if (isOredict(stack)) { if (isOredict(stack)) {
tooltip.add(TextFormatting.BLUE + I18n.format("misc.refinedstorage:pattern.oredict") + TextFormatting.RESET); tooltip.add(TextFormatting.BLUE + I18n.format("misc.refinedstorage:pattern.oredict") + TextFormatting.RESET);
@@ -147,6 +152,44 @@ public class ItemPattern extends ItemBase implements ICraftingPatternProvider {
return stack; return stack;
} }
public static void setFluidInputSlot(ItemStack pattern, int slot, FluidStack stack) {
if (!pattern.hasTagCompound()) {
pattern.setTagCompound(new NBTTagCompound());
}
pattern.getTagCompound().setTag(String.format(NBT_FLUID_INPUT_SLOT, slot), stack.writeToNBT(new NBTTagCompound()));
}
@Nullable
public static FluidStack getFluidInputSlot(ItemStack pattern, int slot) {
String id = String.format(NBT_FLUID_INPUT_SLOT, slot);
if (!pattern.hasTagCompound() || !pattern.getTagCompound().hasKey(id)) {
return null;
}
return FluidStack.loadFluidStackFromNBT(pattern.getTagCompound().getCompoundTag(id));
}
public static void setFluidOutputSlot(ItemStack pattern, int slot, FluidStack stack) {
if (!pattern.hasTagCompound()) {
pattern.setTagCompound(new NBTTagCompound());
}
pattern.getTagCompound().setTag(String.format(NBT_FLUID_OUTPUT_SLOT, slot), stack.writeToNBT(new NBTTagCompound()));
}
@Nullable
public static FluidStack getFluidOutputSlot(ItemStack pattern, int slot) {
String id = String.format(NBT_FLUID_OUTPUT_SLOT, slot);
if (!pattern.hasTagCompound() || !pattern.getTagCompound().hasKey(id)) {
return null;
}
return FluidStack.loadFluidStackFromNBT(pattern.getTagCompound().getCompoundTag(id));
}
public static boolean isProcessing(ItemStack pattern) { public static boolean isProcessing(ItemStack pattern) {
return pattern.hasTagCompound() && pattern.getTagCompound().hasKey(NBT_PROCESSING) && pattern.getTagCompound().getBoolean(NBT_PROCESSING); return pattern.hasTagCompound() && pattern.getTagCompound().hasKey(NBT_PROCESSING) && pattern.getTagCompound().getBoolean(NBT_PROCESSING);
} }

View File

@@ -1,6 +1,8 @@
package com.raoulvdberge.refinedstorage.network; package com.raoulvdberge.refinedstorage.network;
import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElement; import com.raoulvdberge.refinedstorage.api.autocrafting.craftingmonitor.ICraftingMonitorElement;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingRequestInfo;
import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask; import com.raoulvdberge.refinedstorage.api.autocrafting.task.ICraftingTask;
import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab; import com.raoulvdberge.refinedstorage.api.network.grid.IGridTab;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
@@ -8,7 +10,6 @@ import com.raoulvdberge.refinedstorage.gui.GuiBase;
import com.raoulvdberge.refinedstorage.gui.GuiCraftingMonitor; import com.raoulvdberge.refinedstorage.gui.GuiCraftingMonitor;
import com.raoulvdberge.refinedstorage.tile.craftingmonitor.ICraftingMonitor; import com.raoulvdberge.refinedstorage.tile.craftingmonitor.ICraftingMonitor;
import io.netty.buffer.ByteBuf; import io.netty.buffer.ByteBuf;
import net.minecraft.item.ItemStack;
import net.minecraftforge.fml.common.network.ByteBufUtils; import net.minecraftforge.fml.common.network.ByteBufUtils;
import net.minecraftforge.fml.common.network.simpleimpl.IMessage; import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler; import net.minecraftforge.fml.common.network.simpleimpl.IMessageHandler;
@@ -37,7 +38,14 @@ public class MessageCraftingMonitorElements implements IMessage, IMessageHandler
for (int i = 0; i < size; ++i) { for (int i = 0; i < size; ++i) {
UUID id = UUID.fromString(ByteBufUtils.readUTF8String(buf)); UUID id = UUID.fromString(ByteBufUtils.readUTF8String(buf));
ItemStack requested = ByteBufUtils.readItemStack(buf);
ICraftingRequestInfo requested = null;
try {
requested = API.instance().createCraftingRequestInfo(ByteBufUtils.readTag(buf));
} catch (CraftingTaskReadException e) {
e.printStackTrace();
}
int qty = buf.readInt(); int qty = buf.readInt();
long executionStarted = buf.readLong(); long executionStarted = buf.readLong();
@@ -63,7 +71,7 @@ public class MessageCraftingMonitorElements implements IMessage, IMessageHandler
for (ICraftingTask task : craftingMonitor.getTasks()) { for (ICraftingTask task : craftingMonitor.getTasks()) {
ByteBufUtils.writeUTF8String(buf, task.getId().toString()); ByteBufUtils.writeUTF8String(buf, task.getId().toString());
ByteBufUtils.writeItemStack(buf, task.getRequested()); ByteBufUtils.writeTag(buf, task.getRequested().writeToNbt());
buf.writeInt(task.getQuantity()); buf.writeInt(task.getQuantity());
buf.writeLong(task.getExecutionStarted()); buf.writeLong(task.getExecutionStarted());

View File

@@ -37,7 +37,7 @@ public class MessageGridClear extends MessageHandlerPlayerToServer<MessageGridCl
InventoryCrafting matrix = grid.getCraftingMatrix(); InventoryCrafting matrix = grid.getCraftingMatrix();
if (grid.getType() == GridType.CRAFTING && grid.getNetwork() != null && grid.getNetwork().getSecurityManager().hasPermission(Permission.INSERT, player)) { if (grid.getGridType() == GridType.CRAFTING && grid.getNetwork() != null && grid.getNetwork().getSecurityManager().hasPermission(Permission.INSERT, player)) {
for (int i = 0; i < matrix.getSizeInventory(); ++i) { for (int i = 0; i < matrix.getSizeInventory(); ++i) {
ItemStack slot = matrix.getStackInSlot(i); ItemStack slot = matrix.getStackInSlot(i);
@@ -45,7 +45,7 @@ public class MessageGridClear extends MessageHandlerPlayerToServer<MessageGridCl
matrix.setInventorySlotContents(i, StackUtils.nullToEmpty(grid.getNetwork().insertItem(slot, slot.getCount(), Action.PERFORM))); matrix.setInventorySlotContents(i, StackUtils.nullToEmpty(grid.getNetwork().insertItem(slot, slot.getCount(), Action.PERFORM)));
} }
} }
} else if (grid.getType() == GridType.PATTERN) { } else if (grid.getGridType() == GridType.PATTERN) {
((NetworkNodeGrid) grid).clearMatrix(); ((NetworkNodeGrid) grid).clearMatrix();
} }
} }

View File

@@ -11,14 +11,16 @@ public class MessageGridCraftingPreview extends MessageHandlerPlayerToServer<Mes
private int hash; private int hash;
private int quantity; private int quantity;
private boolean noPreview; private boolean noPreview;
private boolean fluids;
public MessageGridCraftingPreview() { public MessageGridCraftingPreview() {
} }
public MessageGridCraftingPreview(int hash, int quantity, boolean noPreview) { public MessageGridCraftingPreview(int hash, int quantity, boolean noPreview, boolean fluids) {
this.hash = hash; this.hash = hash;
this.quantity = quantity; this.quantity = quantity;
this.noPreview = noPreview; this.noPreview = noPreview;
this.fluids = fluids;
} }
@Override @Override
@@ -26,6 +28,7 @@ public class MessageGridCraftingPreview extends MessageHandlerPlayerToServer<Mes
hash = buf.readInt(); hash = buf.readInt();
quantity = buf.readInt(); quantity = buf.readInt();
noPreview = buf.readBoolean(); noPreview = buf.readBoolean();
fluids = buf.readBoolean();
} }
@Override @Override
@@ -33,6 +36,7 @@ public class MessageGridCraftingPreview extends MessageHandlerPlayerToServer<Mes
buf.writeInt(hash); buf.writeInt(hash);
buf.writeInt(quantity); buf.writeInt(quantity);
buf.writeBoolean(noPreview); buf.writeBoolean(noPreview);
buf.writeBoolean(fluids);
} }
@Override @Override
@@ -42,9 +46,15 @@ public class MessageGridCraftingPreview extends MessageHandlerPlayerToServer<Mes
if (container instanceof ContainerGrid) { if (container instanceof ContainerGrid) {
IGrid grid = ((ContainerGrid) container).getGrid(); IGrid grid = ((ContainerGrid) container).getGrid();
if (message.fluids) {
if (grid.getFluidHandler() != null) {
grid.getFluidHandler().onCraftingPreviewRequested(player, message.hash, message.quantity, message.noPreview);
}
} else {
if (grid.getItemHandler() != null) { if (grid.getItemHandler() != null) {
grid.getItemHandler().onCraftingPreviewRequested(player, message.hash, message.quantity, message.noPreview); grid.getItemHandler().onCraftingPreviewRequested(player, message.hash, message.quantity, message.noPreview);
} }
} }
} }
}
} }

View File

@@ -19,23 +19,26 @@ import java.util.LinkedList;
import java.util.List; import java.util.List;
public class MessageGridCraftingPreviewResponse implements IMessage, IMessageHandler<MessageGridCraftingPreviewResponse, IMessage> { public class MessageGridCraftingPreviewResponse implements IMessage, IMessageHandler<MessageGridCraftingPreviewResponse, IMessage> {
public List<ICraftingPreviewElement> stacks; private List<ICraftingPreviewElement> stacks;
public int hash; private int hash;
public int quantity; private int quantity;
private boolean fluids;
public MessageGridCraftingPreviewResponse() { public MessageGridCraftingPreviewResponse() {
} }
public MessageGridCraftingPreviewResponse(List<ICraftingPreviewElement> stacks, int hash, int quantity) { public MessageGridCraftingPreviewResponse(List<ICraftingPreviewElement> stacks, int hash, int quantity, boolean fluids) {
this.stacks = stacks; this.stacks = stacks;
this.hash = hash; this.hash = hash;
this.quantity = quantity; this.quantity = quantity;
this.fluids = fluids;
} }
@Override @Override
public void fromBytes(ByteBuf buf) { public void fromBytes(ByteBuf buf) {
this.hash = buf.readInt(); this.hash = buf.readInt();
this.quantity = buf.readInt(); this.quantity = buf.readInt();
this.fluids = buf.readBoolean();
this.stacks = new LinkedList<>(); this.stacks = new LinkedList<>();
@@ -50,6 +53,7 @@ public class MessageGridCraftingPreviewResponse implements IMessage, IMessageHan
public void toBytes(ByteBuf buf) { public void toBytes(ByteBuf buf) {
buf.writeInt(hash); buf.writeInt(hash);
buf.writeInt(quantity); buf.writeInt(quantity);
buf.writeBoolean(fluids);
buf.writeInt(stacks.size()); buf.writeInt(stacks.size());
@@ -69,7 +73,7 @@ public class MessageGridCraftingPreviewResponse implements IMessage, IMessageHan
screen = ((GuiCraftingStart) screen).getParent(); screen = ((GuiCraftingStart) screen).getParent();
} }
FMLCommonHandler.instance().showGuiScreen(new GuiCraftingPreview(screen, message.stacks, message.hash, message.quantity)); FMLCommonHandler.instance().showGuiScreen(new GuiCraftingPreview(screen, message.stacks, message.hash, message.quantity, message.fluids));
}); });
return null; return null;

View File

@@ -10,25 +10,29 @@ import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
public class MessageGridCraftingStart extends MessageHandlerPlayerToServer<MessageGridCraftingStart> implements IMessage { public class MessageGridCraftingStart extends MessageHandlerPlayerToServer<MessageGridCraftingStart> implements IMessage {
private int hash; private int hash;
private int quantity; private int quantity;
private boolean fluids;
public MessageGridCraftingStart() { public MessageGridCraftingStart() {
} }
public MessageGridCraftingStart(int hash, int quantity) { public MessageGridCraftingStart(int hash, int quantity, boolean fluids) {
this.hash = hash; this.hash = hash;
this.quantity = quantity; this.quantity = quantity;
this.fluids = fluids;
} }
@Override @Override
public void fromBytes(ByteBuf buf) { public void fromBytes(ByteBuf buf) {
hash = buf.readInt(); hash = buf.readInt();
quantity = buf.readInt(); quantity = buf.readInt();
fluids = buf.readBoolean();
} }
@Override @Override
public void toBytes(ByteBuf buf) { public void toBytes(ByteBuf buf) {
buf.writeInt(hash); buf.writeInt(hash);
buf.writeInt(quantity); buf.writeInt(quantity);
buf.writeBoolean(fluids);
} }
@Override @Override
@@ -38,9 +42,15 @@ public class MessageGridCraftingStart extends MessageHandlerPlayerToServer<Messa
if (container instanceof ContainerGrid) { if (container instanceof ContainerGrid) {
IGrid grid = ((ContainerGrid) container).getGrid(); IGrid grid = ((ContainerGrid) container).getGrid();
if (message.fluids) {
if (grid.getFluidHandler() != null) {
grid.getFluidHandler().onCraftingRequested(player, message.hash, message.quantity);
}
} else {
if (grid.getItemHandler() != null) { if (grid.getItemHandler() != null) {
grid.getItemHandler().onCraftingRequested(player, message.hash, message.quantity); grid.getItemHandler().onCraftingRequested(player, message.hash, message.quantity);
} }
} }
} }
}
} }

View File

@@ -0,0 +1,53 @@
package com.raoulvdberge.refinedstorage.network;
import com.raoulvdberge.refinedstorage.api.network.grid.IGrid;
import com.raoulvdberge.refinedstorage.apiimpl.network.node.NetworkNodeGrid;
import com.raoulvdberge.refinedstorage.container.ContainerGrid;
import io.netty.buffer.ByteBuf;
import net.minecraft.entity.player.EntityPlayerMP;
import net.minecraft.inventory.Container;
import net.minecraftforge.fluids.Fluid;
import net.minecraftforge.fml.common.network.simpleimpl.IMessage;
public class MessageGridFluidAmount extends MessageHandlerPlayerToServer<MessageGridFluidAmount> implements IMessage {
private int slot;
private int amount;
public MessageGridFluidAmount(int slot, int amount) {
this.slot = slot;
this.amount = amount;
}
public MessageGridFluidAmount() {
// NO OP
}
@Override
protected void handle(MessageGridFluidAmount message, EntityPlayerMP player) {
Container container = player.openContainer;
if (container instanceof ContainerGrid && message.slot >= 0 && message.amount > 0 && message.amount <= Fluid.BUCKET_VOLUME) {
IGrid grid = ((ContainerGrid) container).getGrid();
if (grid instanceof NetworkNodeGrid) {
NetworkNodeGrid node = (NetworkNodeGrid) grid;
if (message.slot < node.getMatrixProcessingFluids().getSlots()) {
node.getMatrixProcessingFluids().getStackInSlot(message.slot).setCount(message.amount);
}
}
}
}
@Override
public void fromBytes(ByteBuf buf) {
slot = buf.readInt();
amount = buf.readInt();
}
@Override
public void toBytes(ByteBuf buf) {
buf.writeInt(slot);
buf.writeInt(amount);
}
}

View File

@@ -32,7 +32,7 @@ public class MessageGridFluidDelta implements IMessage, IMessageHandler<MessageG
@Override @Override
public void fromBytes(ByteBuf buf) { public void fromBytes(ByteBuf buf) {
clientStack = new GridStackFluid(StackUtils.readFluidStack(buf), buf.readBoolean() ? new StorageTrackerEntry(buf) : null); clientStack = new GridStackFluid(StackUtils.readFluidStack(buf), buf.readBoolean() ? new StorageTrackerEntry(buf) : null, buf.readBoolean(), false);
delta = buf.readInt(); delta = buf.readInt();
} }
@@ -47,6 +47,8 @@ public class MessageGridFluidDelta implements IMessage, IMessageHandler<MessageG
ByteBufUtils.writeUTF8String(buf, entry.getName()); ByteBufUtils.writeUTF8String(buf, entry.getName());
} }
buf.writeBoolean(network.getCraftingManager().getPattern(stack) != null);
buf.writeInt(delta); buf.writeInt(delta);
} }

View File

@@ -1,5 +1,6 @@
package com.raoulvdberge.refinedstorage.network; package com.raoulvdberge.refinedstorage.network;
import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
import com.raoulvdberge.refinedstorage.api.network.INetwork; import com.raoulvdberge.refinedstorage.api.network.INetwork;
import com.raoulvdberge.refinedstorage.api.storage.IStorageTracker; import com.raoulvdberge.refinedstorage.api.storage.IStorageTracker;
import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageTrackerEntry; import com.raoulvdberge.refinedstorage.apiimpl.storage.StorageTrackerEntry;
@@ -38,7 +39,7 @@ public class MessageGridFluidUpdate implements IMessage, IMessageHandler<Message
int items = buf.readInt(); int items = buf.readInt();
for (int i = 0; i < items; ++i) { for (int i = 0; i < items; ++i) {
this.stacks.add(new GridStackFluid(StackUtils.readFluidStack(buf), buf.readBoolean() ? new StorageTrackerEntry(buf) : null)); this.stacks.add(new GridStackFluid(StackUtils.readFluidStack(buf), buf.readBoolean() ? new StorageTrackerEntry(buf) : null, buf.readBoolean(), buf.readBoolean()));
} }
} }
@@ -46,7 +47,13 @@ public class MessageGridFluidUpdate implements IMessage, IMessageHandler<Message
public void toBytes(ByteBuf buf) { public void toBytes(ByteBuf buf) {
buf.writeBoolean(canCraft); buf.writeBoolean(canCraft);
buf.writeInt(network.getFluidStorageCache().getList().getStacks().size()); int size = network.getFluidStorageCache().getList().getStacks().size();
for (ICraftingPattern pattern : network.getCraftingManager().getPatterns()) {
size += pattern.getFluidOutputs().size();
}
buf.writeInt(size);
for (FluidStack stack : network.getFluidStorageCache().getList().getStacks()) { for (FluidStack stack : network.getFluidStorageCache().getList().getStacks()) {
StackUtils.writeFluidStack(buf, stack); StackUtils.writeFluidStack(buf, stack);
@@ -57,6 +64,25 @@ public class MessageGridFluidUpdate implements IMessage, IMessageHandler<Message
buf.writeLong(entry.getTime()); buf.writeLong(entry.getTime());
ByteBufUtils.writeUTF8String(buf, entry.getName()); ByteBufUtils.writeUTF8String(buf, entry.getName());
} }
buf.writeBoolean(network.getCraftingManager().getPattern(stack) != null);
buf.writeBoolean(false);
}
for (ICraftingPattern pattern : network.getCraftingManager().getPatterns()) {
for (FluidStack stack : pattern.getFluidOutputs()) {
StackUtils.writeFluidStack(buf, stack);
IStorageTracker.IStorageTrackerEntry entry = network.getFluidStorageTracker().get(stack);
buf.writeBoolean(entry != null);
if (entry != null) {
buf.writeLong(entry.getTime());
ByteBufUtils.writeUTF8String(buf, entry.getName());
}
buf.writeBoolean(network.getCraftingManager().getPattern(stack) != null);
buf.writeBoolean(true);
}
} }
} }

View File

@@ -40,7 +40,7 @@ public class MessageGridPatternCreate extends MessageHandlerPlayerToServer<Messa
public void handle(MessageGridPatternCreate message, EntityPlayerMP player) { public void handle(MessageGridPatternCreate message, EntityPlayerMP player) {
TileEntity tile = player.getEntityWorld().getTileEntity(new BlockPos(message.x, message.y, message.z)); TileEntity tile = player.getEntityWorld().getTileEntity(new BlockPos(message.x, message.y, message.z));
if (tile instanceof TileGrid && ((TileGrid) tile).getNode().getType() == GridType.PATTERN) { if (tile instanceof TileGrid && ((TileGrid) tile).getNode().getGridType() == GridType.PATTERN) {
((TileGrid) tile).getNode().onCreatePattern(); ((TileGrid) tile).getNode().onCreatePattern();
} }
} }

View File

@@ -65,7 +65,7 @@ public class MessageGridProcessingTransfer extends MessageHandlerPlayerToServer<
if (player.openContainer instanceof ContainerGrid) { if (player.openContainer instanceof ContainerGrid) {
IGrid grid = ((ContainerGrid) player.openContainer).getGrid(); IGrid grid = ((ContainerGrid) player.openContainer).getGrid();
if (grid.getType() == GridType.PATTERN) { if (grid.getGridType() == GridType.PATTERN) {
ItemHandlerBase handler = ((NetworkNodeGrid) grid).getProcessingMatrix(); ItemHandlerBase handler = ((NetworkNodeGrid) grid).getProcessingMatrix();
clearInputsAndOutputs(handler); clearInputsAndOutputs(handler);

View File

@@ -74,7 +74,7 @@ public class MessageGridTransfer extends MessageHandlerPlayerToServer<MessageGri
if (player.openContainer instanceof ContainerGrid) { if (player.openContainer instanceof ContainerGrid) {
IGrid grid = ((ContainerGrid) player.openContainer).getGrid(); IGrid grid = ((ContainerGrid) player.openContainer).getGrid();
if (grid.getType() == GridType.CRAFTING || grid.getType() == GridType.PATTERN) { if (grid.getGridType() == GridType.CRAFTING || grid.getGridType() == GridType.PATTERN) {
grid.onRecipeTransfer(player, message.recipe); grid.onRecipeTransfer(player, message.recipe);
} }
} }

View File

@@ -95,7 +95,7 @@ public class ProxyCommon {
API.instance().getCraftingTaskRegistry().add(CraftingTaskFactory.ID, new CraftingTaskFactory()); API.instance().getCraftingTaskRegistry().add(CraftingTaskFactory.ID, new CraftingTaskFactory());
API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementItemRender.ID, buf -> new CraftingMonitorElementItemRender(StackUtils.readItemStack(buf), buf.readInt(), buf.readInt())); API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementItemRender.ID, buf -> new CraftingMonitorElementItemRender(StackUtils.readItemStack(buf), buf.readInt(), buf.readInt()));
API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementFluidRender.ID, buf -> new CraftingMonitorElementFluidRender(StackUtils.readFluidStack(buf).getRight(), buf.readInt())); API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementFluidRender.ID, buf -> new CraftingMonitorElementFluidRender(StackUtils.readFluidStack(buf).getRight(), buf.readInt(), buf.readInt()));
API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementText.ID, buf -> new CraftingMonitorElementText(ByteBufUtils.readUTF8String(buf), buf.readInt())); API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementText.ID, buf -> new CraftingMonitorElementText(ByteBufUtils.readUTF8String(buf), buf.readInt()));
API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementColor.ID, buf -> { API.instance().getCraftingMonitorElementRegistry().add(CraftingMonitorElementColor.ID, buf -> {
int color = buf.readInt(); int color = buf.readInt();
@@ -183,6 +183,7 @@ public class ProxyCommon {
RS.INSTANCE.network.registerMessage(MessageStorageDiskSizeRequest.class, MessageStorageDiskSizeRequest.class, id++, Side.SERVER); RS.INSTANCE.network.registerMessage(MessageStorageDiskSizeRequest.class, MessageStorageDiskSizeRequest.class, id++, Side.SERVER);
RS.INSTANCE.network.registerMessage(MessageStorageDiskSizeResponse.class, MessageStorageDiskSizeResponse.class, id++, Side.CLIENT); RS.INSTANCE.network.registerMessage(MessageStorageDiskSizeResponse.class, MessageStorageDiskSizeResponse.class, id++, Side.CLIENT);
RS.INSTANCE.network.registerMessage(MessageConfigSync.class, MessageConfigSync.class, id++, Side.CLIENT); RS.INSTANCE.network.registerMessage(MessageConfigSync.class, MessageConfigSync.class, id++, Side.CLIENT);
RS.INSTANCE.network.registerMessage(MessageGridFluidAmount.class, MessageGridFluidAmount.class, id++, Side.SERVER);
NetworkRegistry.INSTANCE.registerGuiHandler(RS.INSTANCE, new GuiHandler()); NetworkRegistry.INSTANCE.registerGuiHandler(RS.INSTANCE, new GuiHandler());

View File

@@ -7,6 +7,7 @@ import com.raoulvdberge.refinedstorage.container.ContainerGrid;
import com.raoulvdberge.refinedstorage.gui.GuiBase; import com.raoulvdberge.refinedstorage.gui.GuiBase;
import com.raoulvdberge.refinedstorage.gui.grid.GuiGrid; import com.raoulvdberge.refinedstorage.gui.grid.GuiGrid;
import com.raoulvdberge.refinedstorage.tile.TileNode; import com.raoulvdberge.refinedstorage.tile.TileNode;
import com.raoulvdberge.refinedstorage.tile.config.IType;
import com.raoulvdberge.refinedstorage.tile.data.TileDataParameter; import com.raoulvdberge.refinedstorage.tile.data.TileDataParameter;
import net.minecraft.network.datasync.DataSerializers; import net.minecraft.network.datasync.DataSerializers;
import net.minecraft.util.EnumFacing; import net.minecraft.util.EnumFacing;
@@ -82,6 +83,7 @@ public class TileGrid extends TileNode<NetworkNodeGrid> {
((ContainerGrid) player.openContainer).sendAllSlots(); ((ContainerGrid) player.openContainer).sendAllSlots();
}); });
}, (initial, p) -> GuiBase.executeLater(GuiGrid.class, GuiBase::initGui)); }, (initial, p) -> GuiBase.executeLater(GuiGrid.class, GuiBase::initGui));
public static final TileDataParameter<Integer, TileGrid> PROCESSING_TYPE = IType.createParameter();
public static void trySortGrid(boolean initial) { public static void trySortGrid(boolean initial) {
if (!initial) { if (!initial) {
@@ -99,6 +101,7 @@ public class TileGrid extends TileNode<NetworkNodeGrid> {
dataManager.addWatchedParameter(TAB_PAGE); dataManager.addWatchedParameter(TAB_PAGE);
dataManager.addWatchedParameter(OREDICT_PATTERN); dataManager.addWatchedParameter(OREDICT_PATTERN);
dataManager.addWatchedParameter(PROCESSING_PATTERN); dataManager.addWatchedParameter(PROCESSING_PATTERN);
dataManager.addWatchedParameter(PROCESSING_TYPE);
} }
@Override @Override
@@ -114,12 +117,12 @@ public class TileGrid extends TileNode<NetworkNodeGrid> {
@Override @Override
public boolean hasCapability(@Nonnull Capability<?> capability, @Nullable EnumFacing side) { public boolean hasCapability(@Nonnull Capability<?> capability, @Nullable EnumFacing side) {
return (getNode().getType() == GridType.PATTERN && capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY) || super.hasCapability(capability, side); return (getNode().getGridType() == GridType.PATTERN && capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY) || super.hasCapability(capability, side);
} }
@Override @Override
public <T> T getCapability(@Nonnull Capability<T> capability, @Nullable EnumFacing side) { public <T> T getCapability(@Nonnull Capability<T> capability, @Nullable EnumFacing side) {
if (getNode().getType() == GridType.PATTERN && capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY) { if (getNode().getGridType() == GridType.PATTERN && capability == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY) {
return CapabilityItemHandler.ITEM_HANDLER_CAPABILITY.cast(getNode().getPatterns()); return CapabilityItemHandler.ITEM_HANDLER_CAPABILITY.cast(getNode().getPatterns());
} }

View File

@@ -61,7 +61,7 @@ public class WirelessFluidGrid implements IGridNetworkAware {
} }
@Override @Override
public GridType getType() { public GridType getGridType() {
return GridType.FLUID; return GridType.FLUID;
} }

View File

@@ -90,7 +90,7 @@ public class WirelessGrid implements IGridNetworkAware {
} }
@Override @Override
public GridType getType() { public GridType getGridType() {
return GridType.NORMAL; return GridType.NORMAL;
} }

View File

@@ -186,7 +186,7 @@ public class PortableGrid implements IGrid, IPortableGrid, IStorageDiskContainer
} }
@Override @Override
public GridType getType() { public GridType getGridType() {
return GridType.NORMAL; return GridType.NORMAL;
} }

View File

@@ -257,7 +257,7 @@ public class TilePortableGrid extends TileBase implements IGrid, IPortableGrid,
} }
@Override @Override
public GridType getType() { public GridType getGridType() {
return GridType.NORMAL; return GridType.NORMAL;
} }

View File

@@ -1,6 +1,7 @@
package com.raoulvdberge.refinedstorage.util; package com.raoulvdberge.refinedstorage.util;
import com.google.common.collect.ImmutableMap; import com.google.common.collect.ImmutableMap;
import com.raoulvdberge.refinedstorage.api.util.IComparer;
import com.raoulvdberge.refinedstorage.apiimpl.API; import com.raoulvdberge.refinedstorage.apiimpl.API;
import net.minecraft.block.state.IBlockState; import net.minecraft.block.state.IBlockState;
import net.minecraft.client.Minecraft; import net.minecraft.client.Minecraft;
@@ -20,6 +21,7 @@ import net.minecraft.client.util.ITooltipFlag;
import net.minecraft.item.ItemStack; import net.minecraft.item.ItemStack;
import net.minecraft.util.BlockRenderLayer; import net.minecraft.util.BlockRenderLayer;
import net.minecraft.util.EnumFacing; import net.minecraft.util.EnumFacing;
import net.minecraft.util.NonNullList;
import net.minecraft.util.ResourceLocation; import net.minecraft.util.ResourceLocation;
import net.minecraft.util.text.TextFormatting; import net.minecraft.util.text.TextFormatting;
import net.minecraftforge.client.ForgeHooksClient; import net.minecraftforge.client.ForgeHooksClient;
@@ -257,6 +259,30 @@ public final class RenderUtils {
} }
} }
public static void addCombinedFluidsToTooltip(List<String> tooltip, NonNullList<FluidStack> stacks) {
Set<Integer> combinedIndices = new HashSet<>();
for (int i = 0; i < stacks.size(); ++i) {
if (!combinedIndices.contains(i)) {
FluidStack stack = stacks.get(i);
String data = stack.getLocalizedName();
int amount = stack.amount;
for (int j = i + 1; j < stacks.size(); ++j) {
if (API.instance().getComparer().isEqual(stack, stacks.get(j), IComparer.COMPARE_NBT)) {
amount += stacks.get(j).amount;
combinedIndices.add(j);
}
}
tooltip.add(API.instance().getQuantityFormatter().formatInBucketForm(amount) + " " + data);
}
}
}
// Copied with some tweaks from GuiUtils#drawHoveringText(@Nonnull final ItemStack stack, List<String> textLines, int mouseX, int mouseY, int screenWidth, int screenHeight, int maxTextWidth, FontRenderer font) // Copied with some tweaks from GuiUtils#drawHoveringText(@Nonnull final ItemStack stack, List<String> textLines, int mouseX, int mouseY, int screenWidth, int screenHeight, int maxTextWidth, FontRenderer font)
public static void drawTooltipWithSmallText(List<String> textLines, List<String> smallTextLines, boolean showSmallText, @Nonnull ItemStack stack, int mouseX, int mouseY, int screenWidth, int screenHeight, FontRenderer fontRenderer) { public static void drawTooltipWithSmallText(List<String> textLines, List<String> smallTextLines, boolean showSmallText, @Nonnull ItemStack stack, int mouseX, int mouseY, int screenWidth, int screenHeight, FontRenderer fontRenderer) {
// RS BEGIN // RS BEGIN

View File

@@ -106,17 +106,15 @@ public final class StackUtils {
} }
} }
public static void writeItems(IItemHandler handler, int id, NBTTagCompound tag) { public static void writeItems(IItemHandler handler, int id, NBTTagCompound tag, Function<ItemStack, NBTTagCompound> serializer) {
NBTTagList tagList = new NBTTagList(); NBTTagList tagList = new NBTTagList();
for (int i = 0; i < handler.getSlots(); i++) { for (int i = 0; i < handler.getSlots(); i++) {
if (!handler.getStackInSlot(i).isEmpty()) { if (!handler.getStackInSlot(i).isEmpty()) {
NBTTagCompound stackTag = new NBTTagCompound(); NBTTagCompound stackTag = serializer.apply(handler.getStackInSlot(i));
stackTag.setInteger(NBT_SLOT, i); stackTag.setInteger(NBT_SLOT, i);
handler.getStackInSlot(i).writeToNBT(stackTag);
tagList.appendTag(stackTag); tagList.appendTag(stackTag);
} }
} }
@@ -124,7 +122,11 @@ public final class StackUtils {
tag.setTag(String.format(NBT_INVENTORY, id), tagList); tag.setTag(String.format(NBT_INVENTORY, id), tagList);
} }
public static void readItems(IItemHandlerModifiable handler, int id, NBTTagCompound tag) { public static void writeItems(IItemHandler handler, int id, NBTTagCompound tag) {
writeItems(handler, id, tag, stack -> stack.writeToNBT(new NBTTagCompound()));
}
public static void readItems(IItemHandlerModifiable handler, int id, NBTTagCompound tag, Function<NBTTagCompound, ItemStack> deserializer) {
String name = String.format(NBT_INVENTORY, id); String name = String.format(NBT_INVENTORY, id);
if (tag.hasKey(name)) { if (tag.hasKey(name)) {
@@ -134,12 +136,16 @@ public final class StackUtils {
int slot = tagList.getCompoundTagAt(i).getInteger(NBT_SLOT); int slot = tagList.getCompoundTagAt(i).getInteger(NBT_SLOT);
if (slot >= 0 && slot < handler.getSlots()) { if (slot >= 0 && slot < handler.getSlots()) {
handler.setStackInSlot(slot, new ItemStack(tagList.getCompoundTagAt(i))); handler.setStackInSlot(slot, deserializer.apply(tagList.getCompoundTagAt(i)));
} }
} }
} }
} }
public static void readItems(IItemHandlerModifiable handler, int id, NBTTagCompound tag) {
readItems(handler, id, tag, ItemStack::new);
}
public static void writeItems(IInventory inventory, int id, NBTTagCompound tag) { public static void writeItems(IInventory inventory, int id, NBTTagCompound tag) {
NBTTagList tagList = new NBTTagList(); NBTTagList tagList = new NBTTagList();

View File

@@ -10,6 +10,7 @@ gui.refinedstorage:grid=Grid
gui.refinedstorage:grid.craft=Craft gui.refinedstorage:grid.craft=Craft
gui.refinedstorage:crafting_grid=Crafting Grid gui.refinedstorage:crafting_grid=Crafting Grid
gui.refinedstorage:pattern_grid=Pattern Grid gui.refinedstorage:pattern_grid=Pattern Grid
gui.refinedstorage:pattern_grid.fluid_amount=Fluid amount in mB
gui.refinedstorage:grid.pattern_create=Create Pattern gui.refinedstorage:grid.pattern_create=Create Pattern
gui.refinedstorage:fluid_grid=Fluid Grid gui.refinedstorage:fluid_grid=Fluid Grid
gui.refinedstorage:disk_drive=Drive gui.refinedstorage:disk_drive=Drive