From cc26a0eeb30af7ff3295eb5d9f88c34030f31cc7 Mon Sep 17 00:00:00 2001 From: Anuken Date: Fri, 24 Jun 2022 21:18:04 -0400 Subject: [PATCH] WIP objective editor progress --- .../sprites/effects/point-laser-center.png | Bin 0 -> 496 bytes .../sprites/effects/point-laser-end.png | Bin 0 -> 539 bytes .../sprites/effects/point-laser.png | Bin 0 -> 131 bytes core/src/mindustry/content/Blocks.java | 4 +- .../mindustry/editor/MapObjectivesDialog.java | 250 +++++++++++++++++- .../entities/bullet/PointLaserBulletType.java | 2 +- core/src/mindustry/game/MapObjectives.java | 7 +- 7 files changed, 256 insertions(+), 7 deletions(-) create mode 100644 core/assets-raw/sprites/effects/point-laser-center.png create mode 100644 core/assets-raw/sprites/effects/point-laser-end.png create mode 100644 core/assets-raw/sprites/effects/point-laser.png diff --git a/core/assets-raw/sprites/effects/point-laser-center.png b/core/assets-raw/sprites/effects/point-laser-center.png new file mode 100644 index 0000000000000000000000000000000000000000..31aa55c04063bab3a4203105f0dc5d1cf4136454 GIT binary patch literal 496 zcmVPx$s!2paRCt{2n?X*)Knz7q#R0ej65NP;z>-Q`6v38zaHE2Hhn|44noZQiPCVaH z(R<5kGSj@+qr`E{000000002sy0}?$@$dcfYh>KR?(;+aU&bgG6qPbYwX8BhSusPZ zM9Bs97BfUGN-9V#r=gT26I3Oqp_0^H(D{6}pSPEgocqVS_sF>8;k1p6Q%LGAC=xkQ zF+(DvdQ0jm$dj{F%n(mhPf6VbRmo{oN$Mh~T27-v(k45Bhf0om?nXL-rlP0f1k9!* zDH}z%nS-a8BWLrpyZHO>*FL;f^j2UlsR+tO&zP7Y5mBlrlI%e}E&I??1_5mHkN8j(`=Opx+Y2m^+=QIR3m~M5afU$2Lw4F$e~nF^w~;1 z#~g?t2g$>#>TbIFF4}CR2wIXR)v48x2#VBZ=A3Z0+>t?6QLHSOnQ79?OjuDo9!}e+ zq-^@AqQ|V@t%kZTt*l3z6>QSVtE-&5!HYu&UOhX|yx>6livtZ*4z%Do(8TFL8?Xb7 mG0000Px$)k#D_RCt{2n?X*)Fc3v26$juB2)GgVfMqKxQAC$;4!BW4y+bcR!^#qh;>^UJ zKas2dmX+(&FEdVTPelkJgb+dqA%qap7TuB;|K2^WE$!~MAA9s~$q_EdDkVp>tS~{f zVunPCYA%9?phc~aok!p;d`R^cM>AHNk{|9q(fBk0Z^LRLIEbVTe-}h73 zF5$|xH<3v>39Fc4drj2O>(g39T<4_FN&5HmrT6GZ6XiK^y9v_ffw@tm5hck*P_&#x zge3S=3?&EMccMCirlKce03y?oR2xO^PqD-tIje{5=;!CJo%veUSAn@yMNn<@mTtLJD^0VDSgayxPEd5JH76(< z3R0jT1qxE2Acf`xS=VP?G$$w;$YNDn7nQ!tM88FgEEGW{X%d}U35X!e-prf<*KT*z z0NYWF+%OZtq?ZVANAY+#ZLE@N(+3qjA_1ow=zVGAezZuyB#peg$i5RiI8@-#v%(?; zRHe~mNh$AwDwe+}G+%<3K$YTM#9|d$r`Wt8bP*@ZfEAjXgD$p^e2fu)qCzNO3?;pE3fd(;ny85}Sb4q9e0Cx8*s{jB1 literal 0 HcmV?d00001 diff --git a/core/src/mindustry/content/Blocks.java b/core/src/mindustry/content/Blocks.java index a4703ef93f..b1ebc86f88 100644 --- a/core/src/mindustry/content/Blocks.java +++ b/core/src/mindustry/content/Blocks.java @@ -4196,14 +4196,14 @@ public class Blocks{ }}; lustre = new ContinuousTurret("lustre"){{ - requirements(Category.turret, with(Items.beryllium, 150, Items.silicon, 200, Items.graphite, 200, Items.carbide, 50)); + requirements(Category.turret, with(Items.silicon, 250, Items.graphite, 200, Items.oxide, 50, Items.carbide, 90)); range = 100f; shootType = new PointLaserBulletType(){{ damage = 150f; buildingDamageMultiplier = 0.3f; - hitColor = Color.valueOf("fd9e81"); + hitColor = Color.valueOf("fda981"); }}; drawer = new DrawTurret("reinforced-"){{ diff --git a/core/src/mindustry/editor/MapObjectivesDialog.java b/core/src/mindustry/editor/MapObjectivesDialog.java index 52554a5fae..6d27ed5a3d 100644 --- a/core/src/mindustry/editor/MapObjectivesDialog.java +++ b/core/src/mindustry/editor/MapObjectivesDialog.java @@ -1,22 +1,36 @@ package mindustry.editor; import arc.*; +import arc.func.*; +import arc.scene.event.*; +import arc.scene.ui.layout.*; import arc.struct.*; +import arc.util.*; +import mindustry.*; +import mindustry.content.*; +import mindustry.ctype.*; +import mindustry.game.*; import mindustry.game.MapObjectives.*; import mindustry.gen.*; +import mindustry.graphics.*; import mindustry.io.*; import mindustry.ui.*; import mindustry.ui.dialogs.*; +import mindustry.world.*; + +import java.lang.reflect.*; import static mindustry.Vars.*; public class MapObjectivesDialog extends BaseDialog{ private Seq objectives = new Seq<>(); + private @Nullable MapObjective selectedObjective; + private Table list = new Table(); public MapObjectivesDialog(){ super("@editor.objectives"); - buttons.defaults().size(180f, 64f).pad(2f); + buttons.defaults().size(170f, 64f).pad(2f); buttons.button("@back", Icon.left, this::hide); buttons.button("@edit", Icon.edit, () -> { @@ -54,17 +68,247 @@ public class MapObjectivesDialog extends BaseDialog{ dialog.addCloseButton(); dialog.show(); }); + + buttons.button("@add", Icon.add, () -> { + var selection = new BaseDialog("@add"); + selection.cont.pane(p -> { + p.background(Tex.button); + p.marginRight(14); + p.defaults().size(195f, 56f); + int i = 0; + for(var gen : MapObjectives.allObjectiveTypes){ + var objective = gen.get(); + + p.button(objective.typeName(), Styles.flatt, () -> { + objectives.add(objective); + setup(); + selection.hide(); + }).with(Table::left).get().getLabelCell().growX().left().padLeft(5).labelAlign(Align.left); + + if(++i % 3 == 0) p.row(); + } + }).scrollX(false); + + selection.addCloseButton(); + selection.show(); + }); + + cont.clear(); + cont.pane(t -> { + list = t; + list.top(); + }).grow(); } public void show(Seq objectives){ super.show(); + selectedObjective = null; this.objectives = objectives; setup(); } void setup(){ - cont.clear(); - cont.add("This editor doesn't work yet. Come back later."); + list.clear(); + + for(var objective : objectives){ + list.table(Tex.button, t -> { + t.margin(0); + + t.button(b -> { + b.left(); + b.add(objective.typeName()).color(Pal.accent); + + b.add().growX(); + + b.button(Icon.upOpen, Styles.emptyi, () -> { + int index = objectives.indexOf(objective); + if(index > 0){ + objectives.swap(index, index - 1); + setup(); + } + }).pad(-6).size(46f); + + b.button(Icon.downOpen, Styles.emptyi, () -> { + int index = objectives.indexOf(objective); + if(index < objectives.size - 1){ + objectives.swap(index, index + 1); + setup(); + } + }).pad(-6).size(46f); + + b.button(Icon.cancel, Styles.emptyi, () -> { + objectives.remove(objective); + list.getCell(t).pad(0f); + + t.remove(); + setup(); + }).pad(-6).size(46f).padRight(-12f); + }, () -> { + if(selectedObjective != objective){ + selectedObjective = objective; + setup(); + } + }).growX().height(46f).pad(-6f).padBottom(0f).row(); + + if(selectedObjective == objective){ + t.table(f -> { + f.left(); + f.margin(10f); + + f.defaults().minHeight(40f).left(); + + var fields = objective.getClass().getFields(); + + for(var field : fields){ + if((field.getModifiers() & Modifier.PUBLIC) == 0) continue; + + f.add(field.getName() + ": "); + + var type = field.getType(); + + if(type == String.class){ + f.field(Reflect.get(objective, field), text -> { + Reflect.set(objective, field, text); + }); + }else if(type == int.class){ + f.field(Reflect.get(objective, field) + "", text -> { + if(Strings.canParseInt(text)){ + Reflect.set(objective, field, Strings.parseInt(text)); + } + }).valid(Strings::canParseInt); + }else if(type == float.class){ + f.field(Reflect.get(objective, field) + "", text -> { + if(Strings.canParsePositiveFloat(text)){ + Reflect.set(objective, field, Strings.parseFloat(text)); + } + }).valid(Strings::canParseFloat); + }else if(type == UnlockableContent.class){ + + f.button(b -> b.image(Reflect.get(objective, field).uiIcon).size(iconSmall), () -> { + showContentSelect(null, result -> { + Reflect.set(objective, field, result); + setup(); + }, b -> b.techNode != null); + }).pad(4); + + }else if(type == Block.class){ + f.button(b -> b.image(Reflect.get(objective, field).uiIcon).size(iconSmall), () -> { + showContentSelect(ContentType.block, result -> { + Reflect.set(objective, field, result); + setup(); + }, b -> ((Block)b).synthetic()); + }).pad(4); + }else if(type == Team.class){ //TODO list of flags + f.button(b -> b.image(Tex.whiteui).color(Reflect.get(objective, field).color).size(iconSmall), () -> { + showTeamSelect(result -> { + Reflect.set(objective, field, result); + setup(); + }); + }).pad(4); + }else if(type == String[].class){ //TODO list of flags + + Table strings = new Table(); + strings.marginLeft(20f); + Runnable[] rebuild = {null}; + + strings.left(); + + float h = 40f; + + rebuild[0] = () -> { + strings.clear(); + strings.left().defaults().padBottom(3f).padTop(3f); + String[] array = Reflect.get(objective, field); + + for(int i = 0; i < array.length; i ++){ + int fi = i; + var str = array[i]; + strings.field(str, result -> { + array[fi] = result; + }).maxTextLength(20).height(h); + + strings.button(Icon.cancel, Styles.squarei, () -> { + + String[] next = new String[array.length - 1]; + System.arraycopy(array, 0, next, 0, fi); + if(fi < array.length - 1){ + System.arraycopy(array, fi + 1, next, fi, array.length - 1 - fi); + } + Reflect.set(objective, field, next); + + rebuild[0].run(); + }).padLeft(4).size(h); + + strings.row(); + } + + strings.button("+ Add", () -> { + String[] next = new String[array.length + 1]; + next[array.length] = ""; + System.arraycopy(array, 0, next, 0, array.length); + Reflect.set(objective, field, next); + + rebuild[0].run(); + }).height(h).width(140f).padLeft(-20f).left().row(); + }; + + rebuild[0].run(); + + f.row(); + f.add(strings).colspan(2).fill(); + + }else{ + f.add("[red]UNFINISHED"); + } + + f.row(); + } + + }).grow(); + } + + }).width(340f).pad(8f).row(); + } + } + + void showContentSelect(@Nullable ContentType type, Cons cons, Boolf check){ + BaseDialog dialog = new BaseDialog(""); + dialog.cont.pane(p -> { + int i = 0; + for(var block : (type == null ? Vars.content.blocks().copy().as() + .add(Vars.content.items()) + .add(Vars.content.liquids()) + .add(Vars.content.units()) : + Vars.content.getBy(type).as())){ + + if(!check.get(block)) continue; + + p.image(block == Blocks.air ? Icon.none.getRegion() : block.uiIcon).size(iconMed).pad(3).with(b -> b.addListener(new HandCursorListener())) + .tooltip(block.localizedName).get().clicked(() -> { + cons.get(block); + dialog.hide(); + }); + if(++i % 10 == 0) p.row(); + } + }); + + dialog.closeOnBack(); + dialog.show(); + } + + void showTeamSelect(Cons cons){ + BaseDialog dialog = new BaseDialog(""); + for(var team : Team.baseTeams){ + + dialog.cont.image(Tex.whiteui).size(iconMed).color(team.color).pad(4).with(i -> i.addListener(new HandCursorListener())) + .tooltip(team.localized()).get().clicked(() -> { + cons.get(team); + dialog.hide(); + }); + } + + dialog.closeOnBack(); + dialog.show(); } } diff --git a/core/src/mindustry/entities/bullet/PointLaserBulletType.java b/core/src/mindustry/entities/bullet/PointLaserBulletType.java index a007f113df..c794f97f14 100644 --- a/core/src/mindustry/entities/bullet/PointLaserBulletType.java +++ b/core/src/mindustry/entities/bullet/PointLaserBulletType.java @@ -12,7 +12,7 @@ import mindustry.graphics.*; /** A continuous bullet type that only damages in a point. */ public class PointLaserBulletType extends BulletType{ - public String sprite = "drill-laser"; + public String sprite = "point-laser"; public TextureRegion laser, laserEnd; public Color color = Color.white; diff --git a/core/src/mindustry/game/MapObjectives.java b/core/src/mindustry/game/MapObjectives.java index b1f3c926b3..07ed022020 100644 --- a/core/src/mindustry/game/MapObjectives.java +++ b/core/src/mindustry/game/MapObjectives.java @@ -365,10 +365,15 @@ public class MapObjectives{ /** Base abstract class for any in-map objective. */ public static abstract class MapObjective{ + public @Nullable String details; public String[] flagsAdded = {}; public String[] flagsRemoved = {}; public ObjectiveMarker[] markers = {}; - public @Nullable String details; + + //TODO localize + public String typeName(){ + return getClass().getSimpleName().replace("Objective", ""); + } public MapObjective withFlags(String... flags){ this.flagsAdded = flags;