mirror of
https://github.com/Ninjdai1/pokeemerald.git
synced 2024-12-26 11:44:17 +01:00
Greatly reduce AI lag (#3308)
This commit is contained in:
commit
de577f955a
@ -277,6 +277,7 @@ struct AIPartyData // Opposing battlers - party mons.
|
|||||||
u8 count[NUM_BATTLE_SIDES];
|
u8 count[NUM_BATTLE_SIDES];
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Ai Data used when deciding which move to use, computed only once before each turn's start.
|
||||||
struct AiLogicData
|
struct AiLogicData
|
||||||
{
|
{
|
||||||
u16 abilities[MAX_BATTLERS_COUNT];
|
u16 abilities[MAX_BATTLERS_COUNT];
|
||||||
@ -286,11 +287,14 @@ struct AiLogicData
|
|||||||
u16 predictedMoves[MAX_BATTLERS_COUNT];
|
u16 predictedMoves[MAX_BATTLERS_COUNT];
|
||||||
u8 hpPercents[MAX_BATTLERS_COUNT];
|
u8 hpPercents[MAX_BATTLERS_COUNT];
|
||||||
u16 partnerMove;
|
u16 partnerMove;
|
||||||
|
u16 speedStats[MAX_BATTLERS_COUNT]; // Speed stats for all battles, calculated only once, same way as damages
|
||||||
|
u8 moveDmgResult[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // MOVE_POWER defines for GetMoveDamageResult ; attacker, target, moveIndex
|
||||||
s32 simulatedDmg[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // attacker, target, moveIndex
|
s32 simulatedDmg[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // attacker, target, moveIndex
|
||||||
u8 effectiveness[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // attacker, target, moveIndex
|
u8 effectiveness[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // attacker, target, moveIndex
|
||||||
u8 moveLimitations[MAX_BATTLERS_COUNT];
|
u8 moveLimitations[MAX_BATTLERS_COUNT];
|
||||||
bool8 shouldSwitchMon; // Because all available moves have no/little effect. Each bit per battler.
|
bool8 shouldSwitchMon; // Because all available moves have no/little effect. Each bit per battler.
|
||||||
u8 monToSwitchId[MAX_BATTLERS_COUNT]; // ID of the mon to switch.
|
u8 monToSwitchId[MAX_BATTLERS_COUNT]; // ID of the mon to switch.
|
||||||
|
bool8 weatherHasEffect; // The same as WEATHER_HAS_EFFECT. Stored here, so it's called only once.
|
||||||
};
|
};
|
||||||
|
|
||||||
struct AI_ThinkingStruct
|
struct AI_ThinkingStruct
|
||||||
@ -298,7 +302,7 @@ struct AI_ThinkingStruct
|
|||||||
u8 aiState;
|
u8 aiState;
|
||||||
u8 movesetIndex;
|
u8 movesetIndex;
|
||||||
u16 moveConsidered;
|
u16 moveConsidered;
|
||||||
s8 score[MAX_MON_MOVES];
|
s32 score[MAX_MON_MOVES];
|
||||||
u32 funcResult;
|
u32 funcResult;
|
||||||
u32 aiFlags;
|
u32 aiFlags;
|
||||||
u8 aiAction;
|
u8 aiAction;
|
||||||
@ -640,7 +644,7 @@ struct BattleStruct
|
|||||||
u16 hpBefore[MAX_BATTLERS_COUNT]; // Hp of battlers before using a move. For Berserk
|
u16 hpBefore[MAX_BATTLERS_COUNT]; // Hp of battlers before using a move. For Berserk
|
||||||
bool8 spriteIgnore0Hp;
|
bool8 spriteIgnore0Hp;
|
||||||
struct Illusion illusion[MAX_BATTLERS_COUNT];
|
struct Illusion illusion[MAX_BATTLERS_COUNT];
|
||||||
s8 aiFinalScore[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // AI, target, moves to make debugging easier
|
s32 aiFinalScore[MAX_BATTLERS_COUNT][MAX_BATTLERS_COUNT][MAX_MON_MOVES]; // AI, target, moves to make debugging easier
|
||||||
u8 aiMoveOrAction[MAX_BATTLERS_COUNT];
|
u8 aiMoveOrAction[MAX_BATTLERS_COUNT];
|
||||||
u8 aiChosenTarget[MAX_BATTLERS_COUNT];
|
u8 aiChosenTarget[MAX_BATTLERS_COUNT];
|
||||||
u8 soulheartBattlerId;
|
u8 soulheartBattlerId;
|
||||||
|
@ -19,15 +19,15 @@
|
|||||||
return score; \
|
return score; \
|
||||||
}
|
}
|
||||||
|
|
||||||
u8 ComputeBattleAiScores(u8 battler);
|
u32 ComputeBattleAiScores(u32 battler);
|
||||||
void BattleAI_SetupItems(void);
|
void BattleAI_SetupItems(void);
|
||||||
void BattleAI_SetupFlags(void);
|
void BattleAI_SetupFlags(void);
|
||||||
void BattleAI_SetupAIData(u8 defaultScoreMoves, u32 battler);
|
void BattleAI_SetupAIData(u8 defaultScoreMoves, u32 battler);
|
||||||
u8 BattleAI_ChooseMoveOrAction(void);
|
u32 BattleAI_ChooseMoveOrAction(void);
|
||||||
void Ai_InitPartyStruct(void);
|
void Ai_InitPartyStruct(void);
|
||||||
void Ai_UpdateSwitchInData(u32 battler);
|
void Ai_UpdateSwitchInData(u32 battler);
|
||||||
void Ai_UpdateFaintData(u32 battler);
|
void Ai_UpdateFaintData(u32 battler);
|
||||||
void SetAiLogicDataForTurn(void);
|
void SetAiLogicDataForTurn(struct AiLogicData *aiData);
|
||||||
|
|
||||||
extern u8 sBattler_AI;
|
extern u8 sBattler_AI;
|
||||||
|
|
||||||
|
@ -7,184 +7,186 @@
|
|||||||
|
|
||||||
#define FOE(battler) ((BATTLE_OPPOSITE(battler)) & BIT_SIDE)
|
#define FOE(battler) ((BATTLE_OPPOSITE(battler)) & BIT_SIDE)
|
||||||
|
|
||||||
bool32 AI_RandLessThan(u8 val);
|
#define AI_STRIKES_FIRST(battlerAi, battlerDef, move)((AI_WhoStrikesFirst(battlerAi, battlerDef, move) == AI_IS_FASTER))
|
||||||
void RecordLastUsedMoveByTarget(void);
|
|
||||||
|
bool32 AI_RandLessThan(u32 val);
|
||||||
bool32 IsAiVsAiBattle(void);
|
bool32 IsAiVsAiBattle(void);
|
||||||
bool32 BattlerHasAi(u32 battlerId);
|
bool32 BattlerHasAi(u32 battlerId);
|
||||||
bool32 IsAiBattlerAware(u32 battlerId);
|
bool32 IsAiBattlerAware(u32 battlerId);
|
||||||
void ClearBattlerMoveHistory(u8 battlerId);
|
void ClearBattlerMoveHistory(u32 battlerId);
|
||||||
void RecordLastUsedMoveBy(u32 battlerId, u32 move);
|
void RecordLastUsedMoveBy(u32 battlerId, u32 move);
|
||||||
void RecordAllMoves(u32 battler);
|
void RecordAllMoves(u32 battler);
|
||||||
void RecordKnownMove(u8 battlerId, u32 move);
|
void RecordKnownMove(u32 battlerId, u32 move);
|
||||||
void RecordAbilityBattle(u8 battlerId, u16 abilityId);
|
void RecordAbilityBattle(u32 battlerId, u32 abilityId);
|
||||||
void ClearBattlerAbilityHistory(u8 battlerId);
|
void ClearBattlerAbilityHistory(u32 battlerId);
|
||||||
void RecordItemEffectBattle(u8 battlerId, u8 itemEffect);
|
void RecordItemEffectBattle(u32 battlerId, u32 itemEffect);
|
||||||
void ClearBattlerItemEffectHistory(u8 battlerId);
|
void ClearBattlerItemEffectHistory(u32 battlerId);
|
||||||
void SaveBattlerData(u8 battlerId);
|
void SaveBattlerData(u32 battlerId);
|
||||||
void SetBattlerData(u8 battlerId);
|
void SetBattlerData(u32 battlerId);
|
||||||
void RestoreBattlerData(u8 battlerId);
|
void RestoreBattlerData(u32 battlerId);
|
||||||
u16 GetAIChosenMove(u8 battlerId);
|
u32 GetAIChosenMove(u32 battlerId);
|
||||||
|
|
||||||
bool32 WillAIStrikeFirst(void);
|
|
||||||
u32 GetTotalBaseStat(u32 species);
|
u32 GetTotalBaseStat(u32 species);
|
||||||
bool32 IsTruantMonVulnerable(u32 battlerAI, u32 opposingBattler);
|
bool32 IsTruantMonVulnerable(u32 battlerAI, u32 opposingBattler);
|
||||||
bool32 AtMaxHp(u8 battler);
|
bool32 AtMaxHp(u32 battler);
|
||||||
u32 GetHealthPercentage(u8 battler);
|
u32 GetHealthPercentage(u32 battler);
|
||||||
bool32 IsBattlerTrapped(u8 battler, bool8 switching);
|
bool32 IsBattlerTrapped(u32 battler, bool32 switching);
|
||||||
u8 AI_WhoStrikesFirst(u8 battlerAI, u8 battler2, u16 consideredMove);
|
u32 AI_WhoStrikesFirst(u32 battlerAI, u32 battler2, u32 moveConsidered);
|
||||||
bool32 CanTargetFaintAi(u8 battlerDef, u8 battlerAtk);
|
bool32 CanTargetFaintAi(u32 battlerDef, u32 battlerAtk);
|
||||||
bool32 CanMoveFaintBattler(u16 move, u8 battlerDef, u8 battlerAtk, u8 nHits);
|
bool32 CanTargetMoveFaintAi(u32 move, u32 battlerDef, u32 battlerAtk, u32 nHits);
|
||||||
bool32 CanTargetFaintAiWithMod(u8 battlerDef, u8 battlerAtk, s32 hpMod, s32 dmgMod);
|
bool32 CanTargetFaintAiWithMod(u32 battlerDef, u32 battlerAtk, s32 hpMod, s32 dmgMod);
|
||||||
s32 AI_GetAbility(u32 battlerId);
|
s32 AI_GetAbility(u32 battlerId);
|
||||||
u16 AI_GetHoldEffect(u32 battlerId);
|
u32 AI_GetHoldEffect(u32 battlerId);
|
||||||
u32 AI_GetMoveAccuracy(u8 battlerAtk, u8 battlerDef, u16 move);
|
u32 AI_GetMoveAccuracy(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
bool32 DoesBattlerIgnoreAbilityChecks(u16 atkAbility, u16 move);
|
bool32 DoesBattlerIgnoreAbilityChecks(u32 atkAbility, u32 move);
|
||||||
bool32 AI_WeatherHasEffect(void);
|
u32 AI_GetWeather(struct AiLogicData *aiData);
|
||||||
bool32 CanAIFaintTarget(u8 battlerAtk, u8 battlerDef, u8 numHits);
|
bool32 CanAIFaintTarget(u32 battlerAtk, u32 battlerDef, u32 numHits);
|
||||||
bool32 CanIndexMoveFaintTarget(u8 battlerAtk, u8 battlerDef, u8 index, u8 numHits);
|
bool32 CanIndexMoveFaintTarget(u32 battlerAtk, u32 battlerDef, u32 index, u32 numHits);
|
||||||
bool32 AI_IsTerrainAffected(u8 battlerId, u32 flags);
|
bool32 AI_IsTerrainAffected(u32 battlerId, u32 flags);
|
||||||
bool32 AI_IsBattlerGrounded(u8 battlerId);
|
bool32 AI_IsBattlerGrounded(u32 battlerId);
|
||||||
bool32 HasDamagingMove(u8 battlerId);
|
bool32 HasDamagingMove(u32 battlerId);
|
||||||
bool32 HasDamagingMoveOfType(u8 battlerId, u8 type);
|
bool32 HasDamagingMoveOfType(u32 battlerId, u32 type);
|
||||||
u32 GetBattlerSecondaryDamage(u8 battlerId);
|
u32 GetBattlerSecondaryDamage(u32 battlerId);
|
||||||
bool32 BattlerWillFaintFromWeather(u8 battler, u16 ability);
|
bool32 BattlerWillFaintFromWeather(u32 battler, u32 ability);
|
||||||
bool32 BattlerWillFaintFromSecondaryDamage(u8 battler, u16 ability);
|
bool32 BattlerWillFaintFromSecondaryDamage(u32 battler, u32 ability);
|
||||||
bool32 ShouldTryOHKO(u8 battlerAtk, u8 battlerDef, u16 atkAbility, u16 defAbility, u16 move);
|
bool32 ShouldTryOHKO(u32 battlerAtk, u32 battlerDef, u32 atkAbility, u32 defAbility, u32 move);
|
||||||
bool32 ShouldUseRecoilMove(u8 battlerAtk, u8 battlerDef, u32 recoilDmg, u8 moveIndex);
|
bool32 ShouldUseRecoilMove(u32 battlerAtk, u32 battlerDef, u32 recoilDmg, u32 moveIndex);
|
||||||
u16 GetBattlerSideSpeedAverage(u8 battler);
|
u32 GetBattlerSideSpeedAverage(u32 battler);
|
||||||
bool32 ShouldAbsorb(u8 battlerAtk, u8 battlerDef, u16 move, s32 damage);
|
bool32 ShouldAbsorb(u32 battlerAtk, u32 battlerDef, u32 move, s32 damage);
|
||||||
bool32 ShouldRecover(u8 battlerAtk, u8 battlerDef, u16 move, u8 healPercent);
|
bool32 ShouldRecover(u32 battlerAtk, u32 battlerDef, u32 move, u32 healPercent);
|
||||||
bool32 ShouldSetScreen(u8 battlerAtk, u8 battlerDef, u16 moveEffect);
|
bool32 ShouldSetScreen(u32 battlerAtk, u32 battlerDef, u32 moveEffect);
|
||||||
bool32 ShouldPivot(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u8 moveIndex);
|
bool32 ShouldPivot(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 move, u32 moveIndex);
|
||||||
bool32 IsRecycleEncouragedItem(u16 item);
|
bool32 IsRecycleEncouragedItem(u32 item);
|
||||||
bool32 ShouldRestoreHpBerry(u8 battlerAtk, u16 item);
|
bool32 ShouldRestoreHpBerry(u32 battlerAtk, u32 item);
|
||||||
bool32 IsStatBoostingBerry(u16 item);
|
bool32 IsStatBoostingBerry(u32 item);
|
||||||
bool32 CanKnockOffItem(u8 battler, u16 item);
|
bool32 CanKnockOffItem(u32 battler, u32 item);
|
||||||
bool32 IsAbilityOfRating(u16 ability, s8 rating);
|
bool32 IsAbilityOfRating(u32 ability, s8 rating);
|
||||||
s8 GetAbilityRating(u16 ability);
|
s8 GetAbilityRating(u32 ability);
|
||||||
bool32 AI_IsAbilityOnSide(u32 battlerId, u32 ability);
|
bool32 AI_IsAbilityOnSide(u32 battlerId, u32 ability);
|
||||||
bool32 AI_MoveMakesContact(u32 ability, u32 holdEffect, u16 move);
|
bool32 AI_MoveMakesContact(u32 ability, u32 holdEffect, u32 move);
|
||||||
u32 AI_GetBattlerMoveTargetType(u8 battlerId, u16 move);
|
u32 AI_GetBattlerMoveTargetType(u32 battlerId, u32 move);
|
||||||
bool32 ShouldUseZMove(u8 activeId, u8 targetId, u16 chosenMove);
|
bool32 ShouldUseZMove(u32 battlerAtk, u32 battlerDef, u32 chosenMove);
|
||||||
|
|
||||||
// stat stage checks
|
// stat stage checks
|
||||||
bool32 AnyStatIsRaised(u8 battlerId);
|
bool32 AnyStatIsRaised(u32 battlerId);
|
||||||
bool32 ShouldLowerStat(u8 battler, u16 battlerAbility, u8 stat);
|
bool32 ShouldLowerStat(u32 battler, u32 battlerAbility, u32 stat);
|
||||||
bool32 BattlerStatCanRise(u8 battler, u16 battlerAbility, u8 stat);
|
bool32 BattlerStatCanRise(u32 battler, u32 battlerAbility, u32 stat);
|
||||||
bool32 AreBattlersStatsMaxed(u8 battler);
|
bool32 AreBattlersStatsMaxed(u32 battler);
|
||||||
bool32 BattlerHasAnyStatRaised(u8 battlerId);
|
bool32 BattlerHasAnyStatRaised(u32 battlerId);
|
||||||
u32 CountPositiveStatStages(u8 battlerId);
|
u32 CountPositiveStatStages(u32 battlerId);
|
||||||
u32 CountNegativeStatStages(u8 battlerId);
|
u32 CountNegativeStatStages(u32 battlerId);
|
||||||
bool32 ShouldLowerAttack(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerAttack(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 ShouldLowerDefense(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerDefense(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 ShouldLowerSpeed(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerSpeed(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 ShouldLowerSpAtk(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerSpAtk(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 ShouldLowerSpDef(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerSpDef(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 ShouldLowerAccuracy(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerAccuracy(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 ShouldLowerEvasion(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 ShouldLowerEvasion(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
|
|
||||||
// move checks
|
// move checks
|
||||||
bool32 IsAffectedByPowder(u8 battler, u16 ability, u16 holdEffect);
|
bool32 IsAffectedByPowder(u32 battler, u32 ability, u32 holdEffect);
|
||||||
bool32 MovesWithSplitUnusable(u32 attacker, u32 target, u32 split);
|
bool32 MovesWithSplitUnusable(u32 attacker, u32 target, u32 split);
|
||||||
s32 AI_CalcDamage(u16 move, u8 battlerAtk, u8 battlerDef, u8 *effectiveness, bool32 considerZPower);
|
s32 AI_CalcDamageSaveBattlers(u32 move, u32 battlerAtk, u32 battlerDef, u8 *typeEffectiveness, bool32 considerZPower);
|
||||||
|
s32 AI_CalcDamage(u32 move, u32 battlerAtk, u32 battlerDef, u8 *typeEffectiveness, bool32 considerZPower, u32 weather);
|
||||||
u32 GetNoOfHitsToKO(u32 dmg, s32 hp);
|
u32 GetNoOfHitsToKO(u32 dmg, s32 hp);
|
||||||
u8 GetMoveDamageResult(u16 move);
|
void SetMoveDamageResult(u32 battlerAtk, u16 *moves);
|
||||||
u32 GetCurrDamageHpPercent(u8 battlerAtk, u8 battlerDef);
|
u32 GetMoveDamageResult(u32 battlerAtk, u32 battlerDef, u32 moveIndex);
|
||||||
uq4_12_t AI_GetTypeEffectiveness(u16 move, u8 battlerAtk, u8 battlerDef);
|
u32 GetCurrDamageHpPercent(u32 battlerAtk, u32 battlerDef);
|
||||||
u32 AI_GetMoveEffectiveness(u16 move, u8 battlerAtk, u8 battlerDef);
|
uq4_12_t AI_GetTypeEffectiveness(u32 move, u32 battlerAtk, u32 battlerDef);
|
||||||
|
u32 AI_GetMoveEffectiveness(u32 move, u32 battlerAtk, u32 battlerDef);
|
||||||
u16 *GetMovesArray(u32 battler);
|
u16 *GetMovesArray(u32 battler);
|
||||||
bool32 IsConfusionMoveEffect(u16 moveEffect);
|
bool32 IsConfusionMoveEffect(u32 moveEffect);
|
||||||
bool32 HasMove(u32 battlerId, u32 move);
|
bool32 HasMove(u32 battlerId, u32 move);
|
||||||
bool32 HasOnlyMovesWithSplit(u32 battlerId, u32 split, bool32 onlyOffensive);
|
bool32 HasOnlyMovesWithSplit(u32 battlerId, u32 split, bool32 onlyOffensive);
|
||||||
bool32 HasMoveWithSplit(u32 battler, u32 split);
|
bool32 HasMoveWithSplit(u32 battler, u32 split);
|
||||||
bool32 HasMoveWithType(u32 battler, u8 type);
|
bool32 HasMoveWithType(u32 battler, u32 type);
|
||||||
bool32 HasMoveWithTypeAndSplit(u32 battler, u8 type, u8 split);
|
bool32 HasMoveWithTypeAndSplit(u32 battler, u32 type, u32 split);
|
||||||
bool32 HasMoveEffect(u32 battlerId, u16 moveEffect);
|
bool32 HasMoveEffect(u32 battlerId, u32 moveEffect);
|
||||||
bool32 HasMoveWithLowAccuracy(u8, u8, u8, bool32, u16, u16, u16, u16);
|
bool32 HasMoveWithLowAccuracy(u32 battlerAtk, u32 battlerDef, u32 accCheck, bool32 ignoreStatus, u32 atkAbility, u32 defAbility, u32 atkHoldEffect, u32 defHoldEffect);
|
||||||
bool32 IsAromaVeilProtectedMove(u16 move);
|
bool32 IsAromaVeilProtectedMove(u32 move);
|
||||||
bool32 IsNonVolatileStatusMoveEffect(u16 moveEffect);
|
bool32 IsNonVolatileStatusMoveEffect(u32 moveEffect);
|
||||||
bool32 IsStatLoweringMoveEffect(u16 moveEffect);
|
bool32 IsStatLoweringMoveEffect(u32 moveEffect);
|
||||||
bool32 IsMoveRedirectionPrevented(u16 move, u16 atkAbility);
|
bool32 IsMoveRedirectionPrevented(u32 move, u32 atkAbility);
|
||||||
bool32 IsMoveEncouragedToHit(u8 battlerAtk, u8 battlerDef, u16 move);
|
bool32 IsMoveEncouragedToHit(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
bool32 IsHazardMoveEffect(u16 moveEffect);
|
bool32 IsHazardMoveEffect(u32 moveEffect);
|
||||||
bool32 MoveCallsOtherMove(u16 move);
|
bool32 MoveCallsOtherMove(u32 move);
|
||||||
bool32 MoveRequiresRecharging(u16 move);
|
bool32 MoveRequiresRecharging(u32 move);
|
||||||
bool32 IsEncoreEncouragedEffect(u16 moveEffect);
|
bool32 IsEncoreEncouragedEffect(u32 moveEffect);
|
||||||
void ProtectChecks(u8 battlerAtk, u8 battlerDef, u16 move, u16 predictedMove, s16 *score);
|
void ProtectChecks(u32 battlerAtk, u32 battlerDef, u32 move, u32 predictedMove, s32 *score);
|
||||||
bool32 ShouldSetSandstorm(u8 battler, u16 ability, u16 holdEffect);
|
bool32 ShouldSetSandstorm(u32 battler, u32 ability, u32 holdEffect);
|
||||||
bool32 ShouldSetHail(u8 battler, u16 ability, u16 holdEffect);
|
bool32 ShouldSetHail(u32 battler, u32 ability, u32 holdEffect);
|
||||||
bool32 ShouldSetSnow(u8 battler, u16 ability, u16 holdEffect);
|
bool32 ShouldSetSnow(u32 battler, u32 ability, u32 holdEffect);
|
||||||
bool32 ShouldSetRain(u8 battlerAtk, u16 ability, u16 holdEffect);
|
bool32 ShouldSetRain(u32 battlerAtk, u32 ability, u32 holdEffect);
|
||||||
bool32 ShouldSetSun(u8 battlerAtk, u16 atkAbility, u16 holdEffect);
|
bool32 ShouldSetSun(u32 battlerAtk, u32 atkAbility, u32 holdEffect);
|
||||||
bool32 HasSleepMoveWithLowAccuracy(u8 battlerAtk, u8 battlerDef);
|
bool32 HasSleepMoveWithLowAccuracy(u32 battlerAtk, u32 battlerDef);
|
||||||
bool32 IsHealingMoveEffect(u16 effect);
|
bool32 IsHealingMoveEffect(u32 effect);
|
||||||
bool32 HasHealingEffect(u32 battler);
|
bool32 HasHealingEffect(u32 battler);
|
||||||
bool32 IsTrappingMoveEffect(u16 effect);
|
bool32 IsTrappingMoveEffect(u32 effect);
|
||||||
bool32 HasTrappingMoveEffect(u8 battler);
|
bool32 HasTrappingMoveEffect(u32 battler);
|
||||||
bool32 ShouldFakeOut(u8 battlerAtk, u8 battlerDef, u16 move);
|
bool32 ShouldFakeOut(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
bool32 HasThawingMove(u8 battler);
|
bool32 HasThawingMove(u32 battler);
|
||||||
bool32 IsStatRaisingEffect(u16 effect);
|
bool32 IsStatRaisingEffect(u32 effect);
|
||||||
bool32 IsStatLoweringEffect(u16 effect);
|
bool32 IsStatLoweringEffect(u32 effect);
|
||||||
bool32 IsStatRaisingEffect(u16 effect);
|
bool32 IsStatRaisingEffect(u32 effect);
|
||||||
bool32 IsAttackBoostMoveEffect(u16 effect);
|
bool32 IsAttackBoostMoveEffect(u32 effect);
|
||||||
bool32 IsUngroundingEffect(u16 effect);
|
bool32 IsUngroundingEffect(u32 effect);
|
||||||
bool32 IsSemiInvulnerable(u8 battlerDef, u16 move);
|
bool32 IsSemiInvulnerable(u32 battlerDef, u32 move);
|
||||||
bool32 HasSoundMove(u8 battler);
|
bool32 HasSoundMove(u32 battler);
|
||||||
bool32 HasHighCritRatioMove(u8 battler);
|
bool32 HasHighCritRatioMove(u32 battler);
|
||||||
bool32 HasMagicCoatAffectedMove(u8 battler);
|
bool32 HasMagicCoatAffectedMove(u32 battler);
|
||||||
bool32 HasSnatchAffectedMove(u8 battler);
|
bool32 HasSnatchAffectedMove(u32 battler);
|
||||||
|
|
||||||
// status checks
|
// status checks
|
||||||
bool32 AI_CanBeBurned(u8 battler, u16 ability);
|
bool32 AI_CanBeBurned(u32 battler, u32 ability);
|
||||||
bool32 AI_CanGetFrostbite(u8 battler, u16 ability);
|
bool32 AI_CanGetFrostbite(u32 battler, u32 ability);
|
||||||
bool32 AI_CanBeConfused(u8 battler, u16 ability);
|
bool32 AI_CanBeConfused(u32 battler, u32 ability);
|
||||||
bool32 AI_CanSleep(u8 battler, u16 ability);
|
bool32 AI_CanSleep(u32 battler, u32 ability);
|
||||||
bool32 IsBattlerIncapacitated(u8 battler, u16 ability);
|
bool32 IsBattlerIncapacitated(u32 battler, u32 ability);
|
||||||
bool32 AI_CanPutToSleep(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u16 partnerMove);
|
bool32 AI_CanPutToSleep(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 move, u32 partnerMove);
|
||||||
bool32 ShouldPoisonSelf(u8 battler, u16 ability);
|
bool32 ShouldPoisonSelf(u32 battler, u32 ability);
|
||||||
bool32 AI_CanPoison(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u16 partnerMove);
|
bool32 AI_CanPoison(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 move, u32 partnerMove);
|
||||||
bool32 AI_CanParalyze(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u16 partnerMove);
|
bool32 AI_CanParalyze(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 move, u32 partnerMove);
|
||||||
bool32 AI_CanConfuse(u8 battlerAtk, u8 battlerDef, u16 defAbility, u8 battlerAtkPartner, u16 move, u16 partnerMove);
|
bool32 AI_CanConfuse(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 battlerAtkPartner, u32 move, u32 partnerMove);
|
||||||
bool32 ShouldBurnSelf(u8 battler, u16 ability);
|
bool32 ShouldBurnSelf(u32 battler, u32 ability);
|
||||||
bool32 AI_CanBurn(u8 battlerAtk, u8 battlerDef, u16 defAbility, u8 battlerAtkPartner, u16 move, u16 partnerMove);
|
bool32 AI_CanBurn(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 battlerAtkPartner, u32 move, u32 partnerMove);
|
||||||
bool32 AI_CanGiveFrostbite(u8 battlerAtk, u8 battlerDef, u16 defAbility, u8 battlerAtkPartner, u16 move, u16 partnerMove);
|
bool32 AI_CanGiveFrostbite(u32 battlerAtk, u32 battlerDef, u32 defAbility, u32 battlerAtkPartner, u32 move, u32 partnerMove);
|
||||||
bool32 AI_CanBeInfatuated(u8 battlerAtk, u8 battlerDef, u16 defAbility);
|
bool32 AI_CanBeInfatuated(u32 battlerAtk, u32 battlerDef, u32 defAbility);
|
||||||
bool32 AnyPartyMemberStatused(u8 battlerId, bool32 checkSoundproof);
|
bool32 AnyPartyMemberStatused(u32 battlerId, bool32 checkSoundproof);
|
||||||
u32 ShouldTryToFlinch(u8 battlerAtk, u8 battlerDef, u16 atkAbility, u16 defAbility, u16 move);
|
u32 ShouldTryToFlinch(u32 battlerAtk, u32 battlerDef, u32 atkAbility, u32 defAbility, u32 move);
|
||||||
bool32 ShouldTrap(u8 battlerAtk, u8 battlerDef, u16 move);
|
bool32 ShouldTrap(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
bool32 IsWakeupTurn(u8 battler);
|
bool32 IsWakeupTurn(u32 battler);
|
||||||
bool32 AI_IsBattlerAsleepOrComatose(u8 battlerId);
|
bool32 AI_IsBattlerAsleepOrComatose(u32 battlerId);
|
||||||
|
|
||||||
// partner logic
|
// partner logic
|
||||||
u16 GetAllyChosenMove(u8 battlerId);
|
#define IS_TARGETING_PARTNER(battlerAtk, battlerDef)((battlerAtk) == (battlerDef ^ BIT_FLANK))
|
||||||
bool32 IsValidDoubleBattle(u8 battlerAtk);
|
u32 GetAllyChosenMove(u32 battlerId);
|
||||||
bool32 IsTargetingPartner(u8 battlerAtk, u8 battlerDef);
|
bool32 IsValidDoubleBattle(u32 battlerAtk);
|
||||||
bool32 DoesPartnerHaveSameMoveEffect(u8 battlerAtkPartner, u8 battlerDef, u16 move, u16 partnerMove);
|
bool32 IsTargetingPartner(u32 battlerAtk, u32 battlerDef);
|
||||||
bool32 PartnerHasSameMoveEffectWithoutTarget(u8 battlerAtkPartner, u16 move, u16 partnerMove);
|
bool32 DoesPartnerHaveSameMoveEffect(u32 battlerAtkPartner, u32 battlerDef, u32 move, u32 partnerMove);
|
||||||
bool32 PartnerMoveEffectIsStatusSameTarget(u8 battlerAtkPartner, u8 battlerDef, u16 partnerMove);
|
bool32 PartnerHasSameMoveEffectWithoutTarget(u32 battlerAtkPartner, u32 move, u32 partnerMove);
|
||||||
bool32 PartnerMoveEffectIsWeather(u8 battlerAtkPartner, u16 partnerMove);
|
bool32 PartnerMoveEffectIsStatusSameTarget(u32 battlerAtkPartner, u32 battlerDef, u32 partnerMove);
|
||||||
bool32 PartnerMoveEffectIsTerrain(u8 battlerAtkPartner, u16 partnerMove);
|
bool32 PartnerMoveEffectIsWeather(u32 battlerAtkPartner, u32 partnerMove);
|
||||||
bool32 PartnerMoveIs(u8 battlerAtkPartner, u16 partnerMove, u16 moveCheck);
|
bool32 PartnerMoveEffectIsTerrain(u32 battlerAtkPartner, u32 partnerMove);
|
||||||
bool32 PartnerMoveIsSameAsAttacker(u8 battlerAtkPartner, u8 battlerDef, u16 move, u16 partnerMove);
|
bool32 PartnerMoveIs(u32 battlerAtkPartner, u32 partnerMove, u32 moveCheck);
|
||||||
bool32 PartnerMoveIsSameNoTarget(u8 battlerAtkPartner, u16 move, u16 partnerMove);
|
bool32 PartnerMoveIsSameAsAttacker(u32 battlerAtkPartner, u32 battlerDef, u32 move, u32 partnerMove);
|
||||||
bool32 ShouldUseWishAromatherapy(u8 battlerAtk, u8 battlerDef, u16 move);
|
bool32 PartnerMoveIsSameNoTarget(u32 battlerAtkPartner, u32 move, u32 partnerMove);
|
||||||
|
bool32 ShouldUseWishAromatherapy(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
|
|
||||||
// party logic
|
// party logic
|
||||||
struct BattlePokemon *AllocSaveBattleMons(void);
|
struct BattlePokemon *AllocSaveBattleMons(void);
|
||||||
void FreeRestoreBattleMons(struct BattlePokemon *savedBattleMons);
|
void FreeRestoreBattleMons(struct BattlePokemon *savedBattleMons);
|
||||||
s32 AI_CalcPartyMonBestMoveDamage(u32 battlerAtk, u32 battlerDef, struct Pokemon *attackerMon, struct Pokemon *targetMon);
|
s32 AI_CalcPartyMonBestMoveDamage(u32 battlerAtk, u32 battlerDef, struct Pokemon *attackerMon, struct Pokemon *targetMon);
|
||||||
s32 CountUsablePartyMons(u8 battlerId);
|
s32 CountUsablePartyMons(u32 battlerId);
|
||||||
bool32 IsPartyFullyHealedExceptBattler(u8 battler);
|
bool32 IsPartyFullyHealedExceptBattler(u32 battler);
|
||||||
bool32 PartyHasMoveSplit(u8 battlerId, u8 split);
|
bool32 PartyHasMoveSplit(u32 battlerId, u32 split);
|
||||||
bool32 SideHasMoveSplit(u8 battlerId, u8 split);
|
bool32 SideHasMoveSplit(u32 battlerId, u32 split);
|
||||||
|
|
||||||
// score increases
|
// score increases
|
||||||
void IncreaseStatUpScore(u8 battlerAtk, u8 battlerDef, u8 statId, s16 *score);
|
void IncreaseStatUpScore(u32 battlerAtk, u32 battlerDef, u32 statId, s32 *score);
|
||||||
void IncreasePoisonScore(u8 battlerAtk, u8 battlerDef, u16 move, s16 *score);
|
void IncreasePoisonScore(u32 battlerAtk, u32 battlerDef, u32 move, s32 *score);
|
||||||
void IncreaseBurnScore(u8 battlerAtk, u8 battlerDef, u16 move, s16 *score);
|
void IncreaseBurnScore(u32 battlerAtk, u32 battlerDef, u32 move, s32 *score);
|
||||||
void IncreaseParalyzeScore(u8 battlerAtk, u8 battlerDef, u16 move, s16 *score);
|
void IncreaseParalyzeScore(u32 battlerAtk, u32 battlerDef, u32 move, s32 *score);
|
||||||
void IncreaseSleepScore(u8 battlerAtk, u8 battlerDef, u16 move, s16 *score);
|
void IncreaseSleepScore(u32 battlerAtk, u32 battlerDef, u32 move, s32 *score);
|
||||||
void IncreaseConfusionScore(u8 battlerAtk, u8 battlerDef, u16 move, s16 *score);
|
void IncreaseConfusionScore(u32 battlerAtk, u32 battlerDef, u32 move, s32 *score);
|
||||||
void IncreaseFrostbiteScore(u8 battlerAtk, u8 battlerDef, u16 move, s16 *score);
|
void IncreaseFrostbiteScore(u32 battlerAtk, u32 battlerDef, u32 move, s32 *score);
|
||||||
|
|
||||||
#endif //GUARD_BATTLE_AI_UTIL_H
|
#endif //GUARD_BATTLE_AI_UTIL_H
|
||||||
|
@ -57,17 +57,19 @@ void SwitchInClearSetData(u32 battler);
|
|||||||
void FaintClearSetData(u32 battler);
|
void FaintClearSetData(u32 battler);
|
||||||
void BattleTurnPassed(void);
|
void BattleTurnPassed(void);
|
||||||
u8 IsRunningFromBattleImpossible(u32 battler);
|
u8 IsRunningFromBattleImpossible(u32 battler);
|
||||||
void SwitchPartyOrder(u8 battlerId);
|
void SwitchPartyOrder(u32 battlerId);
|
||||||
void SwapTurnOrder(u8 id1, u8 id2);
|
void SwapTurnOrder(u8 id1, u8 id2);
|
||||||
u32 GetBattlerTotalSpeedStat(u8 battlerId);
|
u32 GetBattlerTotalSpeedStatArgs(u32 battler, u32 ability, u32 holdEffect);
|
||||||
|
u32 GetBattlerTotalSpeedStat(u32 battler);
|
||||||
s8 GetChosenMovePriority(u32 battlerId);
|
s8 GetChosenMovePriority(u32 battlerId);
|
||||||
s8 GetMovePriority(u32 battlerId, u16 move);
|
s8 GetMovePriority(u32 battlerId, u16 move);
|
||||||
u8 GetWhoStrikesFirst(u8 battlerId1, u8 battlerId2, bool8 ignoreChosenMoves);
|
u32 GetWhichBattlerFasterArgs(u32 battler1, u32 battler2, bool32 ignoreChosenMoves, u32 ability1, u32 ability2,
|
||||||
|
u32 holdEffectBattler1, u32 holdEffectBattler2, u32 speedBattler1, u32 speedBattler2, s32 priority1, s32 priority2);
|
||||||
|
u32 GetWhichBattlerFaster(u32 battler1, u32 battler2, bool32 ignoreChosenMoves);
|
||||||
void RunBattleScriptCommands_PopCallbacksStack(void);
|
void RunBattleScriptCommands_PopCallbacksStack(void);
|
||||||
void RunBattleScriptCommands(void);
|
void RunBattleScriptCommands(void);
|
||||||
bool8 TryRunFromBattle(u8 battlerId);
|
|
||||||
void SpecialStatusesClear(void);
|
void SpecialStatusesClear(void);
|
||||||
void SetTypeBeforeUsingMove(u16 move, u8 battlerAtk);
|
void SetTypeBeforeUsingMove(u32 move, u32 battlerAtk);
|
||||||
bool32 IsWildMonSmart(void);
|
bool32 IsWildMonSmart(void);
|
||||||
u8 CreateNPCTrainerPartyFromTrainer(struct Pokemon *party, const struct Trainer *trainer, bool32 firstTrainer, u32 battleTypeFlags);
|
u8 CreateNPCTrainerPartyFromTrainer(struct Pokemon *party, const struct Trainer *trainer, bool32 firstTrainer, u32 battleTypeFlags);
|
||||||
void ModifyPersonalityForNature(u32 *personality, u32 newNature);
|
void ModifyPersonalityForNature(u32 *personality, u32 newNature);
|
||||||
|
@ -16,8 +16,9 @@ struct StatFractions
|
|||||||
u8 divisor;
|
u8 divisor;
|
||||||
};
|
};
|
||||||
|
|
||||||
s32 CalcCritChanceStage(u8 battlerAtk, u8 battlerDef, u32 move, bool32 recordAbility);
|
s32 CalcCritChanceStageArgs(u32 battlerAtk, u32 battlerDef, u32 move, bool32 recordAbility, u32 abilityAtk, u32 abilityDef, u32 holdEffectAtk);
|
||||||
s8 GetInverseCritChance(u8 battlerAtk, u8 battlerDef, u32 move);
|
s32 CalcCritChanceStage(u32 battlerAtk, u32 battlerDef, u32 move, bool32 recordAbility);
|
||||||
|
s32 GetCritHitChance(s32 critChanceIndex);
|
||||||
u32 GetTotalAccuracy(u32 battlerAtk, u32 battlerDef, u32 move, u32 atkAbility, u32 defAbility, u32 atkHoldEffect, u32 defHoldEffect);
|
u32 GetTotalAccuracy(u32 battlerAtk, u32 battlerDef, u32 move, u32 atkAbility, u32 defAbility, u32 atkHoldEffect, u32 defHoldEffect);
|
||||||
u8 GetBattlerTurnOrderNum(u8 battlerId);
|
u8 GetBattlerTurnOrderNum(u8 battlerId);
|
||||||
bool32 NoAliveMonsForEitherParty(void);
|
bool32 NoAliveMonsForEitherParty(void);
|
||||||
@ -28,8 +29,8 @@ void BattleCreateYesNoCursorAt(u8 cursorPosition);
|
|||||||
void BufferMoveToLearnIntoBattleTextBuff2(void);
|
void BufferMoveToLearnIntoBattleTextBuff2(void);
|
||||||
void HandleBattleWindow(u8 xStart, u8 yStart, u8 xEnd, u8 yEnd, u8 flags);
|
void HandleBattleWindow(u8 xStart, u8 yStart, u8 xEnd, u8 yEnd, u8 flags);
|
||||||
bool8 UproarWakeUpCheck(u8 battlerId);
|
bool8 UproarWakeUpCheck(u8 battlerId);
|
||||||
bool32 DoesSubstituteBlockMove(u8 battlerAtk, u8 battlerDef, u32 move);
|
bool32 DoesSubstituteBlockMove(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
bool32 DoesDisguiseBlockMove(u8 battlerAtk, u8 battlerDef, u32 move);
|
bool32 DoesDisguiseBlockMove(u32 battlerAtk, u32 battlerDef, u32 move);
|
||||||
bool32 CanPoisonType(u8 battlerAttacker, u8 battlerTarget);
|
bool32 CanPoisonType(u8 battlerAttacker, u8 battlerTarget);
|
||||||
bool32 CanParalyzeType(u8 battlerAttacker, u8 battlerTarget);
|
bool32 CanParalyzeType(u8 battlerAttacker, u8 battlerTarget);
|
||||||
bool32 CanUseLastResort(u8 battlerId);
|
bool32 CanUseLastResort(u8 battlerId);
|
||||||
@ -47,6 +48,7 @@ u32 GetHighestStatId(u32 battlerId);
|
|||||||
bool32 ProteanTryChangeType(u32 battler, u32 ability, u32 move, u32 moveType);
|
bool32 ProteanTryChangeType(u32 battler, u32 ability, u32 move, u32 moveType);
|
||||||
bool32 DoSwitchInAbilitiesItems(u32 battlerId);
|
bool32 DoSwitchInAbilitiesItems(u32 battlerId);
|
||||||
u8 GetFirstFaintedPartyIndex(u8 battlerId);
|
u8 GetFirstFaintedPartyIndex(u8 battlerId);
|
||||||
|
bool32 IsMoveAffectedByParentalBond(u32 move, u32 battler);
|
||||||
|
|
||||||
extern void (* const gBattleScriptingCommandsTable[])(void);
|
extern void (* const gBattleScriptingCommandsTable[])(void);
|
||||||
extern const u8 gBattlePalaceNatureToMoveGroupLikelihood[NUM_NATURES][4];
|
extern const u8 gBattlePalaceNatureToMoveGroupLikelihood[NUM_NATURES][4];
|
||||||
|
@ -102,6 +102,7 @@ bool32 IsAffectedByFollowMe(u32 battlerAtk, u32 defSide, u32 move);
|
|||||||
void HandleAction_UseMove(void);
|
void HandleAction_UseMove(void);
|
||||||
void HandleAction_Switch(void);
|
void HandleAction_Switch(void);
|
||||||
void HandleAction_UseItem(void);
|
void HandleAction_UseItem(void);
|
||||||
|
bool32 TryRunFromBattle(u32 battler);
|
||||||
void HandleAction_Run(void);
|
void HandleAction_Run(void);
|
||||||
void HandleAction_WatchesCarefully(void);
|
void HandleAction_WatchesCarefully(void);
|
||||||
void HandleAction_SafariZoneBallThrow(void);
|
void HandleAction_SafariZoneBallThrow(void);
|
||||||
@ -116,106 +117,106 @@ u8 GetBattlerForBattleScript(u8 caseId);
|
|||||||
void PressurePPLose(u8 target, u8 attacker, u16 move);
|
void PressurePPLose(u8 target, u8 attacker, u16 move);
|
||||||
void PressurePPLoseOnUsingPerishSong(u8 attacker);
|
void PressurePPLoseOnUsingPerishSong(u8 attacker);
|
||||||
void PressurePPLoseOnUsingImprison(u8 attacker);
|
void PressurePPLoseOnUsingImprison(u8 attacker);
|
||||||
bool32 IsBattlerMarkedForControllerExec(u8 battler);
|
bool32 IsBattlerMarkedForControllerExec(u32 battler);
|
||||||
void MarkBattlerForControllerExec(u8 battler);
|
void MarkBattlerForControllerExec(u32 battler);
|
||||||
void MarkBattlerReceivedLinkData(u8 battler);
|
void MarkBattlerReceivedLinkData(u32 battler);
|
||||||
void CancelMultiTurnMoves(u8 battler);
|
void CancelMultiTurnMoves(u32 battler);
|
||||||
bool8 WasUnableToUseMove(u8 battler);
|
bool32 WasUnableToUseMove(u32 battler);
|
||||||
void PrepareStringBattle(u16 stringId, u8 battler);
|
void PrepareStringBattle(u16 stringId, u32 battler);
|
||||||
void ResetSentPokesToOpponentValue(void);
|
void ResetSentPokesToOpponentValue(void);
|
||||||
void OpponentSwitchInResetSentPokesToOpponentValue(u8 battler);
|
void OpponentSwitchInResetSentPokesToOpponentValue(u32 battler);
|
||||||
void UpdateSentPokesToOpponentValue(u8 battler);
|
void UpdateSentPokesToOpponentValue(u32 battler);
|
||||||
void BattleScriptPush(const u8 *bsPtr);
|
void BattleScriptPush(const u8 *bsPtr);
|
||||||
void BattleScriptPushCursor(void);
|
void BattleScriptPushCursor(void);
|
||||||
void BattleScriptPop(void);
|
void BattleScriptPop(void);
|
||||||
u32 TrySetCantSelectMoveBattleScript(u32 battler);
|
u32 TrySetCantSelectMoveBattleScript(u32 battler);
|
||||||
u8 CheckMoveLimitations(u8 battler, u8 unusableMoves, u16 check);
|
u8 CheckMoveLimitations(u32 battler, u8 unusableMoves, u16 check);
|
||||||
bool32 AreAllMovesUnusable(u32 battler);
|
bool32 AreAllMovesUnusable(u32 battler);
|
||||||
u8 GetImprisonedMovesCount(u8 battler, u16 move);
|
u8 GetImprisonedMovesCount(u32 battler, u16 move);
|
||||||
u8 DoFieldEndTurnEffects(void);
|
u8 DoFieldEndTurnEffects(void);
|
||||||
s32 GetDrainedBigRootHp(u32 battler, s32 hp);
|
s32 GetDrainedBigRootHp(u32 battler, s32 hp);
|
||||||
u8 DoBattlerEndTurnEffects(void);
|
u8 DoBattlerEndTurnEffects(void);
|
||||||
bool8 HandleWishPerishSongOnTurnEnd(void);
|
bool32 HandleWishPerishSongOnTurnEnd(void);
|
||||||
bool8 HandleFaintedMonActions(void);
|
bool32 HandleFaintedMonActions(void);
|
||||||
void TryClearRageAndFuryCutter(void);
|
void TryClearRageAndFuryCutter(void);
|
||||||
u8 AtkCanceller_UnableToUseMove(u32 moveType);
|
u8 AtkCanceller_UnableToUseMove(u32 moveType);
|
||||||
void SetAtkCancellerForCalledMove(void);
|
void SetAtkCancellerForCalledMove(void);
|
||||||
u8 AtkCanceller_UnableToUseMove2(void);
|
u8 AtkCanceller_UnableToUseMove2(void);
|
||||||
bool8 HasNoMonsToSwitch(u8 battler, u8 r1, u8 r2);
|
bool32 HasNoMonsToSwitch(u32 battler, u8 r1, u8 r2);
|
||||||
bool32 TryChangeBattleWeather(u8 battler, u32 weatherEnumId, bool32 viaAbility);
|
bool32 TryChangeBattleWeather(u32 battler, u32 weatherEnumId, bool32 viaAbility);
|
||||||
u8 AbilityBattleEffects(u8 caseID, u8 battler, u16 ability, u8 special, u16 moveArg);
|
u32 AbilityBattleEffects(u32 caseID, u32 battler, u32 ability, u32 special, u32 moveArg);
|
||||||
bool32 TryPrimalReversion(u8 battler);
|
bool32 TryPrimalReversion(u32 battler);
|
||||||
bool32 IsNeutralizingGasOnField(void);
|
bool32 IsNeutralizingGasOnField(void);
|
||||||
u32 GetBattlerAbility(u8 battler);
|
u32 GetBattlerAbility(u32 battler);
|
||||||
u32 IsAbilityOnSide(u32 battler, u32 ability);
|
u32 IsAbilityOnSide(u32 battler, u32 ability);
|
||||||
u32 IsAbilityOnOpposingSide(u32 battler, u32 ability);
|
u32 IsAbilityOnOpposingSide(u32 battler, u32 ability);
|
||||||
u32 IsAbilityOnField(u32 ability);
|
u32 IsAbilityOnField(u32 ability);
|
||||||
u32 IsAbilityOnFieldExcept(u32 battler, u32 ability);
|
u32 IsAbilityOnFieldExcept(u32 battler, u32 ability);
|
||||||
u32 IsAbilityPreventingEscape(u32 battler);
|
u32 IsAbilityPreventingEscape(u32 battler);
|
||||||
bool32 IsBattlerProtected(u8 battler, u16 move);
|
bool32 IsBattlerProtected(u32 battler, u32 move);
|
||||||
bool32 CanBattlerEscape(u32 battler); // no ability check
|
bool32 CanBattlerEscape(u32 battler); // no ability check
|
||||||
void BattleScriptExecute(const u8 *BS_ptr);
|
void BattleScriptExecute(const u8 *BS_ptr);
|
||||||
void BattleScriptPushCursorAndCallback(const u8 *BS_ptr);
|
void BattleScriptPushCursorAndCallback(const u8 *BS_ptr);
|
||||||
u8 ItemBattleEffects(u8 caseID, u8 battler, bool8 moveTurn);
|
u8 ItemBattleEffects(u8 caseID, u32 battler, bool32 moveTurn);
|
||||||
void ClearFuryCutterDestinyBondGrudge(u8 battler);
|
void ClearFuryCutterDestinyBondGrudge(u32 battler);
|
||||||
void HandleAction_RunBattleScript(void);
|
void HandleAction_RunBattleScript(void);
|
||||||
u32 SetRandomTarget(u32 battler);
|
u32 SetRandomTarget(u32 battler);
|
||||||
u32 GetMoveTarget(u16 move, u8 setTarget);
|
u32 GetMoveTarget(u16 move, u8 setTarget);
|
||||||
u8 IsMonDisobedient(void);
|
u8 IsMonDisobedient(void);
|
||||||
u32 GetBattlerHoldEffect(u8 battler, bool32 checkNegating);
|
u32 GetBattlerHoldEffect(u32 battler, bool32 checkNegating);
|
||||||
u32 GetBattlerHoldEffectParam(u8 battler);
|
u32 GetBattlerHoldEffectParam(u32 battler);
|
||||||
bool32 IsMoveMakingContact(u16 move, u8 battlerAtk);
|
bool32 IsMoveMakingContact(u32 move, u32 battlerAtk);
|
||||||
bool32 IsBattlerGrounded(u8 battler);
|
bool32 IsBattlerGrounded(u32 battler);
|
||||||
bool32 IsBattlerAlive(u8 battler);
|
bool32 IsBattlerAlive(u32 battler);
|
||||||
u8 GetBattleMonMoveSlot(struct BattlePokemon *battleMon, u16 move);
|
u32 GetMoveSlot(u16 *moves, u32 move);
|
||||||
u32 GetBattlerWeight(u8 battler);
|
u32 GetBattlerWeight(u32 battler);
|
||||||
u32 CalcRolloutBasePower(u32 battlerAtk, u32 basePower, u32 rolloutTimer);
|
u32 CalcRolloutBasePower(u32 battlerAtk, u32 basePower, u32 rolloutTimer);
|
||||||
u32 CalcFuryCutterBasePower(u32 basePower, u32 furyCutterCounter);
|
u32 CalcFuryCutterBasePower(u32 basePower, u32 furyCutterCounter);
|
||||||
s32 CalculateMoveDamage(u16 move, u8 battlerAtk, u8 battlerDef, u8 moveType, s32 fixedBasePower, bool32 isCrit, bool32 randomFactor, bool32 updateFlags);
|
s32 CalculateMoveDamage(u32 move, u32 battlerAtk, u32 battlerDef, u32 moveType, s32 fixedBasePower, bool32 isCrit, bool32 randomFactor, bool32 updateFlags);
|
||||||
s32 CalculateMoveDamageAndEffectiveness(u16 move, u8 battlerAtk, u8 battlerDef, u8 moveType, s32 fixedBasePower, uq4_12_t *typeEffectivenessModifier);
|
s32 CalculateMoveDamageVars(u32 move, u32 battlerAtk, u32 battlerDef, u32 moveType, s32 fixedBasePower, uq4_12_t typeEffectivenessModifier,
|
||||||
uq4_12_t CalcTypeEffectivenessMultiplier(u16 move, u8 moveType, u8 battlerAtk, u8 battlerDef, bool32 recordAbilities);
|
u32 weather, bool32 isCrit, u32 holdEffectAtk, u32 holdEffectDef, u32 abilityAtk, u32 abilityDef);
|
||||||
|
uq4_12_t CalcTypeEffectivenessMultiplier(u32 move, u32 moveType, u32 battlerAtk, u32 battlerDef, u32 defAbility, bool32 recordAbilities);
|
||||||
uq4_12_t CalcPartyMonTypeEffectivenessMultiplier(u16 move, u16 speciesDef, u16 abilityDef);
|
uq4_12_t CalcPartyMonTypeEffectivenessMultiplier(u16 move, u16 speciesDef, u16 abilityDef);
|
||||||
uq4_12_t GetTypeModifier(u8 atkType, u8 defType);
|
uq4_12_t GetTypeModifier(u32 atkType, u32 defType);
|
||||||
s32 GetStealthHazardDamage(u8 hazardType, u8 battler);
|
s32 GetStealthHazardDamage(u8 hazardType, u32 battler);
|
||||||
s32 GetStealthHazardDamageByTypesAndHP(u8 hazardType, u8 type1, u8 type2, u32 maxHp);
|
s32 GetStealthHazardDamageByTypesAndHP(u8 hazardType, u8 type1, u8 type2, u32 maxHp);
|
||||||
bool32 CanMegaEvolve(u8 battler);
|
bool32 CanMegaEvolve(u32 battler);
|
||||||
bool32 CanUltraBurst(u8 battler);
|
bool32 CanUltraBurst(u32 battler);
|
||||||
bool32 IsBattlerMegaEvolved(u8 battler);
|
bool32 IsBattlerMegaEvolved(u32 battler);
|
||||||
bool32 IsBattlerPrimalReverted(u8 battler);
|
bool32 IsBattlerPrimalReverted(u32 battler);
|
||||||
bool32 IsBattlerUltraBursted(u8 battler);
|
bool32 IsBattlerUltraBursted(u32 battler);
|
||||||
u16 GetBattleFormChangeTargetSpecies(u8 battler, u16 method);
|
u16 GetBattleFormChangeTargetSpecies(u32 battler, u16 method);
|
||||||
bool32 TryBattleFormChange(u8 battler, u16 method);
|
bool32 TryBattleFormChange(u32 battler, u16 method);
|
||||||
bool32 DoBattlersShareType(u32 battler1, u32 battler2);
|
bool32 DoBattlersShareType(u32 battler1, u32 battler2);
|
||||||
bool32 CanBattlerGetOrLoseItem(u8 battler, u16 itemId);
|
bool32 CanBattlerGetOrLoseItem(u32 battler, u16 itemId);
|
||||||
u32 GetIllusionMonSpecies(u32 battler);
|
u32 GetIllusionMonSpecies(u32 battler);
|
||||||
struct Pokemon *GetIllusionMonPtr(u32 battler);
|
struct Pokemon *GetIllusionMonPtr(u32 battler);
|
||||||
void ClearIllusionMon(u32 battler);
|
void ClearIllusionMon(u32 battler);
|
||||||
bool32 SetIllusionMon(struct Pokemon *mon, u32 battler);
|
bool32 SetIllusionMon(struct Pokemon *mon, u32 battler);
|
||||||
bool8 ShouldGetStatBadgeBoost(u16 flagId, u8 battler);
|
bool32 ShouldGetStatBadgeBoost(u16 flagId, u32 battler);
|
||||||
u8 GetBattleMoveSplit(u32 moveId);
|
u8 GetBattleMoveSplit(u32 moveId);
|
||||||
bool32 CanFling(u32 battler);
|
bool32 CanFling(u32 battler);
|
||||||
bool32 IsTelekinesisBannedSpecies(u16 species);
|
bool32 IsTelekinesisBannedSpecies(u16 species);
|
||||||
bool32 IsHealBlockPreventingMove(u32 battler, u32 move);
|
bool32 IsHealBlockPreventingMove(u32 battler, u32 move);
|
||||||
bool32 HasEnoughHpToEatBerry(u32 battler, u32 hpFraction, u32 itemId);
|
bool32 HasEnoughHpToEatBerry(u32 battler, u32 hpFraction, u32 itemId);
|
||||||
bool32 IsPartnerMonFromSameTrainer(u8 battler);
|
bool32 IsPartnerMonFromSameTrainer(u32 battler);
|
||||||
u8 GetSplitBasedOnStats(u8 battler);
|
u8 GetSplitBasedOnStats(u32 battler);
|
||||||
bool32 TestSheerForceFlag(u8 battler, u16 move);
|
bool32 TestSheerForceFlag(u32 battler, u16 move);
|
||||||
void TryRestoreHeldItems(void);
|
void TryRestoreHeldItems(void);
|
||||||
bool32 CanStealItem(u8 battlerStealing, u8 battlerItem, u16 item);
|
bool32 CanStealItem(u32 battlerStealing, u32 battlerItem, u16 item);
|
||||||
void TrySaveExchangedItem(u8 battler, u16 stolenItem);
|
void TrySaveExchangedItem(u32 battler, u16 stolenItem);
|
||||||
bool32 IsPartnerMonFromSameTrainer(u8 battler);
|
bool32 IsPartnerMonFromSameTrainer(u32 battler);
|
||||||
u8 TryHandleSeed(u8 battler, u32 terrainFlag, u8 statId, u16 itemId, bool32 execute);
|
u8 TryHandleSeed(u32 battler, u32 terrainFlag, u8 statId, u16 itemId, bool32 execute);
|
||||||
bool32 IsBattlerAffectedByHazards(u8 battler, bool32 toxicSpikes);
|
bool32 IsBattlerAffectedByHazards(u32 battler, bool32 toxicSpikes);
|
||||||
void SortBattlersBySpeed(u8 *battlers, bool8 slowToFast);
|
void SortBattlersBySpeed(u8 *battlers, bool32 slowToFast);
|
||||||
bool32 CompareStat(u8 battler, u8 statId, u8 cmpTo, u8 cmpKind);
|
bool32 CompareStat(u32 battler, u8 statId, u8 cmpTo, u8 cmpKind);
|
||||||
bool32 TryRoomService(u8 battler);
|
bool32 TryRoomService(u32 battler);
|
||||||
void BufferStatChange(u8 battler, u8 statId, u8 stringId);
|
void BufferStatChange(u32 battler, u8 statId, u8 stringId);
|
||||||
bool32 BlocksPrankster(u16 move, u8 battlerPrankster, u8 battlerDef, bool32 checkTarget);
|
bool32 BlocksPrankster(u16 move, u32 battlerPrankster, u32 battlerDef, bool32 checkTarget);
|
||||||
u16 GetUsedHeldItem(u8 battler);
|
u16 GetUsedHeldItem(u32 battler);
|
||||||
bool32 IsBattlerWeatherAffected(u8 battler, u32 weatherFlags);
|
bool32 IsBattlerWeatherAffected(u32 battler, u32 weatherFlags);
|
||||||
u32 GetBattlerMoveTargetType(u8 battler, u16 move);
|
u32 GetBattlerMoveTargetType(u32 battler, u32 move);
|
||||||
bool32 CanTargetBattler(u8 battlerAtk, u8 battlerDef, u16 move);
|
bool32 CanTargetBattler(u32 battlerAtk, u32 battlerDef, u16 move);
|
||||||
bool8 IsMoveAffectedByParentalBond(u16 move, u8 battler);
|
|
||||||
void CopyMonLevelAndBaseStatsToBattleMon(u32 battler, struct Pokemon *mon);
|
void CopyMonLevelAndBaseStatsToBattleMon(u32 battler, struct Pokemon *mon);
|
||||||
void CopyMonAbilityAndTypesToBattleMon(u32 battler, struct Pokemon *mon);
|
void CopyMonAbilityAndTypesToBattleMon(u32 battler, struct Pokemon *mon);
|
||||||
void RecalcBattlerStats(u32 battler, struct Pokemon *mon);
|
void RecalcBattlerStats(u32 battler, struct Pokemon *mon);
|
||||||
@ -231,21 +232,21 @@ bool32 IsGastroAcidBannedAbility(u16 ability);
|
|||||||
bool32 IsEntrainmentBannedAbilityAttacker(u16 ability);
|
bool32 IsEntrainmentBannedAbilityAttacker(u16 ability);
|
||||||
bool32 IsEntrainmentTargetOrSimpleBeamBannedAbility(u16 ability);
|
bool32 IsEntrainmentTargetOrSimpleBeamBannedAbility(u16 ability);
|
||||||
|
|
||||||
bool32 CanSleep(u8 battler);
|
bool32 CanSleep(u32 battler);
|
||||||
bool32 CanBePoisoned(u8 battlerAttacker, u8 battlerTarget);
|
bool32 CanBePoisoned(u32 battlerAttacker, u32 battlerTarget);
|
||||||
bool32 CanBeBurned(u8 battler);
|
bool32 CanBeBurned(u32 battler);
|
||||||
bool32 CanBeParalyzed(u8 battler);
|
bool32 CanBeParalyzed(u32 battler);
|
||||||
bool32 CanBeFrozen(u8 battler);
|
bool32 CanBeFrozen(u32 battler);
|
||||||
bool32 CanGetFrostbite(u8 battler);
|
bool32 CanGetFrostbite(u32 battler);
|
||||||
bool32 CanBeConfused(u8 battler);
|
bool32 CanBeConfused(u32 battler);
|
||||||
bool32 IsBattlerTerrainAffected(u8 battler, u32 terrainFlag);
|
bool32 IsBattlerTerrainAffected(u32 battler, u32 terrainFlag);
|
||||||
u32 GetBattlerFriendshipScore(u8 battler);
|
u32 GetBattlerFriendshipScore(u32 battler);
|
||||||
u32 CountBattlerStatIncreases(u8 battler, bool32 countEvasionAcc);
|
u32 CountBattlerStatIncreases(u32 battler, bool32 countEvasionAcc);
|
||||||
bool32 IsMyceliumMightOnField(void);
|
bool32 IsMyceliumMightOnField(void);
|
||||||
bool8 ChangeTypeBasedOnTerrain(u8 battler);
|
bool32 ChangeTypeBasedOnTerrain(u32 battler);
|
||||||
void RemoveConfusionStatus(u8 battler);
|
void RemoveConfusionStatus(u32 battler);
|
||||||
u8 GetBattlerGender(u8 battler);
|
u8 GetBattlerGender(u32 battler);
|
||||||
bool8 AreBattlersOfOppositeGender(u8 battler1, u8 battler2);
|
bool32 AreBattlersOfOppositeGender(u32 battler1, u32 battler2);
|
||||||
u32 CalcSecondaryEffectChance(u8 battler, u8 secondaryEffectChance);
|
u32 CalcSecondaryEffectChance(u32 battler, u8 secondaryEffectChance);
|
||||||
|
|
||||||
#endif // GUARD_BATTLE_UTIL_H
|
#endif // GUARD_BATTLE_UTIL_H
|
||||||
|
@ -63,8 +63,8 @@ bool8 AddPyramidBagItem(u16 itemId, u16 count);
|
|||||||
bool8 RemovePyramidBagItem(u16 itemId, u16 count);
|
bool8 RemovePyramidBagItem(u16 itemId, u16 count);
|
||||||
const u8 *ItemId_GetName(u16 itemId);
|
const u8 *ItemId_GetName(u16 itemId);
|
||||||
u16 ItemId_GetPrice(u16 itemId);
|
u16 ItemId_GetPrice(u16 itemId);
|
||||||
u8 ItemId_GetHoldEffect(u16 itemId);
|
u32 ItemId_GetHoldEffect(u32 itemId);
|
||||||
u8 ItemId_GetHoldEffectParam(u16 itemId);
|
u32 ItemId_GetHoldEffectParam(u32 itemId);
|
||||||
const u8 *ItemId_GetDescription(u16 itemId);
|
const u8 *ItemId_GetDescription(u16 itemId);
|
||||||
u8 ItemId_GetImportance(u16 itemId);
|
u8 ItemId_GetImportance(u16 itemId);
|
||||||
u8 ItemId_GetPocket(u16 itemId);
|
u8 ItemId_GetPocket(u16 itemId);
|
||||||
@ -72,7 +72,7 @@ u8 ItemId_GetType(u16 itemId);
|
|||||||
ItemUseFunc ItemId_GetFieldFunc(u16 itemId);
|
ItemUseFunc ItemId_GetFieldFunc(u16 itemId);
|
||||||
u8 ItemId_GetBattleUsage(u16 itemId);
|
u8 ItemId_GetBattleUsage(u16 itemId);
|
||||||
u8 ItemId_GetSecondaryId(u16 itemId);
|
u8 ItemId_GetSecondaryId(u16 itemId);
|
||||||
u8 ItemId_GetFlingPower(u16 itemId);
|
u32 ItemId_GetFlingPower(u32 itemId);
|
||||||
u32 GetItemStatus1Mask(u16 itemId);
|
u32 GetItemStatus1Mask(u16 itemId);
|
||||||
u32 GetItemStatus2Mask(u16 itemId);
|
u32 GetItemStatus2Mask(u16 itemId);
|
||||||
|
|
||||||
|
1437
src/battle_ai_main.c
1437
src/battle_ai_main.c
File diff suppressed because it is too large
Load Diff
@ -400,7 +400,7 @@ static bool8 ShouldSwitchIfGameStatePrompt(u32 battler)
|
|||||||
&& AnyStatIsRaised(battler))
|
&& AnyStatIsRaised(battler))
|
||||||
switchMon = FALSE;
|
switchMon = FALSE;
|
||||||
if (AiExpectsToFaintPlayer(battler)
|
if (AiExpectsToFaintPlayer(battler)
|
||||||
&& !WillAIStrikeFirst()
|
&& !AI_STRIKES_FIRST(battler, opposingBattler, 0)
|
||||||
&& !AI_OpponentCanFaintAiWithMod(battler, 0))
|
&& !AI_OpponentCanFaintAiWithMod(battler, 0))
|
||||||
switchMon = FALSE;
|
switchMon = FALSE;
|
||||||
}
|
}
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -750,7 +750,7 @@ static void SetAllPlayersBerryData(void)
|
|||||||
{
|
{
|
||||||
s32 numPlayers;
|
s32 numPlayers;
|
||||||
struct BattleEnigmaBerry *src;
|
struct BattleEnigmaBerry *src;
|
||||||
u8 battler;
|
u32 battler;
|
||||||
|
|
||||||
if (gBattleTypeFlags & BATTLE_TYPE_MULTI)
|
if (gBattleTypeFlags & BATTLE_TYPE_MULTI)
|
||||||
{
|
{
|
||||||
@ -2267,7 +2267,7 @@ static void EndLinkBattleInSteps(void)
|
|||||||
case 2:
|
case 2:
|
||||||
if (!gPaletteFade.active)
|
if (!gPaletteFade.active)
|
||||||
{
|
{
|
||||||
u8 battlerCount;
|
u32 battlerCount;
|
||||||
|
|
||||||
gMain.anyLinkBattlerHasFrontierPass = RecordedBattle_GetFrontierPassFlag();
|
gMain.anyLinkBattlerHasFrontierPass = RecordedBattle_GetFrontierPassFlag();
|
||||||
|
|
||||||
@ -3723,7 +3723,7 @@ static void DoBattleIntro(void)
|
|||||||
gBattleStruct->switchInAbilitiesCounter = 0;
|
gBattleStruct->switchInAbilitiesCounter = 0;
|
||||||
gBattleStruct->switchInItemsCounter = 0;
|
gBattleStruct->switchInItemsCounter = 0;
|
||||||
gBattleStruct->overworldWeatherDone = FALSE;
|
gBattleStruct->overworldWeatherDone = FALSE;
|
||||||
SetAiLogicDataForTurn(); // get assumed abilities, hold effects, etc of all battlers
|
SetAiLogicDataForTurn(AI_DATA); // get assumed abilities, hold effects, etc of all battlers
|
||||||
Ai_InitPartyStruct(); // Save mons party counts, and first 2/4 mons on the battlefield.
|
Ai_InitPartyStruct(); // Save mons party counts, and first 2/4 mons on the battlefield.
|
||||||
gBattleMainFunc = TryDoEventsBeforeFirstTurn;
|
gBattleMainFunc = TryDoEventsBeforeFirstTurn;
|
||||||
}
|
}
|
||||||
@ -3770,7 +3770,7 @@ static void TryDoEventsBeforeFirstTurn(void)
|
|||||||
{
|
{
|
||||||
for (j = i + 1; j < gBattlersCount; j++)
|
for (j = i + 1; j < gBattlersCount; j++)
|
||||||
{
|
{
|
||||||
if (GetWhoStrikesFirst(gBattlerByTurnOrder[i], gBattlerByTurnOrder[j], TRUE) != 0)
|
if (GetWhichBattlerFaster(gBattlerByTurnOrder[i], gBattlerByTurnOrder[j], TRUE) != 0)
|
||||||
SwapTurnOrder(i, j);
|
SwapTurnOrder(i, j);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -3856,7 +3856,7 @@ static void TryDoEventsBeforeFirstTurn(void)
|
|||||||
|
|
||||||
gRandomTurnNumber = Random();
|
gRandomTurnNumber = Random();
|
||||||
|
|
||||||
SetAiLogicDataForTurn(); // get assumed abilities, hold effects, etc of all battlers
|
SetAiLogicDataForTurn(AI_DATA); // get assumed abilities, hold effects, etc of all battlers
|
||||||
|
|
||||||
if (gBattleTypeFlags & BATTLE_TYPE_ARENA)
|
if (gBattleTypeFlags & BATTLE_TYPE_ARENA)
|
||||||
{
|
{
|
||||||
@ -3948,7 +3948,7 @@ void BattleTurnPassed(void)
|
|||||||
|
|
||||||
*(&gBattleStruct->absentBattlerFlags) = gAbsentBattlerFlags;
|
*(&gBattleStruct->absentBattlerFlags) = gAbsentBattlerFlags;
|
||||||
BattlePutTextOnWindow(gText_EmptyString3, B_WIN_MSG);
|
BattlePutTextOnWindow(gText_EmptyString3, B_WIN_MSG);
|
||||||
SetAiLogicDataForTurn(); // get assumed abilities, hold effects, etc of all battlers
|
SetAiLogicDataForTurn(AI_DATA); // get assumed abilities, hold effects, etc of all battlers
|
||||||
gBattleMainFunc = HandleTurnActionSelectionState;
|
gBattleMainFunc = HandleTurnActionSelectionState;
|
||||||
gRandomTurnNumber = Random();
|
gRandomTurnNumber = Random();
|
||||||
|
|
||||||
@ -4020,11 +4020,10 @@ u8 IsRunningFromBattleImpossible(u32 battler)
|
|||||||
return BATTLE_RUN_SUCCESS;
|
return BATTLE_RUN_SUCCESS;
|
||||||
}
|
}
|
||||||
|
|
||||||
void SwitchPartyOrder(u8 battler)
|
void SwitchPartyOrder(u32 battler)
|
||||||
{
|
{
|
||||||
s32 i;
|
s32 i;
|
||||||
u8 partyId1;
|
u32 partyId1, partyId2;
|
||||||
u8 partyId2;
|
|
||||||
|
|
||||||
for (i = 0; i < (int)ARRAY_COUNT(gBattlePartyCurrentOrder); i++)
|
for (i = 0; i < (int)ARRAY_COUNT(gBattlePartyCurrentOrder); i++)
|
||||||
gBattlePartyCurrentOrder[i] = *(battler * 3 + i + (u8 *)(gBattleStruct->battlerPartyOrders));
|
gBattlePartyCurrentOrder[i] = *(battler * 3 + i + (u8 *)(gBattleStruct->battlerPartyOrders));
|
||||||
@ -4070,7 +4069,7 @@ static void HandleTurnActionSelectionState(void)
|
|||||||
gBattleCommunication[ACTIONS_CONFIRMED_COUNT] = 0;
|
gBattleCommunication[ACTIONS_CONFIRMED_COUNT] = 0;
|
||||||
for (battler = 0; battler < gBattlersCount; battler++)
|
for (battler = 0; battler < gBattlersCount; battler++)
|
||||||
{
|
{
|
||||||
u8 position = GetBattlerPosition(battler);
|
u32 position = GetBattlerPosition(battler);
|
||||||
switch (gBattleCommunication[battler])
|
switch (gBattleCommunication[battler])
|
||||||
{
|
{
|
||||||
case STATE_TURN_START_RECORD: // Recorded battle related action on start of every turn.
|
case STATE_TURN_START_RECORD: // Recorded battle related action on start of every turn.
|
||||||
@ -4083,7 +4082,7 @@ static void HandleTurnActionSelectionState(void)
|
|||||||
{
|
{
|
||||||
gBattleStruct->aiMoveOrAction[battler] = ComputeBattleAiScores(battler);
|
gBattleStruct->aiMoveOrAction[battler] = ComputeBattleAiScores(battler);
|
||||||
}
|
}
|
||||||
break;
|
// fallthrough
|
||||||
case STATE_BEFORE_ACTION_CHOSEN: // Choose an action.
|
case STATE_BEFORE_ACTION_CHOSEN: // Choose an action.
|
||||||
*(gBattleStruct->monToSwitchIntoId + battler) = PARTY_SIZE;
|
*(gBattleStruct->monToSwitchIntoId + battler) = PARTY_SIZE;
|
||||||
if (gBattleTypeFlags & BATTLE_TYPE_MULTI
|
if (gBattleTypeFlags & BATTLE_TYPE_MULTI
|
||||||
@ -4597,11 +4596,10 @@ void SwapTurnOrder(u8 id1, u8 id2)
|
|||||||
SWAP(gBattlerByTurnOrder[id1], gBattlerByTurnOrder[id2], temp);
|
SWAP(gBattlerByTurnOrder[id1], gBattlerByTurnOrder[id2], temp);
|
||||||
}
|
}
|
||||||
|
|
||||||
u32 GetBattlerTotalSpeedStat(u8 battler)
|
// For AI, so it doesn't 'cheat' by knowing player's ability
|
||||||
|
u32 GetBattlerTotalSpeedStatArgs(u32 battler, u32 ability, u32 holdEffect)
|
||||||
{
|
{
|
||||||
u32 speed = gBattleMons[battler].speed;
|
u32 speed = gBattleMons[battler].speed;
|
||||||
u32 ability = GetBattlerAbility(battler);
|
|
||||||
u32 holdEffect = GetBattlerHoldEffect(battler, TRUE);
|
|
||||||
u32 highestStat = GetHighestStatId(battler);
|
u32 highestStat = GetHighestStatId(battler);
|
||||||
|
|
||||||
// weather abilities
|
// weather abilities
|
||||||
@ -4668,6 +4666,13 @@ u32 GetBattlerTotalSpeedStat(u8 battler)
|
|||||||
return speed;
|
return speed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
u32 GetBattlerTotalSpeedStat(u32 battler)
|
||||||
|
{
|
||||||
|
u32 ability = GetBattlerAbility(battler);
|
||||||
|
u32 holdEffect = GetBattlerHoldEffect(battler, TRUE);
|
||||||
|
return GetBattlerTotalSpeedStatArgs(battler, ability, holdEffect);
|
||||||
|
}
|
||||||
|
|
||||||
s8 GetChosenMovePriority(u32 battler)
|
s8 GetChosenMovePriority(u32 battler)
|
||||||
{
|
{
|
||||||
u16 move;
|
u16 move;
|
||||||
@ -4732,17 +4737,13 @@ s8 GetMovePriority(u32 battler, u16 move)
|
|||||||
return priority;
|
return priority;
|
||||||
}
|
}
|
||||||
|
|
||||||
u8 GetWhoStrikesFirst(u8 battler1, u8 battler2, bool8 ignoreChosenMoves)
|
// Function for AI with variables provided as arguments to speed the computation time
|
||||||
|
u32 GetWhichBattlerFasterArgs(u32 battler1, u32 battler2, bool32 ignoreChosenMoves, u32 ability1, u32 ability2,
|
||||||
|
u32 holdEffectBattler1, u32 holdEffectBattler2, u32 speedBattler1, u32 speedBattler2, s32 priority1, s32 priority2)
|
||||||
{
|
{
|
||||||
u8 strikesFirst = 0;
|
u32 strikesFirst = 0;
|
||||||
u32 speedBattler1 = 0, speedBattler2 = 0;
|
|
||||||
u32 holdEffectBattler1 = 0, holdEffectBattler2 = 0;
|
|
||||||
s8 priority1 = 0, priority2 = 0;
|
|
||||||
u16 ability1 = GetBattlerAbility(battler1), ability2 = GetBattlerAbility(battler2);
|
|
||||||
|
|
||||||
// Battler 1
|
// Battler 1
|
||||||
speedBattler1 = GetBattlerTotalSpeedStat(battler1);
|
|
||||||
holdEffectBattler1 = GetBattlerHoldEffect(battler1, TRUE);
|
|
||||||
// Quick Draw
|
// Quick Draw
|
||||||
if (!ignoreChosenMoves && ability1 == ABILITY_QUICK_DRAW && !IS_MOVE_STATUS(gChosenMoveByBattler[battler1]) && Random() % 100 < 30)
|
if (!ignoreChosenMoves && ability1 == ABILITY_QUICK_DRAW && !IS_MOVE_STATUS(gChosenMoveByBattler[battler1]) && Random() % 100 < 30)
|
||||||
gProtectStructs[battler1].quickDraw = TRUE;
|
gProtectStructs[battler1].quickDraw = TRUE;
|
||||||
@ -4753,8 +4754,6 @@ u8 GetWhoStrikesFirst(u8 battler1, u8 battler2, bool8 ignoreChosenMoves)
|
|||||||
gProtectStructs[battler1].usedCustapBerry = TRUE;
|
gProtectStructs[battler1].usedCustapBerry = TRUE;
|
||||||
|
|
||||||
// Battler 2
|
// Battler 2
|
||||||
speedBattler2 = GetBattlerTotalSpeedStat(battler2);
|
|
||||||
holdEffectBattler2 = GetBattlerHoldEffect(battler2, TRUE);
|
|
||||||
// Quick Draw
|
// Quick Draw
|
||||||
if (!ignoreChosenMoves && ability2 == ABILITY_QUICK_DRAW && !IS_MOVE_STATUS(gChosenMoveByBattler[battler2]) && Random() % 100 < 30)
|
if (!ignoreChosenMoves && ability2 == ABILITY_QUICK_DRAW && !IS_MOVE_STATUS(gChosenMoveByBattler[battler2]) && Random() % 100 < 30)
|
||||||
gProtectStructs[battler2].quickDraw = TRUE;
|
gProtectStructs[battler2].quickDraw = TRUE;
|
||||||
@ -4764,14 +4763,6 @@ u8 GetWhoStrikesFirst(u8 battler1, u8 battler2, bool8 ignoreChosenMoves)
|
|||||||
|| (holdEffectBattler2 == HOLD_EFFECT_CUSTAP_BERRY && HasEnoughHpToEatBerry(battler2, 4, gBattleMons[battler2].item))))
|
|| (holdEffectBattler2 == HOLD_EFFECT_CUSTAP_BERRY && HasEnoughHpToEatBerry(battler2, 4, gBattleMons[battler2].item))))
|
||||||
gProtectStructs[battler2].usedCustapBerry = TRUE;
|
gProtectStructs[battler2].usedCustapBerry = TRUE;
|
||||||
|
|
||||||
if (!ignoreChosenMoves)
|
|
||||||
{
|
|
||||||
if (gChosenActionByBattler[battler1] == B_ACTION_USE_MOVE)
|
|
||||||
priority1 = GetChosenMovePriority(battler1);
|
|
||||||
if (gChosenActionByBattler[battler2] == B_ACTION_USE_MOVE)
|
|
||||||
priority2 = GetChosenMovePriority(battler2);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (priority1 == priority2)
|
if (priority1 == priority2)
|
||||||
{
|
{
|
||||||
// QUICK CLAW / CUSTAP - always first
|
// QUICK CLAW / CUSTAP - always first
|
||||||
@ -4834,6 +4825,28 @@ u8 GetWhoStrikesFirst(u8 battler1, u8 battler2, bool8 ignoreChosenMoves)
|
|||||||
return strikesFirst;
|
return strikesFirst;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
u32 GetWhichBattlerFaster(u32 battler1, u32 battler2, bool32 ignoreChosenMoves)
|
||||||
|
{
|
||||||
|
s32 priority1 = 0, priority2 = 0;
|
||||||
|
u32 ability1 = GetBattlerAbility(battler1);
|
||||||
|
u32 speedBattler1 = GetBattlerTotalSpeedStat(battler1);
|
||||||
|
u32 holdEffectBattler1 = GetBattlerHoldEffect(battler1, TRUE);
|
||||||
|
u32 speedBattler2 = GetBattlerTotalSpeedStat(battler2);
|
||||||
|
u32 holdEffectBattler2 = GetBattlerHoldEffect(battler2, TRUE);
|
||||||
|
u32 ability2 = GetBattlerAbility(battler2);
|
||||||
|
|
||||||
|
if (!ignoreChosenMoves)
|
||||||
|
{
|
||||||
|
if (gChosenActionByBattler[battler1] == B_ACTION_USE_MOVE)
|
||||||
|
priority1 = GetChosenMovePriority(battler1);
|
||||||
|
if (gChosenActionByBattler[battler2] == B_ACTION_USE_MOVE)
|
||||||
|
priority2 = GetChosenMovePriority(battler2);
|
||||||
|
}
|
||||||
|
|
||||||
|
return GetWhichBattlerFasterArgs(battler1, battler2, ignoreChosenMoves, ability1, ability2,
|
||||||
|
holdEffectBattler1, holdEffectBattler2, speedBattler1, speedBattler2, priority1, priority2);
|
||||||
|
}
|
||||||
|
|
||||||
static void SetActionsAndBattlersTurnOrder(void)
|
static void SetActionsAndBattlersTurnOrder(void)
|
||||||
{
|
{
|
||||||
s32 turnOrderId = 0;
|
s32 turnOrderId = 0;
|
||||||
@ -4927,7 +4940,7 @@ static void SetActionsAndBattlersTurnOrder(void)
|
|||||||
&& gActionsByTurnOrder[i] != B_ACTION_THROW_BALL
|
&& gActionsByTurnOrder[i] != B_ACTION_THROW_BALL
|
||||||
&& gActionsByTurnOrder[j] != B_ACTION_THROW_BALL)
|
&& gActionsByTurnOrder[j] != B_ACTION_THROW_BALL)
|
||||||
{
|
{
|
||||||
if (GetWhoStrikesFirst(battler1, battler2, FALSE))
|
if (GetWhichBattlerFaster(battler1, battler2, FALSE))
|
||||||
SwapTurnOrder(i, j);
|
SwapTurnOrder(i, j);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -5091,7 +5104,7 @@ static void TryChangeTurnOrder(void)
|
|||||||
if (gActionsByTurnOrder[i] == B_ACTION_USE_MOVE
|
if (gActionsByTurnOrder[i] == B_ACTION_USE_MOVE
|
||||||
&& gActionsByTurnOrder[j] == B_ACTION_USE_MOVE)
|
&& gActionsByTurnOrder[j] == B_ACTION_USE_MOVE)
|
||||||
{
|
{
|
||||||
if (GetWhoStrikesFirst(battler1, battler2, FALSE))
|
if (GetWhichBattlerFaster(battler1, battler2, FALSE))
|
||||||
SwapTurnOrder(i, j);
|
SwapTurnOrder(i, j);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -5574,7 +5587,7 @@ void RunBattleScriptCommands(void)
|
|||||||
gBattleScriptingCommandsTable[gBattlescriptCurrInstr[0]]();
|
gBattleScriptingCommandsTable[gBattlescriptCurrInstr[0]]();
|
||||||
}
|
}
|
||||||
|
|
||||||
void SetTypeBeforeUsingMove(u16 move, u8 battlerAtk)
|
void SetTypeBeforeUsingMove(u32 move, u32 battlerAtk)
|
||||||
{
|
{
|
||||||
u32 moveType, ateType, attackerAbility;
|
u32 moveType, ateType, attackerAbility;
|
||||||
u16 holdEffect = GetBattlerHoldEffect(battlerAtk, TRUE);
|
u16 holdEffect = GetBattlerHoldEffect(battlerAtk, TRUE);
|
||||||
@ -5713,8 +5726,8 @@ void SetTypeBeforeUsingMove(u16 move, u8 battlerAtk)
|
|||||||
// var8001 - var8007: stat changes
|
// var8001 - var8007: stat changes
|
||||||
void SetTotemBoost(void)
|
void SetTotemBoost(void)
|
||||||
{
|
{
|
||||||
u8 battler = gSpecialVar_0x8000;
|
u32 battler = gSpecialVar_0x8000;
|
||||||
u8 i;
|
u32 i;
|
||||||
|
|
||||||
for (i = 0; i < (NUM_BATTLE_STATS - 1); i++)
|
for (i = 0; i < (NUM_BATTLE_STATS - 1); i++)
|
||||||
{
|
{
|
||||||
|
@ -1753,10 +1753,11 @@ static void Cmd_accuracycheck(void)
|
|||||||
{
|
{
|
||||||
CMD_ARGS(const u8 *failInstr, u16 move);
|
CMD_ARGS(const u8 *failInstr, u16 move);
|
||||||
|
|
||||||
u16 type, move = cmd->move;
|
u32 type, move = cmd->move;
|
||||||
u16 moveTarget = GetBattlerMoveTargetType(gBattlerAttacker, move);
|
u32 moveTarget = GetBattlerMoveTargetType(gBattlerAttacker, move);
|
||||||
u16 gBattlerAttackerAbility = GetBattlerAbility(gBattlerAttacker);
|
u32 abilityAtk = GetBattlerAbility(gBattlerAttacker);
|
||||||
u8 gBattlerAttackerHoldEffect = GetBattlerHoldEffect(gBattlerAttacker, TRUE);
|
u32 abilityDef = GetBattlerAbility(gBattlerTarget);
|
||||||
|
u32 holdEffectAtk = GetBattlerHoldEffect(gBattlerAttacker, TRUE);
|
||||||
|
|
||||||
if (move == ACC_CURR_MOVE)
|
if (move == ACC_CURR_MOVE)
|
||||||
move = gCurrentMove;
|
move = gCurrentMove;
|
||||||
@ -1772,7 +1773,7 @@ static void Cmd_accuracycheck(void)
|
|||||||
}
|
}
|
||||||
else if (gSpecialStatuses[gBattlerAttacker].parentalBondState == PARENTAL_BOND_2ND_HIT
|
else if (gSpecialStatuses[gBattlerAttacker].parentalBondState == PARENTAL_BOND_2ND_HIT
|
||||||
|| (gSpecialStatuses[gBattlerAttacker].multiHitOn
|
|| (gSpecialStatuses[gBattlerAttacker].multiHitOn
|
||||||
&& (gBattlerAttackerAbility == ABILITY_SKILL_LINK || gBattlerAttackerHoldEffect == HOLD_EFFECT_LOADED_DICE
|
&& (abilityAtk == ABILITY_SKILL_LINK || holdEffectAtk == HOLD_EFFECT_LOADED_DICE
|
||||||
|| !(gBattleMoves[move].effect == EFFECT_TRIPLE_KICK || gBattleMoves[move].effect == EFFECT_POPULATION_BOMB))))
|
|| !(gBattleMoves[move].effect == EFFECT_TRIPLE_KICK || gBattleMoves[move].effect == EFFECT_POPULATION_BOMB))))
|
||||||
{
|
{
|
||||||
// No acc checks for second hit of Parental Bond or multi hit moves, except Triple Kick/Triple Axel/Population Bomb
|
// No acc checks for second hit of Parental Bond or multi hit moves, except Triple Kick/Triple Axel/Population Bomb
|
||||||
@ -1792,16 +1793,16 @@ static void Cmd_accuracycheck(void)
|
|||||||
gBattlerAttacker,
|
gBattlerAttacker,
|
||||||
gBattlerTarget,
|
gBattlerTarget,
|
||||||
move,
|
move,
|
||||||
gBattlerAttackerAbility,
|
abilityAtk,
|
||||||
GetBattlerAbility(gBattlerTarget),
|
abilityDef,
|
||||||
gBattlerAttackerHoldEffect,
|
holdEffectAtk,
|
||||||
GetBattlerHoldEffect(gBattlerTarget, TRUE)
|
GetBattlerHoldEffect(gBattlerTarget, TRUE)
|
||||||
);
|
);
|
||||||
|
|
||||||
if (!RandomPercentage(RNG_ACCURACY, accuracy))
|
if (!RandomPercentage(RNG_ACCURACY, accuracy))
|
||||||
{
|
{
|
||||||
gMoveResultFlags |= MOVE_RESULT_MISSED;
|
gMoveResultFlags |= MOVE_RESULT_MISSED;
|
||||||
if (gBattlerAttackerHoldEffect == HOLD_EFFECT_BLUNDER_POLICY)
|
if (holdEffectAtk == HOLD_EFFECT_BLUNDER_POLICY)
|
||||||
gBattleStruct->blunderPolicy = TRUE; // Only activates from missing through acc/evasion checks
|
gBattleStruct->blunderPolicy = TRUE; // Only activates from missing through acc/evasion checks
|
||||||
|
|
||||||
if (gBattleTypeFlags & BATTLE_TYPE_DOUBLE &&
|
if (gBattleTypeFlags & BATTLE_TYPE_DOUBLE &&
|
||||||
@ -1811,7 +1812,7 @@ static void Cmd_accuracycheck(void)
|
|||||||
gBattleCommunication[MISS_TYPE] = B_MSG_MISSED;
|
gBattleCommunication[MISS_TYPE] = B_MSG_MISSED;
|
||||||
|
|
||||||
if (gBattleMoves[move].power)
|
if (gBattleMoves[move].power)
|
||||||
CalcTypeEffectivenessMultiplier(move, type, gBattlerAttacker, gBattlerTarget, TRUE);
|
CalcTypeEffectivenessMultiplier(move, type, gBattlerAttacker, gBattlerTarget, abilityDef, TRUE);
|
||||||
}
|
}
|
||||||
JumpIfMoveFailed(7, move);
|
JumpIfMoveFailed(7, move);
|
||||||
}
|
}
|
||||||
@ -1908,24 +1909,15 @@ static void Cmd_ppreduce(void)
|
|||||||
#endif // B_CRIT_CHANCE
|
#endif // B_CRIT_CHANCE
|
||||||
|
|
||||||
#define BENEFITS_FROM_LEEK(battler, holdEffect)((holdEffect == HOLD_EFFECT_LEEK) && (GET_BASE_SPECIES_ID(gBattleMons[battler].species) == SPECIES_FARFETCHD || gBattleMons[battler].species == SPECIES_SIRFETCHD))
|
#define BENEFITS_FROM_LEEK(battler, holdEffect)((holdEffect == HOLD_EFFECT_LEEK) && (GET_BASE_SPECIES_ID(gBattleMons[battler].species) == SPECIES_FARFETCHD || gBattleMons[battler].species == SPECIES_SIRFETCHD))
|
||||||
s32 CalcCritChanceStage(u8 battlerAtk, u8 battlerDef, u32 move, bool32 recordAbility)
|
s32 CalcCritChanceStageArgs(u32 battlerAtk, u32 battlerDef, u32 move, bool32 recordAbility, u32 abilityAtk, u32 abilityDef, u32 holdEffectAtk)
|
||||||
{
|
{
|
||||||
s32 critChance = 0;
|
s32 critChance = 0;
|
||||||
u32 abilityAtk = GetBattlerAbility(gBattlerAttacker);
|
|
||||||
u32 abilityDef = GetBattlerAbility(gBattlerTarget);
|
|
||||||
u32 holdEffectAtk = GetBattlerHoldEffect(battlerAtk, TRUE);
|
|
||||||
|
|
||||||
if (gSideStatuses[battlerDef] & SIDE_STATUS_LUCKY_CHANT
|
if (gSideStatuses[battlerDef] & SIDE_STATUS_LUCKY_CHANT
|
||||||
|| gStatuses3[gBattlerAttacker] & STATUS3_CANT_SCORE_A_CRIT)
|
|| gStatuses3[battlerAtk] & STATUS3_CANT_SCORE_A_CRIT)
|
||||||
{
|
{
|
||||||
critChance = -1;
|
critChance = -1;
|
||||||
}
|
}
|
||||||
else if (abilityDef == ABILITY_BATTLE_ARMOR || abilityDef == ABILITY_SHELL_ARMOR)
|
|
||||||
{
|
|
||||||
if (recordAbility)
|
|
||||||
RecordAbilityBattle(battlerDef, abilityDef);
|
|
||||||
critChance = -1;
|
|
||||||
}
|
|
||||||
else if (gStatuses3[battlerAtk] & STATUS3_LASER_FOCUS
|
else if (gStatuses3[battlerAtk] & STATUS3_LASER_FOCUS
|
||||||
|| gBattleMoves[move].effect == EFFECT_ALWAYS_CRIT
|
|| gBattleMoves[move].effect == EFFECT_ALWAYS_CRIT
|
||||||
|| (abilityAtk == ABILITY_MERCILESS && gBattleMons[battlerDef].status1 & STATUS1_PSN_ANY)
|
|| (abilityAtk == ABILITY_MERCILESS && gBattleMons[battlerDef].status1 & STATUS1_PSN_ANY)
|
||||||
@ -1935,28 +1927,42 @@ s32 CalcCritChanceStage(u8 battlerAtk, u8 battlerDef, u32 move, bool32 recordAbi
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
critChance = 2 * ((gBattleMons[gBattlerAttacker].status2 & STATUS2_FOCUS_ENERGY) != 0)
|
critChance = 2 * ((gBattleMons[battlerAtk].status2 & STATUS2_FOCUS_ENERGY) != 0)
|
||||||
+ (gBattleMoves[gCurrentMove].highCritRatio)
|
+ (gBattleMoves[gCurrentMove].highCritRatio)
|
||||||
+ (holdEffectAtk == HOLD_EFFECT_SCOPE_LENS)
|
+ (holdEffectAtk == HOLD_EFFECT_SCOPE_LENS)
|
||||||
+ 2 * (holdEffectAtk == HOLD_EFFECT_LUCKY_PUNCH && gBattleMons[gBattlerAttacker].species == SPECIES_CHANSEY)
|
+ 2 * (holdEffectAtk == HOLD_EFFECT_LUCKY_PUNCH && gBattleMons[battlerAtk].species == SPECIES_CHANSEY)
|
||||||
+ 2 * BENEFITS_FROM_LEEK(battlerAtk, holdEffectAtk)
|
+ 2 * BENEFITS_FROM_LEEK(battlerAtk, holdEffectAtk)
|
||||||
#if B_AFFECTION_MECHANICS == TRUE
|
#if B_AFFECTION_MECHANICS == TRUE
|
||||||
+ 2 * (GetBattlerFriendshipScore(gBattlerAttacker) >= FRIENDSHIP_200_TO_254)
|
+ 2 * (GetBattlerFriendshipScore(battlerAtk) >= FRIENDSHIP_200_TO_254)
|
||||||
#endif
|
#endif
|
||||||
+ (abilityAtk == ABILITY_SUPER_LUCK);
|
+ (abilityAtk == ABILITY_SUPER_LUCK);
|
||||||
|
|
||||||
|
if (abilityDef == ABILITY_BATTLE_ARMOR || abilityDef == ABILITY_SHELL_ARMOR)
|
||||||
|
{
|
||||||
|
if (recordAbility && critChance >= 2) // Record ability only if move had at least +1 chance to get a crit.
|
||||||
|
RecordAbilityBattle(battlerDef, abilityDef);
|
||||||
|
critChance = -1;
|
||||||
|
}
|
||||||
|
|
||||||
if (critChance >= ARRAY_COUNT(sCriticalHitChance))
|
if (critChance >= ARRAY_COUNT(sCriticalHitChance))
|
||||||
critChance = ARRAY_COUNT(sCriticalHitChance) - 1;
|
critChance = ARRAY_COUNT(sCriticalHitChance) - 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
return critChance;
|
return critChance;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
s32 CalcCritChanceStage(u32 battlerAtk, u32 battlerDef, u32 move, bool32 recordAbility)
|
||||||
|
{
|
||||||
|
u32 abilityAtk = GetBattlerAbility(gBattlerAttacker);
|
||||||
|
u32 abilityDef = GetBattlerAbility(gBattlerTarget);
|
||||||
|
u32 holdEffectAtk = GetBattlerHoldEffect(battlerAtk, TRUE);
|
||||||
|
return CalcCritChanceStageArgs(battlerAtk, battlerDef, move, recordAbility, abilityAtk, abilityDef, holdEffectAtk);
|
||||||
|
}
|
||||||
#undef BENEFITS_FROM_LEEK
|
#undef BENEFITS_FROM_LEEK
|
||||||
|
|
||||||
s8 GetInverseCritChance(u8 battlerAtk, u8 battlerDef, u32 move)
|
s32 GetCritHitChance(s32 critChanceIndex)
|
||||||
{
|
{
|
||||||
s32 critChanceIndex = CalcCritChanceStage(battlerAtk, battlerDef, move, FALSE);
|
if (critChanceIndex < 0)
|
||||||
if(critChanceIndex < 0)
|
|
||||||
return -1;
|
return -1;
|
||||||
else
|
else
|
||||||
return sCriticalHitChance[critChanceIndex];
|
return sCriticalHitChance[critChanceIndex];
|
||||||
@ -2006,7 +2012,7 @@ static void Cmd_typecalc(void)
|
|||||||
u8 moveType;
|
u8 moveType;
|
||||||
|
|
||||||
GET_MOVE_TYPE(gCurrentMove, moveType);
|
GET_MOVE_TYPE(gCurrentMove, moveType);
|
||||||
CalcTypeEffectivenessMultiplier(gCurrentMove, moveType, gBattlerAttacker, gBattlerTarget, TRUE);
|
CalcTypeEffectivenessMultiplier(gCurrentMove, moveType, gBattlerAttacker, gBattlerTarget, GetBattlerAbility(gBattlerTarget), TRUE);
|
||||||
|
|
||||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||||
}
|
}
|
||||||
@ -5679,6 +5685,7 @@ static void Cmd_moveend(void)
|
|||||||
if (!gSpecialStatuses[gBattlerAttacker].dancerUsedMove)
|
if (!gSpecialStatuses[gBattlerAttacker].dancerUsedMove)
|
||||||
{
|
{
|
||||||
gLastMoves[gBattlerAttacker] = gChosenMove;
|
gLastMoves[gBattlerAttacker] = gChosenMove;
|
||||||
|
RecordKnownMove(gBattlerAttacker, gChosenMove);
|
||||||
gLastResultingMoves[gBattlerAttacker] = gCurrentMove;
|
gLastResultingMoves[gBattlerAttacker] = gCurrentMove;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -8197,7 +8204,7 @@ static void RemoveAllTerrains(void)
|
|||||||
} \
|
} \
|
||||||
}
|
}
|
||||||
|
|
||||||
static bool32 TryDefogClear(u8 battlerAtk, bool32 clear)
|
static bool32 TryDefogClear(u32 battlerAtk, bool32 clear)
|
||||||
{
|
{
|
||||||
s32 i;
|
s32 i;
|
||||||
for (i = 0; i < 2; i++)
|
for (i = 0; i < 2; i++)
|
||||||
@ -14703,7 +14710,7 @@ static void Cmd_settypebasedhalvers(void)
|
|||||||
gBattlescriptCurrInstr = cmd->failInstr;
|
gBattlescriptCurrInstr = cmd->failInstr;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool32 DoesSubstituteBlockMove(u8 battlerAtk, u8 battlerDef, u32 move)
|
bool32 DoesSubstituteBlockMove(u32 battlerAtk, u32 battlerDef, u32 move)
|
||||||
{
|
{
|
||||||
if (!(gBattleMons[battlerDef].status2 & STATUS2_SUBSTITUTE))
|
if (!(gBattleMons[battlerDef].status2 & STATUS2_SUBSTITUTE))
|
||||||
return FALSE;
|
return FALSE;
|
||||||
@ -14719,7 +14726,7 @@ bool32 DoesSubstituteBlockMove(u8 battlerAtk, u8 battlerDef, u32 move)
|
|||||||
return TRUE;
|
return TRUE;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool32 DoesDisguiseBlockMove(u8 battlerAtk, u8 battlerDef, u32 move)
|
bool32 DoesDisguiseBlockMove(u32 battlerAtk, u32 battlerDef, u32 move)
|
||||||
{
|
{
|
||||||
if (gBattleMons[battlerDef].species != SPECIES_MIMIKYU
|
if (gBattleMons[battlerDef].species != SPECIES_MIMIKYU
|
||||||
|| gBattleMons[battlerDef].status2 & STATUS2_TRANSFORMED
|
|| gBattleMons[battlerDef].status2 & STATUS2_TRANSFORMED
|
||||||
@ -15781,7 +15788,7 @@ static const u16 sParentalBondBannedEffects[] =
|
|||||||
EFFECT_UPROAR,
|
EFFECT_UPROAR,
|
||||||
};
|
};
|
||||||
|
|
||||||
bool8 IsMoveAffectedByParentalBond(u16 move, u8 battler)
|
bool32 IsMoveAffectedByParentalBond(u32 move, u32 battler)
|
||||||
{
|
{
|
||||||
if (move != MOVE_NONE && move != MOVE_STRUGGLE
|
if (move != MOVE_NONE && move != MOVE_STRUGGLE
|
||||||
&& gBattleMoves[move].split != SPLIT_STATUS
|
&& gBattleMoves[move].split != SPLIT_STATUS
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -884,12 +884,12 @@ u16 ItemId_GetPrice(u16 itemId)
|
|||||||
return gItems[SanitizeItemId(itemId)].price;
|
return gItems[SanitizeItemId(itemId)].price;
|
||||||
}
|
}
|
||||||
|
|
||||||
u8 ItemId_GetHoldEffect(u16 itemId)
|
u32 ItemId_GetHoldEffect(u32 itemId)
|
||||||
{
|
{
|
||||||
return gItems[SanitizeItemId(itemId)].holdEffect;
|
return gItems[SanitizeItemId(itemId)].holdEffect;
|
||||||
}
|
}
|
||||||
|
|
||||||
u8 ItemId_GetHoldEffectParam(u16 itemId)
|
u32 ItemId_GetHoldEffectParam(u32 itemId)
|
||||||
{
|
{
|
||||||
return gItems[SanitizeItemId(itemId)].holdEffectParam;
|
return gItems[SanitizeItemId(itemId)].holdEffectParam;
|
||||||
}
|
}
|
||||||
@ -956,7 +956,7 @@ u8 ItemId_GetSecondaryId(u16 itemId)
|
|||||||
return gItems[SanitizeItemId(itemId)].secondaryId;
|
return gItems[SanitizeItemId(itemId)].secondaryId;
|
||||||
}
|
}
|
||||||
|
|
||||||
u8 ItemId_GetFlingPower(u16 itemId)
|
u32 ItemId_GetFlingPower(u32 itemId)
|
||||||
{
|
{
|
||||||
return gItems[SanitizeItemId(itemId)].flingPower;
|
return gItems[SanitizeItemId(itemId)].flingPower;
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user