diff options
author | Steelux <70096037+Steelux8@users.noreply.github.com> | 2022-06-09 16:01:59 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2022-06-09 17:01:59 +0200 |
commit | 6ced738344fbf1b2bfccc2b753cf52c4d720e408 (patch) | |
tree | 1c9c6e48d7bb48fad8df59127951e1449e114a22 /src/main/java/gregtech | |
parent | 3e34ad9d9439202d3d9dcc201fc7339f4f6ea0ea (diff) | |
download | GT5-Unofficial-6ced738344fbf1b2bfccc2b753cf52c4d720e408.tar.gz GT5-Unofficial-6ced738344fbf1b2bfccc2b753cf52c4d720e408.tar.bz2 GT5-Unofficial-6ced738344fbf1b2bfccc2b753cf52c4d720e408.zip |
Turbine Rework Beyond Optimal Flow (#1038)
* Turbine Rework
- Changed the tooltip of Turbine items to add more data and clarify some values: it now shows all types of optimal flow rates, EU/t values and the new overflow tier;
- Changed the math for the EU/t value above the optimal flow. Before this change, efficiency drops so quickly that EU/t will never raise above that of optimal flow, but with this change, higher EU/t values are possible, with efficiency losses;
* Prevent Explosions by Voiding Fuel on Startup
- Changed all multiblock turbines so that, when switching from disabled to enabled mode, they void all the fuel in the input hatch and only start running afterwards. This prevents them from exploding due to filled input hatches on startup, but punishes the player by wasting the fuel;
* Revert Voiding Change and Throttle Output
- Reverted the input voiding change done in the previous commit, given that the turbines could still explode on world load;
- Changed the fluidIntoPower functions to never output an EU/t value higher than what the dynamo can handle. If the value is higher, set it to the maximum EU/t of the dynamo and consume the same amount of fuel regardless.
* Changed Tooltip Values to Int
- Changed tooltip values to int, for rounding and simplifying purposes.
Diffstat (limited to 'src/main/java/gregtech')
6 files changed, 202 insertions, 43 deletions
diff --git a/src/main/java/gregtech/api/items/GT_MetaGenerated_Tool.java b/src/main/java/gregtech/api/items/GT_MetaGenerated_Tool.java index 19295c2c43..10b2abe682 100644 --- a/src/main/java/gregtech/api/items/GT_MetaGenerated_Tool.java +++ b/src/main/java/gregtech/api/items/GT_MetaGenerated_Tool.java @@ -354,23 +354,38 @@ public abstract class GT_MetaGenerated_Tool extends GT_MetaBase_Item implements int aBaseEff=(int)(5+getToolCombatDamage(aStack))*1000; int aOptFlow=GT_Utility.safeInt((long)Math.max(Float.MIN_NORMAL, ((GT_MetaGenerated_Tool) aStack.getItem()).getToolStats(aStack).getSpeedMultiplier() * ((GT_MetaGenerated_Tool) aStack.getItem()).getPrimaryMaterial(aStack).mToolSpeed * 50)); - aList.add(tOffset + 0, EnumChatFormatting.WHITE + String.format(transItem("001", "Durability: %s/%s"), "" + EnumChatFormatting.GREEN + (tMaxDamage - getToolDamage(aStack)) + " ", " " + tMaxDamage) + EnumChatFormatting.GRAY); - aList.add(tOffset + 1, EnumChatFormatting.WHITE + String.format(transItem("002", "%s lvl %s"), tMaterial.mLocalizedName + EnumChatFormatting.YELLOW, "" + getHarvestLevel(aStack, "")) + EnumChatFormatting.GRAY); - aList.add(tOffset + 2, EnumChatFormatting.WHITE + String.format(transItem("005", "Turbine Efficiency: %s"), "" + EnumChatFormatting.BLUE + (50.0F + (10.0F * getToolCombatDamage(aStack)))) + EnumChatFormatting.GRAY); - aList.add(tOffset + 3, EnumChatFormatting.WHITE + String.format(transItem("006", "Optimal Steam flow: %sL/t"), "" + EnumChatFormatting.GOLD + Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * (1000 / 20)) + EnumChatFormatting.GRAY)); - aList.add(tOffset + 4, EnumChatFormatting.WHITE + String.format(transItem("900", "Energy from Optimal Steam Flow: %sEU/t"), "" + EnumChatFormatting.GOLD + Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * (1000 / 20)) * (50.0F + (10.0F * getToolCombatDamage(aStack))) / 200 + EnumChatFormatting.GRAY)); + aList.add(tOffset + 0, EnumChatFormatting.GRAY + String.format(transItem("001", "Durability: %s/%s"), "" + EnumChatFormatting.GREEN + (tMaxDamage - getToolDamage(aStack)) + " ", " " + tMaxDamage) + EnumChatFormatting.GRAY); + aList.add(tOffset + 1, EnumChatFormatting.GRAY + String.format(transItem("002", "%s lvl %s"), tMaterial.mLocalizedName + EnumChatFormatting.YELLOW, "" + getHarvestLevel(aStack, "")) + EnumChatFormatting.GRAY); + aList.add(tOffset + 2, EnumChatFormatting.WHITE + String.format(transItem("005", "Turbine Efficiency: %s"), "" + EnumChatFormatting.BLUE + (50.0F + (10.0F * getToolCombatDamage(aStack)))) + "%" + EnumChatFormatting.GRAY); + aList.add(tOffset + 3, EnumChatFormatting.WHITE + String.format(transItem("006", "Optimal Steam flow: %s L/t"), "" + EnumChatFormatting.GOLD + GT_Utility.safeInt((long) (Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * (1000 / 20)))) + EnumChatFormatting.GRAY)); + aList.add(tOffset + 4, EnumChatFormatting.WHITE + String.format(transItem("900", "Energy from Optimal Steam Flow: %s EU/t"), "" + EnumChatFormatting.GOLD + GT_Utility.safeInt((long) (Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * (1000 / 20)) * (50.0F + (10.0F * getToolCombatDamage(aStack))) / 200)) + EnumChatFormatting.GRAY)); { long[] calculatedFlow = calculateLooseFlow(aOptFlow, aBaseEff); - long aOptFlowLoose = calculatedFlow[0]; - long aBaseEffLoose = calculatedFlow[1]; + int aOptFlowLoose = (int) calculatedFlow[0]; + int aBaseEffLoose = (int) calculatedFlow[1]; + + aList.add(tOffset + 5, EnumChatFormatting.AQUA + String.format(transItem("500", "Turbine Efficiency (Loose): %s"), "" + EnumChatFormatting.BLUE + aBaseEffLoose / 100 + "%" + EnumChatFormatting.GRAY)); + aList.add(tOffset + 6, EnumChatFormatting.AQUA + String.format(transItem("501", "Optimal Steam flow (Loose): %s L/t"), "" + EnumChatFormatting.GOLD + aOptFlowLoose + EnumChatFormatting.GRAY)); + aList.add(tOffset + 7, EnumChatFormatting.AQUA + String.format(transItem("901", "Energy from Optimal Steam Flow (Loose): %s EU/t"), "" + EnumChatFormatting.GOLD + (aOptFlowLoose / 10000) * (aBaseEffLoose / 2) + EnumChatFormatting.GRAY)); + aList.add(tOffset + 8, EnumChatFormatting.GRAY + "(Superheated Steam EU values are 2x those of Steam)"); - aList.add(tOffset + 5, EnumChatFormatting.GRAY + String.format(transItem("500", "Turbine Efficiency (Loose): %s"), "" + EnumChatFormatting.BLUE + aBaseEffLoose / 100 + EnumChatFormatting.DARK_GRAY)); - aList.add(tOffset + 6, EnumChatFormatting.GRAY + String.format(transItem("501", "Optimal Steam flow (Loose): %s L/t"), "" + EnumChatFormatting.GOLD + aOptFlowLoose + EnumChatFormatting.DARK_GRAY)); - aList.add(tOffset + 7, EnumChatFormatting.GRAY + String.format(transItem("901", "Energy from Optimal Steam Flow (Loose): %s EU/t"), "" + EnumChatFormatting.GOLD + (aOptFlowLoose / 10000) * (aBaseEffLoose / 2) + EnumChatFormatting.DARK_GRAY)); } - aList.add(tOffset + 8, EnumChatFormatting.WHITE + String.format(transItem("007", "Energy from Optimal Gas Flow: %sEU/t"), "" + EnumChatFormatting.GOLD + Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * 50) * (50.0F + (10.0F * getToolCombatDamage(aStack))) / 100 + EnumChatFormatting.GRAY)); - aList.add(tOffset + 9, EnumChatFormatting.WHITE + String.format(transItem("008", "Energy from Optimal Plasma Flow: %sEU/t"), "" + EnumChatFormatting.GOLD + Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * 2000) * (50.0F + (10.0F * getToolCombatDamage(aStack))) * (1.05 / 100) + EnumChatFormatting.GRAY)); + aList.add(tOffset + 9, EnumChatFormatting.LIGHT_PURPLE + String.format(transItem("007", "Energy from Optimal Gas Flow: %s EU/t"), "" + EnumChatFormatting.GOLD + GT_Utility.safeInt((long) (Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * 50) * (50.0F + (10.0F * getToolCombatDamage(aStack))) / 100)) + EnumChatFormatting.GRAY)); + aList.add(tOffset + 10, EnumChatFormatting.LIGHT_PURPLE + String.format(transItem("008", "Energy from Optimal Plasma Flow: %s EU/t"), "" + EnumChatFormatting.GOLD + GT_Utility.safeInt((long) (Math.max(Float.MIN_NORMAL, tStats.getSpeedMultiplier() * getPrimaryMaterial(aStack).mToolSpeed * 2000) * (50.0F + (10.0F * getToolCombatDamage(aStack))) * (1.05 / 100))) + EnumChatFormatting.GRAY)); + aList.add(tOffset + 12, EnumChatFormatting.GRAY + "(EU/t values include efficiency and are not 100% accurate)"); + int toolQualityLevel = GT_MetaGenerated_Tool.getPrimaryMaterial(aStack).mToolQuality; + int overflowMultiplier = 0; + if (toolQualityLevel >= 6) { + overflowMultiplier = 3; + } + else if (toolQualityLevel >= 3) { + overflowMultiplier = 2; + } + else { + overflowMultiplier = 1; + } + aList.add(tOffset + 11, EnumChatFormatting.LIGHT_PURPLE + String.format(transItem("502", "Overflow Efficiency Tier: %s"), "" + EnumChatFormatting.GOLD + overflowMultiplier + EnumChatFormatting.GRAY)); } else { aList.add(tOffset + 0, EnumChatFormatting.WHITE + String.format(transItem("001", "Durability: %s/%s"), "" + EnumChatFormatting.GREEN + (tMaxDamage - getToolDamage(aStack)) + " ", " " + tMaxDamage) + EnumChatFormatting.GRAY); diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine.java index 2678c3ac72..b5e1db0e6b 100644 --- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine.java +++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine.java @@ -58,6 +58,7 @@ public abstract class GT_MetaTileEntity_LargeTurbine extends GT_MetaTileEntity_E protected int storedFluid = 0; protected int counter = 0; protected boolean looseFit = false; + protected int overflowMultiplier = 0; public GT_MetaTileEntity_LargeTurbine(int aID, String aName, String aNameRegional) { super(aID, aName, aNameRegional); @@ -116,6 +117,7 @@ public abstract class GT_MetaTileEntity_LargeTurbine extends GT_MetaTileEntity_E } ArrayList<FluidStack> tFluids = getStoredFluids(); if (tFluids.size() > 0) { + if (baseEff == 0 || optFlow == 0 || counter >= 512 || this.getBaseMetaTileEntity().hasWorkJustBeenEnabled() || this.getBaseMetaTileEntity().hasInventoryBeenModified()) { counter = 0; @@ -124,6 +126,18 @@ public abstract class GT_MetaTileEntity_LargeTurbine extends GT_MetaTileEntity_E ((GT_MetaGenerated_Tool) aStack.getItem()).getToolStats(aStack).getSpeedMultiplier() * GT_MetaGenerated_Tool.getPrimaryMaterial(aStack).mToolSpeed * 50)); + + int toolQualityLevel = GT_MetaGenerated_Tool.getPrimaryMaterial(aStack).mToolQuality; + if (toolQualityLevel >= 6) { + overflowMultiplier = 3; + } + else if (toolQualityLevel >= 3) { + overflowMultiplier = 2; + } + else { + overflowMultiplier = 1; + } + if(optFlow<=0 || baseEff<=0){ stopMachine();//in case the turbine got removed return false; @@ -133,7 +147,7 @@ public abstract class GT_MetaTileEntity_LargeTurbine extends GT_MetaTileEntity_E } } - int newPower = fluidIntoPower(tFluids, optFlow, baseEff); // How much the turbine should be producing with this flow + int newPower = fluidIntoPower(tFluids, optFlow, baseEff, overflowMultiplier); // How much the turbine should be producing with this flow int difference = newPower - this.mEUt; // difference between current output and new output // Magic numbers: can always change by at least 10 eu/t, but otherwise by at most 1 percent of the difference in power level (per tick) @@ -159,7 +173,21 @@ public abstract class GT_MetaTileEntity_LargeTurbine extends GT_MetaTileEntity_E } } - abstract int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff); + abstract int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff, int overflowMultiplier); + + abstract float getOverflowEfficiency(int totalFlow, int actualOptimalFlow, int overflowMultiplier); + + // Gets the maximum output that the turbine currently can handle. Going above this will cause the turbine to explode + public long getMaximumOutput() { + long aTotal = 0; + for (GT_MetaTileEntity_Hatch_Dynamo aDynamo : mDynamoHatches) { + if (isValidMetaTileEntity(aDynamo)) { + long aVoltage = aDynamo.maxEUOutput(); + aTotal = aDynamo.maxAmperesOut() * aVoltage; + } + } + return aTotal; + } @Override public int getDamageToComponent(ItemStack aStack) { diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Gas.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Gas.java index 6cd1cd567c..f537fbebb8 100644 --- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Gas.java +++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Gas.java @@ -88,7 +88,7 @@ public class GT_MetaTileEntity_LargeTurbine_Gas extends GT_MetaTileEntity_LargeT } @Override - int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff) { + int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff, int overflowMultiplier) { if (aFluids.size() >= 1) { int tEU = 0; int actualOptimalFlow = 0; @@ -109,14 +109,21 @@ public class GT_MetaTileEntity_LargeTurbine_Gas extends GT_MetaTileEntity_LargeT actualOptimalFlow = GT_Utility.safeInt((long) aOptFlow / fuelValue); this.realOptFlow = actualOptimalFlow; - int remainingFlow = GT_Utility.safeInt((long) (actualOptimalFlow * 1.25f)); // Allowed to use up to 125% of optimal flow. Variable required outside of loop for multi-hatch scenarios. + // Allowed to use up to 450% optimal flow rate, depending on the value of overflowMultiplier. + // This value is chosen because the highest EU/t possible depends on the overflowMultiplier, and the formula used + // makes it so the flow rate for that max, per value of overflowMultiplier, is (percentage of optimal flow rate): + // - 150% if it is 1 + // - 300% if it is 2 + // - 450% if it is 3 + // Variable required outside of loop for multi-hatch scenarios. + int remainingFlow = GT_Utility.safeInt((long) (actualOptimalFlow * (1.5f * overflowMultiplier))); int flow = 0; int totalFlow = 0; storedFluid = 0; for (FluidStack aFluid : aFluids) { if (aFluid.isFluidEqual(firstFuelType)) { - flow = Math.min(aFluid.amount, remainingFlow); // try to use up to 125% of optimal flow w/o exceeding remainingFlow + flow = Math.min(aFluid.amount, remainingFlow); // try to use up to the max flow defined just above depleteInput(new FluidStack(aFluid, flow)); // deplete that amount this.storedFluid += aFluid.amount; remainingFlow -= flow; // track amount we're allowed to continue depleting from hatches @@ -129,16 +136,38 @@ public class GT_MetaTileEntity_LargeTurbine_Gas extends GT_MetaTileEntity_LargeT if (totalFlow == actualOptimalFlow) { tEU = GT_Utility.safeInt((long) tEU * (long) aBaseEff / 10000L); } else { - float efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow) / (float) actualOptimalFlow); + float efficiency = getOverflowEfficiency(totalFlow, actualOptimalFlow, overflowMultiplier); tEU *= efficiency; tEU = GT_Utility.safeInt((long) tEU * (long) aBaseEff / 10000L); } + // If next output is above the maximum the dynamo can handle, set it to the maximum instead of exploding the turbine + // Raising the maximum allowed flow rate to account for the efficiency changes beyond the optimal flow rate can explode turbines on world load + if (tEU > getMaximumOutput()){ + tEU = GT_Utility.safeInt(getMaximumOutput()); + } return tEU; } return 0; } + @Override + float getOverflowEfficiency(int totalFlow, int actualOptimalFlow, int overflowMultiplier) { + // overflowMultiplier changes how quickly the turbine loses efficiency after flow goes beyond the optimal value + // At the default value of 1, any flow will generate less EU/t than optimal flow, regardless of the amount of fuel used + // The bigger this number is, the slower efficiency loss happens as flow moves beyond the optimal value + // Gases are the second most efficient in this regard, with plasma being the most efficient + float efficiency = 0; + + if (totalFlow > actualOptimalFlow) { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow)) / ((float) actualOptimalFlow * ((overflowMultiplier * 3) - 1)); + } + else { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow) / (float) actualOptimalFlow); + } + + return efficiency; + } } diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_HPSteam.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_HPSteam.java index 69e5a784a0..ab7c08513f 100644 --- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_HPSteam.java +++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_HPSteam.java @@ -19,6 +19,7 @@ import java.util.ArrayList; import static gregtech.api.enums.Textures.BlockIcons.*; import static gregtech.api.objects.XSTR.XSTR_INSTANCE; +import static gregtech.common.tileentities.machines.multi.GT_MetaTileEntity_LargeTurbine_Steam.calculateLooseFlow; public class GT_MetaTileEntity_LargeTurbine_HPSteam extends GT_MetaTileEntity_LargeTurbine { @@ -83,30 +84,31 @@ public class GT_MetaTileEntity_LargeTurbine_HPSteam extends GT_MetaTileEntity_La } @Override - int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff) { + int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff, int overflowEfficiency) { if (looseFit) { - aOptFlow *= 4; - if (aBaseEff > 10000) { - aOptFlow *= Math.pow(1.1f, ((aBaseEff - 7500) / 10000F) * 20f); - aBaseEff = 7500; - } else if (aBaseEff > 7500) { - aOptFlow *= Math.pow(1.1f, ((aBaseEff - 7500) / 10000F) * 20f); - aBaseEff *= 0.75f; - } else { - aBaseEff *= 0.75f; - } + long[] calculatedFlow = calculateLooseFlow(aOptFlow, aBaseEff); + aOptFlow = GT_Utility.safeInt(calculatedFlow[0]); + aBaseEff = GT_Utility.safeInt(calculatedFlow[1]); } int tEU = 0; int totalFlow = 0; // Byproducts are based on actual flow int flow = 0; - int remainingFlow = GT_Utility.safeInt((long) (aOptFlow * 1.25f)); // Allowed to use up to 125% of optimal flow. Variable required outside of loop for multi-hatch scenarios. + + // Allowed to use up to 300% optimal flow rate, depending on the value of overflowMultiplier. + // This value is chosen because the highest EU/t possible depends on the overflowMultiplier, and the formula used + // makes it so the flow rate for that max, per value of overflowMultiplier, is (percentage of optimal flow rate): + // - 200% if it is 1 + // - 250% if it is 2 + // - 300% if it is 3 + // Variable required outside of loop for multi-hatch scenarios. + int remainingFlow = GT_Utility.safeInt((long) (aOptFlow * (0.5f * overflowMultiplier + 1.5))); this.realOptFlow = aOptFlow; storedFluid = 0; for (int i = 0; i < aFluids.size() && remainingFlow > 0; i++) { final FluidStack aFluidStack = aFluids.get(i); if (GT_ModHandler.isSuperHeatedSteam(aFluidStack)) { - flow = Math.min(aFluidStack.amount, remainingFlow); // try to use up w/o exceeding remainingFlow + flow = Math.min(aFluidStack.amount, remainingFlow); // try to use up to the max flow defined just above depleteInput(new FluidStack(aFluidStack, flow)); // deplete that amount this.storedFluid += aFluidStack.amount; remainingFlow -= flow; // track amount we're allowed to continue depleting from hatches @@ -128,16 +130,39 @@ public class GT_MetaTileEntity_LargeTurbine_HPSteam extends GT_MetaTileEntity_La if (totalFlow == aOptFlow) { tEU = GT_Utility.safeInt((long) tEU * (long) aBaseEff / 10000L); } else { - float efficiency = 1.0f - Math.abs((totalFlow - aOptFlow) / (float) aOptFlow); - //if(totalFlow>aOptFlow){efficiency = 1.0f;} + float efficiency = getOverflowEfficiency(totalFlow, aOptFlow, overflowMultiplier); tEU *= efficiency; tEU = Math.max(1, GT_Utility.safeInt((long) tEU * (long) aBaseEff / 10000L)); } + // If next output is above the maximum the dynamo can handle, set it to the maximum instead of exploding the turbine + // Raising the maximum allowed flow rate to account for the efficiency changes beyond the optimal flow rate can explode turbines on world load + if (tEU > getMaximumOutput()){ + tEU = GT_Utility.safeInt(getMaximumOutput()); + } + return tEU; } @Override + float getOverflowEfficiency(int totalFlow, int actualOptimalFlow, int overflowMultiplier) { + // overflowMultiplier changes how quickly the turbine loses efficiency after flow goes beyond the optimal value + // At the default value of 1, any flow will generate less EU/t than optimal flow, regardless of the amount of fuel used + // The bigger this number is, the slower efficiency loss happens as flow moves beyond the optimal value + // Superheated steam is the second least efficient out of all turbine fuels in this regard, with steam being the least efficient + float efficiency = 0; + + if (totalFlow > actualOptimalFlow) { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow)) / ((float) actualOptimalFlow * (overflowMultiplier + 2)); + } + else { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow) / (float) actualOptimalFlow); + } + + return efficiency; + } + + @Override public void onScrewdriverRightClick(byte aSide, EntityPlayer aPlayer, float aX, float aY, float aZ) { if (aSide == getBaseMetaTileEntity().getFrontFacing()) { looseFit ^= true; diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Plasma.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Plasma.java index 8a5616dafd..17cba19242 100644 --- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Plasma.java +++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Plasma.java @@ -89,7 +89,7 @@ public class GT_MetaTileEntity_LargeTurbine_Plasma extends GT_MetaTileEntity_Lar } @Override - int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff) { + int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff, int overflowMultiplier) { if (aFluids.size() >= 1) { aOptFlow *= 800;//CHANGED THINGS HERE, check recipe runs once per 20 ticks int tEU = 0; @@ -101,14 +101,21 @@ public class GT_MetaTileEntity_LargeTurbine_Plasma extends GT_MetaTileEntity_Lar actualOptimalFlow = GT_Utility.safeInt((long) Math.ceil((double) aOptFlow / (double) fuelValue)); this.realOptFlow = actualOptimalFlow; // For scanner info - int remainingFlow = GT_Utility.safeInt((long) (actualOptimalFlow * 1.25f)); // Allowed to use up to 125% of optimal flow. Variable required outside of loop for multi-hatch scenarios. + // Allowed to use up to 550% optimal flow rate, depending on the value of overflowMultiplier. + // This value is chosen because the highest EU/t possible depends on the overflowMultiplier, and the formula used + // makes it so the flow rate for that max, per value of overflowMultiplier, is (percentage of optimal flow rate): + // - 250% if it is 1 + // - 400% if it is 2 + // - 550% if it is 3 + // Variable required outside of loop for multi-hatch scenarios. + int remainingFlow = GT_Utility.safeInt((long) (actualOptimalFlow * (1.5f * overflowMultiplier + 1))); int flow = 0; int totalFlow = 0; storedFluid = 0; for (FluidStack aFluid : aFluids) { if (aFluid.isFluidEqual(firstFuelType)) { - flow = Math.min(aFluid.amount, remainingFlow); // try to use up w/o exceeding remainingFlow + flow = Math.min(aFluid.amount, remainingFlow); // try to use up to the max flow defined just above depleteInput(new FluidStack(aFluid, flow)); // deplete that amount this.storedFluid += aFluid.amount; remainingFlow -= flow; // track amount we're allowed to continue depleting from hatches @@ -135,12 +142,17 @@ public class GT_MetaTileEntity_LargeTurbine_Plasma extends GT_MetaTileEntity_Lar if (totalFlow == actualOptimalFlow) { tEU = GT_Utility.safeInt((long) (aBaseEff / 10000D * tEU)); } else { - double efficiency = 1.0D - Math.abs((totalFlow - actualOptimalFlow) / (float) actualOptimalFlow); - + float efficiency = getOverflowEfficiency(totalFlow, actualOptimalFlow, overflowMultiplier); tEU = (int) (tEU * efficiency); tEU = GT_Utility.safeInt((long) (aBaseEff / 10000D * tEU)); } + // If next output is above the maximum the dynamo can handle, set it to the maximum instead of exploding the turbine + // Raising the maximum allowed flow rate to account for the efficiency changes beyond the optimal flow rate can explode turbines on world load + if (tEU > getMaximumOutput()){ + tEU = GT_Utility.safeInt(getMaximumOutput()); + } + return tEU; } @@ -148,6 +160,24 @@ public class GT_MetaTileEntity_LargeTurbine_Plasma extends GT_MetaTileEntity_Lar } @Override + float getOverflowEfficiency(int totalFlow, int actualOptimalFlow, int overflowMultiplier) { + // overflowMultiplier changes how quickly the turbine loses efficiency after flow goes beyond the optimal value + // At the default value of 1, any flow will generate less EU/t than optimal flow, regardless of the amount of fuel used + // The bigger this number is, the slower efficiency loss happens as flow moves beyond the optimal value + // Plasmas are the most efficient out of all turbine fuels in this regard + float efficiency = 0; + + if (totalFlow > actualOptimalFlow) { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow)) / ((float) actualOptimalFlow * ((overflowMultiplier * 3) + 1)); + } + else { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow) / (float) actualOptimalFlow); + } + + return efficiency; + } + + @Override public boolean checkRecipe(ItemStack aStack) { if ((counter & 7) == 0 && (aStack == null || !(aStack.getItem() instanceof GT_MetaGenerated_Tool) || aStack.getItemDamage() < 170 || aStack.getItemDamage() > 179)) { stopMachine(); @@ -173,7 +203,7 @@ public class GT_MetaTileEntity_LargeTurbine_Plasma extends GT_MetaTileEntity_Lar return false; } - int newPower = fluidIntoPower(tFluids, optFlow, baseEff); // How much the turbine should be producing with this flow + int newPower = fluidIntoPower(tFluids, optFlow, baseEff, overflowMultiplier); // How much the turbine should be producing with this flow int difference = newPower - this.mEUt; // difference between current output and new output diff --git a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Steam.java b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Steam.java index 86ed51e879..bf9f3bfdbf 100644 --- a/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Steam.java +++ b/src/main/java/gregtech/common/tileentities/machines/multi/GT_MetaTileEntity_LargeTurbine_Steam.java @@ -93,7 +93,7 @@ public class GT_MetaTileEntity_LargeTurbine_Steam extends GT_MetaTileEntity_Larg } @Override - int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff) { + int fluidIntoPower(ArrayList<FluidStack> aFluids, int aOptFlow, int aBaseEff, int overflowEfficiency) { if (looseFit) { long[] calculatedFlow = calculateLooseFlow(aOptFlow, aBaseEff); aOptFlow = GT_Utility.safeInt(calculatedFlow[0]); @@ -102,14 +102,22 @@ public class GT_MetaTileEntity_LargeTurbine_Steam extends GT_MetaTileEntity_Larg int tEU = 0; int totalFlow = 0; // Byproducts are based on actual flow int flow = 0; - int remainingFlow = GT_Utility.safeInt((long) (aOptFlow * 1.25f)); // Allowed to use up to 125% of optimal flow. Variable required outside of loop for multi-hatch scenarios. + + // Allowed to use up to 250% optimal flow rate, depending on the value of overflowMultiplier. + // This value is chosen because the highest EU/t possible depends on the overflowMultiplier, and the formula used + // makes it so the flow rate for that max, per value of overflowMultiplier, is (percentage of optimal flow rate): + // - 150% if it is 1 + // - 200% if it is 2 + // - 250% if it is 3 + // Variable required outside of loop for multi-hatch scenarios. + int remainingFlow = GT_Utility.safeInt((long) (aOptFlow * (0.5f * overflowMultiplier + 1))); this.realOptFlow = aOptFlow; storedFluid = 0; for (int i = 0; i < aFluids.size() && remainingFlow > 0; i++) { // loop through each hatch; extract inputs and track totals. final FluidStack aFluidStack = aFluids.get(i); if (GT_ModHandler.isAnySteam(aFluidStack)) { - flow = Math.min(aFluidStack.amount, remainingFlow); // try to use up w/o exceeding remainingFlow + flow = Math.min(aFluidStack.amount, remainingFlow); // try to use up to the max flow defined just above depleteInput(new FluidStack(aFluidStack, flow)); // deplete that amount this.storedFluid += aFluidStack.amount; remainingFlow -= flow; // track amount we're allowed to continue depleting from hatches @@ -129,14 +137,38 @@ public class GT_MetaTileEntity_LargeTurbine_Steam extends GT_MetaTileEntity_Larg if (totalFlow == aOptFlow) { tEU = GT_Utility.safeInt((long) tEU * (long) aBaseEff / 20000L); } else { - float efficiency = 1.0f - Math.abs((totalFlow - aOptFlow) / (float) aOptFlow); + float efficiency = getOverflowEfficiency(totalFlow, aOptFlow, overflowMultiplier); tEU *= efficiency; tEU = Math.max(1, GT_Utility.safeInt((long) tEU * (long) aBaseEff / 20000L)); } + // If next output is above the maximum the dynamo can handle, set it to the maximum instead of exploding the turbine + // Raising the maximum allowed flow rate to account for the efficiency changes beyond the optimal flow rate can explode turbines on world load + if (tEU > getMaximumOutput()){ + tEU = GT_Utility.safeInt(getMaximumOutput()); + } + return tEU; } + @Override + float getOverflowEfficiency(int totalFlow, int actualOptimalFlow, int overflowMultiplier) { + // overflowMultiplier changes how quickly the turbine loses efficiency after flow goes beyond the optimal value + // At the default value of 1, any flow will generate less EU/t than optimal flow, regardless of the amount of fuel used + // The bigger this number is, the slower efficiency loss happens as flow moves beyond the optimal value + // Steam is the least efficient out of all turbine fuels in this regard + float efficiency = 0; + + if (totalFlow > actualOptimalFlow) { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow)) / ((float) actualOptimalFlow * (overflowMultiplier + 1)); + } + else { + efficiency = 1.0f - Math.abs((totalFlow - actualOptimalFlow) / (float) actualOptimalFlow); + } + + return efficiency; + } + public static long[] calculateLooseFlow(int aOptFlow, int aBaseEff) { aOptFlow *= 4; if(aBaseEff>=26000) { |