mirror of
https://github.com/yairm210/Unciv.git
synced 2025-03-12 10:59:55 +07:00
Likely fixed a bug where AI nukes could hit nations they had a peace treaty with (#5449)
* Likely fixed a bug where AI nukes could hit players they had a peace treaty with * Typefied blast radius unique
This commit is contained in:
parent
9fab1f6ee7
commit
a73b7b008f
@ -14,12 +14,12 @@ object BattleHelper {
|
||||
fun tryAttackNearbyEnemy(unit: MapUnit, stayOnTile: Boolean = false): Boolean {
|
||||
if (unit.hasUnique("Cannot attack")) return false
|
||||
val attackableEnemies = getAttackableEnemies(unit, unit.movement.getDistanceToTiles(), stayOnTile=stayOnTile)
|
||||
// Only take enemies we can fight without dying
|
||||
.filter {
|
||||
BattleDamage.calculateDamageToAttacker(MapUnitCombatant(unit),
|
||||
it.tileToAttackFrom,
|
||||
Battle.getMapCombatantOfTile(it.tileToAttack)!!) < unit.health
|
||||
}
|
||||
// Only take enemies we can fight without dying
|
||||
.filter {
|
||||
BattleDamage.calculateDamageToAttacker(MapUnitCombatant(unit),
|
||||
it.tileToAttackFrom,
|
||||
Battle.getMapCombatantOfTile(it.tileToAttack)!!) < unit.health
|
||||
}
|
||||
|
||||
val enemyTileToAttack = chooseAttackTarget(unit, attackableEnemies)
|
||||
|
||||
|
@ -331,7 +331,7 @@ object SpecificUnitAutomation {
|
||||
val tilesInRange = unit.currentTile.getTilesInDistance(unit.getRange())
|
||||
for (tile in tilesInRange) {
|
||||
// For now AI will only use nukes against cities because in all honesty that's the best use for them.
|
||||
if (tile.isCityCenter() && tile.getOwner()!!.isAtWarWith(unit.civInfo)) {
|
||||
if (tile.isCityCenter() && tile.getOwner()!!.isAtWarWith(unit.civInfo) && Battle.mayUseNuke(MapUnitCombatant(unit), tile)) {
|
||||
Battle.NUKE(MapUnitCombatant(unit), tile)
|
||||
return
|
||||
}
|
||||
|
@ -11,6 +11,7 @@ import com.unciv.logic.map.TileInfo
|
||||
import com.unciv.models.AttackableTile
|
||||
import com.unciv.models.UnitActionType
|
||||
import com.unciv.models.ruleset.unique.Unique
|
||||
import com.unciv.models.ruleset.unique.UniqueType
|
||||
import com.unciv.models.stats.Stat
|
||||
import com.unciv.models.stats.Stats
|
||||
import com.unciv.ui.utils.toPercent
|
||||
@ -538,6 +539,28 @@ object Battle {
|
||||
attacker.popupAlerts.add(PopupAlert(AlertType.Defeated, attackedCiv.civName))
|
||||
}
|
||||
}
|
||||
|
||||
fun mayUseNuke(nuke: MapUnitCombatant, targetTile: TileInfo): Boolean {
|
||||
val blastRadius =
|
||||
if (!nuke.unit.hasUnique(UniqueType.BlastRadius)) 2
|
||||
else nuke.unit.getMatchingUniques(UniqueType.BlastRadius).first().params[0].toInt()
|
||||
|
||||
var canNuke = true
|
||||
val attackerCiv = nuke.getCivInfo()
|
||||
for (tile in targetTile.getTilesInDistance(blastRadius)) {
|
||||
val defendingTileCiv = tile.getCity()?.civInfo
|
||||
if (defendingTileCiv != null && attackerCiv.knows(defendingTileCiv)) {
|
||||
canNuke = canNuke && attackerCiv.getDiplomacyManager(defendingTileCiv).canAttack()
|
||||
}
|
||||
|
||||
val defender = getMapCombatantOfTile(tile) ?: continue
|
||||
val defendingUnitCiv = defender.getCivInfo()
|
||||
if (attackerCiv.knows(defendingUnitCiv)) {
|
||||
canNuke = canNuke && attackerCiv.getDiplomacyManager(defendingUnitCiv).canAttack()
|
||||
}
|
||||
}
|
||||
return canNuke
|
||||
}
|
||||
|
||||
@Suppress("FunctionName") // Yes we want this name to stand out
|
||||
fun NUKE(attacker: MapUnitCombatant, targetTile: TileInfo) {
|
||||
@ -553,8 +576,8 @@ object Battle {
|
||||
}
|
||||
|
||||
val blastRadius =
|
||||
if (!attacker.unit.hasUnique("Blast radius []")) 2
|
||||
else attacker.unit.getMatchingUniques("Blast radius []").first().params[0].toInt()
|
||||
if (!attacker.unit.hasUnique(UniqueType.BlastRadius)) 2
|
||||
else attacker.unit.getMatchingUniques(UniqueType.BlastRadius).first().params[0].toInt()
|
||||
|
||||
val strength = when {
|
||||
(attacker.unit.hasUnique("Nuclear weapon of Strength []")) ->
|
||||
|
@ -187,6 +187,7 @@ enum class UniqueType(val text:String, vararg targets: UniqueTarget) {
|
||||
@Deprecated("As of 3.17.5", ReplaceWith("[amount]% Spread Religion Strength <for [mapUnitFilter] units>"), DeprecationLevel.WARNING)
|
||||
SpreadReligionStrengthUnits("[amount]% Spread Religion Strength for [mapUnitFilter] units", UniqueTarget.Global),
|
||||
|
||||
BlastRadius("Blast radius [amount]", UniqueTarget.Unit),
|
||||
|
||||
CarryAirUnits("Can carry [amount] [mapUnitFilter] units", UniqueTarget.Unit),
|
||||
CarryExtraAirUnits("Can carry [amount] extra [mapUnitFilter] units", UniqueTarget.Unit),
|
||||
|
@ -13,6 +13,7 @@ import com.unciv.logic.automation.UnitAutomation
|
||||
import com.unciv.logic.battle.*
|
||||
import com.unciv.logic.map.TileInfo
|
||||
import com.unciv.models.AttackableTile
|
||||
import com.unciv.models.ruleset.unique.UniqueType
|
||||
import com.unciv.models.translations.tr
|
||||
import com.unciv.ui.utils.*
|
||||
import com.unciv.ui.worldscreen.WorldScreen
|
||||
@ -228,31 +229,17 @@ class BattleTable(val worldScreen: WorldScreen): Table() {
|
||||
attackerNameWrapper.add(UnitGroup(attacker.unit,25f)).padRight(5f)
|
||||
attackerNameWrapper.add(attackerLabel)
|
||||
add(attackerNameWrapper)
|
||||
var canNuke = true
|
||||
val defenderNameWrapper = Table()
|
||||
|
||||
val canNuke = Battle.mayUseNuke(attacker, targetTile)
|
||||
|
||||
val blastRadius =
|
||||
if (!attacker.unit.hasUnique("Blast radius []")) 2
|
||||
else attacker.unit.getMatchingUniques("Blast radius []").first().params[0].toInt()
|
||||
if (!attacker.unit.hasUnique(UniqueType.BlastRadius)) 2
|
||||
else attacker.unit.getMatchingUniques(UniqueType.BlastRadius).first().params[0].toInt()
|
||||
|
||||
val defenderNameWrapper = Table()
|
||||
for (tile in targetTile.getTilesInDistance(blastRadius)) {
|
||||
|
||||
//To make sure we dont nuke civilisations we cant declare war with
|
||||
val attackerCiv = attacker.getCivInfo()
|
||||
val defenderTileCiv = tile.getCity()?.civInfo
|
||||
|
||||
if(defenderTileCiv != null && defenderTileCiv.knows(attackerCiv)) {
|
||||
val canAttackDefenderCiv = attackerCiv.getDiplomacyManager(defenderTileCiv).canAttack()
|
||||
canNuke = canNuke && canAttackDefenderCiv
|
||||
}
|
||||
val defender = tryGetDefenderAtTile(tile, true) ?: continue
|
||||
|
||||
val defenderUnitCiv = defender.getCivInfo()
|
||||
|
||||
if( defenderUnitCiv.knows(attackerCiv))
|
||||
{
|
||||
val canAttackDefenderUnitCiv = attackerCiv.getDiplomacyManager(defenderUnitCiv).canAttack()
|
||||
canNuke = canNuke && canAttackDefenderUnitCiv
|
||||
}
|
||||
|
||||
|
||||
val defenderLabel = Label(defender.getName().tr(), skin)
|
||||
when (defender) {
|
||||
is MapUnitCombatant ->
|
||||
@ -271,7 +258,7 @@ class BattleTable(val worldScreen: WorldScreen): Table() {
|
||||
addSeparator().pad(0f)
|
||||
row().pad(5f)
|
||||
|
||||
val attackButton = "NUKE".toTextButton().apply { color= Color.RED }
|
||||
val attackButton = "NUKE".toTextButton().apply { color = Color.RED }
|
||||
|
||||
val canReach = attacker.unit.currentTile.getTilesInDistance(attacker.unit.getRange()).contains(targetTile)
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user