Actual fix for #2051
This commit is contained in:
@@ -32,12 +32,15 @@ import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.world.World;
|
||||
import net.minecraftforge.common.util.Constants;
|
||||
import net.minecraftforge.fluids.FluidStack;
|
||||
import net.minecraftforge.items.IItemHandler;
|
||||
import net.minecraftforge.items.ItemHandlerHelper;
|
||||
import org.apache.logging.log4j.LogManager;
|
||||
import org.apache.logging.log4j.Logger;
|
||||
|
||||
import javax.annotation.Nullable;
|
||||
import java.util.*;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.IntStream;
|
||||
|
||||
public class CraftingTask implements ICraftingTask {
|
||||
private static final String NBT_REQUESTED = "Requested";
|
||||
@@ -515,7 +518,7 @@ public class CraftingTask implements ICraftingTask {
|
||||
fluidsToReceive.add(output);
|
||||
}
|
||||
|
||||
processing.add(new Processing(pattern, itemsToReceive, fluidsToReceive, new ArrayList<>(itemsToExtract.getStacks()), new ArrayList<>(fluidsToExtract.getStacks()), root));
|
||||
processing.add(new Processing(pattern, itemsToReceive, fluidsToReceive, itemsToExtract, fluidsToExtract, root));
|
||||
} else {
|
||||
if (!fluidsToExtract.isEmpty()) {
|
||||
throw new IllegalStateException("Cannot extract fluids in normal pattern!");
|
||||
@@ -678,7 +681,7 @@ public class CraftingTask implements ICraftingTask {
|
||||
} else {
|
||||
boolean hasAll = true;
|
||||
|
||||
for (ItemStack need : p.getItemsToPut()) {
|
||||
for (ItemStack need : p.getItemsToPut().getStacks()) {
|
||||
if (p.getPattern().getContainer().getConnectedInventory() == null) {
|
||||
p.setState(ProcessingState.MACHINE_NONE);
|
||||
} else {
|
||||
@@ -698,7 +701,11 @@ public class CraftingTask implements ICraftingTask {
|
||||
}
|
||||
}
|
||||
|
||||
for (FluidStack need : p.getFluidsToPut()) {
|
||||
if (hasAll && p.getState() == ProcessingState.READY && !insertIntoInventory(p.getPattern().getContainer().getConnectedInventory(), new ArrayDeque<>(p.getItemsToPut().getStacks()), Action.SIMULATE)) {
|
||||
p.setState(ProcessingState.MACHINE_DOES_NOT_ACCEPT);
|
||||
}
|
||||
|
||||
for (FluidStack need : p.getFluidsToPut().getStacks()) {
|
||||
if (p.getPattern().getContainer().getConnectedFluidInventory() == null) {
|
||||
p.setState(ProcessingState.MACHINE_NONE);
|
||||
} else {
|
||||
@@ -719,37 +726,22 @@ public class CraftingTask implements ICraftingTask {
|
||||
}
|
||||
|
||||
if (p.getState() == ProcessingState.READY && hasAll) {
|
||||
boolean abort = false;
|
||||
|
||||
for (int i = 0; i < p.getItemsToPut().size(); ++i) {
|
||||
ItemStack need = p.getItemsToPut().get(i);
|
||||
Deque<ItemStack> toInsert = new ArrayDeque<>();
|
||||
|
||||
for (ItemStack need : p.getItemsToPut().getStacks()) {
|
||||
ItemStack result = this.internalStorage.extract(need, need.getCount(), DEFAULT_EXTRACT_FLAGS, Action.PERFORM);
|
||||
if (result == null || result.getCount() != need.getCount()) {
|
||||
throw new IllegalStateException("The internal crafting inventory reported that " + need + " was available but we got " + result);
|
||||
}
|
||||
|
||||
ItemStack remainder = ItemHandlerHelper.insertItem(p.getPattern().getContainer().getConnectedInventory(), result, false);
|
||||
if (!remainder.isEmpty()) {
|
||||
LOGGER.warn("In a simulation, " + p.getPattern().getContainer().getConnectedInventory() + " reported that we could insert " + result + " but we got " + remainder + " as a remainder");
|
||||
|
||||
this.internalStorage.insert(remainder, remainder.getCount(), Action.PERFORM);
|
||||
|
||||
p.getItemsToPut().set(i, remainder);
|
||||
|
||||
abort = true;
|
||||
|
||||
break;
|
||||
}
|
||||
toInsert.add(need);
|
||||
}
|
||||
|
||||
if (abort) {
|
||||
continue;
|
||||
if (!insertIntoInventory(p.getPattern().getContainer().getConnectedInventory(), toInsert, Action.PERFORM)) {
|
||||
LOGGER.warn(p.getPattern().getContainer().getConnectedInventory() + " unexpectedly didn't accept items, the remainder has been voided!");
|
||||
}
|
||||
|
||||
for (int i = 0; i < p.getFluidsToPut().size(); ++i) {
|
||||
FluidStack need = p.getFluidsToPut().get(i);
|
||||
|
||||
for (FluidStack need : p.getFluidsToPut().getStacks()) {
|
||||
FluidStack result = this.internalFluidStorage.extract(need, need.amount, IComparer.COMPARE_NBT, Action.PERFORM);
|
||||
if (result == null || result.amount != need.amount) {
|
||||
throw new IllegalStateException("The internal crafting inventory reported that " + need + " was available but we got " + result);
|
||||
@@ -757,22 +749,10 @@ public class CraftingTask implements ICraftingTask {
|
||||
|
||||
int filled = p.getPattern().getContainer().getConnectedFluidInventory().fill(result, true);
|
||||
if (filled != result.amount) {
|
||||
LOGGER.warn("In a simulation, " + p.getPattern().getContainer().getConnectedFluidInventory() + " reported that we could fill " + result + " but we only filled " + filled);
|
||||
|
||||
this.internalFluidStorage.insert(result, result.amount - filled, Action.PERFORM);
|
||||
|
||||
p.getFluidsToPut().set(i, StackUtils.copy(result, result.amount - filled));
|
||||
|
||||
abort = true;
|
||||
|
||||
break;
|
||||
LOGGER.warn(p.getPattern().getContainer().getConnectedFluidInventory() + " unexpectedly didn't accept fluids, the remainder has been voided!");
|
||||
}
|
||||
}
|
||||
|
||||
if (abort) {
|
||||
continue;
|
||||
}
|
||||
|
||||
p.setState(ProcessingState.EXTRACTED_ALL);
|
||||
|
||||
p.getPattern().getContainer().onUsedForProcessing();
|
||||
@@ -786,6 +766,43 @@ public class CraftingTask implements ICraftingTask {
|
||||
}
|
||||
}
|
||||
|
||||
private static boolean insertIntoInventory(@Nullable IItemHandler dest, Deque<ItemStack> stacks, Action action) {
|
||||
if (dest == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
ItemStack current = stacks.poll();
|
||||
|
||||
List<Integer> availableSlots = IntStream.range(0, dest.getSlots()).boxed().collect(Collectors.toList());
|
||||
|
||||
while (current != null && !availableSlots.isEmpty()) {
|
||||
ItemStack remainder = ItemStack.EMPTY;
|
||||
|
||||
for (int i = 0; i < availableSlots.size(); ++i) {
|
||||
int slot = availableSlots.get(i);
|
||||
|
||||
// .copy() is mandatory!
|
||||
remainder = dest.insertItem(slot, current.copy(), action == Action.SIMULATE);
|
||||
|
||||
// If we inserted *something*
|
||||
if (remainder.isEmpty() || current.getCount() != remainder.getCount()) {
|
||||
availableSlots.remove(i);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (remainder.isEmpty()) { // If we inserted successfully, get a next stack.
|
||||
current = stacks.poll();
|
||||
} else if (current.getCount() == remainder.getCount()) { // If we didn't insert anything over ALL these slots, stop here.
|
||||
break;
|
||||
} else { // If we didn't insert all, continue with other slots and use our remainder.
|
||||
current = remainder;
|
||||
}
|
||||
}
|
||||
|
||||
return current == null && stacks.isEmpty();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean update() {
|
||||
if (hasMissing()) {
|
||||
@@ -1024,7 +1041,7 @@ public class CraftingTask implements ICraftingTask {
|
||||
}
|
||||
|
||||
if (processing.getState() == ProcessingState.EXTRACTED_ALL) {
|
||||
for (ItemStack put : processing.getItemsToPut()) {
|
||||
for (ItemStack put : processing.getItemsToPut().getStacks()) {
|
||||
elements.add(new CraftingMonitorElementItemRender(put, 0, 0, put.getCount(), 0, 0));
|
||||
}
|
||||
} else if (processing.getState() == ProcessingState.READY || processing.getState() == ProcessingState.MACHINE_DOES_NOT_ACCEPT || processing.getState() == ProcessingState.MACHINE_NONE || processing.getState() == ProcessingState.LOCKED) {
|
||||
@@ -1060,7 +1077,7 @@ public class CraftingTask implements ICraftingTask {
|
||||
}
|
||||
|
||||
if (processing.getState() == ProcessingState.EXTRACTED_ALL) {
|
||||
for (FluidStack put : processing.getFluidsToPut()) {
|
||||
for (FluidStack put : processing.getFluidsToPut().getStacks()) {
|
||||
elements.add(new CraftingMonitorElementFluidRender(put, 0, 0, put.amount, 0, 0));
|
||||
}
|
||||
} else if (processing.getState() == ProcessingState.READY || processing.getState() == ProcessingState.MACHINE_DOES_NOT_ACCEPT || processing.getState() == ProcessingState.MACHINE_NONE) {
|
||||
|
||||
@@ -4,16 +4,11 @@ import com.raoulvdberge.refinedstorage.api.autocrafting.ICraftingPattern;
|
||||
import com.raoulvdberge.refinedstorage.api.autocrafting.task.CraftingTaskReadException;
|
||||
import com.raoulvdberge.refinedstorage.api.network.INetwork;
|
||||
import com.raoulvdberge.refinedstorage.api.util.IStackList;
|
||||
import com.raoulvdberge.refinedstorage.util.StackUtils;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.nbt.NBTTagCompound;
|
||||
import net.minecraft.nbt.NBTTagList;
|
||||
import net.minecraftforge.common.util.Constants;
|
||||
import net.minecraftforge.fluids.FluidStack;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
class Processing {
|
||||
private static final String NBT_PATTERN = "Pattern";
|
||||
private static final String NBT_ITEMS_TO_RECEIVE = "ItemsToReceive";
|
||||
@@ -26,12 +21,12 @@ class Processing {
|
||||
private ICraftingPattern pattern;
|
||||
private IStackList<ItemStack> itemsToReceive;
|
||||
private IStackList<FluidStack> fluidsToReceive;
|
||||
private ArrayList<ItemStack> itemsToPut;
|
||||
private ArrayList<FluidStack> fluidsToPut;
|
||||
private IStackList<ItemStack> itemsToPut;
|
||||
private IStackList<FluidStack> fluidsToPut;
|
||||
private ProcessingState state = ProcessingState.READY;
|
||||
private boolean root;
|
||||
|
||||
public Processing(ICraftingPattern pattern, IStackList<ItemStack> itemsToReceive, IStackList<FluidStack> fluidsToReceive, ArrayList<ItemStack> itemsToPut, ArrayList<FluidStack> fluidsToPut, boolean root) {
|
||||
public Processing(ICraftingPattern pattern, IStackList<ItemStack> itemsToReceive, IStackList<FluidStack> fluidsToReceive, IStackList<ItemStack> itemsToPut, IStackList<FluidStack> fluidsToPut, boolean root) {
|
||||
this.pattern = pattern;
|
||||
this.itemsToReceive = itemsToReceive;
|
||||
this.fluidsToReceive = fluidsToReceive;
|
||||
@@ -45,33 +40,8 @@ class Processing {
|
||||
this.itemsToReceive = CraftingTask.readItemStackList(tag.getTagList(NBT_ITEMS_TO_RECEIVE, Constants.NBT.TAG_COMPOUND));
|
||||
this.fluidsToReceive = CraftingTask.readFluidStackList(tag.getTagList(NBT_FLUIDS_TO_RECEIVE, Constants.NBT.TAG_COMPOUND));
|
||||
this.root = tag.getBoolean(NBT_ROOT);
|
||||
|
||||
this.itemsToPut = new ArrayList<>();
|
||||
|
||||
NBTTagList itemsToPutList = tag.getTagList(NBT_ITEMS_TO_PUT, Constants.NBT.TAG_COMPOUND);
|
||||
for (int i = 0; i < itemsToPutList.tagCount(); ++i) {
|
||||
ItemStack stack = StackUtils.deserializeStackFromNbt(itemsToPutList.getCompoundTagAt(i));
|
||||
|
||||
if (stack.isEmpty()) {
|
||||
throw new CraftingTaskReadException("Stack is empty!");
|
||||
}
|
||||
|
||||
itemsToPut.add(stack);
|
||||
}
|
||||
|
||||
this.fluidsToPut = new ArrayList<>();
|
||||
|
||||
NBTTagList fluidsToPutList = tag.getTagList(NBT_FLUIDS_TO_PUT, Constants.NBT.TAG_COMPOUND);
|
||||
for (int i = 0; i < fluidsToPutList.tagCount(); ++i) {
|
||||
FluidStack stack = FluidStack.loadFluidStackFromNBT(fluidsToPutList.getCompoundTagAt(i));
|
||||
|
||||
if (stack == null) {
|
||||
throw new CraftingTaskReadException("Stack is empty!");
|
||||
}
|
||||
|
||||
fluidsToPut.add(stack);
|
||||
}
|
||||
|
||||
this.itemsToPut = CraftingTask.readItemStackList(tag.getTagList(NBT_ITEMS_TO_PUT, Constants.NBT.TAG_COMPOUND));
|
||||
this.fluidsToPut = CraftingTask.readFluidStackList(tag.getTagList(NBT_FLUIDS_TO_PUT, Constants.NBT.TAG_COMPOUND));
|
||||
this.state = ProcessingState.values()[tag.getInteger(NBT_STATE)];
|
||||
}
|
||||
|
||||
@@ -87,11 +57,11 @@ class Processing {
|
||||
return fluidsToReceive;
|
||||
}
|
||||
|
||||
public List<ItemStack> getItemsToPut() {
|
||||
public IStackList<ItemStack> getItemsToPut() {
|
||||
return itemsToPut;
|
||||
}
|
||||
|
||||
public List<FluidStack> getFluidsToPut() {
|
||||
public IStackList<FluidStack> getFluidsToPut() {
|
||||
return fluidsToPut;
|
||||
}
|
||||
|
||||
@@ -114,21 +84,8 @@ class Processing {
|
||||
tag.setTag(NBT_ITEMS_TO_RECEIVE, CraftingTask.writeItemStackList(itemsToReceive));
|
||||
tag.setTag(NBT_FLUIDS_TO_RECEIVE, CraftingTask.writeFluidStackList(fluidsToReceive));
|
||||
tag.setBoolean(NBT_ROOT, root);
|
||||
|
||||
NBTTagList itemsToPutList = new NBTTagList();
|
||||
for (ItemStack stack : this.itemsToPut) {
|
||||
itemsToPutList.appendTag(StackUtils.serializeStackToNbt(stack));
|
||||
}
|
||||
|
||||
tag.setTag(NBT_ITEMS_TO_PUT, itemsToPutList);
|
||||
|
||||
NBTTagList fluidsToPutList = new NBTTagList();
|
||||
for (FluidStack stack : this.fluidsToPut) {
|
||||
fluidsToPutList.appendTag(stack.writeToNBT(new NBTTagCompound()));
|
||||
}
|
||||
|
||||
tag.setTag(NBT_FLUIDS_TO_PUT, fluidsToPutList);
|
||||
|
||||
tag.setTag(NBT_ITEMS_TO_PUT, CraftingTask.writeItemStackList(itemsToPut));
|
||||
tag.setTag(NBT_FLUIDS_TO_PUT, CraftingTask.writeFluidStackList(fluidsToPut));
|
||||
tag.setInteger(NBT_STATE, state.ordinal());
|
||||
|
||||
return tag;
|
||||
|
||||
Reference in New Issue
Block a user