Resolved #1696
Specialist allocation - Is now in a separate class - Is immediately viewable on the City screen
This commit is contained in:
parent
45dc3d3587
commit
1633394164
5 changed files with 141 additions and 94 deletions
|
@ -2,7 +2,9 @@ package com.unciv.ui.cityscreen
|
||||||
|
|
||||||
import com.badlogic.gdx.graphics.Color
|
import com.badlogic.gdx.graphics.Color
|
||||||
import com.badlogic.gdx.scenes.scene2d.Touchable
|
import com.badlogic.gdx.scenes.scene2d.Touchable
|
||||||
import com.badlogic.gdx.scenes.scene2d.ui.*
|
import com.badlogic.gdx.scenes.scene2d.ui.ScrollPane
|
||||||
|
import com.badlogic.gdx.scenes.scene2d.ui.Table
|
||||||
|
import com.badlogic.gdx.scenes.scene2d.ui.TextButton
|
||||||
import com.badlogic.gdx.utils.Align
|
import com.badlogic.gdx.utils.Align
|
||||||
import com.unciv.UncivGame
|
import com.unciv.UncivGame
|
||||||
import com.unciv.logic.city.CityInfo
|
import com.unciv.logic.city.CityInfo
|
||||||
|
@ -11,7 +13,6 @@ import com.unciv.models.ruleset.Building
|
||||||
import com.unciv.models.stats.Stat
|
import com.unciv.models.stats.Stat
|
||||||
import com.unciv.models.translations.tr
|
import com.unciv.models.translations.tr
|
||||||
import com.unciv.ui.utils.*
|
import com.unciv.ui.utils.*
|
||||||
import com.unciv.ui.utils.YesNoPopup
|
|
||||||
import java.text.DecimalFormat
|
import java.text.DecimalFormat
|
||||||
|
|
||||||
class CityInfoTable(private val cityScreen: CityScreen) : Table(CameraStageBaseScreen.skin) {
|
class CityInfoTable(private val cityScreen: CityScreen) : Table(CameraStageBaseScreen.skin) {
|
||||||
|
@ -134,13 +135,13 @@ class CityInfoTable(private val cityScreen: CityScreen) : Table(CameraStageBaseS
|
||||||
specialistIcons.row().size(20f).pad(5f)
|
specialistIcons.row().size(20f).pad(5f)
|
||||||
for (stat in building.specialistSlots!!.toHashMap())
|
for (stat in building.specialistSlots!!.toHashMap())
|
||||||
for (i in 0 until stat.value.toInt())
|
for (i in 0 until stat.value.toInt())
|
||||||
specialistIcons.add(getSpecialistIcon(stat.key)).size(20f)
|
specialistIcons.add(ImageGetter.getSpecialistIcon(stat.key)).size(20f)
|
||||||
|
|
||||||
specialistBuildingsTable.add(specialistIcons).pad(0f).row()
|
specialistBuildingsTable.add(specialistIcons).pad(0f).row()
|
||||||
}
|
}
|
||||||
|
|
||||||
// specialist allocation
|
// specialist allocation
|
||||||
addSpecialistAllocation(skin, cityInfo)
|
// addCategory("Specialist Allocation", SpecialistAllocationTable(cityScreen)) todo
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!otherBuildings.isEmpty()) {
|
if (!otherBuildings.isEmpty()) {
|
||||||
|
@ -226,74 +227,5 @@ class CityInfoTable(private val cityScreen: CityScreen) : Table(CameraStageBaseS
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun Table.addSpecialistAllocation(skin: Skin, cityInfo: CityInfo) {
|
|
||||||
val specialistAllocationTable = Table()
|
|
||||||
addCategory("Specialist Allocation", specialistAllocationTable) // todo WRONG, BAD - table should contain all the below specialist stuff
|
|
||||||
|
|
||||||
val currentSpecialists = cityInfo.population.specialists.toHashMap()
|
|
||||||
val maximumSpecialists = cityInfo.population.getMaxSpecialists()
|
|
||||||
|
|
||||||
for (statToMaximumSpecialist in maximumSpecialists.toHashMap()) {
|
|
||||||
val specialistPickerTable = Table()
|
|
||||||
if (statToMaximumSpecialist.value == 0f) continue
|
|
||||||
val stat = statToMaximumSpecialist.key
|
|
||||||
// these two are conflictingly named compared to above...
|
|
||||||
val assignedSpecialists = currentSpecialists[stat]!!.toInt()
|
|
||||||
val maxSpecialists = statToMaximumSpecialist.value.toInt()
|
|
||||||
if (assignedSpecialists > 0 && !cityInfo.isPuppet) {
|
|
||||||
val unassignButton = TextButton("-", skin)
|
|
||||||
unassignButton.label.setFontSize(24)
|
|
||||||
unassignButton.onClick {
|
|
||||||
cityInfo.population.specialists.add(stat, -1f)
|
|
||||||
cityInfo.cityStats.update()
|
|
||||||
cityScreen.update()
|
|
||||||
}
|
|
||||||
if(!UncivGame.Current.worldScreen.isPlayersTurn) unassignButton.disable()
|
|
||||||
specialistPickerTable.add(unassignButton)
|
|
||||||
} else specialistPickerTable.add()
|
|
||||||
|
|
||||||
val specialistIconTable = Table()
|
|
||||||
for (i in 1..maxSpecialists) {
|
|
||||||
val icon = getSpecialistIcon(stat, i <= assignedSpecialists)
|
|
||||||
specialistIconTable.add(icon).size(30f)
|
|
||||||
}
|
|
||||||
specialistPickerTable.add(specialistIconTable)
|
|
||||||
if (assignedSpecialists < maxSpecialists && !cityInfo.isPuppet) {
|
|
||||||
val assignButton = TextButton("+", skin)
|
|
||||||
assignButton.label.setFontSize(24)
|
|
||||||
assignButton.onClick {
|
|
||||||
cityInfo.population.specialists.add(statToMaximumSpecialist.key, 1f)
|
|
||||||
cityInfo.cityStats.update()
|
|
||||||
cityScreen.update()
|
|
||||||
}
|
|
||||||
if (cityInfo.population.getFreePopulation() == 0 || !UncivGame.Current.worldScreen.isPlayersTurn)
|
|
||||||
assignButton.disable()
|
|
||||||
specialistPickerTable.add(assignButton)
|
|
||||||
} else specialistPickerTable.add()
|
|
||||||
specialistAllocationTable.add(specialistPickerTable).row()
|
|
||||||
|
|
||||||
val specialistStatTable = Table().apply { defaults().pad(5f) }
|
|
||||||
val specialistStats = cityInfo.cityStats.getStatsOfSpecialist(stat, cityInfo.civInfo.policies.adoptedPolicies).toHashMap()
|
|
||||||
for (entry in specialistStats) {
|
|
||||||
if (entry.value == 0f) continue
|
|
||||||
specialistStatTable.add(ImageGetter.getStatIcon(entry.key.toString())).size(20f)
|
|
||||||
specialistStatTable.add(entry.value.toInt().toString().toLabel()).padRight(10f)
|
|
||||||
}
|
|
||||||
specialistAllocationTable.add(specialistStatTable).row()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun getSpecialistIcon(stat: Stat, isFilled: Boolean =true): Image {
|
|
||||||
val specialist = ImageGetter.getImage("StatIcons/Specialist")
|
|
||||||
if (!isFilled) specialist.color = Color.GRAY
|
|
||||||
else specialist.color=when(stat){
|
|
||||||
Stat.Production -> Color.BROWN
|
|
||||||
Stat.Gold -> Color.GOLD
|
|
||||||
Stat.Science -> Color.BLUE
|
|
||||||
Stat.Culture -> Color.PURPLE
|
|
||||||
else -> Color.WHITE
|
|
||||||
}
|
|
||||||
|
|
||||||
return specialist
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -37,6 +37,9 @@ class CityScreen(internal val city: CityInfo): CameraStageBaseScreen() {
|
||||||
/** Displays city stats info */
|
/** Displays city stats info */
|
||||||
private var cityStatsTable = CityStatsTable(this.city)
|
private var cityStatsTable = CityStatsTable(this.city)
|
||||||
|
|
||||||
|
/** Displays specialist allocation */
|
||||||
|
private var specialistAllocationTable=SpecialistAllocationTable(this)
|
||||||
|
|
||||||
/** Displays tile info, alternate with selectedConstructionTable - sits on BOTTOM RIGHT */
|
/** Displays tile info, alternate with selectedConstructionTable - sits on BOTTOM RIGHT */
|
||||||
private var tileTable = CityScreenTileTable(city)
|
private var tileTable = CityScreenTileTable(city)
|
||||||
|
|
||||||
|
@ -57,6 +60,7 @@ class CityScreen(internal val city: CityInfo): CameraStageBaseScreen() {
|
||||||
|
|
||||||
//stage.setDebugTableUnderMouse(true)
|
//stage.setDebugTableUnderMouse(true)
|
||||||
stage.addActor(cityStatsTable)
|
stage.addActor(cityStatsTable)
|
||||||
|
stage.addActor(specialistAllocationTable)
|
||||||
stage.addActor(constructionsTable)
|
stage.addActor(constructionsTable)
|
||||||
stage.addActor(tileTable)
|
stage.addActor(tileTable)
|
||||||
stage.addActor(selectedConstructionTable)
|
stage.addActor(selectedConstructionTable)
|
||||||
|
@ -93,6 +97,8 @@ class CityScreen(internal val city: CityInfo): CameraStageBaseScreen() {
|
||||||
|
|
||||||
cityStatsTable.update()
|
cityStatsTable.update()
|
||||||
cityStatsTable.setPosition( stage.width - 5f, stage.height - 5f, Align.topRight)
|
cityStatsTable.setPosition( stage.width - 5f, stage.height - 5f, Align.topRight)
|
||||||
|
specialistAllocationTable.update()
|
||||||
|
specialistAllocationTable.setPosition(stage.width-5, cityStatsTable.y, Align.topRight)
|
||||||
|
|
||||||
updateAnnexAndRazeCityButton()
|
updateAnnexAndRazeCityButton()
|
||||||
updateTileGroups()
|
updateTileGroups()
|
||||||
|
@ -155,19 +161,18 @@ class CityScreen(internal val city: CityInfo): CameraStageBaseScreen() {
|
||||||
val tileInfo = tileGroup.tileInfo
|
val tileInfo = tileGroup.tileInfo
|
||||||
|
|
||||||
tileGroup.onClick {
|
tileGroup.onClick {
|
||||||
if (!city.isPuppet) {
|
if (city.isPuppet) return@onClick
|
||||||
selectedTile = tileInfo
|
|
||||||
selectedConstruction = null
|
selectedTile = tileInfo
|
||||||
if (tileGroup.isWorkable && UncivGame.Current.worldScreen.isPlayersTurn) {
|
selectedConstruction = null
|
||||||
if (!tileInfo.isWorked() && city.population.getFreePopulation() > 0) {
|
if (tileGroup.isWorkable && UncivGame.Current.worldScreen.isPlayersTurn) {
|
||||||
city.workedTiles.add(tileInfo.position)
|
if (!tileInfo.isWorked() && city.population.getFreePopulation() > 0) {
|
||||||
game.settings.addCompletedTutorialTask("Reassign worked tiles")
|
city.workedTiles.add(tileInfo.position)
|
||||||
}
|
game.settings.addCompletedTutorialTask("Reassign worked tiles")
|
||||||
else if (tileInfo.isWorked()) city.workedTiles.remove(tileInfo.position)
|
} else if (tileInfo.isWorked()) city.workedTiles.remove(tileInfo.position)
|
||||||
city.cityStats.update()
|
city.cityStats.update()
|
||||||
}
|
|
||||||
update()
|
|
||||||
}
|
}
|
||||||
|
update()
|
||||||
}
|
}
|
||||||
|
|
||||||
tileGroups.add(tileGroup)
|
tileGroups.add(tileGroup)
|
||||||
|
|
|
@ -7,8 +7,10 @@ import com.unciv.UncivGame
|
||||||
import com.unciv.logic.city.CityInfo
|
import com.unciv.logic.city.CityInfo
|
||||||
import com.unciv.logic.map.TileInfo
|
import com.unciv.logic.map.TileInfo
|
||||||
import com.unciv.models.UncivSound
|
import com.unciv.models.UncivSound
|
||||||
|
import com.unciv.models.stats.Stats
|
||||||
import com.unciv.models.translations.tr
|
import com.unciv.models.translations.tr
|
||||||
import com.unciv.ui.utils.*
|
import com.unciv.ui.utils.*
|
||||||
|
import kotlin.math.roundToInt
|
||||||
|
|
||||||
class CityScreenTileTable(val city: CityInfo): Table(){
|
class CityScreenTileTable(val city: CityInfo): Table(){
|
||||||
val innerTable = Table()
|
val innerTable = Table()
|
||||||
|
@ -32,15 +34,8 @@ class CityScreenTileTable(val city: CityInfo): Table(){
|
||||||
|
|
||||||
innerTable.add(selectedTile.toString().toLabel()).colspan(2)
|
innerTable.add(selectedTile.toString().toLabel()).colspan(2)
|
||||||
innerTable.row()
|
innerTable.row()
|
||||||
|
innerTable.add(getTileStatsTable(stats)).row()
|
||||||
|
|
||||||
val statsTable = Table()
|
|
||||||
statsTable.defaults().pad(2f)
|
|
||||||
for (entry in stats.toHashMap().filterNot { it.value==0f }) {
|
|
||||||
statsTable.add(ImageGetter.getStatIcon(entry.key.toString())).size(20f)
|
|
||||||
statsTable.add(Math.round(entry.value).toString().toLabel())
|
|
||||||
statsTable.row()
|
|
||||||
}
|
|
||||||
innerTable.add(statsTable).row()
|
|
||||||
|
|
||||||
if(selectedTile.getOwner()==null && selectedTile.neighbors.any {it.getCity()==city}
|
if(selectedTile.getOwner()==null && selectedTile.neighbors.any {it.getCity()==city}
|
||||||
&& selectedTile in city.tilesInRange){
|
&& selectedTile in city.tilesInRange){
|
||||||
|
@ -67,4 +62,15 @@ class CityScreenTileTable(val city: CityInfo): Table(){
|
||||||
innerTable.pack()
|
innerTable.pack()
|
||||||
pack()
|
pack()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun getTileStatsTable(stats: Stats): Table {
|
||||||
|
val statsTable = Table()
|
||||||
|
statsTable.defaults().pad(2f)
|
||||||
|
for (entry in stats.toHashMap().filterNot { it.value == 0f }) {
|
||||||
|
statsTable.add(ImageGetter.getStatIcon(entry.key.toString())).size(20f)
|
||||||
|
statsTable.add(entry.value.roundToInt().toString().toLabel())
|
||||||
|
statsTable.row()
|
||||||
|
}
|
||||||
|
return statsTable
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -0,0 +1,89 @@
|
||||||
|
package com.unciv.ui.cityscreen
|
||||||
|
|
||||||
|
import com.badlogic.gdx.graphics.Color
|
||||||
|
import com.badlogic.gdx.scenes.scene2d.Actor
|
||||||
|
import com.badlogic.gdx.scenes.scene2d.ui.Table
|
||||||
|
import com.badlogic.gdx.scenes.scene2d.ui.TextButton
|
||||||
|
import com.unciv.UncivGame
|
||||||
|
import com.unciv.models.stats.Stat
|
||||||
|
import com.unciv.ui.utils.*
|
||||||
|
|
||||||
|
class SpecialistAllocationTable(val cityScreen: CityScreen): Table(CameraStageBaseScreen.skin){
|
||||||
|
val cityInfo = cityScreen.city
|
||||||
|
|
||||||
|
fun update() {
|
||||||
|
background = ImageGetter.getBackground(Color.BLACK.cpy().apply { a=0.7f })
|
||||||
|
clear()
|
||||||
|
|
||||||
|
for (statToMaximumSpecialist in cityInfo.population.getMaxSpecialists().toHashMap()) {
|
||||||
|
if (statToMaximumSpecialist.value == 0f) continue
|
||||||
|
|
||||||
|
val stat = statToMaximumSpecialist.key
|
||||||
|
add(getAllocationTable(stat)).pad(10f)
|
||||||
|
addSeparatorVertical().pad(5f)
|
||||||
|
add(getSpecialistStatsTable(stat)).row()
|
||||||
|
}
|
||||||
|
pack()
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
fun getAllocationTable(stat: Stat):Table{
|
||||||
|
val specialistPickerTable = Table()
|
||||||
|
|
||||||
|
val assignedSpecialists = cityInfo.population.specialists.get(stat).toInt()
|
||||||
|
val maxSpecialists = cityInfo.population.getMaxSpecialists().get(stat).toInt()
|
||||||
|
|
||||||
|
specialistPickerTable.add(getUnassignButton(assignedSpecialists, stat))
|
||||||
|
|
||||||
|
val specialistIconTable = Table()
|
||||||
|
for (i in 1..maxSpecialists) {
|
||||||
|
val icon = ImageGetter.getSpecialistIcon(stat, i <= assignedSpecialists)
|
||||||
|
specialistIconTable.add(icon).size(30f)
|
||||||
|
}
|
||||||
|
specialistPickerTable.add(specialistIconTable)
|
||||||
|
|
||||||
|
specialistPickerTable.add(getAssignButton(assignedSpecialists, maxSpecialists, stat))
|
||||||
|
|
||||||
|
return specialistPickerTable
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun getAssignButton(assignedSpecialists: Int, maxSpecialists: Int, stat: Stat):Actor {
|
||||||
|
if (assignedSpecialists >= maxSpecialists || cityInfo.isPuppet) return Table()
|
||||||
|
val assignButton = TextButton("+", skin)
|
||||||
|
assignButton.label.setFontSize(24)
|
||||||
|
assignButton.onClick {
|
||||||
|
cityInfo.population.specialists.add(stat, 1f)
|
||||||
|
cityInfo.cityStats.update()
|
||||||
|
cityScreen.update()
|
||||||
|
}
|
||||||
|
if (cityInfo.population.getFreePopulation() == 0 || !UncivGame.Current.worldScreen.isPlayersTurn)
|
||||||
|
assignButton.disable()
|
||||||
|
return assignButton
|
||||||
|
}
|
||||||
|
|
||||||
|
private fun getUnassignButton(assignedSpecialists: Int, stat: Stat):Actor {
|
||||||
|
if (assignedSpecialists <= 0 || cityInfo.isPuppet) return Table()
|
||||||
|
|
||||||
|
val unassignButton = TextButton("-", skin)
|
||||||
|
unassignButton.label.setFontSize(24)
|
||||||
|
unassignButton.onClick {
|
||||||
|
cityInfo.population.specialists.add(stat, -1f)
|
||||||
|
cityInfo.cityStats.update()
|
||||||
|
cityScreen.update()
|
||||||
|
}
|
||||||
|
if (!UncivGame.Current.worldScreen.isPlayersTurn) unassignButton.disable()
|
||||||
|
return unassignButton
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private fun getSpecialistStatsTable(stat: Stat): Table {
|
||||||
|
val specialistStatTable = Table().apply { defaults().pad(5f) }
|
||||||
|
val specialistStats = cityInfo.cityStats.getStatsOfSpecialist(stat, cityInfo.civInfo.policies.adoptedPolicies).toHashMap()
|
||||||
|
for (entry in specialistStats) {
|
||||||
|
if (entry.value == 0f) continue
|
||||||
|
specialistStatTable.add(ImageGetter.getStatIcon(entry.key.toString())).size(20f)
|
||||||
|
specialistStatTable.add(entry.value.toInt().toString().toLabel()).padRight(10f)
|
||||||
|
}
|
||||||
|
return specialistStatTable
|
||||||
|
}
|
||||||
|
}
|
|
@ -15,6 +15,7 @@ import com.badlogic.gdx.utils.Align
|
||||||
import com.unciv.models.ruleset.Nation
|
import com.unciv.models.ruleset.Nation
|
||||||
import com.unciv.models.ruleset.Ruleset
|
import com.unciv.models.ruleset.Ruleset
|
||||||
import com.unciv.models.ruleset.tile.ResourceType
|
import com.unciv.models.ruleset.tile.ResourceType
|
||||||
|
import com.unciv.models.stats.Stat
|
||||||
|
|
||||||
object ImageGetter {
|
object ImageGetter {
|
||||||
private const val whiteDotLocation = "OtherIcons/whiteDot"
|
private const val whiteDotLocation = "OtherIcons/whiteDot"
|
||||||
|
@ -288,5 +289,19 @@ object ImageGetter {
|
||||||
|
|
||||||
return line
|
return line
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun getSpecialistIcon(stat: Stat, isFilled: Boolean =true): Image {
|
||||||
|
val specialist = getImage("StatIcons/Specialist")
|
||||||
|
if (!isFilled) specialist.color = Color.GRAY
|
||||||
|
else specialist.color=when(stat){
|
||||||
|
Stat.Production -> Color.BROWN
|
||||||
|
Stat.Gold -> Color.GOLD
|
||||||
|
Stat.Science -> Color.BLUE
|
||||||
|
Stat.Culture -> Color.PURPLE
|
||||||
|
else -> Color.WHITE
|
||||||
|
}
|
||||||
|
|
||||||
|
return specialist
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue