Idle sector resource production
This commit is contained in:
@@ -86,8 +86,26 @@ public class Logic implements ApplicationListener{
|
|||||||
|
|
||||||
//when loading a 'damaged' sector, propagate the damage
|
//when loading a 'damaged' sector, propagate the damage
|
||||||
Events.on(WorldLoadEvent.class, e -> {
|
Events.on(WorldLoadEvent.class, e -> {
|
||||||
if(state.isCampaign() && state.rules.sector.hasWaves() && state.rules.sector.getTurnsPassed() > 0){
|
if(state.isCampaign() && state.rules.sector.getTurnsPassed() > 0){
|
||||||
SectorDamage.apply(state.rules.sector.getTurnsPassed());
|
int passed = state.rules.sector.getTurnsPassed();
|
||||||
|
Building core = state.rules.defaultTeam.core();
|
||||||
|
|
||||||
|
if(state.rules.sector.hasWaves()){
|
||||||
|
SectorDamage.apply(passed);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
//add resources based on turns passed
|
||||||
|
if(state.rules.sector.save != null && core != null){
|
||||||
|
|
||||||
|
state.rules.sector.save.meta.secinfo.production.each((item, stat) -> {
|
||||||
|
core.items.add(item, (int)(stat.mean * passed));
|
||||||
|
|
||||||
|
//ensure positive items
|
||||||
|
if(core.items.get(item) < 0) core.items.set(item, 0);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
state.rules.sector.setTurnsPassed(0);
|
state.rules.sector.setTurnsPassed(0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -12,10 +12,12 @@ import mindustry.world.modules.*;
|
|||||||
import static mindustry.Vars.*;
|
import static mindustry.Vars.*;
|
||||||
|
|
||||||
public class SectorInfo{
|
public class SectorInfo{
|
||||||
/** export window size in seconds */
|
/** average window size in samples */
|
||||||
private static final int exportWindow = 60;
|
private static final int valueWindow = 60;
|
||||||
/** refresh period of export in ticks */
|
/** refresh period of export in ticks */
|
||||||
private static final float refreshPeriod = 60;
|
private static final float refreshPeriod = 60;
|
||||||
|
/** Core input statistics. */
|
||||||
|
public ObjectMap<Item, ExportStat> production = new ObjectMap<>();
|
||||||
/** Export statistics. */
|
/** Export statistics. */
|
||||||
public ObjectMap<Item, ExportStat> export = new ObjectMap<>();
|
public ObjectMap<Item, ExportStat> export = new ObjectMap<>();
|
||||||
/** Items stored in all cores. */
|
/** Items stored in all cores. */
|
||||||
@@ -70,7 +72,8 @@ public class SectorInfo{
|
|||||||
storageCapacity = entity != null ? entity.storageCapacity : 0;
|
storageCapacity = entity != null ? entity.storageCapacity : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Update averages of various stats. */
|
/** Update averages of various stats.
|
||||||
|
* Called every frame. */
|
||||||
public void update(){
|
public void update(){
|
||||||
//create last stored core items
|
//create last stored core items
|
||||||
if(lastCoreItems == null){
|
if(lastCoreItems == null){
|
||||||
@@ -78,10 +81,12 @@ public class SectorInfo{
|
|||||||
updateCoreDeltas();
|
updateCoreDeltas();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
CoreEntity ent = state.rules.defaultTeam.core();
|
||||||
|
|
||||||
//refresh throughput
|
//refresh throughput
|
||||||
if(time.get(refreshPeriod)){
|
if(time.get(refreshPeriod)){
|
||||||
CoreEntity ent = state.rules.defaultTeam.core();
|
|
||||||
|
|
||||||
|
//refresh export
|
||||||
export.each((item, stat) -> {
|
export.each((item, stat) -> {
|
||||||
//initialize stat after loading
|
//initialize stat after loading
|
||||||
if(!stat.loaded){
|
if(!stat.loaded){
|
||||||
@@ -98,10 +103,35 @@ public class SectorInfo{
|
|||||||
stat.mean = stat.means.rawMean();
|
stat.mean = stat.means.rawMean();
|
||||||
});
|
});
|
||||||
|
|
||||||
|
//refresh core items
|
||||||
|
for(Item item : content.items()){
|
||||||
|
ExportStat stat = production.get(item, ExportStat::new);
|
||||||
|
if(!stat.loaded){
|
||||||
|
stat.means.fill(stat.mean);
|
||||||
|
stat.loaded = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
//get item delta
|
||||||
|
//TODO is preventing negative production a good idea?
|
||||||
|
int delta = Math.max((ent == null ? 0 : ent.items.get(item)) - lastCoreItems[item.id], 0);
|
||||||
|
|
||||||
|
//store means
|
||||||
|
stat.means.add(delta);
|
||||||
|
stat.mean = stat.means.rawMean();
|
||||||
|
}
|
||||||
|
|
||||||
updateCoreDeltas();
|
updateCoreDeltas();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @return the items in this sector now, taking into account production. */
|
||||||
|
public ObjectIntMap<Item> getCurrentItems(float turnsPassed){
|
||||||
|
ObjectIntMap<Item> map = new ObjectIntMap<>();
|
||||||
|
map.putAll(coreItems);
|
||||||
|
production.each((item, stat) -> map.increment(item, (int)(stat.mean * turnsPassed)));
|
||||||
|
return map;
|
||||||
|
}
|
||||||
|
|
||||||
private void updateCoreDeltas(){
|
private void updateCoreDeltas(){
|
||||||
CoreEntity ent = state.rules.defaultTeam.core();
|
CoreEntity ent = state.rules.defaultTeam.core();
|
||||||
for(int i = 0; i < lastCoreItems.length; i++){
|
for(int i = 0; i < lastCoreItems.length; i++){
|
||||||
@@ -117,7 +147,7 @@ public class SectorInfo{
|
|||||||
|
|
||||||
public static class ExportStat{
|
public static class ExportStat{
|
||||||
public transient float counter;
|
public transient float counter;
|
||||||
public transient WindowedMean means = new WindowedMean(exportWindow);
|
public transient WindowedMean means = new WindowedMean(valueWindow);
|
||||||
public transient boolean loaded;
|
public transient boolean loaded;
|
||||||
public float mean;
|
public float mean;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -152,8 +152,8 @@ public class Universe{
|
|||||||
//TODO a turn passing may break the core; detect this, send an event and mark the sector as having no base!
|
//TODO a turn passing may break the core; detect this, send an event and mark the sector as having no base!
|
||||||
for(Planet planet : content.planets()){
|
for(Planet planet : content.planets()){
|
||||||
for(Sector sector : planet.sectors){
|
for(Sector sector : planet.sectors){
|
||||||
//attacks happen even for sectors without bases - stuff still gets destroyed
|
//update turns passed for all sectors
|
||||||
if(!sector.isBeingPlayed() && sector.hasSave() && sector.hasWaves()){
|
if(!sector.isBeingPlayed() && sector.hasSave()){
|
||||||
sector.setTurnsPassed(sector.getTurnsPassed() + 1);
|
sector.setTurnsPassed(sector.getTurnsPassed() + 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -162,10 +162,6 @@ public class Universe{
|
|||||||
//calculate passive item generation
|
//calculate passive item generation
|
||||||
//TODO make exports only update for sector with items
|
//TODO make exports only update for sector with items
|
||||||
//TODO items should be added directly to cores!
|
//TODO items should be added directly to cores!
|
||||||
int[] exports = getTotalExports();
|
|
||||||
for(int i = 0; i < exports.length; i++){
|
|
||||||
//data.addItem(content.item(i), exports[i]);
|
|
||||||
}
|
|
||||||
|
|
||||||
Events.fire(new TurnEvent());
|
Events.fire(new TurnEvent());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import arc.math.geom.*;
|
|||||||
import arc.scene.event.*;
|
import arc.scene.event.*;
|
||||||
import arc.scene.ui.*;
|
import arc.scene.ui.*;
|
||||||
import arc.scene.ui.layout.*;
|
import arc.scene.ui.layout.*;
|
||||||
|
import arc.struct.*;
|
||||||
import arc.util.*;
|
import arc.util.*;
|
||||||
import arc.util.ArcAnnotate.*;
|
import arc.util.ArcAnnotate.*;
|
||||||
import mindustry.content.*;
|
import mindustry.content.*;
|
||||||
@@ -307,9 +308,11 @@ public class PlanetDialog extends BaseDialog implements PlanetInterfaceRenderer{
|
|||||||
t.left();
|
t.left();
|
||||||
|
|
||||||
t.table(res -> {
|
t.table(res -> {
|
||||||
|
ObjectIntMap<Item> map = sector.save.meta.secinfo.getCurrentItems(sector.getTurnsPassed());
|
||||||
|
|
||||||
int i = 0;
|
int i = 0;
|
||||||
for(Item item : content.items()){
|
for(Item item : content.items()){
|
||||||
int amount = sector.save.meta.secinfo.coreItems.get(item);
|
int amount = map.get(item);
|
||||||
if(amount > 0){
|
if(amount > 0){
|
||||||
res.image(item.icon(Cicon.small)).padRight(3);
|
res.image(item.icon(Cicon.small)).padRight(3);
|
||||||
res.add(ui.formatAmount(amount)).color(Color.lightGray);
|
res.add(ui.formatAmount(amount)).color(Color.lightGray);
|
||||||
|
|||||||
@@ -1,41 +0,0 @@
|
|||||||
package mindustry.ui.dialogs;
|
|
||||||
|
|
||||||
import mindustry.gen.*;
|
|
||||||
import mindustry.type.*;
|
|
||||||
import mindustry.ui.*;
|
|
||||||
|
|
||||||
import static mindustry.Vars.*;
|
|
||||||
|
|
||||||
public class ResourcesDialog extends BaseDialog{
|
|
||||||
|
|
||||||
public ResourcesDialog(){
|
|
||||||
super("//TODO resources");
|
|
||||||
shown(this::setup);
|
|
||||||
addCloseButton();
|
|
||||||
}
|
|
||||||
|
|
||||||
void setup(){
|
|
||||||
cont.clear();
|
|
||||||
|
|
||||||
cont.table(Tex.button, t -> {
|
|
||||||
t.left();
|
|
||||||
t.margin(10f);
|
|
||||||
int[] exports = universe.getTotalExports();
|
|
||||||
for(Item item : content.items()){
|
|
||||||
//TODO display total items
|
|
||||||
if(exports[item.id] > 0){
|
|
||||||
t.image(item.icon(Cicon.small)).padRight(4);
|
|
||||||
//t.add(ui.formatAmount(data.getItem(item))).color(Color.lightGray);
|
|
||||||
//if(exports[item.id] > 0){
|
|
||||||
t.add("+ [accent]" + ui.formatAmount(exports[item.id]) + " [lightgray]/T");
|
|
||||||
//}else{
|
|
||||||
// t.add();
|
|
||||||
//}
|
|
||||||
t.row();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
Reference in New Issue
Block a user