mirror of
https://github.com/Anuken/Mindustry.git
synced 2025-07-18 11:47:47 +07:00
Selectable tech tree
This commit is contained in:
@ -172,6 +172,9 @@ available = New research available!
|
||||
unlock.incampaign = < Unlock in campaign for details >
|
||||
completed = [accent]Completed
|
||||
techtree = Tech Tree
|
||||
techtree.select = Tech Tree Selection
|
||||
techtree.serpulo = Serpulo
|
||||
techtree.erekir = Erekir
|
||||
research.legacy = [accent]5.0[] research data found.\nDo you want to [accent]load this data[], or [accent]discard it[] and restart research in the new campaign (recommended)?
|
||||
research.load = Load
|
||||
research.discard = Discard
|
||||
|
@ -1096,7 +1096,8 @@ public class Blocks{
|
||||
craftEffect = new RadialEffect(Fx.heatReactorSmoke, 4, 90f, 7f);
|
||||
|
||||
itemCapacity = 20;
|
||||
consumes.item(Items.thorium, 2);
|
||||
consumes.item(Items.thorium, 3);
|
||||
consumes.liquid(Liquids.nitrogen, 1f / 60f);
|
||||
outputItem = new ItemStack(Items.fissileMatter, 1);
|
||||
}};
|
||||
|
||||
@ -2854,7 +2855,7 @@ public class Blocks{
|
||||
restitution = 0.03f;
|
||||
range = 180;
|
||||
shootCone = 3f;
|
||||
health = 300 * size * size;
|
||||
health = 350 * size * size;
|
||||
rotateSpeed = 1.6f;
|
||||
|
||||
limitRange();
|
||||
@ -2862,9 +2863,9 @@ public class Blocks{
|
||||
|
||||
//TODO implementation; splash damage? shotgun? AA? I have no ideas
|
||||
fracture = new ItemTurret("fracture"){{
|
||||
requirements(Category.turret, with(Items.tungsten, 35, Items.silicon, 35));
|
||||
requirements(Category.turret, with(Items.tungsten, 30, Items.graphite, 30, Items.silicon, 35));
|
||||
ammo(
|
||||
Items.tungsten, new ContinuousFlameBulletType(45f){{
|
||||
Items.tungsten, new ContinuousFlameBulletType(50f){{
|
||||
length = 105f;
|
||||
shootEffect = Fx.randLifeSpark;
|
||||
width = 4.5f;
|
||||
@ -2903,7 +2904,7 @@ public class Blocks{
|
||||
range = 90;
|
||||
shootCone = 15f;
|
||||
inaccuracy = 0f;
|
||||
health = 300 * size * size;
|
||||
health = 420 * size * size;
|
||||
rotateSpeed = 3f;
|
||||
}};
|
||||
|
||||
@ -2954,7 +2955,7 @@ public class Blocks{
|
||||
range = 190;
|
||||
shootCone = 15f;
|
||||
inaccuracy = 20f;
|
||||
health = 300 * size * size;
|
||||
health = 400 * size * size;
|
||||
rotateSpeed = 3f;
|
||||
|
||||
//???
|
||||
|
@ -6,7 +6,7 @@ import static mindustry.content.TechTree.*;
|
||||
public class ErekirTechTree{
|
||||
|
||||
public static void load(){
|
||||
rootErekir = node(coreBastion, () -> {
|
||||
Planets.erekir.techTree = nodeRoot("erekir", coreBastion, () -> {
|
||||
node(duct, () -> {
|
||||
node(ductRouter, () -> {
|
||||
node(ductBridge, () -> {
|
||||
@ -142,13 +142,15 @@ public class ErekirTechTree{
|
||||
});
|
||||
|
||||
node(breach, () -> {
|
||||
//fracture turret is broken and thus not listed
|
||||
|
||||
node(fracture, () -> {
|
||||
|
||||
//TODO big tech jump here; incomplete turret
|
||||
node(sublimate, () -> {
|
||||
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
//TODO requirements for these
|
||||
node(coreCitadel, () -> {
|
||||
|
@ -12,7 +12,7 @@ import static mindustry.content.UnitTypes.*;
|
||||
public class SerpuloTechTree{
|
||||
|
||||
public static void load(){
|
||||
root = node(coreShard, () -> {
|
||||
Planets.serpulo.techTree = nodeRoot("serpulo", coreShard, () -> {
|
||||
|
||||
node(conveyor, () -> {
|
||||
|
||||
|
@ -12,8 +12,14 @@ public class TechTree{
|
||||
private static TechNode context = null;
|
||||
|
||||
public static Seq<TechNode> all = new Seq<>();
|
||||
//TODO deprecate and refactor the root system
|
||||
public static TechNode root, rootErekir;
|
||||
public static Seq<TechNode> roots = new Seq<>();
|
||||
|
||||
public static TechNode nodeRoot(String name, UnlockableContent content, Runnable children){
|
||||
var root = node(content, content.researchRequirements(), children);
|
||||
root.name = name;
|
||||
roots.add(root);
|
||||
return root;
|
||||
}
|
||||
|
||||
public static TechNode node(UnlockableContent content, Runnable children){
|
||||
return node(content, content.researchRequirements(), children);
|
||||
@ -69,6 +75,8 @@ public class TechTree{
|
||||
public static class TechNode{
|
||||
/** Depth in tech tree. */
|
||||
public int depth;
|
||||
/** Name for root node - used in tech tree selector. */
|
||||
public @Nullable String name;
|
||||
/** Requirement node. */
|
||||
public @Nullable TechNode parent;
|
||||
/** Content to be researched. */
|
||||
@ -103,6 +111,10 @@ public class TechTree{
|
||||
all.add(this);
|
||||
}
|
||||
|
||||
public String localizedName(){
|
||||
return Core.bundle.get("techtree." + name);
|
||||
}
|
||||
|
||||
public void setupRequirements(ItemStack[] requirements){
|
||||
this.requirements = requirements;
|
||||
this.finishedRequirements = new ItemStack[requirements.length];
|
||||
|
@ -9,6 +9,7 @@ import arc.math.geom.*;
|
||||
import arc.struct.*;
|
||||
import arc.util.*;
|
||||
import arc.util.noise.*;
|
||||
import mindustry.content.TechTree.*;
|
||||
import mindustry.ctype.*;
|
||||
import mindustry.graphics.*;
|
||||
import mindustry.graphics.g3d.*;
|
||||
@ -86,6 +87,8 @@ public class Planet extends UnlockableContent{
|
||||
public Planet solarSystem;
|
||||
/** All planets orbiting this one, in ascending order of radius. */
|
||||
public Seq<Planet> children = new Seq<>();
|
||||
/** Default root node shown when the tech tree is opened here. */
|
||||
public @Nullable TechNode techTree;
|
||||
/** Loads the mesh. Clientside only. Defaults to a boring sphere mesh. */
|
||||
protected Prov<GenericMesh> meshLoader = () -> new ShaderSphereMesh(this, Shaders.unlit, 2), cloudMeshLoader = () -> null;
|
||||
|
||||
|
@ -34,8 +34,8 @@ import static mindustry.Vars.*;
|
||||
public class ResearchDialog extends BaseDialog{
|
||||
public final float nodeSize = Scl.scl(60f);
|
||||
public ObjectSet<TechTreeNode> nodes = new ObjectSet<>();
|
||||
//TODO switch root system
|
||||
public TechTreeNode root = new TechTreeNode(TechTree.rootErekir, null);
|
||||
public TechTreeNode root = new TechTreeNode(TechTree.roots.first(), null);
|
||||
public TechNode lastNode = root.node;
|
||||
public Rect bounds = new Rect();
|
||||
public ItemsDisplay itemDisplay;
|
||||
public View view;
|
||||
@ -45,13 +45,47 @@ public class ResearchDialog extends BaseDialog{
|
||||
public ResearchDialog(){
|
||||
super("");
|
||||
|
||||
titleTable.remove();
|
||||
titleTable.clear();
|
||||
titleTable.button(b -> {
|
||||
//TODO custom icon here.
|
||||
b.image(Icon.tree).padRight(8).size(iconMed);
|
||||
b.add().growX();
|
||||
b.label(() -> root.node.localizedName()).color(Pal.accent);
|
||||
b.add().growX();
|
||||
b.add().size(iconMed);
|
||||
}, () -> {
|
||||
new BaseDialog("@techtree.select"){{
|
||||
cont.pane(t -> {
|
||||
t.table(Tex.button, in -> {
|
||||
in.defaults().width(300f).height(60f);
|
||||
for(TechNode node : TechTree.roots){
|
||||
in.button(node.localizedName(), Styles.cleart, () -> {
|
||||
rebuildTree(node);
|
||||
hide();
|
||||
}).row();
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
addCloseButton();
|
||||
}}.show();
|
||||
}).minWidth(300f);
|
||||
|
||||
margin(0f).marginBottom(8);
|
||||
cont.stack(view = new View(), itemDisplay = new ItemsDisplay()).grow();
|
||||
|
||||
titleTable.toFront();
|
||||
|
||||
shouldPause = true;
|
||||
|
||||
shown(() -> {
|
||||
Planet currPlanet = ui.planet.isShown() ?
|
||||
ui.planet.state.planet :
|
||||
state.isCampaign() ? state.rules.sector.planet : null;
|
||||
|
||||
if(currPlanet != null && currPlanet.techTree != null){
|
||||
switchTree(currPlanet.techTree);
|
||||
}
|
||||
|
||||
items = new ItemSeq(){
|
||||
//store sector item amounts for modifications
|
||||
@ -176,6 +210,28 @@ public class ResearchDialog extends BaseDialog{
|
||||
});
|
||||
}
|
||||
|
||||
public void switchTree(TechNode node){
|
||||
if(lastNode == node || node == null) return;
|
||||
nodes.clear();
|
||||
root = new TechTreeNode(node, null);
|
||||
lastNode = node;
|
||||
view.rebuildAll();
|
||||
}
|
||||
|
||||
public void rebuildTree(TechNode node){
|
||||
switchTree(node);
|
||||
view.panX = 0f;
|
||||
view.panY = -200f;
|
||||
view.setScale(1f);
|
||||
|
||||
view.hoverNode = null;
|
||||
view.infoTable.remove();
|
||||
view.infoTable.clear();
|
||||
|
||||
checkNodes(root);
|
||||
treeLayout();
|
||||
}
|
||||
|
||||
void treeLayout(){
|
||||
float spacing = 20f;
|
||||
LayoutNode node = new LayoutNode(root, null);
|
||||
@ -293,6 +349,13 @@ public class ResearchDialog extends BaseDialog{
|
||||
public Table infoTable = new Table();
|
||||
|
||||
{
|
||||
rebuildAll();
|
||||
}
|
||||
|
||||
public void rebuildAll(){
|
||||
clear();
|
||||
hoverNode = null;
|
||||
infoTable.clear();
|
||||
infoTable.touchable = Touchable.enabled;
|
||||
|
||||
for(TechTreeNode node : nodes){
|
||||
|
@ -24,4 +24,4 @@ android.useAndroidX=true
|
||||
#used for slow jitpack builds; TODO see if this actually works
|
||||
org.gradle.internal.http.socketTimeout=100000
|
||||
org.gradle.internal.http.connectionTimeout=100000
|
||||
archash=3dc6a7fac5
|
||||
archash=f65ae0d8f7
|
||||
|
Reference in New Issue
Block a user