aaaaaaaAAAAAAAAAAAAAAAAAA

This commit is contained in:
Anuken
2021-12-18 23:23:35 -05:00
parent 41b669d6e1
commit 8023ea1d34
14 changed files with 103 additions and 80 deletions
@@ -1 +1 @@
{fields:[{name:ammo,type:float},{name:building,type:Building},{name:controller,type:mindustry.entities.units.UnitController},{name:elevation,type:float},{name:flag,type:double},{name:health,type:float},{name:isShooting,type:boolean},{name:mineTile,type:mindustry.world.Tile},{name:mounts,type:"mindustry.entities.units.WeaponMount[]"},{name:plans,type:arc.struct.Queue<mindustry.entities.units.BuildPlan>},{name:rotation,type:float},{name:shield,type:float},{name:spawnedByCore,type:boolean},{name:stack,type:mindustry.type.ItemStack},{name:statuses,type:arc.struct.Seq<mindustry.entities.units.StatusEntry>},{name:team,type:mindustry.game.Team},{name:type,type:mindustry.type.UnitType},{name:updateBuilding,type:boolean},{name:vel,type:arc.math.geom.Vec2},{name:x,type:float},{name:y,type:float}]} {fields:[{name:ammo,type:float},{name:building,type:Building},{name:controller,type:mindustry.entities.units.UnitController},{name:elevation,type:float},{name:flag,type:double},{name:health,type:float},{name:isShooting,type:boolean},{name:mineTile,type:mindustry.world.Tile},{name:mounts,type:"mindustry.entities.units.WeaponMount[]"},{name:payloads,type:arc.struct.Seq<mindustry.world.blocks.payloads.Payload>},{name:plans,type:arc.struct.Queue<mindustry.entities.units.BuildPlan>},{name:rotation,type:float},{name:shield,type:float},{name:spawnedByCore,type:boolean},{name:stack,type:mindustry.type.ItemStack},{name:statuses,type:arc.struct.Seq<mindustry.entities.units.StatusEntry>},{name:team,type:mindustry.game.Team},{name:type,type:mindustry.type.UnitType},{name:updateBuilding,type:boolean},{name:vel,type:arc.math.geom.Vec2},{name:x,type:float},{name:y,type:float}]}
Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.2 KiB

After

Width:  |  Height:  |  Size: 1.2 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.3 KiB

After

Width:  |  Height:  |  Size: 3.9 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 4.3 KiB

After

Width:  |  Height:  |  Size: 4.3 KiB

