Persistent new game setup (#5016)

* Persistent new game setup

* Persistent new game setup - comments
This commit is contained in:
SomeTroglodyte 2021-08-29 19:40:13 +02:00 committed by GitHub
parent 5094a068fe
commit 3b5489a3b4
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
14 changed files with 85 additions and 30 deletions

View File

@ -16,7 +16,7 @@ import com.unciv.logic.map.mapgenerator.MapGenerator
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.ui.MultiplayerScreen import com.unciv.ui.MultiplayerScreen
import com.unciv.ui.mapeditor.* import com.unciv.ui.mapeditor.*
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import com.unciv.ui.newgamescreen.NewGameScreen import com.unciv.ui.newgamescreen.NewGameScreen
import com.unciv.ui.pickerscreens.ModManagementScreen import com.unciv.ui.pickerscreens.ModManagementScreen
import com.unciv.ui.saves.LoadGameScreen import com.unciv.ui.saves.LoadGameScreen
@ -236,7 +236,7 @@ class MainMenuScreen: CameraStageBaseScreen() {
} }
private fun quickstartNewGame() { private fun quickstartNewGame() {
val newGame = GameStarter.startNewGame(GameSetupInfo().apply { gameParameters.difficulty = "Chieftain" }) val newGame = GameStarter.startNewGame(GameSetupInfo.fromSettings("Chieftain"))
game.loadGame(newGame) game.loadGame(newGame)
} }

View File

@ -2,6 +2,7 @@ package com.unciv.logic
import com.badlogic.gdx.math.Vector2 import com.badlogic.gdx.math.Vector2
import com.unciv.Constants import com.unciv.Constants
import com.unciv.UncivGame
import com.unciv.logic.civilization.* import com.unciv.logic.civilization.*
import com.unciv.logic.map.BFS import com.unciv.logic.map.BFS
import com.unciv.logic.map.TileInfo import com.unciv.logic.map.TileInfo
@ -13,7 +14,7 @@ import com.unciv.models.ruleset.ModOptionsConstants
import com.unciv.models.ruleset.Ruleset import com.unciv.models.ruleset.Ruleset
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.models.ruleset.tile.ResourceType import com.unciv.models.ruleset.tile.ResourceType
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import java.util.* import java.util.*
import kotlin.collections.ArrayList import kotlin.collections.ArrayList
import kotlin.collections.HashMap import kotlin.collections.HashMap
@ -90,6 +91,10 @@ object GameStarter {
// This triggers the one-time greeting from Nation.startIntroPart1/2 // This triggers the one-time greeting from Nation.startIntroPart1/2
addPlayerIntros(gameInfo) addPlayerIntros(gameInfo)
UncivGame.Current.settings.apply {
lastGameSetup = gameSetupInfo
save()
}
return gameInfo return gameInfo
} }

View File

