Sacrifice hivemind to convert craters to drawings

Sad, yes, but crater units would never sync well over the net in its current state, so faking them unto conveyors is the only real option.

Forgive me future ai overlord <3
This commit is contained in:
Patrick 'Quezler' Mounier 2020-01-02 21:29:19 +01:00
parent 10e4268dd5
commit 0ae6527584
No known key found for this signature in database
GPG Key ID: 0D6CA7326C76D8EA
14 changed files with 290 additions and 460 deletions

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.8 KiB

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@ -5716,13 +5716,6 @@ crater
orig: 24, 24
offset: 0, 0
index: -1
unit-crater-full
rotate: false
xy: 285, 1379
size: 24, 24
orig: 24, 24
offset: 0, 0
index: -1
power-cell
rotate: false
xy: 285, 1379

Binary file not shown.

Before

Width:  |  Height:  |  Size: 965 KiB

After

Width:  |  Height:  |  Size: 965 KiB

View File

@ -879,25 +879,26 @@ public class Blocks implements ContentList{
//endregion
//region distribution
conveyor = new Conveyor("conveyor"){{
conveyor = new ItemConveyor("conveyor"){{
requirements(Category.distribution, ItemStack.with(Items.copper, 1), true);
health = 45;
speed = 0.03f;
}};
titaniumConveyor = new Conveyor("titanium-conveyor"){{
titaniumConveyor = new ItemConveyor("titanium-conveyor"){{
requirements(Category.distribution, ItemStack.with(Items.copper, 1, Items.lead, 1, Items.titanium, 1));
health = 65;
speed = 0.08f;
}};
plastaniumConveyor = new PlastaniumConveyor("plastanium-conveyor"){{
requirements(Category.distribution, ItemStack.with(Items.plastanium, 1, Items.surgealloy, 1, Items.phasefabric, 1));
health = 150;
plastaniumConveyor = new CraterConveyor("plastanium-conveyor"){{
requirements(Category.distribution, ItemStack.with(Items.plastanium, 1, Items.silicon, 1, Items.graphite, 1));
itemCapacity = 8;
health = 75;
speed = 0f;
}};
armoredConveyor = new ArmoredConveyor("armored-conveyor"){{
armoredConveyor = new ArmoredItemConveyor("armored-conveyor"){{
requirements(Category.distribution, ItemStack.with(Items.plastanium, 1, Items.thorium, 1, Items.metaglass, 1));
health = 180;
speed = 0.08f;

View File

@ -11,29 +11,12 @@ import mindustry.type.*;
public class UnitTypes implements ContentList{
public static UnitType
crater, draug, spirit, phantom,
draug, spirit, phantom,
wraith, ghoul, revenant, lich, reaper,
dagger, crawler, titan, fortress, eruptor, chaosArray, eradicator;
@Override
public void load(){
crater = new UnitType("crater", CraterUnit::new){{
maxVelocity = 0.75f;
speed = 0.1f;
drag = 0.25f;
hitsize = 3.5f;
mass = 0.5f;
health = 50;
rotatespeed = 0.1f;
itemCapacity = 8;
weapon = new Weapon("hug"){{
length = 1.5f;
reload = 28f;
alternate = true;
ejectEffect = Fx.shellEjectSmall;
bullet = Bullets.standardCopper;
}};
}};
draug = new UnitType("draug", MinerDrone::new){{
flying = true;

View File

@ -1,195 +0,0 @@
package mindustry.entities.type.base;
import arc.*;
import arc.math.*;
import arc.util.*;
import mindustry.ui.*;
import mindustry.type.*;
import mindustry.world.*;
import arc.graphics.g2d.*;
import mindustry.content.*;
import mindustry.entities.*;
import mindustry.graphics.*;
import arc.scene.ui.layout.*;
import mindustry.entities.units.*;
import mindustry.game.EventType.*;
import mindustry.entities.Effects.*;
import mindustry.world.blocks.distribution.*;
import mindustry.world.blocks.distribution.PlastaniumConveyor.*;
import static mindustry.Vars.*;
public class CraterUnit extends GroundUnit{
private final Effect io = Fx.plasticburn; // effect to play when poofing in and out of existence
private int inactivity = 0;
public Tile purpose;
private final UnitState
load = new UnitState(){
public void update(){
// launch when crater is full || launch when it got bumped || launch when idling
if(item().amount >= getItemCapacity() || !velocity.isZero(1f) || inactivity++ > 120) state.set(move);
}
},
move = new UnitState(){
public void update(){
// switch to unload when on an end tile
if(dst(on()) < 1.5f && on(Track.end)) state.set(unload);
}
},
unload = new UnitState(){
public void update(){
/*
Switch back to moving when:
- some unit bumped it off
- track got extended
*/
if(!on(Track.end)){
state.set(move);
return;
}
// update will take care of poofing
while(item.amount > 0 && on().block().offloadDir(on(), item.item)){
item.amount--;
if(on().getNearby(on().rotation()).block() instanceof Conveyor) break; // conveyors accept all of it :|
};
}
};
@Override
public UnitState getStartState(){
return load;
}
@Override
public void drawStats(){
drawBackItems();
drawLight();
}
@Override
public void update(){
super.update();
// in the void || not on a valid track || is empty
if(on() == null || !on().block().compressable || item.amount == 0){
Effects.effect(io, x, y); // poof out of existence
kill();
}
Hivemind.update();
if(purpose != null){
if(dst(purpose) > 1f){ // move to target...
velocity.add(vec.trnsExact(angleTo(purpose), type.speed * Time.delta()));
}else{ // ...but snap on its center
x = Mathf.lerp(x, purpose.getX(), 0.01f);
y = Mathf.lerp(y, purpose.getY(), 0.01f);
}
}
rotation = Mathf.slerpDelta(rotation, angleTo(on().front()), type.rotatespeed);
}
@Override
public void added(){
super.added();
Effects.effect(io, x, y); // poof in to existence
baseRotation = rotation; // needed to prevent wobble: load > move
}
@Override
public void onDeath(){
Events.fire(new UnitDestroyEvent(this)); // prevent deathrattle (explosion/sound/etc)
}
@Override
public boolean isCommanded(){
return false; // it has its own logic
}
public static CraterUnit on(Tile tile){ // summons a crater on said tile
CraterUnit crater = (CraterUnit)UnitTypes.crater.create(tile.getTeam());
crater.set(tile.drawx(), tile.drawy());
crater.rotation = tile.rotation() * 90;
crater.add();
Events.fire(new UnitCreateEvent(crater));
return crater;
}
public boolean on(Track track){
return track.check.get(on());
}
public Tile on(){
return world.ltileWorld(x, y);
}
public Tile aspires(){ // what purpose this crater aspires to
if(state.is(load)) return on();
if(on(Track.end)) return on();
return on().front();
}
private void drawBackItems(){
if(item.amount == 0) return;
float itemtime = 0.5f;
float backTrns = 0f;
float size = itemSize / 1.5f;
Draw.rect(item.item.icon(Cicon.medium),
x + Angles.trnsx(rotation + 180f, backTrns),
y + Angles.trnsy(rotation + 180f, backTrns),
size, size, rotation);
Fonts.outline.draw(item.amount + "",
x + Angles.trnsx(rotation + 180f, backTrns),
y + Angles.trnsy(rotation + 180f, backTrns) - 1,
Pal.accent, 0.25f * itemtime / Scl.scl(1f), false, Align.center);
Draw.reset();
}
public boolean loading(){
return state.is(load);
}
public boolean acceptItem(Item item){
if(this.item.amount > 0 && this.item.item != item) return false;
if(this.item.amount >= getItemCapacity()) return false;
// return on(Track.start);
return true;
}
public void handleItem(Item item){
this.item.item = item;
this.inactivity = 0;
this.item.amount++;
}
/**
* Since normal conveyors get faster when boosted,
* this piece of code changes their capacity,
* make sure capacity is dividable by 4,
* for the best user experience.
*/
@Override
public int getItemCapacity(){
if(on() == null || on().entity == null) return type.itemCapacity;
return Mathf.round(type.itemCapacity * on().entity.timeScale);
}
@Override
public void updateTargeting(){
super.updateTargeting();
}
}

View File

@ -1,51 +0,0 @@
package mindustry.entities.units;
import arc.*;
import arc.util.*;
import arc.struct.*;
import mindustry.world.*;
import mindustry.entities.type.base.*;
import mindustry.world.blocks.distribution.*;
import mindustry.world.blocks.distribution.PlastaniumConveyor.*;
import static mindustry.Vars.*;
public class Hivemind{
private static long lastFrameUpdated = -1;
private static Interval timer = new Interval(1);
private static ObjectMap<Tile, CraterUnit> on = new ObjectMap<>();
public static void update(){
if(Core.graphics.getFrameId() == lastFrameUpdated) return;
lastFrameUpdated = Core.graphics.getFrameId();
if(!timer.get(30)) return;
on.clear();
Array<CraterUnit> craters = new Array<>();
unitGroup.all().each(e -> e instanceof CraterUnit, crater -> craters.add((CraterUnit)crater));
craters.sort(Structs.comparingInt(crater -> sortPriority(crater.on())));
craters.each(crater -> {
on.put(crater.on(), crater);
});
craters.each(crater -> {
if(crater == null || crater.aspires() == null) return;
if(!on.containsKey(crater.aspires())){
crater.purpose = crater.aspires();
on.put(crater.aspires(), crater);
on.remove(crater.on());
}
});
}
private static int sortPriority(Tile tile){
if(tile == null) return 0;
if(!(tile.block() instanceof PlastaniumConveyor)) return 0;
PlastaniumConveyorEntity entity = tile.ent();
return entity.tree;
}
}

File diff suppressed because one or more lines are too long

View File

@ -3,15 +3,15 @@ package mindustry.world.blocks.distribution;
import mindustry.type.*;
import mindustry.world.*;
public class ArmoredConveyor extends Conveyor{
public class ArmoredItemConveyor extends ItemConveyor{
public ArmoredConveyor(String name){
public ArmoredItemConveyor(String name){
super(name);
}
@Override
public boolean acceptItem(Item item, Tile tile, Tile source){
return super.acceptItem(item, tile, source) && (source.block() instanceof Conveyor || Edges.getFacingEdge(source, tile).relativeTo(tile) == tile.rotation());
return super.acceptItem(item, tile, source) && (source.block() instanceof ItemConveyor || Edges.getFacingEdge(source, tile).relativeTo(tile) == tile.rotation());
}
@Override

View File

@ -0,0 +1,9 @@
package mindustry.world.blocks.distribution;
import mindustry.world.*;
abstract public class BaseConveyor extends Block{
public BaseConveyor(String name){
super(name);
}
}

View File

@ -0,0 +1,233 @@
package mindustry.world.blocks.distribution;
import arc.*;
import arc.func.*;
import arc.math.*;
import arc.util.*;
import mindustry.ui.*;
import arc.math.geom.*;
import mindustry.type.*;
import mindustry.world.*;
import arc.graphics.g2d.*;
import mindustry.content.*;
import mindustry.entities.*;
import mindustry.graphics.*;
import arc.scene.ui.layout.*;
import mindustry.world.meta.*;
import mindustry.entities.type.*;
import static mindustry.Vars.itemSize;
public class CraterConveyor extends ArmoredItemConveyor{
private TextureRegion start, end, crater;
public CraterConveyor(String name){
super(name);
compressable = true;
entityType = PlastaniumConveyorEntity::new;
}
@Override
public void load(){
int i;
for(i = 0; i < regions.length; i++){
for(int j = 0; j < 4; j++){
regions[i][j] = Core.atlas.find(name + "-" + i + "-" + 0);
}
}
start = Core.atlas.find(name + "-5-0");
end = Core.atlas.find(name + "-6-0");
crater = Core.atlas.find("crater");
}
@Override
public void setStats(){
super.setStats();
stats.remove(BlockStat.itemCapacity);
stats.remove(BlockStat.itemsMoved);
stats.add(BlockStat.maxUnits, 1, StatUnit.none);
}
@Override
public void draw(Tile tile){
super.draw(tile);
// draws the markings over either end of the track
if(Track.start.check.get(tile) && Track.end.check.get(tile)) return;
if(Track.start.check.get(tile)) Draw.rect(start, tile.drawx(), tile.drawy(), tile.rotation() * 90);
if(Track.end.check.get(tile)) Draw.rect(end, tile.drawx(), tile.drawy(), tile.rotation() * 90);
}
@Override
public void drawLayer(Tile tile){
PlastaniumConveyorEntity entity = tile.ent();
if(entity.crater != null) entity.crater.draw(tile);
}
@Override
public void update(Tile tile){ // tick away the cooldown
PlastaniumConveyorEntity entity = tile.ent();
if(entity.crater == null){
if(entity.items.total() > 0){
entity.crater = new Crater(tile);
Effects.effect(Fx.plasticburn, tile.drawx(), tile.drawy());
}
}else{
if(entity.items.total() == 0){
Effects.effect(Fx.plasticburn, tile.drawx(), tile.drawy());
entity.crater = null;
}else{
Tile destination = tile.front();
if(entity.crater.dst(tile) < 0.5f){
entity.crater.f = tile.rotation() * 90 - 90;
if(!(destination.block() instanceof CraterConveyor)){
while(entity.items.total() > 0 && entity.crater.i != null && offloadDir(tile, entity.crater.i)) entity.items.remove(entity.crater.i, 1);
}
}
if(entity.crater.dst(tile) < 0.1f){
if(destination.block() instanceof CraterConveyor){
PlastaniumConveyorEntity e = destination.ent();
if(e.crater == null){
e.crater = entity.crater;
entity.crater = null;
e.items.addAll(entity.items);
entity.items.clear();
}
}
}
}
}
if(entity.crater != null){
entity.crater.x = Mathf.lerpDelta(entity.crater.x, tile.drawx(), 0.05f);
entity.crater.y = Mathf.lerpDelta(entity.crater.y, tile.drawy(), 0.05f);
entity.crater.r = Mathf.slerpDelta(entity.crater.r, entity.crater.f, 0.1f);
}
}
public class PlastaniumConveyorEntity extends ItemConveyorEntity{
Crater crater;
}
protected class Crater implements Position{
float r;
float f;
float x;
float y;
Item i;
Crater(Tile tile){
x = tile.drawx();
y = tile.drawy();
r = tile.rotation() * 90 - 90;
f = r;
}
public void draw(Tile tile){
Draw.rect(crater, x, y, r);
if(i == null){
i = tile.entity.items.take();
tile.entity.items.add(i, 1);
}
float size = itemSize / 1.5f;
Draw.rect(i.icon(Cicon.medium), x, y, size, size, 0);
Fonts.outline.draw(tile.entity.items.total() + "", x, y - 1,
Pal.accent, 0.25f * 0.5f / Scl.scl(1f), false, Align.center);
}
@Override
public float getX(){
return x;
}
@Override
public float getY(){
return y;
}
}
@Override
public boolean acceptItem(Item item, Tile tile, Tile source){ // summon craters into existence to be loaded
PlastaniumConveyorEntity entity = tile.ent();
if(!Track.start.check.get(tile) && !source.block().compressable) return false;
if(entity.items.total() > 0 && !entity.items.has(item)) return false;
if(entity.items.total() >= getMaximumAccepted(tile, item)) return false;
return true;
}
@Override
public void handleItem(Item item, Tile tile, Tile source){
tile.entity.items.add(item, 1);
}
@Override
public int acceptStack(Item item, int amount, Tile tile, Unit source){
if(acceptItem(item, tile, tile) && hasItems && (source == null || source.getTeam() == tile.getTeam())){
return Math.min(getMaximumAccepted(tile, item) - tile.entity.items.get(item), amount);
}else{
return 0;
}
}
@Override
public void handleStack(Item item, int amount, Tile tile, Unit source){
tile.entity.noSleep();
tile.entity.items.add(item, amount);
}
@Override
public int removeStack(Tile tile, Item item, int amount){
if(tile.entity == null || tile.entity.items == null) return 0;
amount = Math.min(amount, tile.entity.items.get(item));
tile.entity.noSleep();
tile.entity.items.remove(item, amount);
return amount;
}
@Override
public boolean blendsArmored(Tile tile, int rotation, int otherx, int othery, int otherrot, Block otherblock){ // only connect to compressable blocks
return super.blendsArmored(tile, rotation, otherx, othery, otherrot, otherblock) && otherblock.compressable;
}
public enum Track{
// tile is considered the end of the line
end(tile -> {
if(tile.front() == null) return true;
if(tile.getTeam() != tile.front().getTeam()) return true; // comment out to trade
return !tile.front().block().compressable;
}),
// tile is considered the start of the line
start(tile -> {
Tile[] inputs = new Tile[]{tile.back(), tile.left(), tile.right()};
for(Tile input : inputs){
if(input != null && input.getTeam() == tile.getTeam() && input.block().compressable && input.front() == tile) return false;
}
return true;
});
public final Boolf<Tile> check;
Track(Boolf<Tile> check){
this.check = check;
}
}
}

View File

@ -22,7 +22,7 @@ import java.io.*;
import static mindustry.Vars.*;
public class Conveyor extends Block implements Autotiler{
public class ItemConveyor extends BaseConveyor implements Autotiler{
private static final float itemSpace = 0.4f;
private static final float minmove = 1f / (Short.MAX_VALUE - 2);
private static ItemPos drawpos = new ItemPos();
@ -34,7 +34,7 @@ public class Conveyor extends Block implements Autotiler{
public float speed = 0f;
protected Conveyor(String name){
protected ItemConveyor(String name){
super(name);
rotate = true;
update = true;
@ -43,7 +43,7 @@ public class Conveyor extends Block implements Autotiler{
hasItems = true;
itemCapacity = 4;
conveyorPlacement = true;
entityType = ConveyorEntity::new;
entityType = ItemConveyorEntity::new;
idleSound = Sounds.conveyor;
idleSoundVolume = 0.004f;
@ -75,7 +75,7 @@ public class Conveyor extends Block implements Autotiler{
@Override
public void draw(Tile tile){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
byte rotation = tile.rotation();
int frame = entity.clogHeat <= 0.5f ? (int)(((Time.time() * speed * 8f * entity.timeScale)) % 4) : 0;
@ -85,7 +85,7 @@ public class Conveyor extends Block implements Autotiler{
@Override
public boolean shouldIdleSound(Tile tile){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
return entity.clogHeat <= 0.5f ;
}
@ -93,7 +93,7 @@ public class Conveyor extends Block implements Autotiler{
public void onProximityUpdate(Tile tile){
super.onProximityUpdate(tile);
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
int[] bits = buildBlending(tile, tile.rotation(), null, true);
entity.blendbits = bits[0];
entity.blendsclx = bits[1];
@ -122,7 +122,7 @@ public class Conveyor extends Block implements Autotiler{
@Override
public void drawLayer(Tile tile){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
byte rotation = tile.rotation();
@ -148,7 +148,7 @@ public class Conveyor extends Block implements Autotiler{
@Override
public void unitOn(Tile tile, Unit unit){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
if(entity.clogHeat > 0.5f){
return;
@ -178,12 +178,12 @@ public class Conveyor extends Block implements Autotiler{
@Override
public void update(Tile tile){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
entity.minitem = 1f;
Tile next = tile.getNearby(tile.rotation());
if(next != null) next = next.link();
float nextMax = next != null && next.block() instanceof Conveyor && !next.block().compressable && next.block().acceptItem(null, next, tile) ? 1f - Math.max(itemSpace - next.<ConveyorEntity>ent().minitem, 0) : 1f;
float nextMax = next != null && next.block() instanceof ItemConveyor && !next.block().compressable && next.block().acceptItem(null, next, tile) ? 1f - Math.max(itemSpace - next.<ItemConveyorEntity>ent().minitem, 0) : 1f;
int minremove = Integer.MAX_VALUE;
for(int i = entity.convey.size - 1; i >= 0; i--){
@ -210,8 +210,8 @@ public class Conveyor extends Block implements Autotiler{
pos.y = Mathf.clamp(pos.y, 0, nextMax);
if(pos.y >= 0.9999f && offloadDir(tile, pos.item)){
if(next != null && next.block() instanceof Conveyor && !next.block().compressable){
ConveyorEntity othere = next.ent();
if(next != null && next.block() instanceof ItemConveyor && !next.block().compressable){
ItemConveyorEntity othere = next.ent();
ItemPos ni = pos2.set(othere.convey.get(othere.lastInserted), ItemPos.updateShorts);
@ -253,17 +253,17 @@ public class Conveyor extends Block implements Autotiler{
@Override
public Block getReplacement(BuildRequest req, Array<BuildRequest> requests){
Boolf<Point2> cont = p -> requests.contains(o -> o.x == req.x + p.x && o.y == req.y + p.y && o.rotation == req.rotation && (req.block instanceof Conveyor || req.block instanceof Junction));
Boolf<Point2> cont = p -> requests.contains(o -> o.x == req.x + p.x && o.y == req.y + p.y && o.rotation == req.rotation && (req.block instanceof ItemConveyor || req.block instanceof Junction));
return cont.get(Geometry.d4(req.rotation)) &&
cont.get(Geometry.d4(req.rotation - 2)) &&
req.tile() != null &&
req.tile().block() instanceof Conveyor &&
req.tile().block() instanceof ItemConveyor &&
Mathf.mod(req.tile().rotation() - req.rotation, 2) == 1 ? Blocks.junction : this;
}
@Override
public int removeStack(Tile tile, Item item, int amount){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
entity.noSleep();
int removed = 0;
@ -289,13 +289,13 @@ public class Conveyor extends Block implements Autotiler{
@Override
public int acceptStack(Item item, int amount, Tile tile, Unit source){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
return Math.min((int)(entity.minitem / itemSpace), amount);
}
@Override
public void handleStack(Item item, int amount, Tile tile, Unit source){
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
for(int i = amount - 1; i >= 0; i--){
long result = ItemPos.packItem(item, 0f, i * itemSpace);
@ -309,7 +309,7 @@ public class Conveyor extends Block implements Autotiler{
@Override
public boolean acceptItem(Item item, Tile tile, Tile source){
int direction = source == null ? 0 : Math.abs(source.relativeTo(tile.x, tile.y) - tile.rotation());
float minitem = tile.<ConveyorEntity>ent().minitem;
float minitem = tile.<ItemConveyorEntity>ent().minitem;
return (((direction == 0) && minitem > itemSpace) ||
((direction % 2 == 1) && minitem > 0.52f)) && (source == null || !(source.block().rotate && (source.rotation() + 2) % 4 == tile.rotation()));
}
@ -324,7 +324,7 @@ public class Conveyor extends Block implements Autotiler{
float pos = ch == 0 ? 0 : ch % 2 == 1 ? 0.5f : 1f;
float y = (ang == -1 || ang == 3) ? 1 : (ang == 1 || ang == -3) ? -1 : 0;
ConveyorEntity entity = tile.ent();
ItemConveyorEntity entity = tile.ent();
entity.noSleep();
long result = ItemPos.packItem(item, y * 0.9f, pos);
@ -343,7 +343,7 @@ public class Conveyor extends Block implements Autotiler{
entity.lastInserted = (byte)(entity.convey.size - 1);
}
public static class ConveyorEntity extends TileEntity{
public static class ItemConveyorEntity extends TileEntity{
LongArray convey = new LongArray();
byte lastInserted;

View File

@ -1,159 +0,0 @@
package mindustry.world.blocks.distribution;
import arc.*;
import arc.func.*;
import arc.util.*;
import arc.struct.*;
import mindustry.ui.*;
import mindustry.type.*;
import mindustry.world.*;
import arc.graphics.g2d.*;
import mindustry.graphics.*;
import arc.scene.ui.layout.*;
import mindustry.world.meta.*;
import mindustry.entities.type.*;
import mindustry.entities.type.base.*;
public class PlastaniumConveyor extends ArmoredConveyor{
protected TextureRegion start;
public TextureRegion end;
protected static int cooldown = 4; // ticks it needs to wait with spawning when a ground unit has walked on it
public PlastaniumConveyor(String name){
super(name);
compressable = true;
entityType = PlastaniumConveyorEntity::new;
}
@Override
public void load(){
int i;
for(i = 0; i < regions.length; i++){
for(int j = 0; j < 4; j++){
regions[i][j] = Core.atlas.find(name + "-" + i + "-" + 0);
}
}
start = Core.atlas.find(name + "-5-0");
end = Core.atlas.find(name + "-6-0");
}
@Override
public void setStats(){
super.setStats();
stats.remove(BlockStat.itemCapacity);
stats.remove(BlockStat.itemsMoved);
stats.add(BlockStat.maxUnits, 1, StatUnit.none);
}
@Override
public void draw(Tile tile){
super.draw(tile);
// draws the markings over either end of the track
if(Track.start.check.get(tile) && Track.end.check.get(tile)) return;
if(Track.start.check.get(tile)) Draw.rect(start, tile.drawx(), tile.drawy(), tile.rotation() * 90);
if(Track.end.check.get(tile)) Draw.rect(end, tile.drawx(), tile.drawy(), tile.rotation() * 90);
}
@Override
public void drawLayer(Tile tile){
if(true) return; // debug mode
PlastaniumConveyorEntity entity = tile.ent();
Fonts.outline.draw(entity.tree + "",
tile.drawx(),
tile.drawy() + 2,
Pal.accent, 0.25f * 1f / Scl.scl(1f), false, Align.center);
}
@Override
public void unitOn(Tile tile, Unit unit){ // resets the spawner cooldown, as well as adopting stray roomba's
PlastaniumConveyorEntity entity = tile.ent();
if(unit instanceof CraterUnit) entity.crater = (CraterUnit)unit;
entity.reload = cooldown;
}
@Override
public void update(Tile tile){ // tick away the cooldown
PlastaniumConveyorEntity entity = tile.ent();
if(entity.reload > 0) entity.reload--;
Tile cur = tile;
ObjectSet<Tile> walked = new ObjectSet<>();
entity.tree = 0;
while(cur.front() != null && cur.front().block() instanceof PlastaniumConveyor && !walked.contains(cur)){
walked.add(cur);
cur = cur.front();
entity.tree++;
}
}
public class PlastaniumConveyorEntity extends ConveyorEntity{
public int reload = 0;
public CraterUnit crater = null;
public int tree = 0;
}
@Override
public boolean acceptItem(Item item, Tile tile, Tile source){ // summon craters into existence to be loaded
PlastaniumConveyorEntity entity = tile.ent();
if(!Track.start.check.get(tile)) return false;
if(entity.crater == null || entity.crater.dead || !entity.crater.loading() || entity.crater.on() != tile){
if(entity.reload > 0) return false;
entity.reload = cooldown;
entity.crater = CraterUnit.on(tile);
}
return entity.crater.acceptItem(item);
}
@Override
public void handleItem(Item item, Tile tile, Tile source){
((PlastaniumConveyorEntity)tile.ent()).crater.handleItem(item);
}
@Override
public int acceptStack(Item item, int amount, Tile tile, Unit source){
return 0;
}
@Override
public void handleStack(Item item, int amount, Tile tile, Unit source){
//
}
@Override
public boolean blendsArmored(Tile tile, int rotation, int otherx, int othery, int otherrot, Block otherblock){ // only connect to compressable blocks
return super.blendsArmored(tile, rotation, otherx, othery, otherrot, otherblock) && otherblock.compressable;
}
public enum Track{
// tile is considered the end of the line
end(tile -> {
if(tile.front() == null) return true;
if(tile.getTeam() != tile.front().getTeam()) return true; // comment out to trade
return !tile.front().block().compressable;
}),
// tile is considered the start of the line
start(tile -> {
Tile[] inputs = new Tile[]{tile.back(), tile.left(), tile.right()};
for(Tile input : inputs){
if(input != null && input.getTeam() == tile.getTeam() && input.block().compressable && input.front() == tile) return false;
}
return true;
});
public final Boolf<Tile> check;
Track(Boolf<Tile> check){
this.check = check;
}
}
}

View File

@ -0,0 +1,16 @@
package mindustry.world.blocks.distribution;
import mindustry.world.*;
/**
* Shares similarities with a conveyor,
* but handles items fundamentally different,
* so much so that its best kept separated.
*
* (conveyors can't handle the cuteness)
*/
public class PlastaniumTrack extends Block{
public PlastaniumTrack(String name){
super(name);
}
}