readd CANCELLER_GHOST, update some battle_main functions

This commit is contained in:
cawtds 2024-11-01 22:16:36 +01:00
parent a50af80042
commit 93d24a77d4
3 changed files with 66 additions and 35 deletions

View File

@ -2039,15 +2039,15 @@
@ The rest of the arguments are the stat change values to each stat.
@ For example, giving the first opponent +1 to atk and -2 to speed would be: settotemboost B_POSITION_OPPONENT_LEFT, 1, 0, -2
.macro settotemboost battler:req, atk=0,def=0,speed=0,spatk=0,spdef=0,acc=0,evas=0
setvar VAR_0x8000, \battler
setvar VAR_0x8001, \atk
setvar VAR_0x8002, \def
setvar VAR_0x8003, \speed
setvar VAR_0x8004, \spatk
setvar VAR_0x8005, \spdef
setvar VAR_0x8006, \acc
setvar VAR_0x8007, \evas
special SetTotemBoost
callnative ScriptSetTotemBoost
.2byte \battler
.2byte \atk
.2byte \def
.2byte \speed
.2byte \spatk
.2byte \spdef
.2byte \acc
.2byte \evas
.endm
@ useful totem boost macros

View File

@ -35,6 +35,7 @@
#include "roamer.h"
#include "safari_zone.h"
#include "scanline_effect.h"
#include "script.h"
#include "strings.h"
#include "task.h"
#include "test_runner.h"
@ -1659,6 +1660,7 @@ void FreeRestoreBattleData(void)
FreeMonSpritesGfx();
FreeBattleSpritesData();
FreeBattleResources();
ResetDynamicAiFunc();
}
void CB2_QuitRecordedBattle(void)
@ -4217,9 +4219,9 @@ u32 GetBattlerTotalSpeedStatArgs(u32 battler, u32 ability, u32 holdEffect)
speed *= 2;
else if (ability == ABILITY_SLOW_START && gDisableStructs[battler].slowStartTimer != 0)
speed /= 2;
else if (ability == ABILITY_PROTOSYNTHESIS && (gBattleWeather & B_WEATHER_SUN || gBattleStruct->boosterEnergyActivates & (1u << battler)))
else if (ability == ABILITY_PROTOSYNTHESIS && !(gBattleMons[battler].status2 & STATUS2_TRANSFORMED) && ((gBattleWeather & B_WEATHER_SUN && WEATHER_HAS_EFFECT) || gBattleStruct->boosterEnergyActivates & (1u << battler)))
speed = (GetHighestStatId(battler) == STAT_SPEED) ? (speed * 150) / 100 : speed;
else if (ability == ABILITY_QUARK_DRIVE && (gFieldStatuses & STATUS_FIELD_ELECTRIC_TERRAIN || gBattleStruct->boosterEnergyActivates & (1u << battler)))
else if (ability == ABILITY_QUARK_DRIVE && !(gBattleMons[battler].status2 & STATUS2_TRANSFORMED) && (gFieldStatuses & STATUS_FIELD_ELECTRIC_TERRAIN || gBattleStruct->boosterEnergyActivates & (1u << battler)))
speed = (GetHighestStatId(battler) == STAT_SPEED) ? (speed * 150) / 100 : speed;
// stat stages
@ -4599,6 +4601,9 @@ static void TurnValuesCleanUp(bool8 var0)
if (gDisableStructs[i].substituteHP == 0)
gBattleMons[i].status2 &= ~STATUS2_SUBSTITUTE;
if (!(gStatuses3[i] & STATUS3_COMMANDER))
gBattleStruct->commandingDondozo &= ~(1u << i);
gSpecialStatuses[i].parentalBondState = PARENTAL_BOND_OFF;
}
@ -4607,6 +4612,7 @@ static void TurnValuesCleanUp(bool8 var0)
gSideTimers[B_SIDE_PLAYER].followmeTimer = 0;
gSideTimers[B_SIDE_OPPONENT].followmeTimer = 0;
gBattleStruct->usedEjectItem = 0;
gBattleStruct->pledgeMove = FALSE; // combined pledge move may not have been used due to a canceller
}
@ -4670,15 +4676,15 @@ static bool32 TryDoMoveEffectsBeforeMoves(void)
{
gBattleStruct->focusPunchBattlers |= 1u << battlers[i];
gBattlerAttacker = battlers[i];
switch (gChosenMoveByBattler[gBattlerAttacker])
switch (gMovesInfo[gChosenMoveByBattler[gBattlerAttacker]].effect)
{
case MOVE_FOCUS_PUNCH:
case EFFECT_FOCUS_PUNCH:
BattleScriptExecute(BattleScript_FocusPunchSetUp);
return TRUE;
case MOVE_BEAK_BLAST:
case EFFECT_BEAK_BLAST:
BattleScriptExecute(BattleScript_BeakBlastSetUp);
return TRUE;
case MOVE_SHELL_TRAP:
case EFFECT_SHELL_TRAP:
BattleScriptExecute(BattleScript_ShellTrapSetUp);
return TRUE;
}
@ -5054,14 +5060,21 @@ static void FreeResetData_ReturnToOvOrDoEvolutions(void)
{
gBattleMainFunc = ReturnFromBattleToOverworld;
}
}
FreeAllWindowBuffers();
if (!(gBattleTypeFlags & BATTLE_TYPE_LINK))
FreeAllWindowBuffers();
if (!(gBattleTypeFlags & BATTLE_TYPE_LINK))
{
// To account for Battle Factory and Slateport Battle Tent, enemy parties are zeroed out in the facilitites respective src/xxx.c files
// The ZeroEnemyPartyMons() call happens in SaveXXXChallenge function (eg. SaveFactoryChallenge)
if (!(gBattleTypeFlags & BATTLE_TYPE_FRONTIER))
{
FreeMonSpritesGfx();
FreeBattleSpritesData();
FreeBattleResources();
ZeroEnemyPartyMons();
}
ResetDynamicAiFunc();
FreeMonSpritesGfx();
FreeBattleSpritesData();
FreeBattleResources();
}
}
@ -5071,22 +5084,29 @@ static void TryEvolvePokemon(void)
for (i = 0; i < PARTY_SIZE; i++)
{
if (!(sTriedEvolving & gBitTable[i]))
if (!(sTriedEvolving & (1u << i)))
{
u16 species = GetEvolutionTargetSpecies(&gPlayerParty[i], EVO_MODE_BATTLE_SPECIAL, i, NULL);
sTriedEvolving |= gBitTable[i];
bool32 evoModeNormal = TRUE;
sTriedEvolving |= 1u << i;
if (species == SPECIES_NONE && (gLeveledUpInBattle & gBitTable[i]))
{
gLeveledUpInBattle &= ~(gBitTable[i]);
species = GetEvolutionTargetSpecies(&gPlayerParty[i], EVO_MODE_NORMAL, gLeveledUpInBattle, NULL);
if (species == SPECIES_NONE && (gLeveledUpInBattle & (1u << i)))
{
gLeveledUpInBattle &= ~(1u << i);
species = GetEvolutionTargetSpecies(&gPlayerParty[i], EVO_MODE_BATTLE_ONLY, gLeveledUpInBattle, NULL);
}
if (species == SPECIES_NONE)
{
species = GetEvolutionTargetSpecies(&gPlayerParty[i], EVO_MODE_CANT_STOP, ITEM_NONE, NULL);
evoModeNormal = FALSE;
}
if (species != SPECIES_NONE)
{
FreeAllWindowBuffers();
gBattleMainFunc = WaitForEvoSceneToFinish;
EvolutionScene(&gPlayerParty[i], species, TRUE, i);
EvolutionScene(&gPlayerParty[i], species, evoModeNormal, i);
return;
}
}
@ -5457,21 +5477,20 @@ void SetTypeBeforeUsingMove(u32 move, u32 battler)
}
}
// special to set a field's totem boost(s)
// inputs:
// var8000: battler
// var8001 - var8007: stat changes
void SetTotemBoost(void)
// Queues stat boosts for a given battler for totem battles
void ScriptSetTotemBoost(struct ScriptContext *ctx)
{
u32 battler = gSpecialVar_0x8000;
u32 battler = VarGet(ScriptReadHalfword(ctx));
u32 stat;
u32 i;
for (i = 0; i < (NUM_BATTLE_STATS - 1); i++)
{
if (*(&gSpecialVar_0x8001 + i))
stat = VarGet(ScriptReadHalfword(ctx));
if (stat)
{
gQueuedStatBoosts[battler].stats |= (1 << i);
gQueuedStatBoosts[battler].statChanges[i] = *(&gSpecialVar_0x8001 + i);
gQueuedStatBoosts[battler].statChanges[i] = stat;
gQueuedStatBoosts[battler].stats |= 0x80; // used as a flag for the "totem flared to life" script
}
}

View File

@ -3241,6 +3241,18 @@ u8 AtkCanceller_UnableToUseMove(u32 moveType)
}
gBattleStruct->atkCancellerTracker++;
break;
case CANCELLER_GHOST: // GHOST in pokemon tower
if (IS_BATTLE_TYPE_GHOST_WITHOUT_SCOPE(gBattleTypeFlags))
{
if (GetBattlerSide(gBattlerAttacker) == B_SIDE_PLAYER)
gBattlescriptCurrInstr = BattleScript_TooScaredToMove;
else
gBattlescriptCurrInstr = BattleScript_GhostGetOutGetOut;
gBattleCommunication[MULTISTRING_CHOOSER] = 0;
effect = 1;
}
gBattleStruct->atkCancellerTracker++;
break;
case CANCELLER_IN_LOVE: // infatuation
if (!gBattleStruct->isAtkCancelerForCalledMove && gBattleMons[gBattlerAttacker].status2 & STATUS2_INFATUATION)
{