@ -57,6 +57,13 @@ class MapSizeNew {
this.radius = getEquivalentHexagonalRadius(width, height) this.radius = getEquivalentHexagonalRadius(width, height)
} }
fun clone() = MapSizeNew().also {
it.name = name
it.radius = radius
it.width = width
it.height = height
}
/** Check custom dimensions, fix if too extreme /** Check custom dimensions, fix if too extreme
* @param worldWrap whether world wrap is on * @param worldWrap whether world wrap is on
* @return null if size was acceptable, otherwise untranslated reason message * @return null if size was acceptable, otherwise untranslated reason message
@ -141,6 +148,26 @@ class MapParameters {
var resourceRichness = 0.1f var resourceRichness = 0.1f
var waterThreshold = 0f var waterThreshold = 0f
fun clone() = MapParameters().also {
it.name = name
it.type = type
it.shape = shape
it.mapSize = mapSize.clone()
it.noRuins = noRuins
it.noNaturalWonders = noNaturalWonders
it.worldWrap = worldWrap
it.mods = LinkedHashSet(mods)
it.seed = seed
it.tilesPerBiomeArea = tilesPerBiomeArea
it.maxCoastExtension = maxCoastExtension
it.elevationExponent = elevationExponent
it.temperatureExtremeness = temperatureExtremeness
it.vegetationRichness = vegetationRichness
it.rareFeaturesRichness = rareFeaturesRichness
it.resourceRichness = resourceRichness
it.waterThreshold = waterThreshold
}
fun reseed() { fun reseed() {
seed = System.currentTimeMillis() seed = System.currentTimeMillis()
} }

View File

@ -47,6 +47,9 @@ class GameSettings {
var allowAndroidPortrait = false // Opt-in to allow Unciv to follow a screen rotation to portrait var allowAndroidPortrait = false // Opt-in to allow Unciv to follow a screen rotation to portrait
/** Saves the last successful new game's setup */
var lastGameSetup: GameSetupInfo? = null
init { init {
// 26 = Android Oreo. Versions below may display permanent icon in notification bar. // 26 = Android Oreo. Versions below may display permanent icon in notification bar.
if (Gdx.app?.type == Application.ApplicationType.Android && Gdx.app.version < 26) { if (Gdx.app?.type == Application.ApplicationType.Android && Gdx.app.version < 26) {

View File

@ -0,0 +1,36 @@
package com.unciv.models.metadata
import com.badlogic.gdx.files.FileHandle
import com.unciv.UncivGame
import com.unciv.logic.GameInfo
import com.unciv.logic.map.MapParameters
import com.unciv.models.ruleset.Difficulty
class GameSetupInfo(
var gameParameters: GameParameters = GameParameters(),
var mapParameters: MapParameters = MapParameters()
) {
@Transient
var mapFile: FileHandle? = null
// This constructor is used for starting a new game from a running one, cloning the setup, including map seed
constructor(gameInfo: GameInfo) : this(gameInfo.gameParameters.clone(), gameInfo.tileMap.mapParameters.clone())
// Cloning constructor used for [fromSettings] and [GameParametersScreen], reseeds map
constructor(setup: GameSetupInfo): this(setup.gameParameters.clone(), setup.mapParameters.clone())
companion object {
/**
* Get a cloned and reseeded [GameSetupInfo] from saved settings if present, otherwise a default instance.
* @param defaultDifficulty Overrides difficulty only when no saved settings found, so a virgin
* Unciv installation can QuickStart with a different difficulty than New Game defaults to.
*/
fun fromSettings(defaultDifficulty: String? = null) = UncivGame.Current.settings.run {
if (lastGameSetup == null) GameSetupInfo().apply {
if (defaultDifficulty != null) gameParameters.difficulty = defaultDifficulty
}
else GameSetupInfo(lastGameSetup!!).apply {
mapParameters.reseed()
}
}
}
}

View File

@ -3,7 +3,7 @@ package com.unciv.models.simulation
import com.unciv.logic.GameInfo import com.unciv.logic.GameInfo
import com.unciv.logic.GameStarter import com.unciv.logic.GameStarter
import com.unciv.models.ruleset.VictoryType import com.unciv.models.ruleset.VictoryType
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import java.lang.Integer.max import java.lang.Integer.max
import java.time.Duration import java.time.Duration
import kotlin.concurrent.thread import kotlin.concurrent.thread

View File

@ -5,6 +5,7 @@ import com.unciv.UncivGame
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.models.translations.tr import com.unciv.models.translations.tr
import com.unciv.ui.newgamescreen.GameOptionsTable import com.unciv.ui.newgamescreen.GameOptionsTable
import com.unciv.models.metadata.GameSetupInfo
import com.unciv.ui.newgamescreen.PlayerPickerTable import com.unciv.ui.newgamescreen.PlayerPickerTable
import com.unciv.ui.newgamescreen.IPreviousScreen import com.unciv.ui.newgamescreen.IPreviousScreen
import com.unciv.ui.pickerscreens.PickerScreen import com.unciv.ui.pickerscreens.PickerScreen
@ -18,7 +19,7 @@ import com.unciv.ui.utils.*
* @param [mapEditorScreen] previous screen from map editor. * @param [mapEditorScreen] previous screen from map editor.
*/ */
class GameParametersScreen(var mapEditorScreen: MapEditorScreen): IPreviousScreen, PickerScreen(disableScroll = true) { class GameParametersScreen(var mapEditorScreen: MapEditorScreen): IPreviousScreen, PickerScreen(disableScroll = true) {
override var gameSetupInfo = mapEditorScreen.gameSetupInfo.clone() override var gameSetupInfo = GameSetupInfo(mapEditorScreen.gameSetupInfo)
override var ruleset = RulesetCache.getComplexRuleset(gameSetupInfo.gameParameters.mods) override var ruleset = RulesetCache.getComplexRuleset(gameSetupInfo.gameParameters.mods)
var playerPickerTable = PlayerPickerTable(this, gameSetupInfo.gameParameters) var playerPickerTable = PlayerPickerTable(this, gameSetupInfo.gameParameters)
var gameOptionsTable = GameOptionsTable(this) { desiredCiv: String -> playerPickerTable.update(desiredCiv) } var gameOptionsTable = GameOptionsTable(this) { desiredCiv: String -> playerPickerTable.update(desiredCiv) }

View File

@ -10,7 +10,7 @@ import com.unciv.logic.map.TileInfo
import com.unciv.logic.map.TileMap import com.unciv.logic.map.TileMap
import com.unciv.models.ruleset.Ruleset import com.unciv.models.ruleset.Ruleset
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import com.unciv.ui.utils.* import com.unciv.ui.utils.*
class MapEditorScreen(): CameraStageBaseScreen() { class MapEditorScreen(): CameraStageBaseScreen() {

View File

@ -1,6 +1,7 @@
package com.unciv.ui.newgamescreen package com.unciv.ui.newgamescreen
import com.badlogic.gdx.scenes.scene2d.Stage import com.badlogic.gdx.scenes.scene2d.Stage
import com.unciv.models.metadata.GameSetupInfo
import com.unciv.models.ruleset.Ruleset import com.unciv.models.ruleset.Ruleset
/** /**

View File

@ -1,7 +1,6 @@
package com.unciv.ui.newgamescreen package com.unciv.ui.newgamescreen
import com.badlogic.gdx.Gdx import com.badlogic.gdx.Gdx
import com.badlogic.gdx.files.FileHandle
import com.badlogic.gdx.graphics.Color import com.badlogic.gdx.graphics.Color
import com.badlogic.gdx.scenes.scene2d.ui.SelectBox import com.badlogic.gdx.scenes.scene2d.ui.SelectBox
import com.badlogic.gdx.scenes.scene2d.ui.Skin import com.badlogic.gdx.scenes.scene2d.ui.Skin
@ -9,41 +8,24 @@ import com.badlogic.gdx.utils.Array
import com.unciv.UncivGame import com.unciv.UncivGame
import com.unciv.logic.* import com.unciv.logic.*
import com.unciv.logic.civilization.PlayerType import com.unciv.logic.civilization.PlayerType
import com.unciv.logic.map.MapParameters
import com.unciv.logic.map.MapType import com.unciv.logic.map.MapType
import com.unciv.models.metadata.GameParameters import com.unciv.models.metadata.GameSetupInfo
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.models.translations.tr import com.unciv.models.translations.tr
import com.unciv.ui.pickerscreens.PickerScreen import com.unciv.ui.pickerscreens.PickerScreen
import com.unciv.ui.utils.* import com.unciv.ui.utils.*
import com.unciv.ui.worldscreen.mainmenu.OnlineMultiplayer import com.unciv.ui.worldscreen.mainmenu.OnlineMultiplayer
import java.util.* import java.util.*
import kotlin.collections.HashSet
import kotlin.concurrent.thread import kotlin.concurrent.thread
import com.unciv.ui.utils.AutoScrollPane as ScrollPane import com.unciv.ui.utils.AutoScrollPane as ScrollPane
class GameSetupInfo(var gameId:String, var gameParameters: GameParameters, var mapParameters: MapParameters) {
var mapFile: FileHandle? = null
constructor() : this("", GameParameters(), MapParameters())
constructor(gameInfo: GameInfo) : this("", gameInfo.gameParameters.clone(), gameInfo.tileMap.mapParameters)
constructor(gameParameters: GameParameters, mapParameters: MapParameters) : this("", gameParameters, mapParameters)
fun clone(): GameSetupInfo {
val toReturn = GameSetupInfo()
toReturn.gameId = this.gameId
toReturn.gameParameters = this.gameParameters
toReturn.mapParameters = this.mapParameters
return toReturn
}
}
class NewGameScreen( class NewGameScreen(
private val previousScreen: CameraStageBaseScreen, private val previousScreen: CameraStageBaseScreen,
_gameSetupInfo: GameSetupInfo? = null _gameSetupInfo: GameSetupInfo? = null
): IPreviousScreen, PickerScreen() { ): IPreviousScreen, PickerScreen() {
override val gameSetupInfo = _gameSetupInfo ?: GameSetupInfo() override val gameSetupInfo = _gameSetupInfo ?: GameSetupInfo.fromSettings()
override var ruleset = RulesetCache.getComplexRuleset(gameSetupInfo.gameParameters.mods) // needs to be set because the GameOptionsTable etc. depend on this override var ruleset = RulesetCache.getComplexRuleset(gameSetupInfo.gameParameters.mods) // needs to be set because the GameOptionsTable etc. depend on this
private val newGameOptionsTable = GameOptionsTable(this, isNarrowerThan4to3()) { desiredCiv: String -> playerPickerTable.update(desiredCiv) } private val newGameOptionsTable = GameOptionsTable(this, isNarrowerThan4to3()) { desiredCiv: String -> playerPickerTable.update(desiredCiv) }

View File

@ -9,7 +9,7 @@ import com.unciv.models.ruleset.Policy
import com.unciv.models.ruleset.VictoryType import com.unciv.models.ruleset.VictoryType
import com.unciv.models.translations.getPlaceholderParameters import com.unciv.models.translations.getPlaceholderParameters
import com.unciv.models.translations.tr import com.unciv.models.translations.tr
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import com.unciv.ui.newgamescreen.NewGameScreen import com.unciv.ui.newgamescreen.NewGameScreen
import com.unciv.ui.overviewscreen.EmpireOverviewScreen import com.unciv.ui.overviewscreen.EmpireOverviewScreen
import com.unciv.ui.pickerscreens.PickerScreen import com.unciv.ui.pickerscreens.PickerScreen

View File

@ -3,7 +3,7 @@ package com.unciv.ui.worldscreen.mainmenu
import com.badlogic.gdx.Gdx import com.badlogic.gdx.Gdx
import com.unciv.MainMenuScreen import com.unciv.MainMenuScreen
import com.unciv.ui.civilopedia.CivilopediaScreen import com.unciv.ui.civilopedia.CivilopediaScreen
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import com.unciv.ui.newgamescreen.NewGameScreen import com.unciv.ui.newgamescreen.NewGameScreen
import com.unciv.ui.saves.LoadGameScreen import com.unciv.ui.saves.LoadGameScreen
import com.unciv.ui.saves.SaveGameScreen import com.unciv.ui.saves.SaveGameScreen

View File

@ -14,7 +14,7 @@ import com.unciv.models.metadata.Player
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.models.simulation.Simulation import com.unciv.models.simulation.Simulation
import com.unciv.models.tilesets.TileSetCache import com.unciv.models.tilesets.TileSetCache
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
internal object ConsoleLauncher { internal object ConsoleLauncher {
@JvmStatic @JvmStatic

View File

@ -13,7 +13,7 @@ import com.unciv.models.metadata.GameParameters
import com.unciv.models.metadata.GameSettings import com.unciv.models.metadata.GameSettings
import com.unciv.models.metadata.Player import com.unciv.models.metadata.Player
import com.unciv.models.ruleset.RulesetCache import com.unciv.models.ruleset.RulesetCache
import com.unciv.ui.newgamescreen.GameSetupInfo import com.unciv.models.metadata.GameSetupInfo
import org.junit.Assert import org.junit.Assert
import org.junit.Before import org.junit.Before
import org.junit.Test import org.junit.Test