mirror of
https://github.com/infinitefusion/infinitefusion-e18.git
synced 2025-12-09 14:14:59 +00:00
Some more AI function code rewrites
This commit is contained in:
@@ -138,8 +138,16 @@ end
|
||||
# user's Attack and Defense by 1 stage each. (Curse)
|
||||
#===============================================================================
|
||||
class Battle::Move::CurseTargetOrLowerUserSpd1RaiseUserAtkDef1 < Battle::Move
|
||||
attr_reader :statUp, :statDown
|
||||
|
||||
def ignoresSubstitute?(user); return true; end
|
||||
|
||||
def initialize(battle, move)
|
||||
super
|
||||
@statUp = [:ATTACK, 1, :DEFENSE, 1]
|
||||
@statDown = [:SPEED, 1]
|
||||
end
|
||||
|
||||
def pbTarget(user)
|
||||
if user.pbHasType?(:GHOST)
|
||||
ghost_target = (Settings::MECHANICS_GENERATION >= 8) ? :RandomNearFoe : :NearFoe
|
||||
@@ -150,9 +158,18 @@ class Battle::Move::CurseTargetOrLowerUserSpd1RaiseUserAtkDef1 < Battle::Move
|
||||
|
||||
def pbMoveFailed?(user, targets)
|
||||
return false if user.pbHasType?(:GHOST)
|
||||
if !user.pbCanLowerStatStage?(:SPEED, user, self) &&
|
||||
!user.pbCanRaiseStatStage?(:ATTACK, user, self) &&
|
||||
!user.pbCanRaiseStatStage?(:DEFENSE, user, self)
|
||||
failed = true
|
||||
(@statUp.length / 2).times do |i|
|
||||
next if !user.pbCanRaiseStatStage?(@statUp[i * 2], user, self)
|
||||
failed = false
|
||||
break
|
||||
end
|
||||
(@statDown.length / 2).times do |i|
|
||||
next if !user.pbCanLowerStatStage?(@statDown[i * 2], user, self)
|
||||
failed = false
|
||||
break
|
||||
end
|
||||
if failed
|
||||
@battle.pbDisplay(_INTL("But it failed!"))
|
||||
return true
|
||||
end
|
||||
@@ -170,15 +187,19 @@ class Battle::Move::CurseTargetOrLowerUserSpd1RaiseUserAtkDef1 < Battle::Move
|
||||
def pbEffectGeneral(user)
|
||||
return if user.pbHasType?(:GHOST)
|
||||
# Non-Ghost effect
|
||||
if user.pbCanLowerStatStage?(:SPEED, user, self)
|
||||
user.pbLowerStatStage(:SPEED, 1, user)
|
||||
showAnim = true
|
||||
(@statDown.length / 2).times do |i|
|
||||
next if !user.pbCanLowerStatStage?(@statDown[i * 2], user, self)
|
||||
if user.pbLowerStatStage(@statDown[i * 2], @statDown[(i * 2) + 1], user, showAnim)
|
||||
showAnim = false
|
||||
end
|
||||
end
|
||||
showAnim = true
|
||||
if user.pbCanRaiseStatStage?(:ATTACK, user, self)
|
||||
showAnim = false if user.pbRaiseStatStage(:ATTACK, 1, user, showAnim)
|
||||
end
|
||||
if user.pbCanRaiseStatStage?(:DEFENSE, user, self)
|
||||
user.pbRaiseStatStage(:DEFENSE, 1, user, showAnim)
|
||||
(@statUp.length / 2).times do |i|
|
||||
next if !user.pbCanRaiseStatStage?(@statUp[i * 2], user, self)
|
||||
if user.pbRaiseStatStage(@statUp[i * 2], @statUp[(i * 2) + 1], user, showAnim)
|
||||
showAnim = false
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
@@ -36,6 +36,10 @@ class Battle::AI
|
||||
battler.turnCount && battler.turnCount >= 5
|
||||
shouldSwitch = true
|
||||
end
|
||||
# Pokémon is about to faint because of Perish Song
|
||||
if !shouldSwitch && battler.effects[PBEffects::PerishSong] == 1
|
||||
shouldSwitch = true
|
||||
end
|
||||
# Pokémon is Perish Songed and has Baton Pass
|
||||
if @trainer.high_skill? && battler.effects[PBEffects::PerishSong] == 1
|
||||
battler.eachMoveWithIndex do |m, i|
|
||||
@@ -87,15 +91,11 @@ class Battle::AI
|
||||
shouldSwitch = true
|
||||
end
|
||||
end
|
||||
# Pokémon is about to faint because of Perish Song
|
||||
if !shouldSwitch && battler.effects[PBEffects::PerishSong] == 1
|
||||
shouldSwitch = true
|
||||
end
|
||||
if shouldSwitch
|
||||
list = []
|
||||
idxPartyStart, idxPartyEnd = @battle.pbTeamIndexRangeFromBattlerIndex(battler.index)
|
||||
@battle.pbParty(battler.index).each_with_index do |pkmn, i|
|
||||
next if i == idxPartyEnd - 1 # Don't choose to switch in ace
|
||||
next if @trainer.has_skill_flag?("ReserveLastPokemon") && i == idxPartyEnd - 1 # Don't choose to switch in ace
|
||||
next if !@battle.pbCanSwitch?(battler.index, i)
|
||||
# If perish count is 1, it may be worth it to switch
|
||||
# even with Spikes, since Perish Song's effect will end
|
||||
@@ -152,7 +152,9 @@ class Battle::AI
|
||||
enemies = []
|
||||
idxPartyStart, idxPartyEnd = @battle.pbTeamIndexRangeFromBattlerIndex(idxBattler)
|
||||
party.each_with_index do |_p, i|
|
||||
next if i == idxPartyEnd - 1 && enemies.length > 0 # Ignore ace if possible
|
||||
if @trainer.has_skill_flag?("ReserveLastPokemon")
|
||||
next if i == idxPartyEnd - 1 && enemies.length > 0 # Ignore ace if possible
|
||||
end
|
||||
enemies.push(i) if @battle.pbCanSwitchLax?(idxBattler, i)
|
||||
end
|
||||
return -1 if enemies.length == 0
|
||||
|
||||
@@ -246,9 +246,9 @@ class Battle::AI
|
||||
score -= 20
|
||||
else
|
||||
has_special_moves = @user.check_for_move { |m| m.specialMove?(m.type) }
|
||||
inc = (has_special_moves) ? 5 : 10
|
||||
score += inc * (2 - old_stage) * inc_mult
|
||||
score += 4 * inc_mult if @user.hp == @user.totalhp
|
||||
inc = (has_special_moves) ? 10 : 20
|
||||
score += inc * inc_mult
|
||||
score += 8 * inc_mult if @user.hp == @user.totalhp
|
||||
end
|
||||
|
||||
when :DEFENSE
|
||||
@@ -256,8 +256,8 @@ class Battle::AI
|
||||
if old_stage >= 2
|
||||
score -= 20
|
||||
else
|
||||
score += 5 * (2 - old_stage) * inc_mult
|
||||
score += 4 * inc_mult if @user.hp == @user.totalhp
|
||||
score += 10 * inc_mult
|
||||
score += 8 * inc_mult if @user.hp == @user.totalhp
|
||||
end
|
||||
|
||||
when :SPECIAL_ATTACK
|
||||
@@ -269,9 +269,9 @@ class Battle::AI
|
||||
has_physical_moves = @user.check_for_move { |m| m.physicalMove?(m.type) &&
|
||||
m.function != "UseUserDefenseInsteadOfUserAttack" &&
|
||||
m.function != "UseTargetAttackInsteadOfUserAttack" }
|
||||
inc = (has_physical_moves) ? 5 : 10
|
||||
score += inc * (2 - old_stage) * inc_mult
|
||||
score += 4 * inc_mult if @user.hp == @user.totalhp
|
||||
inc = (has_physical_moves) ? 10 : 20
|
||||
score += inc * inc_mult
|
||||
score += 8 * inc_mult if @user.hp == @user.totalhp
|
||||
end
|
||||
|
||||
when :SPECIAL_DEFENSE
|
||||
@@ -279,8 +279,8 @@ class Battle::AI
|
||||
if old_stage >= 2
|
||||
score -= 20
|
||||
else
|
||||
score += 5 * (2 - old_stage) * inc_mult
|
||||
score += 4 * inc_mult if @user.hp == @user.totalhp
|
||||
score += 10 * inc_mult
|
||||
score += 8 * inc_mult if @user.hp == @user.totalhp
|
||||
end
|
||||
|
||||
when :SPEED
|
||||
@@ -312,8 +312,8 @@ class Battle::AI
|
||||
end
|
||||
min_accuracy = min_accuracy * stage_mul[old_stage] / stage_div[old_stage]
|
||||
if min_accuracy < 90
|
||||
score += 5 * (2 - old_stage) * inc_mult
|
||||
score += 4 * inc_mult if @user.hp == @user.totalhp
|
||||
score += 10 * inc_mult
|
||||
score += 8 * inc_mult if @user.hp == @user.totalhp
|
||||
end
|
||||
end
|
||||
|
||||
@@ -330,8 +330,8 @@ class Battle::AI
|
||||
if old_stage >= 2
|
||||
score -= 20
|
||||
else
|
||||
score += 5 * (2 - old_stage) * inc_mult
|
||||
score += 4 * inc_mult if @user.hp == @user.totalhp
|
||||
score += 10 * (2 - old_stage) * inc_mult
|
||||
score += 8 * inc_mult if @user.hp == @user.totalhp
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
@@ -404,22 +404,27 @@ Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("StartDamageTargetEachTur
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("StartLeechSeedTarget",
|
||||
proc { |move, user, target, ai, battle|
|
||||
next true if target.effects[PBEffects::LeechSeed] >= 0
|
||||
next true if target.has_type?(:GRASS)
|
||||
next true if target.has_type?(:GRASS) || !target.battler.takesIndirectDamage?
|
||||
}
|
||||
)
|
||||
Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("StartLeechSeedTarget",
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
# Prefer early on
|
||||
score += 10 if user.turnCount < 2
|
||||
if ai.trainer.medium_skill?
|
||||
if !user.check_for_move { |m| m.damagingMove? }
|
||||
score += 20
|
||||
end
|
||||
score -= 20 if target.has_active_ability?([:LIQUIDOOZE]) || !target.battler.takesIndirectDamage?
|
||||
# Prefer if the user has no damaging moves
|
||||
score += 20 if !user.check_for_move { |m| m.damagingMove? }
|
||||
# Prefer if the target can't switch out to remove its seeding
|
||||
score += 10 if !battle.pbCanChooseNonActive?(target.index)
|
||||
# Don't prefer if the leeched HP will hurt the user
|
||||
score -= 20 if target.has_active_ability?([:LIQUIDOOZE])
|
||||
end
|
||||
if ai.trainer.high_skill?
|
||||
# Prefer if user can stall while damage is dealt
|
||||
if user.check_for_move { |m| m.is_a?(Battle::Move::ProtectMove) }
|
||||
score += 15
|
||||
end
|
||||
# Don't prefer if target can remove the seed
|
||||
if target.check_for_move { |m| m.is_a?(Battle::Move::RemoveUserBindingAndEntryHazards) }
|
||||
score -= 15
|
||||
end
|
||||
|
||||
@@ -1,18 +1,32 @@
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveEffectScore.add("RedirectAllMovesToUser",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Useless if there is no ally to redirect attacks from
|
||||
next Battle::AI::MOVE_USELESS_SCORE if user.battler.allAllies.length == 0
|
||||
# Prefer if ally is at low HP and user is at high HP
|
||||
if user.hp > user.totalhp * 2 / 3
|
||||
ai.each_ally(user.index) do |b, i|
|
||||
score += 10 if b.hp <= b.totalhp / 3
|
||||
end
|
||||
end
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("RedirectAllMovesToTarget",
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
next Battle::AI::MOVE_USELESS_SCORE if user.battler.allAllies.length == 0
|
||||
if target.opposes?(user)
|
||||
# Useless if target is a foe but there is only one foe
|
||||
next Battle::AI::MOVE_USELESS_SCORE if target.battler.allAllies.length == 0
|
||||
# Useless if there is no ally to attack the spotlighted foe
|
||||
next Battle::AI::MOVE_USELESS_SCORE if user.battler.allAllies.length == 0
|
||||
end
|
||||
# Generaly don't prefer this move, as it's a waste of the user's turn
|
||||
next score - 15
|
||||
}
|
||||
)
|
||||
|
||||
@@ -49,7 +63,7 @@ Battle::AI::Handlers::MoveBasePower.add("RandomlyDamageOrHealTarget",
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("HealAllyOrDamageFoe",
|
||||
proc { |move, user, target, ai, battle|
|
||||
@@ -59,8 +73,12 @@ Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("HealAllyOrDamageFoe",
|
||||
Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("HealAllyOrDamageFoe",
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
if !target.opposes?(user)
|
||||
score += 50
|
||||
score -= target.hp * 100 / target.totalhp
|
||||
# Consider how much HP will be restored
|
||||
if target.hp >= target.totalhp * 0.5
|
||||
score -= 10
|
||||
else
|
||||
score += 20 * (target.totalhp - target.hp) / target.totalhp
|
||||
end
|
||||
end
|
||||
next score
|
||||
}
|
||||
@@ -72,15 +90,26 @@ Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("HealAllyOrDamageFoe",
|
||||
Battle::AI::Handlers::MoveFailureCheck.add("CurseTargetOrLowerUserSpd1RaiseUserAtkDef1",
|
||||
proc { |move, user, ai, battle|
|
||||
if !user.has_type?(:GHOST)
|
||||
next true if !user.battler.pbCanLowerStatStage?(:SPEED, user.battler, move.move) &&
|
||||
!user.battler.pbCanRaiseStatStage?(:ATTACK, user.battler, move.move) &&
|
||||
!user.battler.pbCanRaiseStatStage?(:DEFENSE, user.battler, move.move)
|
||||
will_fail = true
|
||||
(move.move.statUp.length / 2).times do |i|
|
||||
next if !user.battler.pbCanRaiseStatStage?(move.move.statUp[i * 2], user.battler, move.move)
|
||||
will_fail = false
|
||||
break
|
||||
end
|
||||
(move.move.statDown.length / 2).times do |i|
|
||||
next if !user.battler.pbCanLowerStatStage?(move.move.statDown[i * 2], user.battler, move.move)
|
||||
will_fail = false
|
||||
break
|
||||
end
|
||||
next will_fail
|
||||
end
|
||||
}
|
||||
)
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("CurseTargetOrLowerUserSpd1RaiseUserAtkDef1",
|
||||
proc { |move, user, target, ai, battle|
|
||||
next true if user.has_type?(:GHOST) && target.effects[PBEffects::Curse]
|
||||
if user.has_type?(:GHOST)
|
||||
next true if target.effects[PBEffects::Curse] || !target.battler.takesIndirectDamage?
|
||||
end
|
||||
}
|
||||
)
|
||||
Battle::AI::Handlers::MoveEffectScore.add("CurseTargetOrLowerUserSpd1RaiseUserAtkDef1",
|
||||
@@ -96,12 +125,20 @@ Battle::AI::Handlers::MoveEffectScore.add("CurseTargetOrLowerUserSpd1RaiseUserAt
|
||||
Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("CurseTargetOrLowerUserSpd1RaiseUserAtkDef1",
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
next score if !user.has_type?(:GHOST)
|
||||
if user.hp <= user.totalhp / 2
|
||||
if battle.pbAbleNonActiveCount(user.idxOwnSide) == 0
|
||||
score -= 90
|
||||
else
|
||||
score -= 50
|
||||
score -= 30 if battle.switchStyle
|
||||
# Don't prefer if user will faint because of using this move
|
||||
next Battle::AI::MOVE_USELESS_SCORE if user.hp <= user.totalhp / 2
|
||||
# Prefer early on
|
||||
score += 10 if user.turnCount < 2
|
||||
if ai.trainer.medium_skill?
|
||||
# Prefer if the user has no damaging moves
|
||||
score += 20 if !user.check_for_move { |m| m.damagingMove? }
|
||||
# Prefer if the target can't switch out to remove its curse
|
||||
score += 10 if !battle.pbCanChooseNonActive?(target.index)
|
||||
end
|
||||
if ai.trainer.high_skill?
|
||||
# Prefer if user can stall while damage is dealt
|
||||
if user.check_for_move { |m| m.is_a?(Battle::Move::ProtectMove) }
|
||||
score += 15
|
||||
end
|
||||
end
|
||||
next score
|
||||
@@ -144,14 +181,30 @@ Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("TargetNextFireMoveDamage
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
# DoublePowerAfterFusionFlare
|
||||
Battle::AI::Handlers::MoveEffectScore.add("DoublePowerAfterFusionFlare",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Prefer if an ally knows Fusion Flare
|
||||
ai.each_ally(user.index) do |b, i|
|
||||
score += 10 if b.check_for_move { |m| m.function == "DoublePowerAfterFusionBolt" }
|
||||
end
|
||||
next score
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
# DoublePowerAfterFusionBolt
|
||||
Battle::AI::Handlers::MoveEffectScore.add("DoublePowerAfterFusionBolt",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Prefer if an ally knows Fusion Bolt
|
||||
ai.each_ally(user.index) do |b, i|
|
||||
score += 10 if b.check_for_move { |m| m.function == "DoublePowerAfterFusionFlare" }
|
||||
end
|
||||
next score
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
@@ -287,19 +340,43 @@ Battle::AI::Handlers::MoveEffectScore.add("HealUserDependingOnUserStockpile",
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
# GrassPledge
|
||||
Battle::AI::Handlers::MoveEffectScore.add("GrassPledge",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Prefer if an ally knows a different Pledge move
|
||||
ai.each_ally(user.index) do |b, i|
|
||||
score += 10 if b.check_for_move { |m| ["FirePledge", "WaterPledge"].include?(m.function) }
|
||||
end
|
||||
next score
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
# FirePledge
|
||||
Battle::AI::Handlers::MoveEffectScore.add("FirePledge",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Prefer if an ally knows a different Pledge move
|
||||
ai.each_ally(user.index) do |b, i|
|
||||
score += 10 if b.check_for_move { |m| ["GrassPledge", "WaterPledge"].include?(m.function) }
|
||||
end
|
||||
next score
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
# WaterPledge
|
||||
Battle::AI::Handlers::MoveEffectScore.add("WaterPledge",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Prefer if an ally knows a different Pledge move
|
||||
ai.each_ally(user.index) do |b, i|
|
||||
score += 10 if b.check_for_move { |m| ["GrassPledge", "FirePledge"].include?(m.function) }
|
||||
end
|
||||
next score
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
@@ -392,29 +469,36 @@ Battle::AI::Handlers::MoveFailureCheck.add("UseRandomUserMoveIfAsleep",
|
||||
# StealAndUseBeneficialStatusMove
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("ReplaceMoveThisBattleWithTargetLastMoveUsed",
|
||||
proc { |move, user, target, ai, battle|
|
||||
next true if user.effects[PBEffects::Transform] || user.battler.pbHasMove?(move.id)
|
||||
last_move_data = GameData::Move.try_get(target.battler.lastRegularMoveUsed)
|
||||
next true if !last_move_data ||
|
||||
user.battler.pbHasMove?(target.battler.lastRegularMoveUsed) ||
|
||||
move.move.moveBlacklist.include?(last_move_data.function_code) ||
|
||||
last_move_data.type == :SHADOW
|
||||
next true if user.effects[PBEffects::Transform] || !user.battler.pbHasMove?(move.id)
|
||||
if user.faster_than?(target)
|
||||
last_move_data = GameData::Move.try_get(target.battler.lastRegularMoveUsed)
|
||||
next true if !last_move_data ||
|
||||
user.battler.pbHasMove?(target.battler.lastRegularMoveUsed) ||
|
||||
move.move.moveBlacklist.include?(last_move_data.function_code) ||
|
||||
last_move_data.type == :SHADOW
|
||||
end
|
||||
}
|
||||
)
|
||||
Battle::AI::Handlers::MoveEffectScore.add("ReplaceMoveThisBattleWithTargetLastMoveUsed",
|
||||
proc { |score, move, user, ai, battle|
|
||||
# Generally don't prefer, as this wastes the user's turn just to gain a move
|
||||
# of unknown utility
|
||||
score -= 8
|
||||
# Slightly prefer if this move will definitely succeed, just for the sake of
|
||||
# getting rid of this move
|
||||
score += 5 if user.faster_than?(target)
|
||||
next score
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("ReplaceMoveWithTargetLastMoveUsed",
|
||||
proc { |move, user, target, ai, battle|
|
||||
next true if user.effects[PBEffects::Transform] || !user.battler.pbHasMove?(move.id)
|
||||
last_move_data = GameData::Move.try_get(target.battler.lastRegularMoveUsed)
|
||||
next true if !last_move_data ||
|
||||
user.battler.pbHasMove?(target.battler.lastRegularMoveUsed) ||
|
||||
move.move.moveBlacklist.include?(last_move_data.function_code) ||
|
||||
last_move_data.type == :SHADOW
|
||||
}
|
||||
)
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.copy("ReplaceMoveThisBattleWithTargetLastMoveUsed",
|
||||
"ReplaceMoveWithTargetLastMoveUsed")
|
||||
Battle::AI::Handlers::MoveEffectScore.copy("ReplaceMoveThisBattleWithTargetLastMoveUsed",
|
||||
"ReplaceMoveWithTargetLastMoveUsed")
|
||||
|
||||
@@ -22,8 +22,8 @@ Battle::AI::Handlers::MoveFailureCheck.add("SwitchOutUserStatusMove",
|
||||
Battle::AI::Handlers::MoveEffectScore.add("SwitchOutUserStatusMove",
|
||||
proc { |score, move, user, ai, battle|
|
||||
next score + 10 if user.wild?
|
||||
if battle.pbTeamAbleNonActiveCount(user.index) == 1 # Don't switch in ace
|
||||
score -= 60
|
||||
if ai.trainer.has_skill_flag?("ReserveLastPokemon") && battle.pbTeamAbleNonActiveCount(user.index) == 1
|
||||
score -= 60 # Don't switch in ace
|
||||
else
|
||||
score += 40 if user.effects[PBEffects::Confusion] > 0
|
||||
total = 0
|
||||
@@ -51,8 +51,8 @@ Battle::AI::Handlers::MoveEffectScore.add("SwitchOutUserStatusMove",
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveEffectScore.add("SwitchOutUserDamagingMove",
|
||||
proc { |score, move, user, ai, battle|
|
||||
next 0 if !battle.pbCanChooseNonActive?(user.index) ||
|
||||
battle.pbTeamAbleNonActiveCount(user.index) == 1 # Don't switch in ace
|
||||
next 0 if !battle.pbCanChooseNonActive?(user.index)
|
||||
next 0 if ai.trainer.has_skill_flag?("ReserveLastPokemon") && battle.pbTeamAbleNonActiveCount(user.index) == 1 # Don't switch in ace
|
||||
}
|
||||
)
|
||||
|
||||
@@ -326,20 +326,24 @@ Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("HigherPriorityInGrassyTe
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("LowerPPOfTargetLastMoveBy3",
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
last_move = target.battler.pbGetMoveWithID(target.battler.lastRegularMoveUsed)
|
||||
if last_move && last_move.total_pp > 0 && last_move.pp <= 3
|
||||
score += 50
|
||||
if user.faster_than?(target)
|
||||
last_move = target.battler.pbGetMoveWithID(target.battler.lastRegularMoveUsed)
|
||||
if last_move && last_move.total_pp > 0
|
||||
next score + 20 if last_move.pp <= 3 # Will fully deplete the move's PP
|
||||
next score + 10 if last_move.pp <= 5
|
||||
next score - 10 if last_move.pp > 9 # Too much PP left to make a difference
|
||||
end
|
||||
end
|
||||
next score
|
||||
next score # Don't know which move it will affect; treat as just a damaging move
|
||||
}
|
||||
)
|
||||
|
||||
#===============================================================================
|
||||
# TODO: Review score modifiers.
|
||||
#
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("LowerPPOfTargetLastMoveBy4",
|
||||
proc { |move, user, target, ai, battle|
|
||||
@@ -349,7 +353,13 @@ Battle::AI::Handlers::MoveFailureAgainstTargetCheck.add("LowerPPOfTargetLastMove
|
||||
)
|
||||
Battle::AI::Handlers::MoveEffectAgainstTargetScore.add("LowerPPOfTargetLastMoveBy4",
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
next Battle::AI::MOVE_USELESS_SCORE
|
||||
if user.faster_than?(target)
|
||||
last_move = target.battler.pbGetMoveWithID(target.battler.lastRegularMoveUsed)
|
||||
next score + 20 if last_move.pp <= 4 # Will fully deplete the move's PP
|
||||
next score + 10 if last_move.pp <= 6
|
||||
next score - 10 if last_move.pp > 10 # Too much PP left to make a difference
|
||||
end
|
||||
next score - 10 # Don't know which move it will affect; don't prefer
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
# TODO: Review score modifier.
|
||||
#===============================================================================
|
||||
# TODO:
|
||||
# => Prefer move if it will KO the target (moreso if user is slower than target)
|
||||
# => Don't prefer damaging move if it won't KO, user has Stance Change and
|
||||
# is in shield form, and user is slower than the target
|
||||
# => Check memory for past damage dealt by a target's non-high priority move,
|
||||
@@ -38,6 +37,7 @@ Battle::AI::Handlers::GeneralMoveAgainstTargetScore.add(:shiny_target,
|
||||
# => If target has previously used a move that will hurt the user by 30% of
|
||||
# its current HP or more, moreso don't prefer a status move.
|
||||
# => Include EOR damage in this?
|
||||
# => Prefer move if it will KO the target (moreso if user is slower than target)
|
||||
#===============================================================================
|
||||
Battle::AI::Handlers::GeneralMoveAgainstTargetScore.add(:add_predicted_damage,
|
||||
proc { |score, move, user, target, ai, battle|
|
||||
|
||||
@@ -13,6 +13,7 @@
|
||||
# PredictMoveFailure
|
||||
# ScoreMoves
|
||||
# PreferMultiTargetMoves
|
||||
# ReserveLastPokemon (don't switch it in if possible)
|
||||
#===============================================================================
|
||||
class Battle::AI::AITrainer
|
||||
attr_reader :side, :trainer_index
|
||||
@@ -36,6 +37,10 @@ class Battle::AI::AITrainer
|
||||
@skill_flags.push("ScoreMoves")
|
||||
@skill_flags.push("PreferMultiTargetMoves")
|
||||
end
|
||||
if @skill >= 100
|
||||
# TODO: Also have flag "DontReserveLastPokemon" which negates this.
|
||||
@skill_flags.push("ReserveLastPokemon")
|
||||
end
|
||||
end
|
||||
|
||||
def has_skill_flag?(flag)
|
||||
|
||||
Reference in New Issue
Block a user