aboutsummaryrefslogtreecommitdiff
path: root/src/main
diff options
context:
space:
mode:
Diffstat (limited to 'src/main')
-rw-r--r--src/main/java/gregtech/api/fluid/FluidTankGT.java15
-rw-r--r--src/main/java/gregtech/api/interfaces/fluid/IFluidStore.java22
-rw-r--r--src/main/java/gregtech/api/interfaces/modularui/ControllerWithOptionalFeatures.java26
-rw-r--r--src/main/java/gregtech/api/interfaces/tileentity/IVoidable.java64
-rw-r--r--src/main/java/gregtech/api/metatileentity/MetaTileEntity.java5
-rw-r--r--src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_Hatch_Output.java29
-rw-r--r--src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_MultiBlockBase.java82
-rw-r--r--src/main/java/gregtech/api/multitileentity/multiblock/base/Controller.java29
-rw-r--r--src/main/java/gregtech/api/util/GT_ParallelHelper.java4
-rw-r--r--src/main/java/gregtech/api/util/GT_Recipe.java4
-rw-r--r--src/main/java/gregtech/api/util/GT_RecipeBuilder.java39
-rw-r--r--src/main/java/gregtech/api/util/GT_Utility.java4
-rw-r--r--src/main/java/gregtech/api/util/OutputHatchWrapper.java65
-rw-r--r--src/main/java/gregtech/api/util/VoidProtectionHelper.java188
-rw-r--r--src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_DistillationTower.java6
-rw-r--r--src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_ElectricBlastFurnace.java70
16 files changed, 415 insertions, 237 deletions
diff --git a/src/main/java/gregtech/api/fluid/FluidTankGT.java b/src/main/java/gregtech/api/fluid/FluidTankGT.java
index 2102f725ae..0c224985e6 100644
--- a/src/main/java/gregtech/api/fluid/FluidTankGT.java
+++ b/src/main/java/gregtech/api/fluid/FluidTankGT.java
@@ -6,15 +6,18 @@ import java.util.ArrayList;
import java.util.List;
import java.util.Map;
+import javax.annotation.Nonnull;
+
import net.minecraft.nbt.NBTTagCompound;
import net.minecraftforge.fluids.Fluid;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fluids.FluidTankInfo;
import net.minecraftforge.fluids.IFluidTank;
+import gregtech.api.interfaces.fluid.IFluidStore;
import gregtech.api.util.GT_Utility;
-public class FluidTankGT implements IFluidTank {
+public class FluidTankGT implements IFluidTank, IFluidStore {
public final FluidTankGT[] AS_ARRAY = new FluidTankGT[] { this };
private FluidStack mFluid;
@@ -469,4 +472,14 @@ public class FluidTankGT implements IFluidTank {
}
return fluidStacks.toArray(new FluidStack[0]);
}
+
+ @Override
+ public boolean isEmptyAndAcceptsAnyFluid() {
+ return getFluidAmount() == 0;
+ }
+
+ @Override
+ public boolean canStoreFluid(@Nonnull FluidStack fluidStack) {
+ return GT_Utility.areFluidsEqual(mFluid, fluidStack);
+ }
}
diff --git a/src/main/java/gregtech/api/interfaces/fluid/IFluidStore.java b/src/main/java/gregtech/api/interfaces/fluid/IFluidStore.java
new file mode 100644
index 0000000000..047cf4df5b
--- /dev/null
+++ b/src/main/java/gregtech/api/interfaces/fluid/IFluidStore.java
@@ -0,0 +1,22 @@
+package gregtech.api.interfaces.fluid;
+
+import javax.annotation.Nonnull;
+
+import net.minecraftforge.fluids.FluidStack;
+import net.minecraftforge.fluids.IFluidTank;
+
+/**
+ * Objects implementing this interface can be used for storing certain fluid, especially for recipe output.
+ */
+public interface IFluidStore extends IFluidTank {
+
+ /**
+ * @return If this does not have partially filled fluid nor have restriction on what fluid to accept.
+ */
+ boolean isEmptyAndAcceptsAnyFluid();
+
+ /**
+ * @return Whether to allow given fluid to be inserted into this.
+ */
+ boolean canStoreFluid(@Nonnull FluidStack fluidStack);
+}
diff --git a/src/main/java/gregtech/api/interfaces/modularui/ControllerWithOptionalFeatures.java b/src/main/java/gregtech/api/interfaces/modularui/ControllerWithOptionalFeatures.java
index cf740a6bc6..04b6b4e6a9 100644
--- a/src/main/java/gregtech/api/interfaces/modularui/ControllerWithOptionalFeatures.java
+++ b/src/main/java/gregtech/api/interfaces/modularui/ControllerWithOptionalFeatures.java
@@ -19,6 +19,7 @@ import com.gtnewhorizons.modularui.common.widget.FakeSyncWidget;
import gregtech.api.enums.SoundResource;
import gregtech.api.enums.VoidingMode;
import gregtech.api.gui.modularui.GT_UITextures;
+import gregtech.api.interfaces.tileentity.IVoidable;
/**
* Machines implementing this interface can have logic and GUI buttons
@@ -31,7 +32,7 @@ import gregtech.api.gui.modularui.GT_UITextures;
* <li>Recipe locking</li>
* </ul>
*/
-public interface ControllerWithOptionalFeatures {
+public interface ControllerWithOptionalFeatures extends IVoidable {
boolean isAllowedToWork();
@@ -72,29 +73,6 @@ public interface ControllerWithOptionalFeatures {
return (ButtonWidget) button;
}
- /**
- * @return if this machine can prevent excess item and fluid from voiding.
- */
- boolean supportsVoidProtection();
-
- /**
- * @return if this machine is configured to not void excess item.
- */
- default boolean protectsExcessItem() {
- return supportsVoidProtection() && getVoidingMode().protectItem;
- }
-
- /**
- * @return if this machine is configured to not void excess fluid.
- */
- default boolean protectsExcessFluid() {
- return supportsVoidProtection() && getVoidingMode().protectFluid;
- }
-
- VoidingMode getVoidingMode();
-
- void setVoidingMode(VoidingMode mode);
-
Pos2d getVoidingModeButtonPos();
default ButtonWidget createVoidExcessButton(IWidgetBuilder<?> builder) {
diff --git a/src/main/java/gregtech/api/interfaces/tileentity/IVoidable.java b/src/main/java/gregtech/api/interfaces/tileentity/IVoidable.java
new file mode 100644
index 0000000000..d6325e8597
--- /dev/null
+++ b/src/main/java/gregtech/api/interfaces/tileentity/IVoidable.java
@@ -0,0 +1,64 @@
+package gregtech.api.interfaces.tileentity;
+
+import java.util.List;
+
+import net.minecraft.item.ItemStack;
+import net.minecraftforge.fluids.FluidStack;
+
+import gregtech.api.enums.VoidingMode;
+import gregtech.api.interfaces.fluid.IFluidStore;
+
+/**
+ * Machines implementing this interface can have logic to configure whether to void excess output or not.
+ */
+public interface IVoidable {
+
+ /**
+ * @return if this machine can prevent excess item and fluid from voiding.
+ */
+ boolean supportsVoidProtection();
+
+ /**
+ * @return if this machine is configured to not void excess item.
+ */
+ default boolean protectsExcessItem() {
+ return supportsVoidProtection() && getVoidingMode().protectItem;
+ }
+
+ /**
+ * @return if this machine is configured to not void excess fluid.
+ */
+ default boolean protectsExcessFluid() {
+ return supportsVoidProtection() && getVoidingMode().protectFluid;
+ }
+
+ VoidingMode getVoidingMode();
+
+ void setVoidingMode(VoidingMode mode);
+
+ /**
+ * @param toOutput List of items this machine is going to output.
+ * @return List of slots available for item outputs. Null element represents empty slot.
+ */
+ List<ItemStack> getItemOutputSlots(ItemStack[] toOutput);
+
+ /**
+ * @param toOutput List of fluids this machine is going to output.
+ * @return List of slots available for fluid outputs.
+ */
+ List<? extends IFluidStore> getFluidOutputSlots(FluidStack[] toOutput);
+
+ /**
+ * @return If this machine has ability to dump item outputs to ME network.
+ * This doesn't need to check if it can actually dump to ME,
+ * as this might be called every tick and cause lag.
+ */
+ boolean canDumpItemToME();
+
+ /**
+ * @return If this machine has ability to dump fluid outputs to ME network.
+ * This doesn't need to check if it can actually dump to ME,
+ * as this might be called every tick and cause lag.
+ */
+ boolean canDumpFluidToME();
+}
diff --git a/src/main/java/gregtech/api/metatileentity/MetaTileEntity.java b/src/main/java/gregtech/api/metatileentity/MetaTileEntity.java
index bb3095084a..a6c5497e8e 100644
--- a/src/main/java/gregtech/api/metatileentity/MetaTileEntity.java
+++ b/src/main/java/gregtech/api/metatileentity/MetaTileEntity.java
@@ -173,6 +173,11 @@ public abstract class MetaTileEntity implements IMetaTileEntity, IMachineCallbac
}
}
+ public boolean isValid() {
+ return getBaseMetaTileEntity() != null && getBaseMetaTileEntity().getMetaTileEntity() == this
+ && !getBaseMetaTileEntity().isDead();
+ }
+
@Override
public ItemStack getStackForm(long aAmount) {
return new ItemStack(GregTech_API.sBlockMachines, (int) aAmount, getBaseMetaTileEntity().getMetaTileID());
diff --git a/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_Hatch_Output.java b/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_Hatch_Output.java
index fe3144f3a3..d488eaae3e 100644
--- a/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_Hatch_Output.java
+++ b/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_Hatch_Output.java
@@ -5,6 +5,8 @@ import static gregtech.api.enums.Textures.BlockIcons.OVERLAY_PIPE_OUT;
import java.lang.ref.WeakReference;
+import javax.annotation.Nonnull;
+
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
@@ -24,6 +26,7 @@ import gregtech.GT_Mod;
import gregtech.api.gui.modularui.GT_UIInfos;
import gregtech.api.gui.modularui.GT_UITextures;
import gregtech.api.interfaces.ITexture;
+import gregtech.api.interfaces.fluid.IFluidStore;
import gregtech.api.interfaces.metatileentity.IFluidLockable;
import gregtech.api.interfaces.modularui.IAddUIWidgets;
import gregtech.api.interfaces.tileentity.IGregTechTileEntity;
@@ -33,7 +36,8 @@ import gregtech.api.util.GT_ModHandler;
import gregtech.api.util.GT_Utility;
import gregtech.common.gui.modularui.widget.FluidLockWidget;
-public class GT_MetaTileEntity_Hatch_Output extends GT_MetaTileEntity_Hatch implements IFluidLockable, IAddUIWidgets {
+public class GT_MetaTileEntity_Hatch_Output extends GT_MetaTileEntity_Hatch
+ implements IFluidStore, IFluidLockable, IAddUIWidgets {
private String lockedFluidName = null;
private WeakReference<EntityPlayer> playerThatLockedfluid = null;
@@ -403,12 +407,27 @@ public class GT_MetaTileEntity_Hatch_Output extends GT_MetaTileEntity_Hatch impl
return true;
}
- public boolean canStoreFluid(Fluid fluid) {
+ @Override
+ public boolean isEmptyAndAcceptsAnyFluid() {
+ return mMode == 0 && getFluidAmount() == 0;
+ }
+
+ @Override
+ public boolean canStoreFluid(@Nonnull FluidStack fluidStack) {
+ if (mFluid != null && !GT_Utility.areFluidsEqual(mFluid, fluidStack)) {
+ return false;
+ }
if (isFluidLocked()) {
- if (lockedFluidName == null) return true;
- return lockedFluidName.equals(fluid.getName());
+ if (lockedFluidName == null) {
+ return true;
+ }
+ return lockedFluidName.equals(
+ fluidStack.getFluid()
+ .getName());
+ }
+ if (GT_ModHandler.isSteam(fluidStack)) {
+ return outputsSteam();
}
- if (GT_ModHandler.isSteam(new FluidStack(fluid, 0))) return outputsSteam();
return outputsLiquids();
}
diff --git a/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_MultiBlockBase.java b/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_MultiBlockBase.java
index a60f9b1cd2..7884301e97 100644
--- a/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_MultiBlockBase.java
+++ b/src/main/java/gregtech/api/metatileentity/implementations/GT_MetaTileEntity_MultiBlockBase.java
@@ -6,7 +6,9 @@ import static mcp.mobius.waila.api.SpecialChars.RED;
import static mcp.mobius.waila.api.SpecialChars.RESET;
import java.util.ArrayList;
+import java.util.Collection;
import java.util.List;
+import java.util.stream.Collectors;
import javax.annotation.Nonnull;
import javax.annotation.Nullable;
@@ -14,6 +16,7 @@ import javax.annotation.Nullable;
import net.minecraft.client.Minecraft;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.entity.player.EntityPlayerMP;
+import net.minecraft.inventory.IInventory;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.NBTTagCompound;
import net.minecraft.tileentity.TileEntity;
@@ -43,6 +46,7 @@ import gregtech.api.enums.SoundResource;
import gregtech.api.enums.VoidingMode;
import gregtech.api.gui.modularui.GT_UIInfos;
import gregtech.api.gui.modularui.GT_UITextures;
+import gregtech.api.interfaces.fluid.IFluidStore;
import gregtech.api.interfaces.metatileentity.IMetaTileEntity;
import gregtech.api.interfaces.modularui.ControllerWithOptionalFeatures;
import gregtech.api.interfaces.modularui.IAddGregtechLogo;
@@ -57,6 +61,8 @@ import gregtech.api.util.GT_Recipe.GT_Recipe_Map;
import gregtech.client.GT_SoundLoop;
import gregtech.common.GT_Pollution;
import gregtech.common.items.GT_MetaGenerated_Tool_01;
+import gregtech.common.tileentities.machines.GT_MetaTileEntity_Hatch_OutputBus_ME;
+import gregtech.common.tileentities.machines.GT_MetaTileEntity_Hatch_Output_ME;
import gregtech.common.tileentities.machines.multi.GT_MetaTileEntity_DrillerBase;
import gregtech.common.tileentities.machines.multi.GT_MetaTileEntity_LargeTurbine;
import mcp.mobius.waila.api.IWailaConfigHandler;
@@ -126,11 +132,15 @@ public abstract class GT_MetaTileEntity_MultiBlockBase extends MetaTileEntity
voidingMode = supportsVoidProtection() ? VoidingMode.VOID_NONE : VoidingMode.VOID_ALL;
}
+ // maybe remove this at some point?
public static boolean isValidMetaTileEntity(MetaTileEntity aMetaTileEntity) {
- return aMetaTileEntity.getBaseMetaTileEntity() != null && aMetaTileEntity.getBaseMetaTileEntity()
- .getMetaTileEntity() == aMetaTileEntity
- && !aMetaTileEntity.getBaseMetaTileEntity()
- .isDead();
+ return aMetaTileEntity.isValid();
+ }
+
+ public static <T extends MetaTileEntity> List<T> filterValidMetaTileEntities(Collection<T> metaTileEntities) {
+ return metaTileEntities.stream()
+ .filter(MetaTileEntity::isValid)
+ .collect(Collectors.toList());
}
@Override
@@ -907,7 +917,7 @@ public abstract class GT_MetaTileEntity_MultiBlockBase extends MetaTileEntity
if (!isValidMetaTileEntity(tHatch) || (restrictiveHatchesOnly && tHatch.mMode == 0)) {
continue;
}
- if (!tHatch.canStoreFluid(copiedFluidStack.getFluid())) continue;
+ if (!tHatch.canStoreFluid(copiedFluidStack)) continue;
int tAmount = tHatch.fill(copiedFluidStack, false);
if (tAmount >= copiedFluidStack.amount) {
boolean filled = tHatch.fill(copiedFluidStack, true) >= copiedFluidStack.amount;
@@ -1560,7 +1570,7 @@ public abstract class GT_MetaTileEntity_MultiBlockBase extends MetaTileEntity
return true;
}
- VoidProtectionHelper voidProtectionHelper = new VoidProtectionHelper().setController(this)
+ VoidProtectionHelper voidProtectionHelper = new VoidProtectionHelper().setMachine(this)
.setItemOutputs(items)
.setFluidOutputs(fluids)
.build();
@@ -1603,6 +1613,66 @@ public abstract class GT_MetaTileEntity_MultiBlockBase extends MetaTileEntity
}
@Override
+ public List<ItemStack> getItemOutputSlots(ItemStack[] toOutput) {
+ List<ItemStack> ret = new ArrayList<>();
+ for (final GT_MetaTileEntity_Hatch tBus : filterValidMetaTileEntities(mOutputBusses)) {
+ final IInventory tBusInv = tBus.getBaseMetaTileEntity();
+ for (int i = 0; i < tBusInv.getSizeInventory(); i++) {
+ ret.add(tBus.getStackInSlot(i));
+ }
+ }
+ return ret;
+ }
+
+ @Override
+ public List<? extends IFluidStore> getFluidOutputSlots(FluidStack[] toOutput) {
+ return filterValidMetaTileEntities(mOutputHatches);
+ }
+
+ /**
+ * Util method for DT-like structure to collect list of output hatches.
+ */
+ protected <T extends GT_MetaTileEntity_Hatch_Output> List<? extends IFluidStore> getFluidOutputSlotsByLayer(
+ FluidStack[] toOutput, List<List<T>> hatchesByLayer) {
+ List<IFluidStore> ret = new ArrayList<>();
+ for (int i = 0; i < toOutput.length; i++) {
+ if (i >= hatchesByLayer.size()) {
+ break;
+ }
+ FluidStack fluidOutputForLayer = toOutput[i];
+ for (GT_MetaTileEntity_Hatch_Output hatch : hatchesByLayer.get(i)) {
+ if (!hatch.isValid()) continue;
+ if (fluidOutputForLayer != null) {
+ ret.add(new OutputHatchWrapper(hatch, f -> GT_Utility.areFluidsEqual(f, fluidOutputForLayer)));
+ } else {
+ ret.add(hatch);
+ }
+ }
+ }
+ return ret;
+ }
+
+ @Override
+ public boolean canDumpItemToME() {
+ for (GT_MetaTileEntity_Hatch tHatch : filterValidMetaTileEntities(mOutputBusses)) {
+ if (tHatch instanceof GT_MetaTileEntity_Hatch_OutputBus_ME) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ @Override
+ public boolean canDumpFluidToME() {
+ for (IFluidStore tHatch : getFluidOutputSlots(new FluidStack[0])) {
+ if (tHatch instanceof GT_MetaTileEntity_Hatch_Output_ME) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ @Override
public Pos2d getVoidingModeButtonPos() {
return new Pos2d(8, 91);
}
diff --git a/src/main/java/gregtech/api/multitileentity/multiblock/base/Controller.java b/src/main/java/gregtech/api/multitileentity/multiblock/base/Controller.java
index afc456f41a..14e7883398 100644
--- a/src/main/java/gregtech/api/multitileentity/multiblock/base/Controller.java
+++ b/src/main/java/gregtech/api/multitileentity/multiblock/base/Controller.java
@@ -52,6 +52,7 @@ import com.gtnewhorizon.structurelib.structure.ISurvivalBuildEnvironment;
import com.gtnewhorizon.structurelib.util.Vec3Impl;
import com.gtnewhorizons.modularui.api.ModularUITextures;
import com.gtnewhorizons.modularui.api.drawable.ItemDrawable;
+import com.gtnewhorizons.modularui.api.forge.IItemHandler;
import com.gtnewhorizons.modularui.api.forge.IItemHandlerModifiable;
import com.gtnewhorizons.modularui.api.forge.ItemStackHandler;
import com.gtnewhorizons.modularui.api.forge.ListItemHandler;
@@ -78,6 +79,7 @@ import gregtech.api.enums.VoidingMode;
import gregtech.api.fluid.FluidTankGT;
import gregtech.api.gui.modularui.GT_UITextures;
import gregtech.api.interfaces.IDescribable;
+import gregtech.api.interfaces.fluid.IFluidStore;
import gregtech.api.interfaces.modularui.ControllerWithOptionalFeatures;
import gregtech.api.logic.PowerLogic;
import gregtech.api.logic.ProcessingLogic;
@@ -1978,6 +1980,33 @@ public abstract class Controller<T extends Controller<T>> extends MultiTileBasic
}
@Override
+ public List<ItemStack> getItemOutputSlots(ItemStack[] toOutput) {
+ List<ItemStack> ret = new ArrayList<>();
+ IItemHandler inv = getOutputInventory();
+ if (inv != null && inv.getSlots() > 0) {
+ for (int i = 0; i < inv.getSlots(); i++) {
+ ret.add(inv.getStackInSlot(i));
+ }
+ }
+ return ret;
+ }
+
+ @Override
+ public List<? extends IFluidStore> getFluidOutputSlots(FluidStack[] toOutput) {
+ return Arrays.asList(getOutputTanks());
+ }
+
+ @Override
+ public boolean canDumpItemToME() {
+ return false;
+ }
+
+ @Override
+ public boolean canDumpFluidToME() {
+ return false;
+ }
+
+ @Override
public Pos2d getVoidingModeButtonPos() {
return new Pos2d(54, 0);
}
diff --git a/src/main/java/gregtech/api/util/GT_ParallelHelper.java b/src/main/java/gregtech/api/util/GT_ParallelHelper.java
index ff45f8213b..66f1bac8b8 100644
--- a/src/main/java/gregtech/api/util/GT_ParallelHelper.java
+++ b/src/main/java/gregtech/api/util/GT_ParallelHelper.java
@@ -299,9 +299,9 @@ public class GT_ParallelHelper {
if (protectExcessItem || protectExcessFluid) {
VoidProtectionHelper voidProtectionHelper = new VoidProtectionHelper();
if (mMachineMeta != null) {
- voidProtectionHelper.setController(mMachineMeta, protectExcessItem, protectExcessFluid);
+ voidProtectionHelper.setMachine(mMachineMeta, protectExcessItem, protectExcessFluid);
} else if (mMachineMulti != null) {
- voidProtectionHelper.setController(mMachineMulti, protectExcessItem, protectExcessFluid);
+ voidProtectionHelper.setMachine(mMachineMulti, protectExcessItem, protectExcessFluid);
}
voidProtectionHelper.setItemOutputs(mRecipe.mOutputs)
.setFluidOutputs(mRecipe.mFluidOutputs)
diff --git a/src/main/java/gregtech/api/util/GT_Recipe.java b/src/main/java/gregtech/api/util/GT_Recipe.java
index 6f0c7c403e..43dfd0c5b2 100644
--- a/src/main/java/gregtech/api/util/GT_Recipe.java
+++ b/src/main/java/gregtech/api/util/GT_Recipe.java
@@ -172,8 +172,8 @@ public class GT_Recipe implements Comparable<GT_Recipe> {
public List<List<StackTraceElement>> stackTraces = new ArrayList<>();
private GT_Recipe(GT_Recipe aRecipe, boolean shallow) {
- mInputs = shallow ? aRecipe.mInputs : GT_Utility.copyStackArray((Object[]) aRecipe.mInputs);
- mOutputs = shallow ? aRecipe.mOutputs : GT_Utility.copyStackArray((Object[]) aRecipe.mOutputs);
+ mInputs = shallow ? aRecipe.mInputs : GT_Utility.copyItemArray(aRecipe.mInputs);
+ mOutputs = shallow ? aRecipe.mOutputs : GT_Utility.copyItemArray(aRecipe.mOutputs);
mSpecialItems = aRecipe.mSpecialItems;
mChances = aRecipe.mChances;
mFluidInputs = shallow ? aRecipe.mFluidInputs : GT_Utility.copyFluidArray(aRecipe.mFluidInputs);
diff --git a/src/main/java/gregtech/api/util/GT_RecipeBuilder.java b/src/main/java/gregtech/api/util/GT_RecipeBuilder.java
index 41ad02e242..e05798479e 100644
--- a/src/main/java/gregtech/api/util/GT_RecipeBuilder.java
+++ b/src/main/java/gregtech/api/util/GT_RecipeBuilder.java
@@ -1,5 +1,8 @@
package gregtech.api.util;
+import static gregtech.api.util.GT_Utility.copyFluidArray;
+import static gregtech.api.util.GT_Utility.copyItemArray;
+
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
@@ -378,26 +381,6 @@ public class GT_RecipeBuilder {
return metadata(GT_RecipeConstants.LOW_GRAVITY, true);
}
- private static ItemStack[] copy(ItemStack[] arr) {
- if (arr == null) return null;
- ItemStack[] ret = new ItemStack[arr.length];
- for (int i = 0; i < arr.length; i++) {
- if (arr[i] == null) continue;
- ret[i] = arr[i].copy();
- }
- return ret;
- }
-
- private static FluidStack[] copy(FluidStack[] arr) {
- if (arr == null) return null;
- FluidStack[] ret = new FluidStack[arr.length];
- for (int i = 0; i < arr.length; i++) {
- if (arr[i] == null) continue;
- ret[i] = arr[i].copy();
- }
- return ret;
- }
-
private static <T> T[] copy(T[] arr) {
return arr == null ? null : arr.clone();
}
@@ -414,12 +397,12 @@ public class GT_RecipeBuilder {
*/
public GT_RecipeBuilder copy() {
return new GT_RecipeBuilder(
- copy(inputsBasic),
+ copyItemArray(inputsBasic),
copy(inputsOreDict),
- copy(outputs),
+ copyItemArray(outputs),
copy(alts),
- copy(fluidInputs),
- copy(fluidOutputs),
+ copyFluidArray(fluidInputs),
+ copyFluidArray(fluidOutputs),
copy(chances),
special,
duration,
@@ -441,12 +424,12 @@ public class GT_RecipeBuilder {
*/
public GT_RecipeBuilder copyNoMetadata() {
return new GT_RecipeBuilder(
- copy(inputsBasic),
+ copyItemArray(inputsBasic),
copy(inputsOreDict),
- copy(outputs),
+ copyItemArray(outputs),
copy(alts),
- copy(fluidInputs),
- copy(fluidOutputs),
+ copyFluidArray(fluidInputs),
+ copyFluidArray(fluidOutputs),
copy(chances),
special,
duration,
diff --git a/src/main/java/gregtech/api/util/GT_Utility.java b/src/main/java/gregtech/api/util/GT_Utility.java
index 5e8e9efbca..7f423e0c19 100644
--- a/src/main/java/gregtech/api/util/GT_Utility.java
+++ b/src/main/java/gregtech/api/util/GT_Utility.java
@@ -2816,12 +2816,14 @@ public class GT_Utility {
}
public static FluidStack[] copyFluidArray(FluidStack... aStacks) {
+ if (aStacks == null) return null;
FluidStack[] rStacks = new FluidStack[aStacks.length];
for (int i = 0; i < aStacks.length; i++) if (aStacks[i] != null) rStacks[i] = aStacks[i].copy();
return rStacks;
}
- public static ItemStack[] copyStackArray(Object... aStacks) {
+ public static ItemStack[] copyItemArray(ItemStack... aStacks) {
+ if (aStacks == null) return null;
ItemStack[] rStacks = new ItemStack[aStacks.length];
for (int i = 0; i < aStacks.length; i++) rStacks[i] = copy(aStacks[i]);
return rStacks;
diff --git a/src/main/java/gregtech/api/util/OutputHatchWrapper.java b/src/main/java/gregtech/api/util/OutputHatchWrapper.java
new file mode 100644
index 0000000000..b2e74d24cf
--- /dev/null
+++ b/src/main/java/gregtech/api/util/OutputHatchWrapper.java
@@ -0,0 +1,65 @@
+package gregtech.api.util;
+
+import java.util.function.Predicate;
+
+import net.minecraftforge.fluids.FluidStack;
+import net.minecraftforge.fluids.FluidTankInfo;
+
+import org.jetbrains.annotations.NotNull;
+
+import gregtech.api.interfaces.fluid.IFluidStore;
+import gregtech.api.metatileentity.implementations.GT_MetaTileEntity_Hatch_Output;
+
+/**
+ * Wrapper for output hatch to allow multiblocks to apply specific filter.
+ */
+public class OutputHatchWrapper implements IFluidStore {
+
+ private final GT_MetaTileEntity_Hatch_Output outputHatch;
+ private final Predicate<FluidStack> filter;
+
+ public OutputHatchWrapper(GT_MetaTileEntity_Hatch_Output outputHatch, Predicate<FluidStack> filter) {
+ this.outputHatch = outputHatch;
+ this.filter = filter;
+ }
+
+ @Override
+ public FluidStack getFluid() {
+ return outputHatch.getFluid();
+ }
+
+ @Override
+ public int getFluidAmount() {
+ return outputHatch.getFluidAmount();
+ }
+
+ @Override
+ public int getCapacity() {
+ return outputHatch.getCapacity();
+ }
+
+ @Override
+ public FluidTankInfo getInfo() {
+ return outputHatch.getInfo();
+ }
+
+ @Override
+ public int fill(FluidStack resource, boolean doFill) {
+ return outputHatch.fill(resource, doFill);
+ }
+
+ @Override
+ public FluidStack drain(int maxDrain, boolean doDrain) {
+ return outputHatch.drain(maxDrain, doDrain);
+ }
+
+ @Override
+ public boolean isEmptyAndAcceptsAnyFluid() {
+ return outputHatch.isEmptyAndAcceptsAnyFluid();
+ }
+
+ @Override
+ public boolean canStoreFluid(@NotNull FluidStack fluidStack) {
+ return outputHatch.canStoreFluid(fluidStack) && filter.test(fluidStack);
+ }
+}
diff --git a/src/main/java/gregtech/api/util/VoidProtectionHelper.java b/src/main/java/gregtech/api/util/VoidProtectionHelper.java
index 9a66a55874..fe80bc97b4 100644
--- a/src/main/java/gregtech/api/util/VoidProtectionHelper.java
+++ b/src/main/java/gregtech/api/util/VoidProtectionHelper.java
@@ -1,28 +1,19 @@
package gregtech.api.util;
-import java.util.ArrayList;
-import java.util.Arrays;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.PriorityQueue;
-import java.util.function.BiFunction;
-import java.util.function.Function;
-import net.minecraft.inventory.IInventory;
import net.minecraft.item.ItemStack;
import net.minecraftforge.fluids.FluidStack;
-import net.minecraftforge.fluids.IFluidTank;
import com.gtnewhorizon.gtnhlib.util.map.ItemStackMap;
-import com.gtnewhorizons.modularui.api.forge.IItemHandler;
-import gregtech.api.metatileentity.implementations.GT_MetaTileEntity_Hatch;
+import gregtech.api.interfaces.fluid.IFluidStore;
+import gregtech.api.interfaces.tileentity.IVoidable;
import gregtech.api.metatileentity.implementations.GT_MetaTileEntity_MultiBlockBase;
-import gregtech.api.multitileentity.multiblock.base.Controller;
-import gregtech.common.tileentities.machines.GT_MetaTileEntity_Hatch_OutputBus_ME;
-import gregtech.common.tileentities.machines.GT_MetaTileEntity_Hatch_Output_ME;
/**
* Helper class to calculate how many parallels of items / fluids can fit in the output buses / hatches.
@@ -30,13 +21,9 @@ import gregtech.common.tileentities.machines.GT_MetaTileEntity_Hatch_Output_ME;
public class VoidProtectionHelper {
/**
- * A MetaTileEntity Controller
+ * Machine used for calculation
*/
- private GT_MetaTileEntity_MultiBlockBase machineMeta;
- /**
- * A MultiTileEntity Controller
- */
- private Controller<?> machineMulti;
+ private IVoidable machine;
/**
* Does void protection enabled for items
*/
@@ -66,37 +53,39 @@ public class VoidProtectionHelper {
/**
* Sets MetaTE controller, with current configuration for void protection mode.
+ *
+ * @deprecated Use {@link #setMachine(IVoidable)}
*/
+ @Deprecated
public VoidProtectionHelper setController(GT_MetaTileEntity_MultiBlockBase machineMeta) {
return setController(machineMeta, machineMeta.protectsExcessItem(), machineMeta.protectsExcessFluid());
}
/**
* Sets MetaTE controller, with void protection mode forcibly.
+ *
+ * @deprecated Use {@link #setMachine(IVoidable, boolean, boolean)}
*/
+ @Deprecated
public VoidProtectionHelper setController(GT_MetaTileEntity_MultiBlockBase machineMeta, boolean protectExcessItem,
boolean protectExcessFluid) {
- this.protectExcessItem = protectExcessItem;
- this.protectExcessFluid = protectExcessFluid;
- this.machineMeta = machineMeta;
- return this;
+ return setMachine(machineMeta, protectExcessItem, protectExcessFluid);
}
/**
- * Sets MuTE controller, with current configuration for void protection mode.
+ * Sets machine, with current configuration for void protection mode.
*/
- public VoidProtectionHelper setController(Controller<?> machineMulti) {
- return setController(machineMulti, machineMulti.protectsExcessItem(), machineMulti.protectsExcessFluid());
+ public VoidProtectionHelper setMachine(IVoidable machine) {
+ return setMachine(machine, machine.protectsExcessItem(), machine.protectsExcessFluid());
}
/**
- * Sets MuTE controller, with void protection mode forcibly.
+ * Sets machine, with void protection mode forcibly.
*/
- public VoidProtectionHelper setController(Controller<?> machineMulti, boolean protectExcessItem,
- boolean protectExcessFluid) {
+ public VoidProtectionHelper setMachine(IVoidable machine, boolean protectExcessItem, boolean protectExcessFluid) {
this.protectExcessItem = protectExcessItem;
this.protectExcessFluid = protectExcessFluid;
- this.machineMulti = machineMulti;
+ this.machine = machine;
return this;
}
@@ -125,6 +114,9 @@ public class VoidProtectionHelper {
if (built) {
throw new IllegalStateException("Tried to build twice");
}
+ if (machine == null) {
+ throw new IllegalStateException("Machine is not set");
+ }
built = true;
determineParallel();
return this;
@@ -151,85 +143,21 @@ public class VoidProtectionHelper {
fluidOutputs = new FluidStack[0];
}
- // Don't check ControllerWithOptionalFeatures#protectsExcessItem nor #protectsExcessFluid here,
+ // Don't check IVoidable#protectsExcessItem nor #protectsExcessFluid here,
// to allow more involved setting for void protections (see ComplexParallelProcessingLogic)
- if (machineMeta != null) {
- boolean tMEOutputBus = false;
- boolean tMEOutputHatch = false;
- for (GT_MetaTileEntity_Hatch tHatch : machineMeta.mOutputBusses) {
- if (tHatch instanceof GT_MetaTileEntity_Hatch_OutputBus_ME) {
- tMEOutputBus = true;
- break;
- }
- }
-
- for (GT_MetaTileEntity_Hatch tHatch : machineMeta.mOutputHatches) {
- if (tHatch instanceof GT_MetaTileEntity_Hatch_Output_ME) {
- tMEOutputHatch = true;
- break;
- }
- }
-
- if (protectExcessItem && itemOutputs.length > 0 && !tMEOutputBus) {
- maxParallel = Math.min(calculateMaxItemParallelsForMetaTEs(), maxParallel);
- }
- if (protectExcessFluid && fluidOutputs.length > 0 && !tMEOutputHatch) {
- maxParallel = Math.min(calculateMaxFluidParallelsForMetaTEs(), maxParallel);
- }
- } else if (machineMulti != null) {
- if (protectExcessItem && itemOutputs.length > 0) {
- maxParallel = Math.min(calculateMaxItemParallelsForMuTEs(), maxParallel);
- }
- if (protectExcessFluid && fluidOutputs.length > 0) {
- maxParallel = Math.min(calculateMaxFluidParallelsForMuTEs(), maxParallel);
- }
- }
- }
-
- /**
- * Calculates the max parallel for fluids if void protection is turned on
- */
- private int calculateMaxFluidParallelsForMuTEs() {
- if (machineMulti == null || machineMulti.getOutputTanks() == null) {
- return 0;
+ if (protectExcessItem && itemOutputs.length > 0 && !machine.canDumpItemToME()) {
+ maxParallel = Math.min(calculateMaxItemParallels(), maxParallel);
}
- return calculateMaxFluidParallels(
- Arrays.asList(machineMulti.getOutputTanks()),
- tHatch -> tHatch.getFluidAmount() == 0,
- (tHatch, fluidStack) -> true);
- }
-
- /**
- * Calculates the max parallel for fluids if void protection is turned on
- */
- private int calculateMaxFluidParallelsForMetaTEs() {
- if (machineMeta == null) {
- return 0;
+ if (protectExcessFluid && fluidOutputs.length > 0 && !machine.canDumpFluidToME()) {
+ maxParallel = Math.min(calculateMaxFluidParallels(), maxParallel);
}
- return calculateMaxFluidParallels(
- machineMeta.mOutputHatches,
- tHatch -> tHatch.mMode == 0 && tHatch.getFluidAmount() == 0,
- (tHatch, fluidStack) -> {
- if (GT_ModHandler.isSteam(fluidStack)) {
- return tHatch.outputsSteam();
- } else {
- if (!tHatch.outputsLiquids()) {
- return false;
- }
- String tLockedFluidName = tHatch.getLockedFluidName();
- return !tHatch.isFluidLocked() || tLockedFluidName == null
- || tLockedFluidName.equals(
- fluidStack.getFluid()
- .getName());
- }
- });
}
/**
* Calculates the max parallel for fluids if void protection is turned on
*/
- private <T extends IFluidTank> int calculateMaxFluidParallels(List<T> hatches, Function<T, Boolean> isEmpty,
- BiFunction<T, FluidStack, Boolean> acceptsFluid) {
+ private int calculateMaxFluidParallels() {
+ List<? extends IFluidStore> hatches = machine.getFluidOutputSlots(fluidOutputs);
if (hatches.size() < fluidOutputs.length) {
return 0;
}
@@ -257,25 +185,23 @@ public class VoidProtectionHelper {
return maxParallel;
}
- for (T tHatch : hatches) {
+ for (IFluidStore tHatch : hatches) {
int tSpaceLeft = tHatch.getCapacity() - tHatch.getFluidAmount();
// check if hatch filled
if (tSpaceLeft <= 0) continue;
// check if hatch is empty and unrestricted
- if (isEmpty.apply(tHatch)) continue;
+ if (tHatch.isEmptyAndAcceptsAnyFluid()) continue;
for (Map.Entry<FluidStack, ParallelData> entry : tParallels.entrySet()) {
FluidStack tFluidOutput = entry.getKey();
- if (!acceptsFluid.apply(tHatch, tFluidOutput)) continue;
+ if (!tHatch.canStoreFluid(tFluidOutput)) continue;
// this fluid is not prevented by restrictions on output hatch
- if (tHatch.getFluidAmount() == 0 || GT_Utility.areFluidsEqual(tHatch.getFluid(), tFluidOutput)) {
- ParallelData tParallel = entry.getValue();
- Integer tCraftSize = tFluidOutputMap.get(tFluidOutput);
- tParallel.batch += (tParallel.partial + tSpaceLeft) / tCraftSize;
- tParallel.partial = (tParallel.partial + tSpaceLeft) % tCraftSize;
- }
+ ParallelData tParallel = entry.getValue();
+ Integer tCraftSize = tFluidOutputMap.get(tFluidOutput);
+ tParallel.batch += (tParallel.partial + tSpaceLeft) / tCraftSize;
+ tParallel.partial = (tParallel.partial + tSpaceLeft) % tCraftSize;
}
}
// now that all partial/restricted hatches have been counted, create a priority queue for our outputs
@@ -287,9 +213,9 @@ public class VoidProtectionHelper {
.add(new ParallelStackInfo<>(entry.getValue().batch, entry.getValue().partial, entry.getKey()));
}
// add extra parallels for open slots as well
- for (T tHatch : hatches) {
- // partially filled or restricted hatch. done in last pass
- if (!isEmpty.apply(tHatch)) continue;
+ for (IFluidStore tHatch : hatches) {
+ // partially filled or restricted hatch. done in the last pass
+ if (!tHatch.isEmptyAndAcceptsAnyFluid()) continue;
ParallelStackInfo<FluidStack> tParallel = aParallelQueue.poll();
assert tParallel != null; // will always be true, specifying assert here to avoid IDE/compiler warnings
@@ -305,44 +231,8 @@ public class VoidProtectionHelper {
/**
* Calculates the max parallels one can do with items if void protection is on
*/
- private int calculateMaxItemParallelsForMuTEs() {
- List<ItemStack> busStacks = new ArrayList<>();
- if (machineMulti != null) {
- IItemHandler inv = machineMulti.getOutputInventory();
- if (inv != null && inv.getSlots() > 0) {
- for (int i = 0; i < inv.getSlots(); i++) {
- busStacks.add(inv.getStackInSlot(i));
- }
- }
- }
- return calculateMaxItemParallels(busStacks);
- }
-
- /**
- * Calculates the max parallels one can do with items if void protection is on
- */
- private int calculateMaxItemParallelsForMetaTEs() {
- List<ItemStack> busStacks = new ArrayList<>();
- if (machineMeta != null) {
- for (final GT_MetaTileEntity_Hatch tBus : machineMeta.mOutputBusses) {
- if (!GT_MetaTileEntity_MultiBlockBase.isValidMetaTileEntity(tBus)) {
- continue;
- }
- final IInventory tBusInv = tBus.getBaseMetaTileEntity();
- for (int i = 0; i < tBusInv.getSizeInventory(); i++) {
- busStacks.add(tBus.getStackInSlot(i));
- }
- }
- }
- return calculateMaxItemParallels(busStacks);
- }
-
- /**
- * Calculates the max parallels one can do with items if void protection is on
- *
- * @param busStacks List of itemstacks that are already stored in buses
- */
- private int calculateMaxItemParallels(List<ItemStack> busStacks) {
+ private int calculateMaxItemParallels() {
+ List<ItemStack> busStacks = machine.getItemOutputSlots(itemOutputs);
// A map to hold the items we will be 'inputting' into the output buses. These itemstacks are actually the
// recipe outputs.
Map<ItemStack, Integer> tItemOutputMap = new ItemStackMap<>();
diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_DistillationTower.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_DistillationTower.java
index 5c23d6cc7b..e8443fbe88 100644
--- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_DistillationTower.java
+++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_DistillationTower.java
@@ -32,6 +32,7 @@ import gregtech.api.enums.Textures;
import gregtech.api.enums.Textures.BlockIcons;
import gregtech.api.interfaces.IHatchElement;
import gregtech.api.interfaces.ITexture;
+import gregtech.api.interfaces.fluid.IFluidStore;
import gregtech.api.interfaces.metatileentity.IMetaTileEntity;
import gregtech.api.interfaces.tileentity.IGregTechTileEntity;
import gregtech.api.metatileentity.implementations.GT_MetaTileEntity_EnhancedMultiBlockBase;
@@ -278,6 +279,11 @@ public class GT_MetaTileEntity_DistillationTower extends
}
@Override
+ public List<? extends IFluidStore> getFluidOutputSlots(FluidStack[] toOutput) {
+ return getFluidOutputSlotsByLayer(toOutput, mOutputHatchesByLayer);
+ }
+
+ @Override
protected IAlignmentLimits getInitialAlignmentLimits() {
// don't rotate a freaking tower, it won't work
return (d, r, f) -> (d.flag & (ForgeDirection.UP.flag | ForgeDirection.DOWN.flag)) == 0 && r.isNotRotated()
diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_ElectricBlastFurnace.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_ElectricBlastFurnace.java
index dbb934cb80..a7b845b5de 100644
--- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_ElectricBlastFurnace.java
+++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_ElectricBlastFurnace.java
@@ -9,6 +9,11 @@ import static gregtech.api.util.GT_StructureUtility.buildHatchAdder;
import static gregtech.api.util.GT_StructureUtility.ofCoil;
import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+import javax.annotation.Nonnull;
+import javax.annotation.Nullable;
import net.minecraft.entity.player.EntityPlayer;
import net.minecraft.item.ItemStack;
@@ -28,6 +33,7 @@ import gregtech.api.GregTech_API;
import gregtech.api.enums.HeatingCoilLevel;
import gregtech.api.enums.Materials;
import gregtech.api.interfaces.ITexture;
+import gregtech.api.interfaces.fluid.IFluidStore;
import gregtech.api.interfaces.metatileentity.IMetaTileEntity;
import gregtech.api.interfaces.tileentity.IGregTechTileEntity;
import gregtech.api.metatileentity.implementations.*;
@@ -207,7 +213,7 @@ public class GT_MetaTileEntity_ElectricBlastFurnace extends
if (tRecipe == null) return false;
if (this.mHeatingCapacity < tRecipe.mSpecialValue) return false;
- if (!canOutputAll(tRecipe)) return false;
+ if (!canOutputAll(tRecipe.mOutputs, getPollutionMultiplierAppliedFluids(tRecipe.mFluidOutputs))) return false;
if (!tRecipe.isRecipeInputEqual(true, tFluids, tItems)) return false;
// In case recipe is too OP for that machine
if (mMaxProgresstime == Integer.MAX_VALUE - 1 && mEUt == Integer.MAX_VALUE - 1) return false;
@@ -281,6 +287,16 @@ public class GT_MetaTileEntity_ElectricBlastFurnace extends
return timesOverclocked;
}
+ private FluidStack[] getPollutionMultiplierAppliedFluids(FluidStack[] original) {
+ FluidStack[] fluids = GT_Utility.copyFluidArray(original);
+ for (FluidStack fluid : fluids) {
+ if (isPollutionFluid(fluid)) {
+ multiplyPollutionFluidAmount(fluid);
+ }
+ }
+ return fluids;
+ }
+
public boolean addOutputHatchToTopList(IGregTechTileEntity aTileEntity, int aBaseCasingIndex) {
if (aTileEntity == null) return false;
IMetaTileEntity aMetaTileEntity = aTileEntity.getMetaTileEntity();
@@ -314,37 +330,53 @@ public class GT_MetaTileEntity_ElectricBlastFurnace extends
public boolean addOutput(FluidStack aLiquid) {
if (aLiquid == null) return false;
FluidStack tLiquid = aLiquid.copy();
- boolean isOutputPollution = false;
- for (FluidStack pollutionFluidStack : pollutionFluidStacks) {
- if (!tLiquid.isFluidEqual(pollutionFluidStack)) continue;
-
- isOutputPollution = true;
- break;
- }
ArrayList<GT_MetaTileEntity_Hatch_Output> tOutputHatches;
- if (isOutputPollution) {
+ if (isPollutionFluid(tLiquid)) {
tOutputHatches = this.mPollutionOutputHatches;
- int pollutionReduction = 0;
- for (GT_MetaTileEntity_Hatch_Muffler tHatch : mMufflerHatches) {
- if (!isValidMetaTileEntity(tHatch)) continue;
- pollutionReduction = 100 - tHatch.calculatePollutionReduction(100);
- break;
- }
- tLiquid.amount = tLiquid.amount * (pollutionReduction + 5) / 100;
+ multiplyPollutionFluidAmount(tLiquid);
} else {
tOutputHatches = this.mOutputHatches;
}
return dumpFluid(tOutputHatches, tLiquid, true) || dumpFluid(tOutputHatches, tLiquid, false);
}
+ protected boolean isPollutionFluid(@Nullable FluidStack fluidStack) {
+ if (fluidStack == null) return false;
+ for (FluidStack pollutionFluidStack : pollutionFluidStacks) {
+ if (!fluidStack.isFluidEqual(pollutionFluidStack)) continue;
+ return true;
+ }
+ return false;
+ }
+
@Override
- public String[] getInfoData() {
- int mPollutionReduction = 0;
+ public List<? extends IFluidStore> getFluidOutputSlots(FluidStack[] toOutput) {
+ if (Arrays.stream(toOutput)
+ .anyMatch(this::isPollutionFluid)) {
+ return filterValidMetaTileEntities(mPollutionOutputHatches);
+ }
+ return filterValidMetaTileEntities(mOutputHatches);
+ }
+
+ /**
+ * @return 100 -> all released to air, 0 -> all dumped to hatch
+ */
+ public int getPollutionReduction() {
+ int reduction = 100;
for (GT_MetaTileEntity_Hatch_Muffler tHatch : mMufflerHatches) {
if (!isValidMetaTileEntity(tHatch)) continue;
- mPollutionReduction = Math.max(tHatch.calculatePollutionReduction(100), mPollutionReduction);
+ reduction = Math.min(tHatch.calculatePollutionReduction(100), reduction);
}
+ return reduction;
+ }
+
+ protected void multiplyPollutionFluidAmount(@Nonnull FluidStack fluid) {
+ fluid.amount = fluid.amount * Math.min(100 - getPollutionReduction() + 5, 100) / 100;
+ }
+ @Override
+ public String[] getInfoData() {
+ int mPollutionReduction = getPollutionReduction();
long storedEnergy = 0;
long maxEnergy = 0;
for (GT_MetaTileEntity_Hatch_Energy tHatch : mEnergyHatches) {