mirror of
https://github.com/Anuken/Mindustry.git
synced 2025-01-03 13:30:25 +07:00
Fixed occassional crashes of Power Tests and continued TDD
This commit is contained in:
parent
11e071289b
commit
f56e1933a6
@ -19,17 +19,17 @@ public class PowerBlocks extends BlockList implements ContentList{
|
||||
|
||||
thermalGenerator = new LiquidHeatGenerator("thermal-generator"){{
|
||||
maxLiquidGenerate = 4f;
|
||||
// TODO: Adapt to new power system
|
||||
powerProduction = -1;
|
||||
powerPerLiquid = 0.1f;
|
||||
// TODO: Balance
|
||||
powerProduction = 0.17f;
|
||||
liquidPowerMultiplier = 0.1f;
|
||||
generateEffect = BlockFx.redgeneratespark;
|
||||
size = 2;
|
||||
}};
|
||||
|
||||
turbineGenerator = new TurbineGenerator("turbine-generator"){{
|
||||
// TODO: Adapt to new power system
|
||||
// TODO: Balance
|
||||
powerProduction = 0.28f;
|
||||
powerPerLiquid = 0.1f;
|
||||
liquidPowerMultiplier = 0.3f;
|
||||
itemDuration = 30f;
|
||||
consumes.liquid(Liquids.water, 0.05f);
|
||||
size = 2;
|
||||
|
@ -14,7 +14,7 @@ import static io.anuke.mindustry.Vars.tilesize;
|
||||
|
||||
public abstract class ItemLiquidGenerator extends ItemGenerator{
|
||||
protected float minLiquidEfficiency = 0.2f;
|
||||
protected float powerPerLiquid = 0.13f;
|
||||
protected float liquidPowerMultiplier = 1.3f; // A liquid with 100% flammability will be 30% more efficient than an item with 100% flammability.
|
||||
/**Maximum liquid used per frame.*/
|
||||
protected float maxLiquidGenerate = 0.4f;
|
||||
|
||||
@ -46,15 +46,16 @@ public abstract class ItemLiquidGenerator extends ItemGenerator{
|
||||
}
|
||||
|
||||
//liquid takes priority over solids
|
||||
float calculationDelta = entity.delta();
|
||||
if(liquid != null && entity.liquids.get(liquid) >= 0.001f && entity.cons.valid()){
|
||||
float powerPerLiquid = getLiquidEfficiency(liquid) * this.powerPerLiquid;
|
||||
float used = Math.min(entity.liquids.get(liquid), maxLiquidGenerate * entity.delta());
|
||||
// TODO: Adapt to new power system
|
||||
//used = Math.min(used, (powerCapacity - entity.power.amount) / powerPerLiquid);
|
||||
float baseLiquidEfficiency = getLiquidEfficiency(liquid) * this.liquidPowerMultiplier;
|
||||
float maximumPossible = maxLiquidGenerate * calculationDelta;
|
||||
float used = Math.min(entity.liquids.get(liquid), maximumPossible);
|
||||
|
||||
entity.liquids.remove(liquid, used);
|
||||
// TODO: Adapt to new power system
|
||||
//entity.power.amount += used * powerPerLiquid;
|
||||
|
||||
// Note: 1 Item with 100% Flammability = 100% efficiency. This means 100% is not max but rather a reference point for this generator.
|
||||
entity.productionEfficiency = baseLiquidEfficiency * used / maximumPossible;
|
||||
|
||||
if(used > 0.001f && Mathf.chance(0.05 * entity.delta())){
|
||||
Effects.effect(generateEffect, tile.drawx() + Mathf.range(3f), tile.drawy() + Mathf.range(3f));
|
||||
|
@ -13,7 +13,7 @@ import io.anuke.ucore.util.Mathf;
|
||||
|
||||
public abstract class LiquidGenerator extends PowerGenerator{
|
||||
protected float minEfficiency = 0.2f;
|
||||
protected float powerPerLiquid;
|
||||
protected float liquidPowerMultiplier;
|
||||
/**Maximum liquid used per frame.*/
|
||||
protected float maxLiquidGenerate;
|
||||
protected Effect generateEffect = BlockFx.generatespark;
|
||||
@ -50,8 +50,9 @@ public abstract class LiquidGenerator extends PowerGenerator{
|
||||
public void update(Tile tile){
|
||||
TileEntity entity = tile.entity();
|
||||
|
||||
// TODO Code duplication with ItemLiquidGenerator
|
||||
if(entity.liquids.get(entity.liquids.current()) >= 0.001f){
|
||||
float powerPerLiquid = getEfficiency(entity.liquids.current()) * this.powerPerLiquid;
|
||||
//float powerPerLiquid = getEfficiency(entity.liquids.current()) * this.powerPerLiquid;
|
||||
float used = Math.min(entity.liquids.currentAmount(), maxLiquidGenerate * entity.delta());
|
||||
// TODO Adapt to new power system
|
||||
//used = Math.min(used, (powerCapacity - entity.power.amount) / powerPerLiquid);
|
||||
|
@ -14,9 +14,9 @@ public class LiquidHeatGenerator extends LiquidGenerator{
|
||||
public void setStats(){
|
||||
super.setStats();
|
||||
|
||||
// TODO Verify for new power system
|
||||
stats.remove(BlockStat.basePowerGeneration);
|
||||
stats.add(BlockStat.basePowerGeneration, maxLiquidGenerate * powerPerLiquid * 60f, StatUnit.powerSecond);
|
||||
// TODO Adapt to new new power system. Maybe this override can be removed.
|
||||
//stats.add(BlockStat.basePowerGeneration, <Do something with maxLiquidGenerate, basePowerGeneration and liquidPowerMultiplier> * 60f, StatUnit.powerSecond);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -10,7 +10,7 @@ import io.anuke.mindustry.world.meta.BlockStat;
|
||||
|
||||
public class PowerGenerator extends PowerDistributor{
|
||||
/** The amount of power produced per tick. */
|
||||
public float powerProduction;
|
||||
protected float powerProduction;
|
||||
public BlockStat generationType = BlockStat.basePowerGeneration;
|
||||
|
||||
public PowerGenerator(String name){
|
||||
|
@ -1,37 +1,57 @@
|
||||
package power;
|
||||
|
||||
import io.anuke.mindustry.content.Liquids;
|
||||
import io.anuke.mindustry.type.Item;
|
||||
import io.anuke.mindustry.type.Liquid;
|
||||
import io.anuke.mindustry.world.Tile;
|
||||
import io.anuke.mindustry.world.blocks.power.BurnerGenerator;
|
||||
import io.anuke.mindustry.world.blocks.power.ItemGenerator;
|
||||
import io.anuke.mindustry.world.blocks.power.ItemLiquidGenerator;
|
||||
import io.anuke.mindustry.world.blocks.power.PowerGenerator;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assumptions.assumeTrue;
|
||||
import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
/** This class tests the abstract ItemLiquidGenerator class and maybe some of its dependencies. */
|
||||
public class ItemLiquidGeneratorTests extends PowerTestFixture{
|
||||
|
||||
private ItemLiquidGenerator sut; // system under test (https://en.wikipedia.org/wiki/System_under_test)
|
||||
private ItemLiquidGenerator generator;
|
||||
private Tile tile;
|
||||
private ItemGenerator.ItemGeneratorEntity entity;
|
||||
private final float fakeLiquidPowerMultiplier = 2.0f;
|
||||
private final float fakeMaxLiquidGenerate = 0.5f;
|
||||
|
||||
@BeforeEach
|
||||
public void createItemLiquidGenerator(){
|
||||
sut = new ItemLiquidGenerator("fakegen"){
|
||||
@Override
|
||||
protected float getLiquidEfficiency(Liquid liquid){
|
||||
return liquid.flammability;
|
||||
}
|
||||
public void createBurnerGenerator(){
|
||||
// Use a burner generator instead of a custom ItemLiquidGenerator subclass since we would implement abstract methods the same way.
|
||||
generator = new BurnerGenerator("fakegen"){{
|
||||
powerProduction = 0.1f;
|
||||
itemDuration = 60f;
|
||||
liquidPowerMultiplier = fakeLiquidPowerMultiplier;
|
||||
maxLiquidGenerate = fakeMaxLiquidGenerate;
|
||||
}};
|
||||
|
||||
@Override
|
||||
protected float getItemEfficiency(Item item){
|
||||
return item.flammability;
|
||||
}
|
||||
};
|
||||
tile = createFakeTile(0, 0, sut);
|
||||
tile = createFakeTile(0, 0, generator);
|
||||
entity = tile.entity();
|
||||
}
|
||||
|
||||
@Test
|
||||
void detectCrashes(){
|
||||
sut.update(tile);
|
||||
void testLiquidConsumption(){
|
||||
final float providedUsage = 0.1f;
|
||||
final float expectedEfficiency = providedUsage / fakeMaxLiquidGenerate * fakeLiquidPowerMultiplier * Liquids.oil.flammability;
|
||||
|
||||
entity.liquids.add(Liquids.oil, providedUsage);
|
||||
entity.cons.update(tile.entity);
|
||||
assumeTrue(entity.cons.valid());
|
||||
|
||||
// Perform an update on the generator once - This should use up all oil and produce a fraction of what's possible
|
||||
generator.update(tile);
|
||||
|
||||
assertEquals(0.0f, entity.liquids.get(Liquids.oil));
|
||||
assertEquals(expectedEfficiency, entity.productionEfficiency);
|
||||
}
|
||||
}
|
||||
|
@ -3,17 +3,25 @@ package power;
|
||||
import io.anuke.mindustry.Vars;
|
||||
import io.anuke.mindustry.content.blocks.Blocks;
|
||||
import io.anuke.mindustry.core.ContentLoader;
|
||||
import io.anuke.mindustry.core.World;
|
||||
import io.anuke.mindustry.entities.TileEntity;
|
||||
import io.anuke.mindustry.world.Block;
|
||||
import io.anuke.mindustry.world.Tile;
|
||||
import io.anuke.mindustry.world.blocks.PowerBlock;
|
||||
import io.anuke.mindustry.world.blocks.power.Battery;
|
||||
import io.anuke.mindustry.world.blocks.power.PowerGenerator;
|
||||
import io.anuke.mindustry.world.modules.ConsumeModule;
|
||||
import io.anuke.mindustry.world.modules.ItemModule;
|
||||
import io.anuke.mindustry.world.modules.LiquidModule;
|
||||
import io.anuke.mindustry.world.modules.PowerModule;
|
||||
import io.anuke.ucore.entities.Entities;
|
||||
import org.junit.jupiter.api.BeforeAll;
|
||||
|
||||
import java.lang.reflect.Field;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import static io.anuke.mindustry.Vars.world;
|
||||
|
||||
/** This class provides objects commonly used by power related unit tests.
|
||||
* For now, this is a helper with static methods, but this might change.
|
||||
* */
|
||||
@ -62,7 +70,7 @@ public class PowerTestFixture{
|
||||
|
||||
// Using the Tile(int, int, byte, byte) constructor would require us to register any fake block or tile we create
|
||||
// Since this part shall not be part of the test and would require more work anyway, we manually set the block and floor
|
||||
// and call the private changed() method through reflections.
|
||||
// through reflections and then simulate part of what the changed() method does.
|
||||
|
||||
Field field = Tile.class.getDeclaredField("wall");
|
||||
field.setAccessible(true);
|
||||
@ -72,10 +80,15 @@ public class PowerTestFixture{
|
||||
field.setAccessible(true);
|
||||
field.set(tile, Blocks.sand);
|
||||
|
||||
Method method = Tile.class.getDeclaredMethod("changed");
|
||||
method.setAccessible(true);
|
||||
method.invoke(tile);
|
||||
|
||||
// Simulate the "changed" method. Calling it through reflections would require half the game to be initialized.
|
||||
tile.entity = block.newEntity().init(tile, false);
|
||||
tile.entity.cons = new ConsumeModule();
|
||||
if(block.hasItems) tile.entity.items = new ItemModule();
|
||||
if(block.hasLiquids) tile.entity.liquids = new LiquidModule();
|
||||
if(block.hasPower){
|
||||
tile.entity.power = new PowerModule();
|
||||
tile.entity.power.graph.add(tile);
|
||||
}
|
||||
return tile;
|
||||
}catch(Exception ex){
|
||||
return null;
|
||||
|
Loading…
Reference in New Issue
Block a user