+9 -5
View File
@@ -1,22 +1,26 @@
package mindustry.ai.types; package mindustry.ai.types;
import arc.math.*;
import arc.math.geom.*; import arc.math.geom.*;
import mindustry.entities.units.*; import mindustry.entities.units.*;
import mindustry.gen.*;
import mindustry.world.blocks.units.UnitAssembler.*;
public class AssemblerAI extends AIController{ public class AssemblerAI extends AIController{
public Vec2 targetPos = new Vec2(); public Vec2 targetPos = new Vec2();
public float targetAngle;
@Override @Override
public void updateMovement(){ public void updateMovement(){
//TODO //TODO
if(!targetPos.isZero()){ if(!targetPos.isZero()){
moveTo(targetPos, 8f, 11f); moveTo(targetPos, 1f, 3f);
} }
if(unit instanceof BuildingTetherc tether && tether.building() instanceof UnitAssemblerBuild assembler){ if(unit.within(targetPos, 5f)){
unit.lookAt(assembler.getUnitSpawn()); unit.lookAt(targetAngle);
} }
} }
public boolean inPosition(){
return unit.within(targetPos, 10f) && Angles.within(unit.rotation, targetAngle, 15f);
}
} }
+1 -1
View File
@@ -3319,7 +3319,7 @@ public class Blocks{
//TODO completely unfinished //TODO completely unfinished
tankAssembler = new UnitAssembler("tank-assembler"){{ tankAssembler = new UnitAssembler("tank-assembler"){{
requirements(Category.units, with(Items.graphite, 10)); requirements(Category.units, with(Items.graphite, 10));
size = 3; size = 5;
droneType = UnitTypes.manifold; droneType = UnitTypes.manifold;
plans.add(new AssemblerUnitPlan(UnitTypes.vanquish, 60f * 5f, BlockStack.list(Blocks.thoriumWallLarge, 4, Blocks.duct, 2))); plans.add(new AssemblerUnitPlan(UnitTypes.vanquish, 60f * 5f, BlockStack.list(Blocks.thoriumWallLarge, 4, Blocks.duct, 2)));
consumes.power(1f); consumes.power(1f);
+12
View File
@@ -13,6 +13,7 @@ import mindustry.gen.*;
import mindustry.graphics.*; import mindustry.graphics.*;
import mindustry.type.*; import mindustry.type.*;
import mindustry.world.*; import mindustry.world.*;
import mindustry.world.blocks.units.UnitAssembler.*;
import static arc.graphics.g2d.Draw.rect; import static arc.graphics.g2d.Draw.rect;
import static arc.graphics.g2d.Draw.*; import static arc.graphics.g2d.Draw.*;
@@ -226,6 +227,17 @@ public class Fx{
}); });
}), }),
payloadDeposit = new Effect(30f, e -> {
if(!(e.data instanceof YeetData data)) return;
Tmp.v1.set(e.x, e.y).lerp(data.target, e.finpow());
float x = Tmp.v1.x, y = Tmp.v1.y;
scl(e.fout(Interp.pow3Out) * 1.05f);
Drawf.squareShadow(x, y, data.block.size * tilesize * 1.85f, 1f);
mixcol(Pal.accent, e.fin());
rect(data.block.fullIcon, x, y);
}).layer(Layer.flyingUnitLow - 5f),
select = new Effect(23, e -> { select = new Effect(23, e -> {
color(Pal.accent); color(Pal.accent);
stroke(e.fout() * 3f); stroke(e.fout() * 3f);
+8 -4
View File
@@ -68,8 +68,8 @@ public class UnitTypes{
//special block unit type //special block unit type
public static @EntityDef({Unitc.class, BlockUnitc.class}) UnitType block; public static @EntityDef({Unitc.class, BlockUnitc.class}) UnitType block;
//special tethered //special tethered (has payload capability, because it's necessary sometimes)
public static @EntityDef({Unitc.class, BuildingTetherc.class}) UnitType manifold, assemblyDrone; public static @EntityDef({Unitc.class, BuildingTetherc.class, Payloadc.class}) UnitType manifold, assemblyDrone, payloadDrone;
//tank //tank
//TODO tank comp //TODO tank comp
@@ -2431,7 +2431,7 @@ public class UnitTypes{
hitSize = 28f; hitSize = 28f;
treadPullOffset = 4; treadPullOffset = 4;
speed = 0.6f; speed = 0.6f;
health = 10000; health = 9000;
armor = 20f; armor = 20f;
treadRect = new Rect(22f, 16f, 28f, 130f); treadRect = new Rect(22f, 16f, 28f, 130f);
@@ -2448,7 +2448,7 @@ public class UnitTypes{
y = 0; y = 0;
shadow = 28f; shadow = 28f;
bullet = new BasicBulletType(7f, 50){{ bullet = new BasicBulletType(7f, 90){{
sprite = "missile-large"; sprite = "missile-large";
width = 9f; width = 9f;
height = 15f; height = 15f;
@@ -2744,6 +2744,10 @@ public class UnitTypes{
envDisabled = Env.none; envDisabled = Env.none;
}}; }};
//payloadDrone = new UnitType("payload-drone"){{
//}};
//endregion //endregion
//region neoplasm //region neoplasm
+6
View File
@@ -224,6 +224,12 @@ public class Drawf{
shadow(x, y, rad, 1f); shadow(x, y, rad, 1f);
} }
public static void squareShadow(float x, float y, float rad, float alpha){
Draw.color(0, 0, 0, 0.4f * alpha);
Draw.rect("square-shadow", x, y, rad * Draw.xscl, rad * Draw.yscl);
Draw.color();
}
public static void shadow(float x, float y, float rad, float alpha){ public static void shadow(float x, float y, float rad, float alpha){
Draw.color(0, 0, 0, 0.4f * alpha); Draw.color(0, 0, 0, 0.4f * alpha);
Draw.rect("circle-shadow", x, y, rad * Draw.xscl, rad * Draw.yscl); Draw.rect("circle-shadow", x, y, rad * Draw.xscl, rad * Draw.yscl);
@@ -252,12 +252,12 @@ public class ErekirPlanetGenerator extends PlanetGenerator{
state.rules.defaultTeam.items().add(Seq.with(ItemStack.with(Items.beryllium, 300, Items.graphite, 300))); state.rules.defaultTeam.items().add(Seq.with(ItemStack.with(Items.beryllium, 300, Items.graphite, 300)));
//TODO proper waves //TODO proper waves
state.rules.waves = false; state.rules.waves = true;
state.rules.showSpawns = true; state.rules.showSpawns = true;
state.rules.waveTimer = true; state.rules.waveTimer = true;
state.rules.waveSpacing = 60f * 60f * 10f; state.rules.waveSpacing = 60f * 60f * 15f;
state.rules.spawns = Seq.with(new SpawnGroup(){{ state.rules.spawns = Seq.with(new SpawnGroup(){{
type = UnitTypes.fortress; type = UnitTypes.vanquish;
spacing = 1; spacing = 1;
shieldScaling = 60; shieldScaling = 60;
unitScaling = 2f; unitScaling = 2f;
@@ -85,13 +85,15 @@ public class BuildPayload implements Payload{
@Override @Override
public void drawShadow(float alpha){ public void drawShadow(float alpha){
Drawf.shadow(build.x, build.y, build.block.size * tilesize * 2f, alpha); Drawf.squareShadow(build.x, build.y, build.block.size * tilesize * 1.85f, alpha);
} }
@Override @Override
public void draw(){ public void draw(){
drawShadow(1f);
float prevZ = Draw.z(); float prevZ = Draw.z();
Draw.z(prevZ - 0.0001f);
drawShadow(1f);
Draw.z(prevZ);
Draw.zTransform(z -> z >= Layer.flyingUnitLow ? z : 0.0011f + Mathf.clamp(z, prevZ - 0.001f, prevZ + 0.9f)); Draw.zTransform(z -> z >= Layer.flyingUnitLow ? z : 0.0011f + Mathf.clamp(z, prevZ - 0.001f, prevZ + 0.9f));
build.tile = emptyTile; build.tile = emptyTile;
build.payloadDraw(); build.payloadDraw();
@@ -92,12 +92,12 @@ public class UnitAssembler extends PayloadBlock{
@Override @Override
public void init(){ public void init(){
clipSize = Math.max(clipSize, (areaSize + size) * tilesize * 2);
consumes.add(new ConsumePayloadDynamic((UnitAssemblerBuild build) -> build.plan().requirements)); consumes.add(new ConsumePayloadDynamic((UnitAssemblerBuild build) -> build.plan().requirements));
super.init(); super.init();
} }
@Override @Override
public void setStats(){ public void setStats(){
super.setStats(); super.setStats();
@@ -137,6 +137,16 @@ public class UnitAssembler extends PayloadBlock{
AssemblerUnitPlan(){} AssemblerUnitPlan(){}
} }
public static class YeetData{
public Vec2 target;
public Block block;
public YeetData(Vec2 target, Block block){
this.target = target;
this.block = block;
}
}
public class UnitAssemblerBuild extends PayloadBlockBuild<BuildPayload>{ public class UnitAssemblerBuild extends PayloadBlockBuild<BuildPayload>{
protected IntSeq readUnits = new IntSeq(); protected IntSeq readUnits = new IntSeq();
@@ -146,7 +156,6 @@ public class UnitAssembler extends PayloadBlock{
public float progress, warmup; public float progress, warmup;
public float invalidWarmup = 0f; public float invalidWarmup = 0f;
public int currentTier = 0; public int currentTier = 0;
public boolean wasOccupied = false; public boolean wasOccupied = false;
public Vec2 getUnitSpawn(){ public Vec2 getUnitSpawn(){
@@ -173,7 +182,6 @@ public class UnitAssembler extends PayloadBlock{
public void updateModules(UnitAssemblerModuleBuild build){ public void updateModules(UnitAssemblerModuleBuild build){
modules.addUnique(build); modules.addUnique(build);
checkTier(); checkTier();
//TODO tier check
} }
public void removeModule(UnitAssemblerModuleBuild build){ public void removeModule(UnitAssemblerModuleBuild build){
@@ -211,7 +219,7 @@ public class UnitAssembler extends PayloadBlock{
Drawf.selected(module, Pal.accent); Drawf.selected(module, Pal.accent);
} }
//TODO draw area //TODO draw area when no power
} }
//is this necessary? wastes a lot of space //is this necessary? wastes a lot of space
@@ -265,10 +273,10 @@ public class UnitAssembler extends PayloadBlock{
readUnits.clear(); readUnits.clear();
} }
units.removeAll(u -> !u.isAdded() || u.dead); units.removeAll(u -> !u.isAdded() || u.dead || !(u.controller() instanceof AssemblerAI));
//TODO build up units, don't spawn immediately in batches
if(efficiency() > 0 && units.size < dronesCreated){ if(efficiency() > 0 && units.size < dronesCreated){
//TODO build animation? distribute spawning?
var unit = droneType.create(team); var unit = droneType.create(team);
if(unit instanceof BuildingTetherc bt){ if(unit instanceof BuildingTetherc bt){
bt.building(this); bt.building(this);
@@ -281,20 +289,26 @@ public class UnitAssembler extends PayloadBlock{
units.add(unit); units.add(unit);
} }
//TODO units should move stuff into position //TODO units should pick up and move payloads into position
Vec2 spawn = getUnitSpawn(); Vec2 spawn = getUnitSpawn();
if(moveInPayload() && !wasOccupied){
yeetPayload(payload);
payload = null;
}
//arrange units around perimeter //arrange units around perimeter
for(int i = 0; i < units.size; i++){ for(int i = 0; i < units.size; i++){
var unit = units.get(i); var unit = units.get(i);
if(unit.controller() instanceof AssemblerAI ai){ var ai = (AssemblerAI)unit.controller();
ai.targetPos.trns(i * 90f + 45f, areaSize / 2f * Mathf.sqrt2 * tilesize).add(spawn);
} ai.targetPos.trns(i * 90f + 45f, areaSize / 2f * Mathf.sqrt2 * tilesize).add(spawn);
ai.targetAngle = i * 90f + 45f + 180f;
} }
wasOccupied = checkSolid(spawn); wasOccupied = checkSolid(spawn);
float eff = (units.size / (float)dronesCreated); float eff = (units.count(u -> ((AssemblerAI)u.controller()).inPosition()) / (float)dronesCreated);
invalidWarmup = Mathf.lerpDelta(invalidWarmup, wasOccupied ? 1f : 0f, 0.1f); invalidWarmup = Mathf.lerpDelta(invalidWarmup, wasOccupied ? 1f : 0f, 0.1f);
@@ -312,7 +326,8 @@ public class UnitAssembler extends PayloadBlock{
var unit = plan.unit.create(team); var unit = plan.unit.create(team);
unit.set(spawn.x + Mathf.range(0.001f), spawn.y + Mathf.range(0.001f)); unit.set(spawn.x + Mathf.range(0.001f), spawn.y + Mathf.range(0.001f));
unit.rotation = 90f; unit.rotation = 90f;
unit.add(); //TODO annoying so nothing is created yet
//unit.add();
progress = 0f; progress = 0f;
Fx.spawn.at(unit); Fx.spawn.at(unit);
@@ -329,7 +344,6 @@ public class UnitAssembler extends PayloadBlock{
@Override @Override
public void draw(){ public void draw(){
Draw.rect(region, x, y); Draw.rect(region, x, y);
//Draw.rect(outRegion, x, y, rotdeg());
//draw input conveyors //draw input conveyors
for(int i = 0; i < 4; i++){ for(int i = 0; i < 4; i++){
@@ -340,12 +354,13 @@ public class UnitAssembler extends PayloadBlock{
Draw.z(Layer.blockOver); Draw.z(Layer.blockOver);
//payRotation = rotdeg(); payRotation = rotdeg();
//drawPayload(); drawPayload();
Draw.z(Layer.blockOver + 0.1f); Draw.z(Layer.blockOver + 0.1f);
Draw.rect(topRegion, x, y); //TODO top?
//Draw.rect(topRegion, x, y);
Vec2 spawn = getUnitSpawn(); Vec2 spawn = getUnitSpawn();
@@ -355,7 +370,6 @@ public class UnitAssembler extends PayloadBlock{
Draw.rect(plan.unit.fullIcon, spawn.x, spawn.y); Draw.rect(plan.unit.fullIcon, spawn.x, spawn.y);
//TODO which layer?
Draw.z(Layer.buildBeam); Draw.z(Layer.buildBeam);
//draw unit outline //draw unit outline
@@ -364,16 +378,16 @@ public class UnitAssembler extends PayloadBlock{
Draw.rect(plan.unit.fullIcon, spawn.x, spawn.y); Draw.rect(plan.unit.fullIcon, spawn.x, spawn.y);
Draw.alpha(warmup * Draw.getColor().a); Draw.alpha(warmup * Draw.getColor().a);
int c = 0;
//draw build beams
for(var unit : units){ for(var unit : units){
if(!Angles.within(unit.rotation, c * 90f + 45f + 180f, 15f)) continue; if(!((AssemblerAI)unit.controller()).inPosition()) continue;
float float
px = unit.x + Angles.trnsx(unit.rotation, unit.type.buildBeamOffset), px = unit.x + Angles.trnsx(unit.rotation, unit.type.buildBeamOffset),
py = unit.y + Angles.trnsy(unit.rotation, unit.type.buildBeamOffset); py = unit.y + Angles.trnsy(unit.rotation, unit.type.buildBeamOffset);
Drawf.buildBeam(px, py, spawn.x, spawn.y, plan.unit.hitSize/2f); Drawf.buildBeam(px, py, spawn.x, spawn.y, plan.unit.hitSize/2f);
c ++;
} }
Draw.reset(); Draw.reset();
@@ -389,37 +403,30 @@ public class UnitAssembler extends PayloadBlock{
Draw.reset(); Draw.reset();
float outSize = plan.unit.hitSize + 9f; float outSize = plan.unit.hitSize + 9f;
float hs = size * tilesize/2f, ha = outSize/2f;
Lines.stroke(2f, Tmp.c3.set(Pal.accent).lerp(Pal.remove, invalidWarmup).a(efficiency()));
//draw small square for area //draw small square for area
//TODO dash rect for output, fades in/out Lines.stroke(2f, Tmp.c3.set(Pal.accent).lerp(Pal.remove, invalidWarmup).a(efficiency()));
Drawf.dashSquareBasic(spawn.x, spawn.y, outSize); Drawf.dashSquareBasic(spawn.x, spawn.y, outSize);
/*
for(int i : Mathf.signs){
Tmp.v1.trns(rotation * 90, hs, hs * i).add(x, y);
Tmp.v2.trns(rotation * 90, -ha, ha * i).add(spawn);
Draw.color();
Drawf.dashLine(color, Tmp.v1.x, Tmp.v1.y, Tmp.v2.x, Tmp.v2.y);
}*/
Draw.reset();
Draw.z(Layer.overlayUI - 1);
//TODO dashes bad
Draw.reset(); Draw.reset();
} }
public boolean checkSolid(Vec2 v){ public boolean checkSolid(Vec2 v){
var output = unit(); var output = unit();
return !output.flying && (collisions.overlapsTile(Tmp.r1.setCentered(v.x, v.y, output.hitSize), EntityCollisions::solid) || Units.anyEntities(v.x, v.y, output.hitSize)); return !output.flying && (collisions.overlapsTile(Tmp.r1.setCentered(v.x, v.y, output.hitSize), EntityCollisions::solid) || Units.anyEntities(v.x, v.y, output.hitSize * 1.4f));
}
/** @return true if this block is ready to produce units, e.g. requirements met */
public boolean ready(){
return consValid() && !wasOccupied;
}
public void yeetPayload(BuildPayload payload){
var spawn = getUnitSpawn();
blocks.add(payload.block(), 1);
float rot = payload.angleTo(spawn);
Fx.shootPayloadDriver.at(payload.x(), payload.y(), rot);
Fx.payloadDeposit.at(payload.x(), payload.y(), rot, new YeetData(spawn.cpy(), payload.block()));
} }
@Override @Override
@@ -427,19 +434,10 @@ public class UnitAssembler extends PayloadBlock{
return blocks; return blocks;
} }
@Override
public void handlePayload(Building source, Payload payload){
//super.handlePayload(source, payload);
blocks.add(((BuildPayload)payload).block());
//payloads.add((BuildPayload)payload);
}
@Override @Override
public boolean acceptPayload(Building source, Payload payload){ public boolean acceptPayload(Building source, Payload payload){
var plan = plan(); var plan = plan();
return payload instanceof BuildPayload bp && plan.requirements.contains(b -> b.block == bp.block() && blocks.get(bp.block()) < b.amount); return this.payload == null && payload instanceof BuildPayload bp && plan.requirements.contains(b -> b.block == bp.block() && blocks.get(bp.block()) < b.amount);
} }
@Override @Override
@@ -453,11 +451,6 @@ public class UnitAssembler extends PayloadBlock{
} }
blocks.write(write); blocks.write(write);
//TODO save:
//- unit IDs
//- progress
//- payloads in position (should they have positions?)
} }
@Override @Override
@@ -81,7 +81,7 @@ public class UnitAssemblerModule extends PayloadBlock{
@Override @Override
public boolean acceptPayload(Building source, Payload payload){ public boolean acceptPayload(Building source, Payload payload){
return link != null && payload == null && link.acceptPayload(source, payload); return link != null && this.payload == null && link.acceptPayload(source, payload);
} }
@Override @Override
@@ -108,10 +108,9 @@ public class UnitAssemblerModule extends PayloadBlock{
findLink(); findLink();
} }
if(moveInPayload()){ if(moveInPayload() && link != null && link.moduleFits(block, x, y, rotation) && link.acceptPayload(this, payload)){
if(link != null && link.moduleFits(block, x, y, rotation) && link.acceptPayload(this, payload)){ link.yeetPayload(payload);
link.handlePayload(this, payload); payload = null;
}
} }
} }
@@ -53,8 +53,11 @@ public class ConsumePayloadFilter extends Consume{
var inv = build.getBlockPayloads(); var inv = build.getBlockPayloads();
MultiReqImage image = new MultiReqImage(); MultiReqImage image = new MultiReqImage();
content.blocks().each(i -> filter.get(i) && i.unlockedNow(), block -> image.add(new ReqImage(new ItemImage(block.uiIcon, 1),
() -> inv.contains(block, 1)))); content.blocks().each(i -> filter.get(i) && i.unlockedNow(),
block -> image.add(new ReqImage(new ItemImage(block.uiIcon, 1),
() -> inv.contains(block, 1)))
);
table.add(image).size(8 * 4); table.add(image).size(8 * 4);
} }