From d48d7aa9fed0d71fbdea3f526ec4f6ce919d7955 Mon Sep 17 00:00:00 2001 From: Yair Morgenstern Date: Fri, 24 Aug 2018 12:28:27 +0300 Subject: [PATCH] You now choose civilizations from a list which also tells you what's unique to that civ --- core/src/com/unciv/GameStarter.kt | 27 +++-- core/src/com/unciv/UnCivGame.kt | 3 +- core/src/com/unciv/ui/NewGameScreen.kt | 142 ++++++++++++++++++++----- 3 files changed, 132 insertions(+), 40 deletions(-) diff --git a/core/src/com/unciv/GameStarter.kt b/core/src/com/unciv/GameStarter.kt index 94b40c35..a0c07a1b 100644 --- a/core/src/com/unciv/GameStarter.kt +++ b/core/src/com/unciv/GameStarter.kt @@ -5,28 +5,29 @@ import com.unciv.logic.GameInfo import com.unciv.logic.civilization.CivilizationInfo import com.unciv.logic.map.TileMap import com.unciv.models.gamebasics.GameBasics +import com.unciv.ui.NewGameScreen import com.unciv.ui.utils.getRandom class GameStarter(){ - fun startNewGame(mapRadius: Int, numberOfCivs: Int, civilization: String, difficulty:String): GameInfo { + fun startNewGame(newGameParameters: NewGameScreen.NewGameParameters): GameInfo { val gameInfo = GameInfo() - gameInfo.tileMap = TileMap(mapRadius) + gameInfo.tileMap = TileMap(newGameParameters.mapRadius) gameInfo.tileMap.gameInfo = gameInfo // need to set this transient before placing units in the map fun vectorIsWithinNTilesOfEdge(vector: Vector2,n:Int): Boolean { - return vector.x < mapRadius-n - && vector.x > n-mapRadius - && vector.y < mapRadius-n - && vector.y > n-mapRadius + return vector.x < newGameParameters.mapRadius-n + && vector.x > n-newGameParameters.mapRadius + && vector.y < newGameParameters.mapRadius-n + && vector.y > n-newGameParameters.mapRadius } val distanceAroundStartingPointNoOneElseWillStartIn = 5 val freeTiles = gameInfo.tileMap.values.toMutableList().filter { vectorIsWithinNTilesOfEdge(it.position,3)}.toMutableList() val playerPosition = freeTiles.getRandom().position - val playerCiv = CivilizationInfo(civilization, gameInfo) - playerCiv.difficulty=difficulty + val playerCiv = CivilizationInfo(newGameParameters.nation, gameInfo) + playerCiv.difficulty=newGameParameters.difficulty gameInfo.civilizations.add(playerCiv) // first one is player civ freeTiles.removeAll(gameInfo.tileMap.getTilesInDistance(playerPosition, distanceAroundStartingPointNoOneElseWillStartIn )) @@ -34,8 +35,9 @@ class GameStarter(){ val barbarianCivilization = CivilizationInfo() gameInfo.civilizations.add(barbarianCivilization)// second is barbarian civ - for (civname in GameBasics.Nations.keys.filterNot { it=="Barbarians" || it==civilization }.take(numberOfCivs)) { - val civ = CivilizationInfo(civname, gameInfo) + for (nationName in GameBasics.Nations.keys.filterNot { it=="Barbarians" || it==newGameParameters.nation }.shuffled() + .take(newGameParameters.numberOfEnemies)) { + val civ = CivilizationInfo(nationName, gameInfo) civ.tech.techsResearched.addAll(playerCiv.getDifficulty().aiFreeTechs) gameInfo.civilizations.add(civ) } @@ -48,7 +50,10 @@ class GameStarter(){ // and only now do we add units for everyone, because otherwise both the gameInfo.setTransients() and the placeUnit will both add the unit to the civ's unit list! for (civ in gameInfo.civilizations.toList().filter { !it.isBarbarianCivilization() }) { - if(freeTiles.isEmpty()) gameInfo.civilizations.remove(civ) // we can't add any more civs. + if(freeTiles.isEmpty()){ + gameInfo.civilizations.remove(civ) + continue + } // we can't add any more civs. val startingLocation = freeTiles.toList().getRandom().position civ.placeUnitNearTile(startingLocation, "Settler") diff --git a/core/src/com/unciv/UnCivGame.kt b/core/src/com/unciv/UnCivGame.kt index 017802f4..b79f61ad 100644 --- a/core/src/com/unciv/UnCivGame.kt +++ b/core/src/com/unciv/UnCivGame.kt @@ -5,6 +5,7 @@ import com.badlogic.gdx.Gdx import com.unciv.logic.GameInfo import com.unciv.logic.GameSaver import com.unciv.models.gamebasics.GameBasics +import com.unciv.ui.NewGameScreen import com.unciv.ui.utils.ImageGetter import com.unciv.ui.worldscreen.WorldScreen @@ -49,7 +50,7 @@ class UnCivGame : Game() { } fun startNewGame() { - val newGame = GameStarter().startNewGame(20, 3, "Babylon","Chieftain") + val newGame = GameStarter().startNewGame(NewGameScreen.NewGameParameters().apply { difficulty="Chieftain" }) gameInfo = newGame worldScreen = WorldScreen() diff --git a/core/src/com/unciv/ui/NewGameScreen.kt b/core/src/com/unciv/ui/NewGameScreen.kt index fe163c8d..19e91fe9 100644 --- a/core/src/com/unciv/ui/NewGameScreen.kt +++ b/core/src/com/unciv/ui/NewGameScreen.kt @@ -1,51 +1,139 @@ package com.unciv.ui import com.badlogic.gdx.Gdx -import com.badlogic.gdx.scenes.scene2d.ui.SelectBox -import com.badlogic.gdx.scenes.scene2d.ui.Skin -import com.badlogic.gdx.scenes.scene2d.ui.Table +import com.badlogic.gdx.graphics.Color +import com.badlogic.gdx.scenes.scene2d.Actor +import com.badlogic.gdx.scenes.scene2d.Touchable +import com.badlogic.gdx.scenes.scene2d.ui.* +import com.badlogic.gdx.scenes.scene2d.utils.ChangeListener import com.badlogic.gdx.utils.Array import com.unciv.GameStarter import com.unciv.logic.GameInfo import com.unciv.models.gamebasics.GameBasics +import com.unciv.models.gamebasics.Nation import com.unciv.ui.pickerscreens.PickerScreen -import com.unciv.ui.utils.addClickListener -import com.unciv.ui.utils.disable -import com.unciv.ui.utils.enable -import com.unciv.ui.utils.tr +import com.unciv.ui.utils.* import com.unciv.ui.worldscreen.WorldScreen +import kotlin.concurrent.thread class NewGameScreen: PickerScreen(){ + + class NewGameParameters{ + var difficulty="Prince" + var nation="Babylon" + var mapRadius=20 + var numberOfEnemies=3 + } + + val newGameParameters=NewGameParameters() + + class NationTable(val nation:Nation,val newGameParameters: NewGameParameters, skin:Skin, onClick:()->Unit):Table(skin){ + init { + pad(10f) + background=ImageGetter.getBackground(nation.getColor().apply { a=0.5f }) + add(Label(nation.name, skin).apply { setFontColor(Color.WHITE)}).row() + add(Label(getUniqueLabel(nation), skin).apply { setFontColor(Color.WHITE)}) + addClickListener { newGameParameters.nation=nation.name; onClick() } + touchable=Touchable.enabled + update() + } + + private fun getUniqueLabel(nation: Nation): CharSequence? { + for (building in GameBasics.Buildings.values) + if (building.uniqueTo == nation.name) { + var text = building.name + " - {replaces} " + building.replaces + "\n" + val originalBuilding = GameBasics.Buildings[building.replaces]!! + val originalBuildingStatMap = originalBuilding.toHashMap() + for (stat in building.toHashMap()) + if (stat.value != originalBuildingStatMap[stat.key]) + text += stat.value.toInt().toString() + " " + stat.key + " vs " + originalBuildingStatMap[stat.key]!!.toInt() + "\n" + if (building.maintenance != originalBuilding.maintenance) + text += "{Maintainance} " + building.maintenance + " vs " + originalBuilding.maintenance + "\n" + return text.tr() + } + + for (unit in GameBasics.Units.values) + if (unit.uniqueTo == nation.name) { + var text = unit.name + " - {replaces} " + unit.replaces + "\n" + val originalUnit = GameBasics.Units[unit.replaces]!! + if (unit.strength != originalUnit.strength) + text += "{Combat strength} " + unit.strength + " vs " + originalUnit.strength + "\n" + if (unit.rangedStrength!= originalUnit.rangedStrength) + text += "{Ranged strength} " + unit.rangedStrength+ " vs " + originalUnit.rangedStrength + "\n" + if (unit.range!= originalUnit.range) + text += "{Range} " + unit.range+ " vs " + originalUnit.range + "\n" + if (unit.movement!= originalUnit.movement) + text += "{Movement} " + unit.movement+ " vs " + originalUnit.movement + "\n" + return text.tr() + } + + return "" + } + + + fun update(){ + val color = nation.getColor() + if(newGameParameters.nation!=nation.name) color.a=0.5f + background=ImageGetter.getBackground(color) + } + } + + val nationTables = ArrayList() + init { + val mainTable = Table() + mainTable.add(getOptionsTable()) + val civPickerTable = Table().apply { defaults().pad(5f) } + for(nation in GameBasics.Nations.values.filterNot { it.name == "Barbarians" }){ + val nationTable = NationTable(nation,newGameParameters,skin){updateNationTables()} + nationTables.add(nationTable) + civPickerTable.add(nationTable).width(stage.width/3).row() + } + mainTable.setFillParent(true) + mainTable.add(ScrollPane(civPickerTable)) + topTable.addActor(mainTable) + } + + fun updateNationTables(){ + nationTables.forEach { it.update() } + } + + private fun getOptionsTable(): Table { val table = Table() - table.skin= skin - - - table.add("{Civilization}:".tr()) - val civSelectBox = TranslatedSelectBox(GameBasics.Nations.keys.filterNot { it=="Barbarians" }, - "Babylon",skin) - table.add(civSelectBox).pad(10f).row() - + table.skin = skin + table.add("{World size}:".tr()) - val worldSizeToRadius=LinkedHashMap() + val worldSizeToRadius = LinkedHashMap() worldSizeToRadius["Small"] = 10 worldSizeToRadius["Medium"] = 20 worldSizeToRadius["Large"] = 30 - val worldSizeSelectBox = TranslatedSelectBox(worldSizeToRadius.keys,"Medium",skin) + val worldSizeSelectBox = TranslatedSelectBox(worldSizeToRadius.keys, "Medium", skin) + + worldSizeSelectBox.addListener(object : ChangeListener() { + override fun changed(event: ChangeEvent?, actor: Actor?) { + newGameParameters.mapRadius = worldSizeToRadius[worldSizeSelectBox.selected.value]!! + } + }) table.add(worldSizeSelectBox).pad(10f).row() table.add("{Number of enemies}:".tr()) val enemiesSelectBox = SelectBox(skin) - val enemiesArray=Array() + val enemiesArray = Array() (1..5).forEach { enemiesArray.add(it) } - enemiesSelectBox.items=enemiesArray - enemiesSelectBox.selected=3 + enemiesSelectBox.items = enemiesArray + enemiesSelectBox.selected = newGameParameters.numberOfEnemies + + enemiesSelectBox.addListener(object : ChangeListener() { + override fun changed(event: ChangeEvent?, actor: Actor?) { + newGameParameters.numberOfEnemies = enemiesSelectBox.selected + } + }) table.add(enemiesSelectBox).pad(10f).row() table.add("{Difficulty}:".tr()) - val difficultySelectBox = TranslatedSelectBox(GameBasics.Difficulties.keys, "Prince", skin) + val difficultySelectBox = TranslatedSelectBox(GameBasics.Difficulties.keys, newGameParameters.difficulty, skin) table.add(difficultySelectBox).pad(10f).row() @@ -56,17 +144,15 @@ class NewGameScreen: PickerScreen(){ rightSideButton.disable() rightSideButton.setText("Working...".tr()) - kotlin.concurrent.thread { // Creating a new game can tke a while and we don't want ANRs - newGame = GameStarter().startNewGame( - worldSizeToRadius[worldSizeSelectBox.selected.value]!!, enemiesSelectBox.selected, - civSelectBox.selected.value, difficultySelectBox.selected.value ) + thread { + // Creating a new game can tke a while and we don't want ANRs + newGame = GameStarter().startNewGame(newGameParameters) } } - - table.setFillParent(true) table.pack() - stage.addActor(table) + return table } + var newGame:GameInfo?=null override fun render(delta: Float) {