Ai_TryOnAlly and reorganize files

This commit is contained in:
Evan 2020-12-20 14:47:20 -07:00
parent c5597e2e18
commit 7988a1f41d
23 changed files with 641 additions and 5812 deletions

File diff suppressed because it is too large Load Diff

View File

@ -316,7 +316,6 @@ struct BattleResources
struct StatsArray* beforeLvlUp;
struct AI_ThinkingStruct *ai;
struct BattleHistory *battleHistory;
struct BattleScriptsStack *AI_ScriptsStack;
u8 bufferA[MAX_BATTLERS_COUNT][0x200];
u8 bufferB[MAX_BATTLERS_COUNT][0x200];
};

View File

@ -1,5 +1,5 @@
#ifndef GUARD_BATTLE_AI_SCRIPT_COMMANDS_H
#define GUARD_BATTLE_AI_SCRIPT_COMMANDS_H
#ifndef GUARD_BATTLE_AI_MAIN_H
#define GUARD_BATTLE_AI_MAIN_H
// return values for BattleAI_ChooseMoveOrAction
// 0 - 3 are move idx
@ -11,10 +11,7 @@ void BattleAI_SetupItems(void);
void BattleAI_SetupFlags(void);
void BattleAI_SetupAIData(u8 defaultScoreMoves);
u8 BattleAI_ChooseMoveOrAction(void);
bool32 IsTruantMonVulnerable(u32 battlerAI, u32 opposingBattler);
bool32 IsBattlerAIControlled(u32 battlerId);
void ClearBattlerMoveHistory(u8 battlerId);
extern u8 sBattler_AI;
#endif // GUARD_BATTLE_AI_SCRIPT_COMMANDS_H
#endif // GUARD_BATTLE_AI_MAIN_H

View File

@ -20,6 +20,8 @@ void SaveBattlerData(u8 battlerId);
void SetBattlerData(u8 battlerId);
void RestoreBattlerData(u8 battlerId);
u32 GetTotalBaseStat(u32 species);
bool32 IsTruantMonVulnerable(u32 battlerAI, u32 opposingBattler);
bool32 AtMaxHp(u8 battler);
u32 GetHealthPercentage(u8 battler);
bool32 IsBattlerTrapped(u8 battler, bool8 switching);
@ -105,12 +107,17 @@ bool32 HasHealingEffect(u32 battler);
bool32 ShouldFakeOut(u8 battlerAtk, u8 battlerDef, u16 move);
bool32 IsThawingMove(u16 move);
bool32 HasThawingMove(u8 battlerId);
bool32 IsStatRaisingEffect(u16 effect);
bool32 IsStatLoweringEffect(u16 effect);
bool32 IsStatRaisingEffect(u16 effect);
bool32 IsAttackBoostMoveEffect(u16 effect);
// status checks
bool32 CanBeBurned(u8 battler, u16 ability);
bool32 CanBePoisoned(u8 battler, u16 ability);
bool32 IsBattlerIncapacitated(u8 battler, u16 ability);
bool32 CanBeConfused(u8 battler, u16 ability);
bool32 CanSleep(u8 battler, u16 ability);
bool32 IsBattlerIncapacitated(u8 battler, u16 ability);
bool32 AI_CanPutToSleep(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u16 partnerMove);
bool32 ShouldPoisonSelf(u8 battler, u16 ability);
bool32 AI_CanPoison(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u16 partnerMove);

View File

@ -43,12 +43,13 @@
#define AI_FLAG_RISKY (1 << 4)
#define AI_FLAG_PREFER_STRONGEST_MOVE (1 << 5)
#define AI_FLAG_PREFER_BATON_PASS (1 << 6)
#define AI_FLAG_DOUBLE_BATTLE (1 << 7)
#define AI_FLAG_DOUBLE_BATTLE (1 << 7) // removed, split between AI_FLAG_CHECK_BAD_MOVE & AI_FLAG_CHECK_GOOD_MOVE
#define AI_FLAG_HP_AWARE (1 << 8)
// Flags that don't run specific checks themselves, but are used in other score functions
#define AI_FLAG_NEGATE_AWARE (1 << 9) // AI is aware of negating effects like wonder room, mold breaker, etc (eg. smart trainers). TODO unfinished
#define AI_FLAG_HELP_PARTNER (1 << 10) // AI can try to help partner. If not set, will tend not to target partner
#define AI_FLAG_WILL_SUICIDE (1 << 11) // AI will use explosion / self destruct / final gambit / etc
// New, Trainer Handicap Flags
#define AI_FLAG_NEGATE_UNAWARE (1 << 9) // AI is NOT aware of negating effects like wonder room, mold breaker, etc
#define AI_FLAG_WILL_SUICIDE (1 << 10) // AI will use explosion / self destruct / final gambit / etc
// New, Trainer Strategy Flags
#define AI_FLAG_HELP_PARTNER (1 << 11) // AI can try to help partner. If not set, will tend not to target partner
#define AI_FLAG_PREFER_STATUS_MOVES (1 << 12) // AI gets a score bonus for status moves. Should be combined with AI_FLAG_CHECK_BAD_MOVE to prevent using only status moves
#define AI_FLAG_STALL (1 << 13) // AI stalls battle and prefers secondary damage/trapping/etc. TODO not finished
#define AI_FLAG_SCREENER (1 << 14) // AI prefers screening effects like reflect, mist, etc. TODO unfinished

