Fix free buildings triggering from conditionals in incorrect places (#10532)

* ignore trigger condtional uniques

* Have UniqueTriggerActivation only add the buildings of its unique

* (minor optimization) move where we find the free building

* Once again I forget about imports
This commit is contained in:
SeventhM
2023-11-22 13:59:53 -08:00
committed by GitHub
parent 3604d82fa9
commit a6ac9aa24d
2 changed files with 28 additions and 6 deletions

View File

@ -97,6 +97,7 @@ class CivConstructions : IsPartOfGameInfoSerialization {
private fun addFreeStatsBuildings() {
val statUniquesData = civInfo.getMatchingUniques(UniqueType.FreeStatBuildings)
.filter { !it.hasTriggerConditional() }
.groupBy { it.params[0] }
.mapKeys { Stat.valueOf(it.key) }
.mapValues { unique -> unique.value.sumOf { it.params[1].toInt() } }
@ -106,7 +107,7 @@ class CivConstructions : IsPartOfGameInfoSerialization {
}
}
private fun addFreeStatBuildings(stat: Stat, amount: Int) {
fun addFreeStatBuildings(stat: Stat, amount: Int) {
for (city in civInfo.cities.take(amount)) {
if (freeStatBuildingsProvided.contains(stat.name, city.id)) continue
val building = city.cityConstructions.cheapestStatBuilding(stat)
@ -120,6 +121,7 @@ class CivConstructions : IsPartOfGameInfoSerialization {
private fun addFreeSpecificBuildings() {
val buildingsUniquesData = civInfo.getMatchingUniques(UniqueType.FreeSpecificBuildings)
.filter { !it.hasTriggerConditional() }
.groupBy { it.params[0] }
.mapValues { unique -> unique.value.sumOf { it.params[1].toInt() } }
@ -129,7 +131,7 @@ class CivConstructions : IsPartOfGameInfoSerialization {
}
}
private fun addFreeBuildings(building: Building, amount: Int) {
fun addFreeBuildings(building: Building, amount: Int) {
for (city in civInfo.cities.take(amount)) {
if (freeSpecificBuildingsProvided.contains(building.name, city.id)
|| city.cityConstructions.containsBuildingOrEquivalent(building.name)) continue
@ -149,7 +151,8 @@ class CivConstructions : IsPartOfGameInfoSerialization {
for (city in civInfo.cities) {
val freeBuildingsFromCity = city.getMatchingLocalOnlyUniques(UniqueType.GainFreeBuildings, StateForConditionals.IgnoreConditionals)
val freeBuildingUniques = (freeBuildingsFromCiv + freeBuildingsFromCity)
.filter { city.matchesFilter(it.params[1]) && it.conditionalsApply(StateForConditionals(city.civ, city)) }
.filter { city.matchesFilter(it.params[1]) && it.conditionalsApply(StateForConditionals(city.civ, city))
&& !it.hasTriggerConditional() }
for (unique in freeBuildingUniques) {
val freeBuilding = city.civ.getEquivalentBuilding(unique.params[0])
city.cityConstructions.freeBuildingsProvidedFromThisCity.addToMapOfSets(city.id, freeBuilding.name)

View File

@ -20,6 +20,7 @@ import com.unciv.models.stats.Stat
import com.unciv.models.stats.Stats
import com.unciv.models.translations.fillPlaceholders
import com.unciv.models.translations.hasPlaceholderParameters
import com.unciv.ui.components.extensions.addToMapOfSets
import com.unciv.ui.components.MayaCalendar
import com.unciv.ui.screens.worldscreen.unit.actions.UnitActionsUpgrade
import kotlin.math.roundToInt
@ -664,10 +665,28 @@ object UniqueTriggerActivation {
return true
}
UniqueType.FreeStatBuildings, UniqueType.FreeSpecificBuildings,
UniqueType.GainFreeBuildings -> {
civInfo.civConstructions.tryAddFreeBuildings()
return true // not fully correct
val freeBuilding = civInfo.getEquivalentBuilding(unique.params[0])
val applicableCities =
if (unique.params[1] == "in this city") sequenceOf(city!!)
else civInfo.cities.asSequence().filter { it.matchesFilter(unique.params[1]) }
for (applicableCity in applicableCities) {
applicableCity.cityConstructions.freeBuildingsProvidedFromThisCity.addToMapOfSets(applicableCity.id, freeBuilding.name)
if (applicableCity.cityConstructions.containsBuildingOrEquivalent(freeBuilding.name)) continue
applicableCity.cityConstructions.constructionComplete(freeBuilding)
}
return true
}
UniqueType.FreeStatBuildings -> {
val stat = Stat.safeValueOf(unique.params[0]) ?: return false
civInfo.civConstructions.addFreeStatBuildings(stat, unique.params[1].toInt())
return true
}
UniqueType.FreeSpecificBuildings ->{
val building = ruleSet.buildings[unique.params[0]] ?: return false
civInfo.civConstructions.addFreeBuildings(building, unique.params[1].toInt())
return true
}
UniqueType.RemoveBuilding -> {