🔩 Add (plastanium) diode (#964)

* Add plastanium diode

* Only rotate the arrow part

* Use the sum of graph batteries from both sides

* Make diode send power overflow

Diode keeps one-way equalizing while the sending graph has batteries that are ¬ yet fully filled.

* Remove redundant block != null check

* Remove free power

* Stash

* Revert "Stash"

This reverts commit 0c14854519.

* Equalize graph storage percentage

* Update sprite

* Move nearby link check

* DRY

* Fire deathstar at extra spaces

* 〃

* Fix ghost rotation

* Please overlord anuke

* Mild cleanup

* Konami code

* 〃

* Lowercase float

* Newline begone

* Fix overclocking issue

* Fix rotation and name
This commit is contained in:
Patrick 'Quezler' Mounier
2019-11-12 05:29:03 +01:00
committed by Anuken
parent dcdec7f55f
commit f5c1eb74af
13 changed files with 10855 additions and 10670 deletions

View File

@@ -63,7 +63,7 @@ public class Blocks implements ContentList{
//power
combustionGenerator, thermalGenerator, turbineGenerator, differentialGenerator, rtgGenerator, solarPanel, largeSolarPanel, thoriumReactor,
impactReactor, battery, batteryLarge, powerNode, powerNodeLarge, surgeTower,
impactReactor, battery, batteryLarge, powerNode, powerNodeLarge, surgeTower, diode,
//production
mechanicalDrill, pneumaticDrill, laserDrill, blastDrill, waterExtractor, oilExtractor, cultivator,
@@ -1065,6 +1065,10 @@ public class Blocks implements ContentList{
laserRange = 30f;
}};
diode = new PowerDiode("diode"){{
requirements(Category.power, ItemStack.with(Items.silicon, 10, Items.phasefabric, 5, Items.plastanium, 2, Items.metaglass, 1));
}};
battery = new Battery("battery"){{
requirements(Category.power, ItemStack.with(Items.copper, 4, Items.lead, 20));
consumes.powerBuffered(4000f);

View File

@@ -318,6 +318,31 @@ public class Tile implements Position, TargetTrait{
return null;
}
public Tile getNearbyLink(int rotation){
if(rotation == 0) return world.ltile(x + 1, y);
if(rotation == 1) return world.ltile(x, y + 1);
if(rotation == 2) return world.ltile(x - 1, y);
if(rotation == 3) return world.ltile(x, y - 1);
return null;
}
// ▲ ▲ ▼ ▼ ◀ ▶ ◀ ▶ B A
public Tile front(){
return getNearbyLink((rotation + 4) % 4);
}
public Tile right(){
return getNearbyLink((rotation + 3) % 4);
}
public Tile back(){
return getNearbyLink((rotation + 2) % 4);
}
public Tile left(){
return getNearbyLink((rotation + 1) % 4);
}
public boolean interactable(Team team){
return getTeam() == Team.derelict || team == getTeam();
}

View File

@@ -0,0 +1,89 @@
package io.anuke.mindustry.world.blocks.power;
import io.anuke.arc.Core;
import io.anuke.arc.math.Mathf;
import io.anuke.mindustry.ui.Bar;
import io.anuke.arc.util.Eachable;
import io.anuke.mindustry.ui.Cicon;
import io.anuke.mindustry.world.Tile;
import io.anuke.mindustry.world.Block;
import io.anuke.arc.graphics.g2d.Draw;
import io.anuke.mindustry.graphics.Pal;
import io.anuke.arc.graphics.g2d.TextureRegion;
import io.anuke.mindustry.entities.traits.BuilderTrait;
public class PowerDiode extends Block{
protected TextureRegion arrow;
public PowerDiode(String name){
super(name);
rotate = true;
update = true;
solid = true;
insulated = true;
}
@Override
public void update(Tile tile){
super.update(tile);
if(!tile.back().block().hasPower || !tile.front().block().hasPower) return;
PowerGraph backGraph = tile.back().entity.power.graph;
PowerGraph frontGraph = tile.front().entity.power.graph;
if(backGraph == frontGraph) return;
// 0f - 1f of battery capacity in use
float backStored = backGraph.getBatteryStored() / backGraph.getTotalBatteryCapacity();
float frontStored = frontGraph.getBatteryStored() / frontGraph.getTotalBatteryCapacity();
// try to send if the back side has more % capacity stored than the front side
if(backStored > frontStored) {
// send half of the difference
float amount = backGraph.getBatteryStored() * (backStored - frontStored) / 2;
// prevent sending more than the front can handle
amount = Mathf.clamp(amount, 0, frontGraph.getTotalBatteryCapacity() * (1 - frontStored));
backGraph.useBatteries(amount);
frontGraph.chargeBatteries(amount);
}
}
// battery % of the graph on either side, defaults to zero
protected float bar(Tile tile){
return tile.block().hasPower ? tile.entity.power.graph.getBatteryStored() / tile.entity.power.graph.getTotalBatteryCapacity() : 0f;
}
@Override
public void setBars(){
super.setBars();
bars.add("back", entity -> new Bar("bar.input", Pal.lighterOrange, () -> bar(entity.tile.back())) );
bars.add("front", entity -> new Bar("bar.output", Pal.lighterOrange, () -> bar(entity.tile.front())) );
}
@Override
public void load(){
super.load();
arrow = Core.atlas.find(name + "-arrow");
}
@Override
public void draw(Tile tile){
Draw.rect(region, tile.drawx(), tile.drawy(), 0);
Draw.rect(arrow, tile.drawx(), tile.drawy(), rotate ? tile.rotation() * 90 : 0);
}
@Override
public void drawRequestRegion(BuilderTrait.BuildRequest req, Eachable<BuilderTrait.BuildRequest> list) {
TextureRegion reg = icon(Cicon.full);
Draw.rect(icon(Cicon.full), req.drawx(), req.drawy(),
reg.getWidth() * req.animScale * Draw.scl,
reg.getHeight() * req.animScale * Draw.scl,
0);
Draw.rect(arrow, req.drawx(), req.drawy(),
arrow.getWidth() * req.animScale * Draw.scl,
arrow.getHeight() * req.animScale * Draw.scl,
!rotate ? 0 : req.rotation * 90);
}
}