diff --git a/core/src/mindustry/content/SerpuloTechTree.java b/core/src/mindustry/content/SerpuloTechTree.java index 85c379ca45..593b6893fe 100644 --- a/core/src/mindustry/content/SerpuloTechTree.java +++ b/core/src/mindustry/content/SerpuloTechTree.java @@ -361,7 +361,7 @@ public class SerpuloTechTree{ }); }); - node(nova, () -> { + node(nova, Seq.with(new SectorComplete(fungalPass)), () -> { node(pulsar, () -> { node(quasar, () -> { node(vela, () -> { diff --git a/core/src/mindustry/core/PerfCounter.java b/core/src/mindustry/core/PerfCounter.java index 02de189ab6..1bb2c116ca 100644 --- a/core/src/mindustry/core/PerfCounter.java +++ b/core/src/mindustry/core/PerfCounter.java @@ -8,6 +8,7 @@ public enum PerfCounter{ frame, update, entityUpdate, + ui, render; public static final PerfCounter[] all = values(); diff --git a/core/src/mindustry/core/UI.java b/core/src/mindustry/core/UI.java index c2e777ac5e..8a3d830d8f 100644 --- a/core/src/mindustry/core/UI.java +++ b/core/src/mindustry/core/UI.java @@ -154,6 +154,8 @@ public class UI implements ApplicationListener, Loadable{ public void update(){ if(disableUI || Core.scene == null) return; + PerfCounter.ui.begin(); + Events.fire(Trigger.uiDrawBegin); Core.scene.act(); @@ -167,6 +169,8 @@ public class UI implements ApplicationListener, Loadable{ } Events.fire(Trigger.uiDrawEnd); + + PerfCounter.ui.end(); } @Override diff --git a/core/src/mindustry/entities/Units.java b/core/src/mindustry/entities/Units.java index 5bc18116fd..9b8f505132 100644 --- a/core/src/mindustry/entities/Units.java +++ b/core/src/mindustry/entities/Units.java @@ -34,6 +34,18 @@ public class Units{ return false; }; + public static void notifyUnitSpawn(Unit unit){ + if(net.server()){ + Call.unitSpawn(new UnitContainer(unit)); + } + } + + //syncs a unit spawn so that it appears immediately without waiting for a snapshot + @Remote(unreliable = true, priority = PacketPriority.low) + public static void unitSpawn(UnitContainer container){ + //doesn't actually do anything, reading calls add() + } + @Remote(called = Loc.server) public static void unitCapDeath(Unit unit){ if(unit != null){ @@ -488,4 +500,15 @@ public class Units{ public interface BuildingPriorityf{ float priority(Building build); } + + public static class UnitContainer{ + public Unit unit; + + public UnitContainer(){ + } + + public UnitContainer(Unit unit){ + this.unit = unit; + } + } } diff --git a/core/src/mindustry/entities/bullet/BulletType.java b/core/src/mindustry/entities/bullet/BulletType.java index 903c0b0844..24f5059f24 100644 --- a/core/src/mindustry/entities/bullet/BulletType.java +++ b/core/src/mindustry/entities/bullet/BulletType.java @@ -590,6 +590,7 @@ public class BulletType extends Content implements Cloneable{ Tmp.v1.rnd(Mathf.random(despawnUnitRadius)); var u = despawnUnit.spawn(b.team, x + Tmp.v1.x, y + Tmp.v1.y); u.rotation = faceOutwards ? Tmp.v1.angle() : b.rotation(); + Units.notifyUnitSpawn(u); } } } @@ -899,6 +900,7 @@ public class BulletType extends Content implements Cloneable{ } spawned.add(); + Units.notifyUnitSpawn(spawned); } //Since bullet init is never called, handle killing shooter here if(killShooter && owner instanceof Healthc h && !h.dead()) h.kill(); diff --git a/core/src/mindustry/io/TypeIO.java b/core/src/mindustry/io/TypeIO.java index 70f28cae9d..0438d561b1 100644 --- a/core/src/mindustry/io/TypeIO.java +++ b/core/src/mindustry/io/TypeIO.java @@ -12,6 +12,7 @@ import mindustry.annotations.Annotations.*; import mindustry.content.TechTree.*; import mindustry.ctype.*; import mindustry.entities.*; +import mindustry.entities.Units.*; import mindustry.entities.abilities.*; import mindustry.entities.bullet.*; import mindustry.entities.units.*; @@ -278,6 +279,46 @@ public class TypeIO{ return noAbilities; } + public static void writeUnitContainer(Writes write, Units.UnitContainer cont){ + write.i(cont.unit.id); + write.b(cont.unit.classId() & 0xFF); + cont.unit.beforeWrite(); + cont.unit.writeSync(write); + } + + public static UnitContainer readUnitContainer(Reads read){ + int id = read.i(); + int typeID = read.ub(); + + Unit entity = Groups.unit.getByID(id); + boolean add = false, created = false; + + if(entity == null){ + entity = (Unit)EntityMapping.map(typeID & 0xFF).get(); + entity.id(id); + + if(!netClient.isEntityUsed(entity.id())){ + add = true; + } + created = true; + } + + //read the entity + entity.readSync(read); + + if(created){ + //snap initial starting position + entity.snapSync(); + } + + if(add){ + entity.add(); + netClient.addRemovedEntity(entity.id()); + } + + return null; //no need to actually return anything + } + public static void writeUnit(Writes write, Unit unit){ write.b(unit == null ? 0 : unit instanceof BlockUnitc ? 1 : 2); diff --git a/core/src/mindustry/world/blocks/payloads/UnitPayload.java b/core/src/mindustry/world/blocks/payloads/UnitPayload.java index cffdcaafc6..9983ae9f5c 100644 --- a/core/src/mindustry/world/blocks/payloads/UnitPayload.java +++ b/core/src/mindustry/world/blocks/payloads/UnitPayload.java @@ -130,6 +130,7 @@ public class UnitPayload implements Payload{ unit.add(); unit.unloaded(); Events.fire(new UnitUnloadEvent(unit)); + Units.notifyUnitSpawn(unit); return true; }