package zmaster587.advancedRocketry.cable; import java.util.Iterator; import java.util.Random; import java.util.Map.Entry; import net.minecraft.tileentity.TileEntity; import net.minecraftforge.common.util.ForgeDirection; import net.minecraftforge.fluids.Fluid; import net.minecraftforge.fluids.FluidStack; import net.minecraftforge.fluids.FluidTankInfo; import net.minecraftforge.fluids.IFluidHandler; public class LiquidNetwork extends CableNetwork { private final int MAX_TRANSFER = 100; /** * Create a new network and get an ID * @return ID of this new network */ public static LiquidNetwork initNetwork() { Random random = new Random(System.currentTimeMillis()); int id = random.nextInt(); while(usedIds.contains(id)){ id = random.nextInt(); }; LiquidNetwork net = new LiquidNetwork(); usedIds.add(id); net.networkID = id; return net; } //TODO: balance tanks @Override public void tick() { int amount = MAX_TRANSFER; //Return if there is nothing to do if(sinks.isEmpty() || sources.isEmpty()) return; Iterator<Entry<TileEntity,ForgeDirection>> sinkItr = sinks.iterator(); //Go through all sinks, if one is not full attempt to fill it while(sinkItr.hasNext()) { //Get tile and key Entry<TileEntity,ForgeDirection> obj = (Entry<TileEntity, ForgeDirection>)sinkItr.next(); IFluidHandler fluidHandleSink = (IFluidHandler)obj.getKey(); ForgeDirection dir = obj.getValue(); Iterator<Entry<TileEntity,ForgeDirection>> sourceItr = sources.iterator(); Fluid fluid = null; //If the sink already has fluid in it then lets only try to fill it with that particular fluid if(fluidHandleSink.getTankInfo(dir) != null) { for(FluidTankInfo info : fluidHandleSink.getTankInfo(dir)) { if(info != null && info.fluid != null) { fluid = info.fluid.getFluid(); break; } } } //If no fluid can be found then find the first source with a fluid in it if(fluid == null) { out: while(sourceItr.hasNext()) { Entry<TileEntity,ForgeDirection> objSource = (Entry<TileEntity, ForgeDirection>)sourceItr.next(); IFluidHandler fluidHandleSource = (IFluidHandler)objSource.getKey(); if(fluidHandleSource.getTankInfo(objSource.getValue()) != null) { for(FluidTankInfo srcInfo : fluidHandleSource.getTankInfo(objSource.getValue())) { if(srcInfo != null && srcInfo.fluid != null) { fluid = srcInfo.fluid.getFluid(); break out; } } } } } //No fluids can be moved if(fluid == null) break; if(fluidHandleSink.canFill(dir, fluid)) { //Distribute? and drain tanks //Get the max the tank can take this tick then iterate through all sources until it's been filled sourceItr = sources.iterator(); int maxFill = Math.min(fluidHandleSink.fill(dir, new FluidStack(fluid, amount), false), amount); int actualFill = 0; while(sourceItr.hasNext()) { Entry<TileEntity,ForgeDirection> objSource = (Entry<TileEntity, ForgeDirection>)sourceItr.next(); IFluidHandler fluidHandleSource = (IFluidHandler)objSource.getKey(); if(fluidHandleSource.canDrain(objSource.getValue(), fluid)) { int buffer; FluidStack fluid2 = fluidHandleSource.drain(objSource.getValue(), maxFill, true); //drain sometimes returns a null value even when canDrain returns true if(fluid2 == null) buffer = 0; else buffer=fluid2.amount; maxFill -= buffer; actualFill += buffer; } if(maxFill == 0) break; } fluidHandleSink.fill(dir, new FluidStack(fluid, actualFill), true); } } } }