mirror of
https://github.com/yairm210/Unciv.git
synced 2025-09-24 20:31:51 -04:00
Bug 1/2 of #13451 - 'connect road' acknowledges availability uniques on road/railroad
This commit is contained in:
parent
41fd4ff649
commit
b01e1df24d
@ -0,0 +1,69 @@
|
||||
package com.unciv.logic.civilization.managers
|
||||
|
||||
import com.unciv.logic.civilization.Civilization
|
||||
import com.unciv.logic.map.tile.ImprovementBuildingProblem
|
||||
import com.unciv.logic.map.tile.Tile
|
||||
import com.unciv.models.ruleset.tile.TileImprovement
|
||||
import com.unciv.models.ruleset.unique.StateForConditionals
|
||||
import com.unciv.models.ruleset.unique.UniqueType
|
||||
|
||||
object ImprovementFunctions {
|
||||
|
||||
/** Generates a sequence of reasons that prevent building given [improvement].
|
||||
* If the sequence is empty, improvement can be built immediately.
|
||||
*/
|
||||
fun getImprovementBuildingProblems(improvement: TileImprovement, civInfo: Civilization, tile: Tile? = null): Sequence<ImprovementBuildingProblem> = sequence {
|
||||
val stateForConditionals = StateForConditionals(civInfo, tile = tile)
|
||||
|
||||
if (improvement.uniqueTo != null && !civInfo.matchesFilter(improvement.uniqueTo!!))
|
||||
yield(ImprovementBuildingProblem.WrongCiv)
|
||||
if (civInfo.cache.uniqueImprovements.any { it.replaces == improvement.name })
|
||||
yield(ImprovementBuildingProblem.Replaced)
|
||||
if (improvement.techRequired != null && !civInfo.tech.isResearched(improvement.techRequired!!))
|
||||
yield(ImprovementBuildingProblem.MissingTech)
|
||||
if (improvement.getMatchingUniques(UniqueType.Unbuildable, StateForConditionals.IgnoreConditionals)
|
||||
.any { it.modifiers.isEmpty() })
|
||||
yield(ImprovementBuildingProblem.Unbuildable)
|
||||
else if (improvement.hasUnique(UniqueType.Unbuildable, stateForConditionals))
|
||||
yield(ImprovementBuildingProblem.ConditionallyUnbuildable)
|
||||
|
||||
if (improvement.hasUnique(UniqueType.Unavailable, stateForConditionals))
|
||||
yield(ImprovementBuildingProblem.ConditionallyUnbuildable)
|
||||
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.OnlyAvailable, StateForConditionals.IgnoreConditionals)
|
||||
.any { !it.conditionalsApply(stateForConditionals) })
|
||||
yield(ImprovementBuildingProblem.UnmetConditional)
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.ObsoleteWith, stateForConditionals)
|
||||
.any { civInfo.tech.isResearched(it.params[0]) })
|
||||
yield(ImprovementBuildingProblem.Obsolete)
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.ConsumesResources, stateForConditionals)
|
||||
.any { civInfo.getResourceAmount(it.params[1]) < it.params[0].toInt() })
|
||||
yield(ImprovementBuildingProblem.MissingResources)
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.CostsResources)
|
||||
.any { civInfo.getResourceAmount(it.params[1]) < it.params[0].toInt() *
|
||||
(if (it.isModifiedByGameSpeed()) civInfo.gameInfo.speed.modifier else 1f) })
|
||||
yield(ImprovementBuildingProblem.MissingResources)
|
||||
|
||||
if (tile != null){
|
||||
if (tile.getOwner() != civInfo && !improvement.hasUnique(UniqueType.CanBuildOutsideBorders, stateForConditionals)) {
|
||||
if (!improvement.hasUnique(UniqueType.CanBuildJustOutsideBorders, stateForConditionals))
|
||||
yield(ImprovementBuildingProblem.OutsideBorders)
|
||||
else if (tile.neighbors.none { it.getOwner() == civInfo })
|
||||
yield(ImprovementBuildingProblem.NotJustOutsideBorders)
|
||||
}
|
||||
val knownFeatureRemovals = tile.ruleset.nonRoadTileRemovals
|
||||
.filter { rulesetImprovement ->
|
||||
rulesetImprovement.techRequired == null || civInfo.tech.isResearched(rulesetImprovement.techRequired!!)
|
||||
}
|
||||
|
||||
if (!tile.improvementFunctions.canImprovementBeBuiltHere(improvement, tile.hasViewableResource(civInfo), knownFeatureRemovals, stateForConditionals))
|
||||
// There are way too many conditions in that functions, besides, they are not interesting
|
||||
// at least for the current usecases. Improve if really needed.
|
||||
yield(ImprovementBuildingProblem.Other)
|
||||
}
|
||||
}
|
||||
}
|
@ -537,11 +537,13 @@ class TechManager : IsPartOfGameInfoSerialization {
|
||||
|
||||
fun getBestRoadAvailable(): RoadStatus {
|
||||
val railroadImprovement = getRuleset().railroadImprovement // May not exist in mods
|
||||
if (railroadImprovement != null && (railroadImprovement.techRequired == null || isResearched(railroadImprovement.techRequired!!)))
|
||||
if (railroadImprovement != null && (railroadImprovement.techRequired == null || isResearched(railroadImprovement.techRequired!!))
|
||||
&& ImprovementFunctions.getImprovementBuildingProblems(railroadImprovement, civInfo).none())
|
||||
return RoadStatus.Railroad
|
||||
|
||||
val roadImprovement = getRuleset().roadImprovement
|
||||
if (roadImprovement != null && (roadImprovement.techRequired == null || isResearched(roadImprovement.techRequired!!)))
|
||||
if (roadImprovement != null && (roadImprovement.techRequired == null || isResearched(roadImprovement.techRequired!!))
|
||||
&& ImprovementFunctions.getImprovementBuildingProblems(roadImprovement, civInfo).none())
|
||||
return RoadStatus.Road
|
||||
|
||||
return RoadStatus.None
|
||||
|
@ -5,6 +5,7 @@ import com.unciv.logic.civilization.Civilization
|
||||
import com.unciv.logic.civilization.LocationAction
|
||||
import com.unciv.logic.civilization.NotificationCategory
|
||||
import com.unciv.logic.civilization.NotificationIcon
|
||||
import com.unciv.logic.civilization.managers.ImprovementFunctions
|
||||
import com.unciv.logic.map.mapunit.MapUnit
|
||||
import com.unciv.models.ruleset.tile.TileImprovement
|
||||
import com.unciv.models.ruleset.unique.StateForConditionals
|
||||
@ -41,58 +42,8 @@ class TileImprovementFunctions(val tile: Tile) {
|
||||
/** Generates a sequence of reasons that prevent building given [improvement].
|
||||
* If the sequence is empty, improvement can be built immediately.
|
||||
*/
|
||||
fun getImprovementBuildingProblems(improvement: TileImprovement, civInfo: Civilization): Sequence<ImprovementBuildingProblem> = sequence {
|
||||
val stateForConditionals = StateForConditionals(civInfo, tile = tile)
|
||||
|
||||
if (improvement.uniqueTo != null && !civInfo.matchesFilter(improvement.uniqueTo!!))
|
||||
yield(ImprovementBuildingProblem.WrongCiv)
|
||||
if (civInfo.cache.uniqueImprovements.any { it.replaces == improvement.name })
|
||||
yield(ImprovementBuildingProblem.Replaced)
|
||||
if (improvement.techRequired != null && !civInfo.tech.isResearched(improvement.techRequired!!))
|
||||
yield(ImprovementBuildingProblem.MissingTech)
|
||||
if (improvement.getMatchingUniques(UniqueType.Unbuildable, StateForConditionals.IgnoreConditionals)
|
||||
.any { it.modifiers.isEmpty() })
|
||||
yield(ImprovementBuildingProblem.Unbuildable)
|
||||
else if (improvement.hasUnique(UniqueType.Unbuildable, stateForConditionals))
|
||||
yield(ImprovementBuildingProblem.ConditionallyUnbuildable)
|
||||
|
||||
if (improvement.hasUnique(UniqueType.Unavailable, stateForConditionals))
|
||||
yield(ImprovementBuildingProblem.ConditionallyUnbuildable)
|
||||
|
||||
if (tile.getOwner() != civInfo && !improvement.hasUnique(UniqueType.CanBuildOutsideBorders, stateForConditionals)) {
|
||||
if (!improvement.hasUnique(UniqueType.CanBuildJustOutsideBorders, stateForConditionals))
|
||||
yield(ImprovementBuildingProblem.OutsideBorders)
|
||||
else if (tile.neighbors.none { it.getOwner() == civInfo })
|
||||
yield(ImprovementBuildingProblem.NotJustOutsideBorders)
|
||||
}
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.OnlyAvailable, StateForConditionals.IgnoreConditionals)
|
||||
.any { !it.conditionalsApply(stateForConditionals) })
|
||||
yield(ImprovementBuildingProblem.UnmetConditional)
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.ObsoleteWith, stateForConditionals)
|
||||
.any { civInfo.tech.isResearched(it.params[0]) })
|
||||
yield(ImprovementBuildingProblem.Obsolete)
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.ConsumesResources, stateForConditionals)
|
||||
.any { civInfo.getResourceAmount(it.params[1]) < it.params[0].toInt() })
|
||||
yield(ImprovementBuildingProblem.MissingResources)
|
||||
|
||||
if (improvement.getMatchingUniques(UniqueType.CostsResources)
|
||||
.any { civInfo.getResourceAmount(it.params[1]) < it.params[0].toInt() *
|
||||
(if (it.isModifiedByGameSpeed()) civInfo.gameInfo.speed.modifier else 1f) })
|
||||
yield(ImprovementBuildingProblem.MissingResources)
|
||||
|
||||
val knownFeatureRemovals = tile.ruleset.nonRoadTileRemovals
|
||||
.filter { rulesetImprovement ->
|
||||
rulesetImprovement.techRequired == null || civInfo.tech.isResearched(rulesetImprovement.techRequired!!)
|
||||
}
|
||||
|
||||
if (!canImprovementBeBuiltHere(improvement, tile.hasViewableResource(civInfo), knownFeatureRemovals, stateForConditionals))
|
||||
// There are way too many conditions in that functions, besides, they are not interesting
|
||||
// at least for the current usecases. Improve if really needed.
|
||||
yield(ImprovementBuildingProblem.Other)
|
||||
}
|
||||
fun getImprovementBuildingProblems(improvement: TileImprovement, civInfo: Civilization): Sequence<ImprovementBuildingProblem> =
|
||||
ImprovementFunctions.getImprovementBuildingProblems(improvement, civInfo, tile)
|
||||
|
||||
/** Without regards to what CivInfo it is (so no tech requirement check), a lot of the checks are just for the improvement on the tile.
|
||||
* Doubles as a check for the map editor.
|
||||
|
Loading…
x
Reference in New Issue
Block a user