View File

@ -213,7 +213,7 @@ SECTIONS {
src/decoration.o(.text);
src/slot_machine.o(.text);
src/contest_painting.o(.text);
src/battle_ai_script_commands.o(.text);
src/battle_ai_main.o(.text);
src/battle_ai_util.o(.text);
src/trader.o(.text);
src/starter_choose.o(.text);
@ -346,7 +346,6 @@ SECTIONS {
data/battle_scripts_1.o(script_data);
data/field_effect_scripts.o(script_data);
data/battle_scripts_2.o(script_data);
data/battle_ai_scripts.o(script_data);
data/contest_ai_scripts.o(script_data);
data/mystery_event_script_cmd_table.o(script_data);
} =0
@ -589,7 +588,7 @@ SECTIONS {
src/decoration.o(.rodata);
src/slot_machine.o(.rodata);
src/contest_painting.o(.rodata);
src/battle_ai_script_commands.o(.rodata);
src/battle_ai_main.o(.rodata);
src/battle_ai_util.o(.rodata);
src/trader.o(.rodata);
src/starter_choose.o(.rodata);

File diff suppressed because it is too large Load Diff

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_ai_util.h"
#include "battle_anim.h"
#include "battle_controllers.h"

View File

@ -3,7 +3,7 @@
#include "battle.h"
#include "battle_anim.h"
#include "battle_ai_util.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_ai_switch_items.h"
#include "battle_factory.h"
#include "battle_setup.h"
@ -603,6 +603,31 @@ bool32 IsBattlerTrapped(u8 battler, bool8 checkSwitch)
return FALSE;
}
u32 GetTotalBaseStat(u32 species)
{
return gBaseStats[species].baseHP
+ gBaseStats[species].baseAttack
+ gBaseStats[species].baseDefense
+ gBaseStats[species].baseSpeed
+ gBaseStats[species].baseSpAttack
+ gBaseStats[species].baseSpDefense;
}
bool32 IsTruantMonVulnerable(u32 battlerAI, u32 opposingBattler)
{
int i;
for (i = 0; i < MAX_MON_MOVES; i++)
{
u32 move = gBattleResources->battleHistory->usedMoves[opposingBattler][i];
if (gBattleMoves[move].effect == EFFECT_PROTECT && move != MOVE_ENDURE)
return TRUE;
if (gBattleMoves[move].effect == EFFECT_SEMI_INVULNERABLE && GetWhoStrikesFirst(battlerAI, opposingBattler, TRUE) == 1)
return TRUE;
}
return FALSE;
}
// move checks
bool32 IsAffectedByPowder(u8 battler, u16 ability, u16 holdEffect)
{
@ -1028,15 +1053,15 @@ u16 AI_GetHoldEffect(u32 battlerId)
else
holdEffect = GetBattlerHoldEffect(battlerId, FALSE);
if (AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_AWARE)
{
if (gStatuses3[battlerId] & STATUS3_EMBARGO)
return HOLD_EFFECT_NONE;
if (gFieldStatuses & STATUS_FIELD_MAGIC_ROOM)
return HOLD_EFFECT_NONE;
if (AI_GetAbility(battlerId) == ABILITY_KLUTZ && !(gStatuses3[battlerId] & STATUS3_GASTRO_ACID))
return HOLD_EFFECT_NONE;
}
if (AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_UNAWARE)
return holdEffect;
if (gStatuses3[battlerId] & STATUS3_EMBARGO)
return HOLD_EFFECT_NONE;
if (gFieldStatuses & STATUS_FIELD_MAGIC_ROOM)
return HOLD_EFFECT_NONE;
if (AI_GetAbility(battlerId) == ABILITY_KLUTZ && !(gStatuses3[battlerId] & STATUS3_GASTRO_ACID))
return HOLD_EFFECT_NONE;
}
// different from IsBattlerGrounded in that we don't always know battler's hold effect or ability
@ -1070,7 +1095,7 @@ bool32 DoesBattlerIgnoreAbilityChecks(u16 atkAbility, u16 move)
{
u32 i;
if (!(AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_AWARE))
if (AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_UNAWARE)
return FALSE; // AI doesn't understand ability suppression concept
for (i = 0; i < ARRAY_COUNT(sIgnoreMoldBreakerMoves); i++)
@ -1089,7 +1114,7 @@ bool32 DoesBattlerIgnoreAbilityChecks(u16 atkAbility, u16 move)
bool32 AI_WeatherHasEffect(void)
{
if (!(AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_AWARE))
if (AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_UNAWARE)
return FALSE; // AI doesn't understand ability suppression concept
return WEATHER_HAS_EFFECT;
@ -1183,7 +1208,7 @@ bool32 IsHazardMoveEffect(u16 moveEffect)
bool32 IsMoveRedirectionPrevented(u16 move, u16 atkAbility)
{
if (!(AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_AWARE))
if (AI_THINKING_STRUCT->aiFlags & AI_FLAG_NEGATE_UNAWARE)
return FALSE;
if (move == MOVE_SKY_DROP
@ -1844,6 +1869,95 @@ bool32 HasThawingMove(u8 battlerId)
return FALSE;
}
bool32 IsAttackBoostMoveEffect(u16 effect)
{
switch (effect)
{
case EFFECT_ATTACK_UP:
case EFFECT_ATTACK_UP_2:
case EFFECT_ATTACK_ACCURACY_UP:
case EFFECT_ATTACK_SPATK_UP:
case EFFECT_DRAGON_DANCE:
case EFFECT_COIL:
case EFFECT_BELLY_DRUM:
case EFFECT_BULK_UP:
return TRUE;
default:
return FALSE;
}
}
bool32 IsStatRaisingEffect(u16 effect)
{
switch (effect)
{
case EFFECT_ATTACK_UP:
case EFFECT_ATTACK_UP_2:
case EFFECT_DEFENSE_UP:
case EFFECT_DEFENSE_UP_2:
case EFFECT_DEFENSE_UP_3:
case EFFECT_SPEED_UP:
case EFFECT_SPEED_UP_2:
case EFFECT_SPECIAL_ATTACK_UP:
case EFFECT_SPECIAL_ATTACK_UP_2:
case EFFECT_SPECIAL_ATTACK_UP_3:
case EFFECT_SPECIAL_DEFENSE_UP:
case EFFECT_SPECIAL_DEFENSE_UP_2:
case EFFECT_ACCURACY_UP:
case EFFECT_ACCURACY_UP_2:
case EFFECT_EVASION_UP:
case EFFECT_EVASION_UP_2:
case EFFECT_MINIMIZE:
case EFFECT_DEFENSE_CURL:
case EFFECT_CHARGE:
case EFFECT_CALM_MIND:
case EFFECT_COSMIC_POWER:
case EFFECT_DRAGON_DANCE:
case EFFECT_ACUPRESSURE:
case EFFECT_SHELL_SMASH:
case EFFECT_SHIFT_GEAR:
case EFFECT_ATTACK_ACCURACY_UP:
case EFFECT_ATTACK_SPATK_UP:
case EFFECT_GROWTH:
case EFFECT_COIL:
case EFFECT_QUIVER_DANCE:
case EFFECT_BULK_UP:
case EFFECT_GEOMANCY:
case EFFECT_STOCKPILE:
return TRUE;
default:
return FALSE;
}
}
bool32 IsStatLoweringEffect(u16 effect)
{
// ignore other potentially-beneficial effects like defog, gravity
switch (effect)
{
case EFFECT_ATTACK_DOWN:
case EFFECT_DEFENSE_DOWN:
case EFFECT_SPEED_DOWN:
case EFFECT_SPECIAL_ATTACK_DOWN:
case EFFECT_SPECIAL_DEFENSE_DOWN:
case EFFECT_ACCURACY_DOWN:
case EFFECT_EVASION_DOWN:
case EFFECT_ATTACK_DOWN_2:
case EFFECT_DEFENSE_DOWN_2:
case EFFECT_SPEED_DOWN_2:
case EFFECT_SPECIAL_ATTACK_DOWN_2:
case EFFECT_SPECIAL_DEFENSE_DOWN_2:
case EFFECT_ACCURACY_DOWN_2:
case EFFECT_EVASION_DOWN_2:
case EFFECT_TICKLE:
case EFFECT_CAPTIVATE:
case EFFECT_NOBLE_ROAR:
return TRUE;
default:
return FALSE;
}
}
bool32 HasDamagingMove(u8 battlerId)
{
u32 i;
@ -2438,11 +2552,18 @@ bool32 AI_CanParalyze(u8 battlerAtk, u8 battlerDef, u16 defAbility, u16 move, u1
return TRUE;
}
bool32 CanBeConfused(u8 battler, u16 ability)
{
if ((gBattleMons[battler].status2 & STATUS2_CONFUSION)
|| (ability == ABILITY_OWN_TEMPO)
|| (IsBattlerGrounded(battler) && (gFieldStatuses & STATUS_FIELD_MISTY_TERRAIN)))
return FALSE;
return TRUE;
}
bool32 AI_CanConfuse(u8 battlerAtk, u8 battlerDef, u16 defAbility, u8 battlerAtkPartner, u16 move, u16 partnerMove)
{
if ((gBattleMons[battlerDef].status2 & STATUS2_CONFUSION)
|| (!DoesBattlerIgnoreAbilityChecks(battlerAtk, move) && defAbility == ABILITY_OWN_TEMPO)
|| (IsBattlerGrounded(battlerDef) && (gFieldStatuses & STATUS_FIELD_MISTY_TERRAIN))
if (CanBeConfused(battlerDef, defAbility)
|| gSideStatuses[GetBattlerSide(battlerDef)] & SIDE_STATUS_SAFEGUARD
|| DoesSubstituteBlockMove(battlerAtk, battlerDef, move)
|| DoesPartnerHaveSameMoveEffect(battlerAtkPartner, battlerDef, move, partnerMove))

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_controllers.h"
#include "battle_interface.h"

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_controllers.h"
#include "battle_interface.h"

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_arena.h"
#include "battle_controllers.h"

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_controllers.h"
#include "battle_message.h"

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_controllers.h"
#include "battle_interface.h"

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_controllers.h"
#include "battle_message.h"

View File

@ -1,6 +1,6 @@
#include "global.h"
#include "battle.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "battle_controllers.h"
#include "battle_message.h"

View File

@ -18,7 +18,8 @@
#include "text_window.h"
#include "international_string_util.h"
#include "strings.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_ai_util.h"
#include "list_menu.h"
#include "decompress.h"
#include "trainer_pokemon_sprites.h"

View File

@ -1,7 +1,7 @@
#include "global.h"
#include "battle.h"
#include "battle_controllers.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_anim.h"
#include "constants/battle_anim.h"
#include "battle_interface.h"

View File

@ -1,7 +1,7 @@
#include "global.h"
#include "battle.h"
#include "battle_anim.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_ai_util.h"
#include "battle_arena.h"
#include "battle_controllers.h"

View File

@ -4,7 +4,7 @@
#include "constants/battle_script_commands.h"
#include "battle_message.h"
#include "battle_anim.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_ai_util.h"
#include "battle_scripts.h"
#include "constants/moves.h"

View File

@ -23,7 +23,7 @@
#include "trig.h"
#include "window.h"
#include "battle_message.h"
#include "battle_ai_script_commands.h"
#include "battle_ai_main.h"
#include "battle_ai_util.h"
#include "event_data.h"
#include "link.h"

View File

@ -26,7 +26,6 @@ void AllocateBattleResources(void)
gBattleResources->beforeLvlUp = AllocZeroed(sizeof(*gBattleResources->beforeLvlUp));
gBattleResources->ai = AllocZeroed(sizeof(*gBattleResources->ai));
gBattleResources->battleHistory = AllocZeroed(sizeof(*gBattleResources->battleHistory));
gBattleResources->AI_ScriptsStack = AllocZeroed(sizeof(*gBattleResources->AI_ScriptsStack));
gLinkBattleSendBuffer = AllocZeroed(BATTLE_BUFFER_LINK_SIZE);
gLinkBattleRecvBuffer = AllocZeroed(BATTLE_BUFFER_LINK_SIZE);
@ -58,7 +57,6 @@ void FreeBattleResources(void)
FREE_AND_SET_NULL(gBattleResources->beforeLvlUp);
FREE_AND_SET_NULL(gBattleResources->ai);
FREE_AND_SET_NULL(gBattleResources->battleHistory);
FREE_AND_SET_NULL(gBattleResources->AI_ScriptsStack);
FREE_AND_SET_NULL(gBattleResources);
FREE_AND_SET_NULL(gLinkBattleSendBuffer);

View File

@ -91,7 +91,7 @@
.include "src/region_map.o"
.include "src/decoration.o"
.include "src/slot_machine.o"
.include "src/battle_ai_script_commands.o"
.include "src/battle_ai_main.o"
.include "src/fldeff_misc.o"
.include "src/pokeblock.o"
.include "src/field_specials.o"