EndTurnEffectOrder Refactor (#6224)
This commit is contained in:
commit
81ed774c00
@ -1007,7 +1007,7 @@
|
||||
.4byte \jumpInstr
|
||||
.endm
|
||||
|
||||
.macro unused_bb
|
||||
.macro tryhealingitem
|
||||
.byte 0xbb
|
||||
.endm
|
||||
|
||||
@ -1140,9 +1140,8 @@
|
||||
.4byte \failInstr
|
||||
.endm
|
||||
|
||||
.macro trywish turnNumber:req, failInstr:req
|
||||
.macro trywish failInstr:req
|
||||
.byte 0xd4
|
||||
.byte \turnNumber
|
||||
.4byte \failInstr
|
||||
.endm
|
||||
|
||||
|
||||
@ -414,12 +414,12 @@ BattleScript_MoveEffectSaltCure::
|
||||
return
|
||||
|
||||
BattleScript_SaltCureExtraDamage::
|
||||
playanimation BS_TARGET, B_ANIM_SALT_CURE_DAMAGE, NULL
|
||||
playanimation BS_ATTACKER, B_ANIM_SALT_CURE_DAMAGE, NULL
|
||||
waitanimation
|
||||
call BattleScript_HurtTarget_NoString
|
||||
printstring STRINGID_TARGETISHURTBYSALTCURE
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
tryfaintmon BS_TARGET
|
||||
tryfaintmon BS_ATTACKER
|
||||
end2
|
||||
|
||||
BattleScript_HurtTarget_NoString:
|
||||
@ -4977,7 +4977,7 @@ BattleScript_EffectWish::
|
||||
attackcanceler
|
||||
attackstring
|
||||
ppreduce
|
||||
trywish 0, BattleScript_ButItFailed
|
||||
trywish BattleScript_ButItFailed
|
||||
attackanimation
|
||||
waitanimation
|
||||
goto BattleScript_MoveEnd
|
||||
@ -5770,13 +5770,13 @@ BattleScript_FogEnded_Ret::
|
||||
return
|
||||
|
||||
BattleScript_IceBodyHeal::
|
||||
call BattleScript_AbilityPopUpScripting
|
||||
playanimation BS_SCRIPTING, B_ANIM_SIMPLE_HEAL
|
||||
healthbarupdate BS_SCRIPTING
|
||||
datahpupdate BS_SCRIPTING
|
||||
call BattleScript_AbilityPopUp
|
||||
playanimation BS_ATTACKER, B_ANIM_SIMPLE_HEAL
|
||||
healthbarupdate BS_ATTACKER
|
||||
datahpupdate BS_ATTACKER
|
||||
printstring STRINGID_ICEBODYHPGAIN
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
end2
|
||||
end3
|
||||
|
||||
BattleScript_OverworldStatusStarts::
|
||||
printfromtable gStartingStatusStringIds
|
||||
@ -5837,12 +5837,14 @@ BattleScript_WonderRoomEnds::
|
||||
BattleScript_MagicRoomEnds::
|
||||
printstring STRINGID_MAGICROOMENDS
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
setbyte gBattlerTarget, 0
|
||||
BattleScript_MagicRoomHealingItemsLoop:
|
||||
copyarraywithindex gBattlerAttacker, gBattlerByTurnOrder, gBattlerTarget, 1
|
||||
tryhealingitem
|
||||
addbyte gBattlerTarget, 1
|
||||
jumpifbytenotequal gBattlerTarget, gBattlersCount, BattleScript_MagicRoomHealingItemsLoop
|
||||
end2
|
||||
|
||||
BattleScript_GrassyTerrainEnds::
|
||||
call BattleScript_GrassyTerrainHeals_Ret
|
||||
goto BattleScript_TerrainEnds
|
||||
|
||||
BattleScript_TerrainEnds_Ret::
|
||||
printfromtable gTerrainStringIds
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
@ -6608,7 +6610,6 @@ BattleScript_SelectingNotAllowedCurrentMoveInPalace::
|
||||
goto BattleScript_SelectingUnusableMoveInPalace
|
||||
|
||||
BattleScript_WishComesTrue::
|
||||
trywish 1, BattleScript_WishButFullHp
|
||||
playanimation BS_TARGET, B_ANIM_WISH_HEAL
|
||||
printstring STRINGID_PKMNWISHCAMETRUE
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
@ -6927,7 +6928,7 @@ BattleScript_CudChewActivates::
|
||||
pause B_WAIT_TIME_SHORTEST
|
||||
call BattleScript_AbilityPopUp
|
||||
setbyte sBERRY_OVERRIDE, 1 @ override the requirements for eating berries
|
||||
consumeberry BS_SCRIPTING, FALSE
|
||||
consumeberry BS_ATTACKER, FALSE
|
||||
setbyte sBERRY_OVERRIDE, 0
|
||||
end3
|
||||
|
||||
@ -7079,6 +7080,7 @@ BattleScript_DoTurnDmg:
|
||||
datahpupdate BS_ATTACKER
|
||||
tryfaintmon BS_ATTACKER
|
||||
checkteamslost BattleScript_DoTurnDmgEnd
|
||||
tryhealingitem
|
||||
BattleScript_DoTurnDmgEnd:
|
||||
end2
|
||||
|
||||
@ -7326,6 +7328,7 @@ BattleScript_YawnEnd:
|
||||
BattleScript_EmbargoEndTurn::
|
||||
printstring STRINGID_EMBARGOENDS
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
tryhealingitem
|
||||
end2
|
||||
|
||||
BattleScript_TelekinesisEndTurn::
|
||||
@ -7544,6 +7547,37 @@ BattleScript_EmergencyExitWild::
|
||||
finishaction
|
||||
return
|
||||
|
||||
BattleScript_EmergencyExitEnd2::
|
||||
pause 5
|
||||
call BattleScript_AbilityPopUp
|
||||
pause B_WAIT_TIME_LONG
|
||||
playanimation BS_ATTACKER, B_ANIM_SLIDE_OFFSCREEN
|
||||
waitanimation
|
||||
openpartyscreen BS_ATTACKER, BattleScript_EmergencyExitRetEnd2
|
||||
switchoutabilities BS_ATTACKER
|
||||
waitstate
|
||||
switchhandleorder BS_ATTACKER, 2
|
||||
returntoball BS_TARGET, FALSE
|
||||
getswitchedmondata BS_ATTACKER
|
||||
switchindataupdate BS_ATTACKER
|
||||
hpthresholds BS_ATTACKER
|
||||
printstring STRINGID_SWITCHINMON
|
||||
switchinanim BS_ATTACKER, FALSE, TRUE
|
||||
waitstate
|
||||
switchineffects BS_ATTACKER
|
||||
BattleScript_EmergencyExitRetEnd2:
|
||||
end2
|
||||
|
||||
BattleScript_EmergencyExitWildEnd2::
|
||||
pause 5
|
||||
call BattleScript_AbilityPopUp
|
||||
pause B_WAIT_TIME_LONG
|
||||
playanimation BS_ATTACKER, B_ANIM_SLIDE_OFFSCREEN
|
||||
waitanimation
|
||||
setoutcomeonteleport BS_ATTACKER
|
||||
finishaction
|
||||
end2
|
||||
|
||||
BattleScript_TraceActivates::
|
||||
pause B_WAIT_TIME_SHORT
|
||||
call BattleScript_AbilityPopUpScripting
|
||||
@ -7586,6 +7620,7 @@ BattleScript_PickupActivates::
|
||||
call BattleScript_AbilityPopUp
|
||||
printstring STRINGID_XFOUNDONEY
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
tryhealingitem
|
||||
BattleScript_PickupActivatesEnd:
|
||||
end3
|
||||
|
||||
@ -7595,6 +7630,7 @@ BattleScript_HarvestActivates::
|
||||
call BattleScript_AbilityPopUp
|
||||
printstring STRINGID_HARVESTBERRY
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
tryhealingitem
|
||||
BattleScript_HarvestActivatesEnd:
|
||||
end3
|
||||
|
||||
@ -8229,25 +8265,13 @@ BattleScript_MoveUsedPsychicTerrainPrevents::
|
||||
goto BattleScript_MoveEnd
|
||||
|
||||
BattleScript_GrassyTerrainHeals::
|
||||
call BattleScript_GrassyTerrainHeals_Ret
|
||||
end2
|
||||
|
||||
BattleScript_GrassyTerrainHeals_Ret::
|
||||
setbyte gBattleCommunication, 0
|
||||
BattleScript_GrassyTerrainLoop:
|
||||
copyarraywithindex gBattlerAttacker, gBattlerByTurnOrder, gBattleCommunication, 1
|
||||
checkgrassyterrainheal BS_ATTACKER, BattleScript_GrassyTerrainLoopIncrement
|
||||
printstring STRINGID_GRASSYTERRAINHEALS
|
||||
waitmessage B_WAIT_TIME_LONG
|
||||
orword gHitMarker, HITMARKER_IGNORE_BIDE | HITMARKER_IGNORE_SUBSTITUTE | HITMARKER_PASSIVE_DAMAGE
|
||||
healthbarupdate BS_ATTACKER
|
||||
datahpupdate BS_ATTACKER
|
||||
BattleScript_GrassyTerrainLoopIncrement::
|
||||
addbyte gBattleCommunication, 1
|
||||
jumpifbytenotequal gBattleCommunication, gBattlersCount, BattleScript_GrassyTerrainLoop
|
||||
bicword gHitMarker, HITMARKER_IGNORE_BIDE | HITMARKER_IGNORE_SUBSTITUTE | HITMARKER_PASSIVE_DAMAGE
|
||||
BattleScript_GrassyTerrainHealEnd:
|
||||
return
|
||||
end2
|
||||
|
||||
BattleScript_AbilityNoSpecificStatLoss::
|
||||
pause B_WAIT_TIME_SHORT
|
||||
|
||||
@ -85,12 +85,12 @@ struct DisableStruct
|
||||
s8 stockpileBeforeSpDef;
|
||||
u8 substituteHP;
|
||||
u8 encoredMovePos;
|
||||
u8 disableTimer:4;
|
||||
u8 encoreTimer:4;
|
||||
u8 perishSongTimer:4;
|
||||
u8 rolloutTimer:4;
|
||||
u8 rolloutTimerStartValue:4;
|
||||
u8 tauntTimer:4;
|
||||
u16 disableTimer;
|
||||
u16 encoreTimer;
|
||||
u16 perishSongTimer;
|
||||
u16 rolloutTimer;
|
||||
u16 rolloutTimerStartValue;
|
||||
u16 tauntTimer;
|
||||
u8 furyCutterCounter;
|
||||
u8 battlerPreventingEscape;
|
||||
u8 battlerWithSureHit;
|
||||
@ -99,16 +99,16 @@ struct DisableStruct
|
||||
u8 chargeTimer:4;
|
||||
u8 rechargeTimer;
|
||||
u8 autotomizeCount;
|
||||
u8 slowStartTimer;
|
||||
u8 embargoTimer;
|
||||
u8 magnetRiseTimer;
|
||||
u8 telekinesisTimer;
|
||||
u8 healBlockTimer;
|
||||
u8 laserFocusTimer;
|
||||
u8 throatChopTimer;
|
||||
u16 slowStartTimer;
|
||||
u16 embargoTimer;
|
||||
u16 magnetRiseTimer;
|
||||
u16 telekinesisTimer;
|
||||
u16 healBlockTimer;
|
||||
u16 laserFocusTimer;
|
||||
u16 throatChopTimer;
|
||||
u8 wrapTurns;
|
||||
u8 syrupBombTimer;
|
||||
u8 tormentTimer:4; // used for G-Max Meltdown
|
||||
u16 syrupBombTimer;
|
||||
u16 tormentTimer; // used for G-Max Meltdown
|
||||
u8 usedMoves:4;
|
||||
u8 truantCounter:1;
|
||||
u8 truantSwitchInHack:1;
|
||||
@ -270,7 +270,7 @@ struct FieldTimer
|
||||
|
||||
struct WishFutureKnock
|
||||
{
|
||||
u8 futureSightCounter[MAX_BATTLERS_COUNT];
|
||||
u16 futureSightCounter[MAX_BATTLERS_COUNT];
|
||||
u8 futureSightBattlerIndex[MAX_BATTLERS_COUNT];
|
||||
u8 futureSightPartyIndex[MAX_BATTLERS_COUNT];
|
||||
u16 futureSightMove[MAX_BATTLERS_COUNT];
|
||||
@ -557,7 +557,7 @@ struct ZMoveData
|
||||
|
||||
struct DynamaxData
|
||||
{
|
||||
u8 dynamaxTurns[MAX_BATTLERS_COUNT];
|
||||
u16 dynamaxTurns[MAX_BATTLERS_COUNT];
|
||||
u16 baseMoves[MAX_BATTLERS_COUNT]; // base move of Max Move
|
||||
u16 lastUsedBaseMove;
|
||||
};
|
||||
@ -634,9 +634,9 @@ struct BattlerState
|
||||
struct BattleStruct
|
||||
{
|
||||
struct BattlerState battlerState[MAX_BATTLERS_COUNT];
|
||||
u8 turnEffectsTracker;
|
||||
u8 eventBlockCounter;
|
||||
u8 turnEffectsBattlerId;
|
||||
u8 turnCountersTracker;
|
||||
u8 endTurnEventsCounter;
|
||||
u16 wrappedMove[MAX_BATTLERS_COUNT];
|
||||
u16 moveTarget[MAX_BATTLERS_COUNT];
|
||||
u32 expShareExpValue;
|
||||
@ -707,8 +707,6 @@ struct BattleStruct
|
||||
struct LinkBattlerHeader linkBattlerHeader;
|
||||
struct BattleVideo battleVideo;
|
||||
} multiBuffer;
|
||||
u8 wishPerishSongState;
|
||||
u8 wishPerishSongBattlerId;
|
||||
u8 startingStatus:6; // status to apply at battle start. defined in constants/battle.h
|
||||
u8 startingStatusDone:1;
|
||||
u8 terrainDone:1;
|
||||
@ -718,7 +716,7 @@ struct BattleStruct
|
||||
u8 friskedAbility:1; // If identifies two mons, show the ability pop-up only once.
|
||||
u8 fickleBeamBoosted:1;
|
||||
u8 poisonPuppeteerConfusion:1;
|
||||
u8 startingStatusTimer;
|
||||
u16 startingStatusTimer;
|
||||
u8 atkCancellerTracker;
|
||||
struct BattleTvMovePoints tvMovePoints;
|
||||
struct BattleTv tv;
|
||||
|
||||
7
include/battle_end_turn.h
Normal file
7
include/battle_end_turn.h
Normal file
@ -0,0 +1,7 @@
|
||||
#ifndef GUARD_BATTLE_END_TURN
|
||||
#define GUARD_BATTLE_END_TURN
|
||||
|
||||
u32 DoEndTurnEffects(void);
|
||||
|
||||
#endif // GUARD_BATTLE_END_TURN
|
||||
|
||||
@ -101,6 +101,7 @@ extern const u8 BattleScript_SelectingTormentedMoveInPalace[];
|
||||
extern const u8 BattleScript_SelectingNotAllowedMoveTaunt[];
|
||||
extern const u8 BattleScript_MoveUsedIsTaunted[];
|
||||
extern const u8 BattleScript_SelectingNotAllowedMoveTauntInPalace[];
|
||||
extern const u8 BattleScript_WishButFullHp[];
|
||||
extern const u8 BattleScript_WishComesTrue[];
|
||||
extern const u8 BattleScript_IngrainTurnHeal[];
|
||||
extern const u8 BattleScript_AtkDefDown[];
|
||||
@ -269,7 +270,6 @@ extern const u8 BattleScript_WonderRoomEnds[];
|
||||
extern const u8 BattleScript_MagicRoomEnds[];
|
||||
extern const u8 BattleScript_TerrainEnds[];
|
||||
extern const u8 BattleScript_TerrainEnds_Ret[];
|
||||
extern const u8 BattleScript_GrassyTerrainEnds[];
|
||||
extern const u8 BattleScript_MudSportEnds[];
|
||||
extern const u8 BattleScript_WaterSportEnds[];
|
||||
extern const u8 BattleScript_SturdiedMsg[];
|
||||
@ -385,6 +385,8 @@ extern const u8 BattleScript_FriskMsgWithPopup[];
|
||||
extern const u8 BattleScript_MoodyActivates[];
|
||||
extern const u8 BattleScript_EmergencyExit[];
|
||||
extern const u8 BattleScript_EmergencyExitWild[];
|
||||
extern const u8 BattleScript_EmergencyExitEnd2[];
|
||||
extern const u8 BattleScript_EmergencyExitWildEnd2[];
|
||||
extern const u8 BattleScript_CheekPouchActivates[];
|
||||
extern const u8 BattleScript_TotemVar[];
|
||||
extern const u8 BattleScript_TotemFlaredToLife[];
|
||||
|
||||
@ -68,6 +68,7 @@ enum ItemCaseId
|
||||
ITEMEFFECT_ON_SWITCH_IN,
|
||||
ITEMEFFECT_ON_SWITCH_IN_FIRST_TURN,
|
||||
ITEMEFFECT_NORMAL,
|
||||
ITEMEFFECT_TRY_HEALING,
|
||||
ITEMEFFECT_MOVE_END,
|
||||
ITEMEFFECT_KINGSROCK,
|
||||
ITEMEFFECT_TARGET,
|
||||
@ -172,6 +173,8 @@ enum SleepClauseBlock
|
||||
};
|
||||
|
||||
void HandleAction_ThrowBall(void);
|
||||
u32 GetCurrentBattleWeather(void);
|
||||
bool32 EndOrContinueWeather(void);
|
||||
bool32 IsAffectedByFollowMe(u32 battlerAtk, u32 defSide, u32 move);
|
||||
bool32 HandleMoveTargetRedirection(void);
|
||||
void HandleAction_UseMove(void);
|
||||
@ -205,11 +208,9 @@ u32 TrySetCantSelectMoveBattleScript(u32 battler);
|
||||
u8 CheckMoveLimitations(u32 battler, u8 unusableMoves, u16 check);
|
||||
bool32 AreAllMovesUnusable(u32 battler);
|
||||
u8 GetImprisonedMovesCount(u32 battler, u16 move);
|
||||
u8 DoFieldEndTurnEffects(void);
|
||||
s32 GetDrainedBigRootHp(u32 battler, s32 hp);
|
||||
bool32 IsMagicGuardProtected(u32 battler, u32 ability);
|
||||
u8 DoBattlerEndTurnEffects(void);
|
||||
bool32 HandleWishPerishSongOnTurnEnd(void);
|
||||
u32 DoEndTurnEffects(void);
|
||||
bool32 HandleFaintedMonActions(void);
|
||||
void TryClearRageAndFuryCutter(void);
|
||||
u32 AtkCanceller_MoveSuccessOrder(void);
|
||||
@ -327,6 +328,7 @@ bool32 CanBeConfused(u32 battler);
|
||||
bool32 IsBattlerTerrainAffected(u32 battler, u32 terrainFlag);
|
||||
u32 GetBattlerAffectionHearts(u32 battler);
|
||||
void TryToRevertMimicryAndFlags(void);
|
||||
bool32 BattleArenaTurnEnd(void);
|
||||
u32 CountBattlerStatIncreases(u32 battler, bool32 countEvasionAcc);
|
||||
bool32 ChangeTypeBasedOnTerrain(u32 battler);
|
||||
void RemoveConfusionStatus(u32 battler);
|
||||
|
||||
@ -1040,7 +1040,7 @@ static s32 AI_CheckBadMove(u32 battlerAtk, u32 battlerDef, u32 move, s32 score)
|
||||
// the following checks apply to any target (including user)
|
||||
|
||||
// throat chop check
|
||||
if (gDisableStructs[battlerAtk].throatChopTimer && IsSoundMove(move))
|
||||
if (gDisableStructs[battlerAtk].throatChopTimer > gBattleTurnCounter && IsSoundMove(move))
|
||||
return 0; // Can't even select move at all
|
||||
// heal block check
|
||||
if (gStatuses3[battlerAtk] & STATUS3_HEAL_BLOCK && IsHealBlockPreventingMove(battlerAtk, move))
|
||||
@ -2447,7 +2447,7 @@ static s32 AI_CheckBadMove(u32 battlerAtk, u32 battlerDef, u32 move, s32 score)
|
||||
break;
|
||||
case EFFECT_EMBARGO:
|
||||
if (!IsBattlerItemEnabled(battlerAtk)
|
||||
|| gDisableStructs[battlerDef].embargoTimer != 0
|
||||
|| gStatuses3[battlerDef] & STATUS3_EMBARGO
|
||||
|| PartnerMoveIsSameAsAttacker(BATTLE_PARTNER(battlerAtk), battlerDef, move, aiData->partnerMove))
|
||||
ADJUST_SCORE(-10);
|
||||
break;
|
||||
@ -2465,7 +2465,7 @@ static s32 AI_CheckBadMove(u32 battlerAtk, u32 battlerDef, u32 move, s32 score)
|
||||
ADJUST_SCORE(-10);
|
||||
break;
|
||||
case EFFECT_HEAL_BLOCK:
|
||||
if (gDisableStructs[battlerDef].healBlockTimer != 0
|
||||
if (gStatuses3[battlerDef] & STATUS3_HEAL_BLOCK
|
||||
|| PartnerMoveIsSameAsAttacker(BATTLE_PARTNER(battlerAtk), battlerDef, move, aiData->partnerMove))
|
||||
ADJUST_SCORE(-10);
|
||||
break;
|
||||
|
||||
@ -178,7 +178,7 @@ void ActivateDynamax(u32 battler)
|
||||
// Set appropriate use flags.
|
||||
SetActiveGimmick(battler, GIMMICK_DYNAMAX);
|
||||
SetGimmickAsActivated(battler, GIMMICK_DYNAMAX);
|
||||
gBattleStruct->dynamax.dynamaxTurns[battler] = DYNAMAX_TURNS_COUNT;
|
||||
gBattleStruct->dynamax.dynamaxTurns[battler] = gBattleTurnCounter + DYNAMAX_TURNS_COUNT;
|
||||
|
||||
// Substitute is removed upon Dynamaxing.
|
||||
gBattleMons[battler].status2 &= ~STATUS2_SUBSTITUTE;
|
||||
@ -209,7 +209,6 @@ void UndoDynamax(u32 battler)
|
||||
|
||||
// Makes sure there are no Dynamax flags set, including on switch / faint.
|
||||
SetActiveGimmick(battler, GIMMICK_NONE);
|
||||
gBattleStruct->dynamax.dynamaxTurns[battler] = 0;
|
||||
|
||||
// Undo form change if needed.
|
||||
if (IsGigantamaxed(battler))
|
||||
|
||||
1596
src/battle_end_turn.c
Normal file
1596
src/battle_end_turn.c
Normal file
File diff suppressed because it is too large
Load Diff
@ -5,6 +5,7 @@
|
||||
#include "battle_ai_util.h"
|
||||
#include "battle_arena.h"
|
||||
#include "battle_controllers.h"
|
||||
#include "battle_end_turn.h"
|
||||
#include "battle_interface.h"
|
||||
#include "battle_main.h"
|
||||
#include "battle_message.h"
|
||||
@ -3878,13 +3879,11 @@ static void TryDoEventsBeforeFirstTurn(void)
|
||||
gBattleStruct->appearedInBattle |= 1u << gBattlerPartyIndexes[i];
|
||||
}
|
||||
|
||||
*(&gBattleStruct->turnEffectsTracker) = 0;
|
||||
*(&gBattleStruct->eventBlockCounter) = 0;
|
||||
*(&gBattleStruct->turnEffectsBattlerId) = 0;
|
||||
*(&gBattleStruct->wishPerishSongState) = 0;
|
||||
*(&gBattleStruct->wishPerishSongBattlerId) = 0;
|
||||
gBattleScripting.moveendState = 0;
|
||||
gBattleStruct->faintedActionsState = 0;
|
||||
gBattleStruct->turnCountersTracker = 0;
|
||||
gBattleStruct->endTurnEventsCounter = 0;
|
||||
|
||||
memset(gQueuedStatBoosts, 0, sizeof(gQueuedStatBoosts));
|
||||
SetShellSideArmCategory();
|
||||
@ -3918,11 +3917,9 @@ static void HandleEndTurn_ContinueBattle(void)
|
||||
if ((gBattleMons[i].status1 & STATUS1_SLEEP) && (gBattleMons[i].status2 & STATUS2_MULTIPLETURNS))
|
||||
CancelMultiTurnMoves(i);
|
||||
}
|
||||
gBattleStruct->turnEffectsTracker = 0;
|
||||
gBattleStruct->eventBlockCounter = 0;
|
||||
gBattleStruct->turnEffectsBattlerId = 0;
|
||||
gBattleStruct->wishPerishSongState = 0;
|
||||
gBattleStruct->wishPerishSongBattlerId = 0;
|
||||
gBattleStruct->turnCountersTracker = 0;
|
||||
gBattleStruct->endTurnEventsCounter = 0;
|
||||
}
|
||||
}
|
||||
|
||||
@ -3933,18 +3930,14 @@ void BattleTurnPassed(void)
|
||||
gBattleStruct->speedTieBreaks = RandomUniform(RNG_SPEED_TIE, 0, Factorial(MAX_BATTLERS_COUNT) - 1);
|
||||
|
||||
TurnValuesCleanUp(TRUE);
|
||||
if (gBattleOutcome == 0)
|
||||
{
|
||||
if (DoFieldEndTurnEffects())
|
||||
return;
|
||||
if (DoBattlerEndTurnEffects())
|
||||
return;
|
||||
if (HandleWishPerishSongOnTurnEnd())
|
||||
return;
|
||||
}
|
||||
|
||||
if (gBattleOutcome == 0 && DoEndTurnEffects())
|
||||
return;
|
||||
if (BattleArenaTurnEnd())
|
||||
return;
|
||||
if (HandleFaintedMonActions())
|
||||
return;
|
||||
|
||||
gBattleStruct->faintedActionsState = 0;
|
||||
|
||||
TurnValuesCleanUp(FALSE);
|
||||
@ -3979,6 +3972,8 @@ void BattleTurnPassed(void)
|
||||
gBattleStruct->battlerState[i].absent = (gAbsentBattlerFlags & (1u << i) ? TRUE : FALSE);
|
||||
gBattleStruct->monToSwitchIntoId[i] = PARTY_SIZE;
|
||||
gStatuses4[i] &= ~STATUS4_ELECTRIFIED;
|
||||
gBattleMons[i].status2 &= ~STATUS2_FLINCHED;
|
||||
gBattleMons[i].status2 &= ~STATUS2_POWDER;
|
||||
}
|
||||
|
||||
for (i = 0; i < NUM_BATTLE_SIDES; i++)
|
||||
@ -3987,6 +3982,8 @@ void BattleTurnPassed(void)
|
||||
gSideTimers[i].retaliateTimer--;
|
||||
}
|
||||
|
||||
gFieldStatuses &= ~STATUS_FIELD_ION_DELUGE;
|
||||
|
||||
BattlePutTextOnWindow(gText_EmptyString3, B_WIN_MSG);
|
||||
AssignUsableGimmicks();
|
||||
SetShellSideArmCategory();
|
||||
|
||||
@ -962,7 +962,8 @@ const u16 gTerrainPreventsStringIds[] =
|
||||
|
||||
const u16 gHealingWishStringIds[] =
|
||||
{
|
||||
STRINGID_HEALINGWISHCAMETRUE, STRINGID_LUNARDANCECAMETRUE
|
||||
STRINGID_HEALINGWISHCAMETRUE,
|
||||
STRINGID_LUNARDANCECAMETRUE
|
||||
};
|
||||
|
||||
const u16 gDmgHazardsStringIds[] =
|
||||
|
||||
@ -533,7 +533,7 @@ static void Cmd_presentdamagecalculation(void);
|
||||
static void Cmd_setsafeguard(void);
|
||||
static void Cmd_magnitudedamagecalculation(void);
|
||||
static void Cmd_jumpifnopursuitswitchdmg(void);
|
||||
static void Cmd_unused_bb(void);
|
||||
static void Cmd_tryhealingitem(void);
|
||||
static void Cmd_halvehp(void);
|
||||
static void Cmd_copyfoestats(void);
|
||||
static void Cmd_rapidspinfree(void);
|
||||
@ -792,7 +792,7 @@ void (* const gBattleScriptingCommandsTable[])(void) =
|
||||
Cmd_setsafeguard, //0xB8
|
||||
Cmd_magnitudedamagecalculation, //0xB9
|
||||
Cmd_jumpifnopursuitswitchdmg, //0xBA
|
||||
Cmd_unused_bb, //0xBB
|
||||
Cmd_tryhealingitem, //0xBB
|
||||
Cmd_halvehp, //0xBC
|
||||
Cmd_copyfoestats, //0xBD
|
||||
Cmd_rapidspinfree, //0xBE
|
||||
@ -3987,7 +3987,7 @@ void SetMoveEffect(bool32 primary, bool32 certain)
|
||||
}
|
||||
break;
|
||||
case MOVE_EFFECT_THROAT_CHOP:
|
||||
gDisableStructs[gEffectBattler].throatChopTimer = 2;
|
||||
gDisableStructs[gEffectBattler].throatChopTimer = gBattleTurnCounter + 2;
|
||||
gBattlescriptCurrInstr++;
|
||||
break;
|
||||
case MOVE_EFFECT_INCINERATE:
|
||||
@ -4194,7 +4194,7 @@ void SetMoveEffect(bool32 primary, bool32 certain)
|
||||
else if (!(gStatuses3[gEffectBattler] & STATUS3_HEAL_BLOCK))
|
||||
{
|
||||
gStatuses3[gEffectBattler] |= STATUS3_HEAL_BLOCK;
|
||||
gDisableStructs[gEffectBattler].healBlockTimer = 2;
|
||||
gDisableStructs[gEffectBattler].healBlockTimer = gBattleTurnCounter + 2;
|
||||
BattleScriptPush(gBattlescriptCurrInstr + 1);
|
||||
gBattlescriptCurrInstr = BattleScript_EffectPsychicNoise;
|
||||
}
|
||||
@ -7691,7 +7691,7 @@ static void Cmd_sethealblock(void)
|
||||
else
|
||||
{
|
||||
gStatuses3[gBattlerTarget] |= STATUS3_HEAL_BLOCK;
|
||||
gDisableStructs[gBattlerTarget].healBlockTimer = 5;
|
||||
gDisableStructs[gBattlerTarget].healBlockTimer = gBattleTurnCounter + 5;
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
}
|
||||
@ -8345,6 +8345,7 @@ static bool32 DoSwitchInEffectsForBattler(u32 battler)
|
||||
else if ((gBattleStruct->battlerState[battler].storedHealingWish || gBattleStruct->battlerState[battler].storedLunarDance)
|
||||
&& (gBattleMons[battler].hp != gBattleMons[battler].maxHP || gBattleMons[battler].status1 != 0 || B_HEALING_WISH_SWITCH < GEN_8))
|
||||
{
|
||||
gBattlerAttacker = battler;
|
||||
if (gBattleStruct->battlerState[battler].storedHealingWish)
|
||||
{
|
||||
BattleScriptPushCursor();
|
||||
@ -14304,7 +14305,7 @@ static void Cmd_setembargo(void)
|
||||
else
|
||||
{
|
||||
gStatuses3[gBattlerTarget] |= STATUS3_EMBARGO;
|
||||
gDisableStructs[gBattlerTarget].embargoTimer = 5;
|
||||
gDisableStructs[gBattlerTarget].embargoTimer = gBattleTurnCounter + 5;
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
}
|
||||
@ -14480,8 +14481,18 @@ static void Cmd_jumpifnopursuitswitchdmg(void)
|
||||
}
|
||||
}
|
||||
|
||||
static void Cmd_unused_bb(void)
|
||||
static void Cmd_tryhealingitem(void)
|
||||
{
|
||||
CMD_ARGS();
|
||||
|
||||
if (gItemsInfo[gBattleMons[gBattlerAttacker].item].pocket == POCKET_BERRIES
|
||||
|| GetBattlerHoldEffect(gBattlerAttacker, TRUE) == HOLD_EFFECT_RESTORE_HP) // Edge case for Berry Juice
|
||||
{
|
||||
if (ItemBattleEffects(ITEMEFFECT_TRY_HEALING, gBattlerAttacker, FALSE))
|
||||
return;
|
||||
}
|
||||
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
|
||||
// Belly Drum, Fillet Away
|
||||
@ -14935,7 +14946,6 @@ static void Cmd_settorment(void)
|
||||
else
|
||||
{
|
||||
gBattleMons[gBattlerTarget].status2 |= STATUS2_TORMENT;
|
||||
gDisableStructs[gBattlerTarget].tormentTimer = PERMANENT_TORMENT; // permanent
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
}
|
||||
@ -15143,36 +15153,17 @@ static void Cmd_trycopyability(void)
|
||||
|
||||
static void Cmd_trywish(void)
|
||||
{
|
||||
CMD_ARGS(u8 turnNumber, const u8 *failInstr);
|
||||
CMD_ARGS(const u8 *failInstr);
|
||||
|
||||
switch (cmd->turnNumber)
|
||||
if (gWishFutureKnock.wishCounter[gBattlerAttacker] <= gBattleTurnCounter)
|
||||
{
|
||||
case 0: // use wish
|
||||
if (gWishFutureKnock.wishCounter[gBattlerAttacker] <= gBattleTurnCounter)
|
||||
{
|
||||
gWishFutureKnock.wishCounter[gBattlerAttacker] = gBattleTurnCounter + 2;
|
||||
gWishFutureKnock.wishPartyId[gBattlerAttacker] = gBattlerPartyIndexes[gBattlerAttacker];
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
else
|
||||
{
|
||||
gBattlescriptCurrInstr = cmd->failInstr;
|
||||
}
|
||||
break;
|
||||
case 1: // heal effect
|
||||
PREPARE_MON_NICK_WITH_PREFIX_BUFFER(gBattleTextBuff1, gBattlerTarget, gWishFutureKnock.wishPartyId[gBattlerTarget])
|
||||
if (B_WISH_HP_SOURCE >= GEN_5)
|
||||
gBattleStruct->moveDamage[gBattlerTarget] = max(1, GetMonData(&GetBattlerParty(gBattlerTarget)[gWishFutureKnock.wishPartyId[gBattlerTarget]], MON_DATA_MAX_HP) / 2);
|
||||
else
|
||||
gBattleStruct->moveDamage[gBattlerTarget] = max(1, GetNonDynamaxMaxHP(gBattlerAttacker) / 2);
|
||||
|
||||
gBattleStruct->moveDamage[gBattlerTarget] *= -1;
|
||||
if (gBattleMons[gBattlerTarget].hp == gBattleMons[gBattlerTarget].maxHP)
|
||||
gBattlescriptCurrInstr = cmd->failInstr;
|
||||
else
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
|
||||
break;
|
||||
gWishFutureKnock.wishCounter[gBattlerAttacker] = gBattleTurnCounter + 2;
|
||||
gWishFutureKnock.wishPartyId[gBattlerAttacker] = gBattlerPartyIndexes[gBattlerAttacker];
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
else
|
||||
{
|
||||
gBattlescriptCurrInstr = cmd->failInstr;
|
||||
}
|
||||
}
|
||||
|
||||
@ -15405,9 +15396,9 @@ static void Cmd_setuserstatus3(void)
|
||||
{
|
||||
gStatuses3[gBattlerAttacker] |= flags;
|
||||
if (flags & STATUS3_MAGNET_RISE)
|
||||
gDisableStructs[gBattlerAttacker].magnetRiseTimer = 5;
|
||||
gDisableStructs[gBattlerAttacker].magnetRiseTimer = gBattleTurnCounter + 5;
|
||||
if (flags & STATUS3_LASER_FOCUS)
|
||||
gDisableStructs[gBattlerAttacker].laserFocusTimer = 2;
|
||||
gDisableStructs[gBattlerAttacker].laserFocusTimer = gBattleTurnCounter + 2;
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
}
|
||||
@ -16647,7 +16638,7 @@ static void Cmd_settelekinesis(void)
|
||||
else
|
||||
{
|
||||
gStatuses3[gBattlerTarget] |= STATUS3_TELEKINESIS;
|
||||
gDisableStructs[gBattlerTarget].telekinesisTimer = 3;
|
||||
gDisableStructs[gBattlerTarget].telekinesisTimer = gBattleTurnCounter + 3;
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
}
|
||||
}
|
||||
@ -18748,7 +18739,7 @@ void BS_TrySetTorment(void)
|
||||
&& !IsAbilityOnSide(gBattlerTarget, ABILITY_AROMA_VEIL))
|
||||
{
|
||||
gBattleMons[gBattlerTarget].status2 |= STATUS2_TORMENT;
|
||||
gDisableStructs[gBattlerTarget].tormentTimer = 3; // 3 turns excluding current turn
|
||||
gDisableStructs[gBattlerTarget].tormentTimer = gBattleTurnCounter + 3; // 3 turns excluding current turn
|
||||
gBattleCommunication[MULTISTRING_CHOOSER] = 3;
|
||||
gEffectBattler = gBattlerTarget;
|
||||
gBattlescriptCurrInstr = cmd->nextInstr;
|
||||
|
||||
1465
src/battle_util.c
1465
src/battle_util.c
File diff suppressed because it is too large
Load Diff
@ -66,3 +66,45 @@ DOUBLE_BATTLE_TEST("Only the fastest Wimp Out (Emergency Exit) user switches out
|
||||
ABILITY_POPUP(opponentRight, ABILITY_WIMP_OUT);
|
||||
}
|
||||
}
|
||||
|
||||
SINGLE_BATTLE_TEST("Emergency Exit activates when taking residual damage and falling under 50% max-hp - Burn")
|
||||
{
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_WOBBUFFET);
|
||||
OPPONENT(SPECIES_GOLISOPOD) { Ability(ABILITY_EMERGENCY_EXIT); MaxHP(263); HP(134); Status1(STATUS1_BURN); };
|
||||
OPPONENT(SPECIES_WOBBUFFET);
|
||||
} WHEN {
|
||||
TURN { SEND_OUT(opponent, 1); }
|
||||
} SCENE {
|
||||
HP_BAR(opponent);
|
||||
ABILITY_POPUP(opponent, ABILITY_EMERGENCY_EXIT);
|
||||
}
|
||||
}
|
||||
|
||||
SINGLE_BATTLE_TEST("Emergency Exit activates when taking residual damage and falling under 50% max-hp - Weather")
|
||||
{
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_WOBBUFFET);
|
||||
OPPONENT(SPECIES_GOLISOPOD) { Ability(ABILITY_EMERGENCY_EXIT); MaxHP(263); HP(134); };
|
||||
OPPONENT(SPECIES_WOBBUFFET);
|
||||
} WHEN {
|
||||
TURN { MOVE(player, MOVE_SANDSTORM); SEND_OUT(opponent, 1); }
|
||||
} SCENE {
|
||||
HP_BAR(opponent);
|
||||
ABILITY_POPUP(opponent, ABILITY_EMERGENCY_EXIT);
|
||||
}
|
||||
}
|
||||
|
||||
SINGLE_BATTLE_TEST("Emergency Exit activates when taking residual damage and falling under 50% max-hp - Salt Cure")
|
||||
{
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_WOBBUFFET);
|
||||
OPPONENT(SPECIES_GOLISOPOD) { Ability(ABILITY_EMERGENCY_EXIT); MaxHP(263); HP(160); };
|
||||
OPPONENT(SPECIES_WOBBUFFET);
|
||||
} WHEN {
|
||||
TURN { MOVE(player, MOVE_SALT_CURE); SEND_OUT(opponent, 1); }
|
||||
} SCENE {
|
||||
HP_BAR(opponent);
|
||||
ABILITY_POPUP(opponent, ABILITY_EMERGENCY_EXIT);
|
||||
}
|
||||
}
|
||||
|
||||
@ -26,8 +26,6 @@ DOUBLE_BATTLE_TEST("Healer cures adjacent ally's status condition 30% of the tim
|
||||
|
||||
DOUBLE_BATTLE_TEST("Healer cures status condition before burn or poison damage is dealt")
|
||||
{
|
||||
KNOWN_FAILING; // According to Bulbapedia, Healer should trigger before status damage and Wobbuffet should live
|
||||
// Source: https://bulbapedia.bulbagarden.net/wiki/Healer_(Ability)#Effect
|
||||
u16 status;
|
||||
PARAMETRIZE { status = STATUS1_POISON; }
|
||||
PARAMETRIZE { status = STATUS1_BURN; }
|
||||
@ -42,10 +40,8 @@ DOUBLE_BATTLE_TEST("Healer cures status condition before burn or poison damage i
|
||||
} WHEN {
|
||||
TURN {}
|
||||
} SCENE {
|
||||
NOT {
|
||||
MESSAGE("The opposing Wobbuffet fainted!");
|
||||
}
|
||||
MESSAGE("The opposing Chansey's Healer cured Foe Wobbuffet's problem!");
|
||||
NOT MESSAGE("The opposing Wobbuffet fainted!");
|
||||
MESSAGE("The opposing Chansey's Healer cured the opposing Wobbuffet's problem!");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
31
test/battle/end_turn_effects.c
Normal file
31
test/battle/end_turn_effects.c
Normal file
@ -0,0 +1,31 @@
|
||||
#include "global.h"
|
||||
#include "test/battle.h"
|
||||
|
||||
DOUBLE_BATTLE_TEST("End Turn Effects: First Event Block is executed correctly")
|
||||
{
|
||||
s16 healed;
|
||||
s16 damage;
|
||||
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_WYNAUT) { HP(100); Speed(1); }
|
||||
PLAYER(SPECIES_EKANS) { HP(100); Ability(ABILITY_SHED_SKIN); Status1(STATUS1_BURN); Speed(2); }
|
||||
OPPONENT(SPECIES_WYNAUT) { HP(100); Item(ITEM_LEFTOVERS); Speed(3); }
|
||||
OPPONENT(SPECIES_WOBBUFFET) { HP(100); Item(ITEM_BLACK_SLUDGE); Speed(4); }
|
||||
} WHEN {
|
||||
TURN { MOVE(playerLeft, MOVE_GRASSY_TERRAIN); }
|
||||
} SCENE {
|
||||
MESSAGE("The opposing Wobbuffet is healed by the grassy terrain!");
|
||||
HP_BAR(opponentRight, captureDamage: &healed);
|
||||
HP_BAR(opponentRight, captureDamage: &damage);
|
||||
MESSAGE("The opposing Wobbuffet was hurt by the Black Sludge!");
|
||||
MESSAGE("The opposing Wynaut is healed by the grassy terrain!");
|
||||
MESSAGE("The opposing Wynaut restored a little HP using its Leftovers!");
|
||||
MESSAGE("Ekans is healed by the grassy terrain!");
|
||||
MESSAGE("Ekans's Shed Skin cured its burn problem!");
|
||||
MESSAGE("Wynaut is healed by the grassy terrain!");
|
||||
} THEN {
|
||||
EXPECT_GT(0, healed);
|
||||
EXPECT_GT(damage, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@ -107,11 +107,11 @@ DOUBLE_BATTLE_TEST("Court Change used by the player swaps Mist, Safeguard, Auror
|
||||
MESSAGE("Wynaut used Court Change!");
|
||||
MESSAGE("Wynaut swapped the battle effects affecting each side of the field!");
|
||||
// The effects now end for the player side.
|
||||
MESSAGE("Your team's Mist wore off!");
|
||||
MESSAGE("Your team is no longer protected by Safeguard!");
|
||||
MESSAGE("Your team's Mist wore off!");
|
||||
MESSAGE("Your team's Reflect wore off!");
|
||||
MESSAGE("Your team's Aurora Veil wore off!");
|
||||
MESSAGE("Your team's Tailwind petered out!");
|
||||
MESSAGE("Your team's Aurora Veil wore off!");
|
||||
MESSAGE("Your team's Light Screen wore off!");
|
||||
}
|
||||
}
|
||||
@ -144,11 +144,12 @@ DOUBLE_BATTLE_TEST("Court Change used by the opponent swaps Mist, Safeguard, Aur
|
||||
MESSAGE("The opposing Wynaut used Court Change!");
|
||||
MESSAGE("The opposing Wynaut swapped the battle effects affecting each side of the field!");
|
||||
// The effects now end for the player side.
|
||||
MESSAGE("The opposing team's Mist wore off!");
|
||||
MESSAGE("The snow stopped.");
|
||||
MESSAGE("The opposing team is no longer protected by Safeguard!");
|
||||
MESSAGE("The opposing team's Mist wore off!");
|
||||
MESSAGE("The opposing team's Reflect wore off!");
|
||||
MESSAGE("The opposing team's Aurora Veil wore off!");
|
||||
MESSAGE("The opposing team's Tailwind petered out!");
|
||||
MESSAGE("The opposing team's Aurora Veil wore off!");
|
||||
MESSAGE("The opposing team's Light Screen wore off!");
|
||||
}
|
||||
}
|
||||
|
||||
@ -8,9 +8,20 @@ SINGLE_BATTLE_TEST("Grassy Terrain recovers 1/16th HP at end of turn")
|
||||
OPPONENT(SPECIES_WOBBUFFET) { MaxHP(100); HP(1); };
|
||||
} WHEN {
|
||||
TURN { MOVE(player, MOVE_GRASSY_TERRAIN); }
|
||||
TURN {}
|
||||
} SCENE {
|
||||
s32 maxHPPlayer = GetMonData(&PLAYER_PARTY[0], MON_DATA_MAX_HP);
|
||||
s32 maxHPOpponent = GetMonData(&OPPONENT_PARTY[0], MON_DATA_MAX_HP);
|
||||
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_GRASSY_TERRAIN, player);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_CELEBRATE, opponent);
|
||||
MESSAGE("Wobbuffet is healed by the grassy terrain!");
|
||||
HP_BAR(player, damage: -maxHPPlayer / 16);
|
||||
MESSAGE("The opposing Wobbuffet is healed by the grassy terrain!");
|
||||
HP_BAR(opponent, damage: -maxHPOpponent / 16);
|
||||
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_CELEBRATE, player);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_CELEBRATE, opponent);
|
||||
MESSAGE("Wobbuffet is healed by the grassy terrain!");
|
||||
HP_BAR(player, damage: -maxHPPlayer / 16);
|
||||
MESSAGE("The opposing Wobbuffet is healed by the grassy terrain!");
|
||||
|
||||
@ -58,6 +58,36 @@ SINGLE_BATTLE_TEST("Leech Seed recovery is prevented by Heal Block")
|
||||
}
|
||||
}
|
||||
|
||||
DOUBLE_BATTLE_TEST("Leech Seed will drain HP based on speed of the drained mon")
|
||||
{
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_WYNAUT) { Speed(1); }
|
||||
PLAYER(SPECIES_WOBBUFFET) { Speed(2); }
|
||||
OPPONENT(SPECIES_WYNAUT) { Speed(3); }
|
||||
OPPONENT(SPECIES_WOBBUFFET) { Speed(4); }
|
||||
} WHEN {
|
||||
TURN {
|
||||
MOVE(playerLeft, MOVE_LEECH_SEED, target: opponentLeft);
|
||||
MOVE(playerRight, MOVE_LEECH_SEED, target: opponentRight);
|
||||
MOVE(opponentLeft, MOVE_LEECH_SEED, target: playerLeft);
|
||||
MOVE(opponentRight, MOVE_LEECH_SEED, target: playerRight);
|
||||
}
|
||||
} SCENE {
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_LEECH_SEED, opponentRight);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_LEECH_SEED, opponentLeft);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_LEECH_SEED, playerRight);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_LEECH_SEED, playerLeft);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_LEECH_SEED_DRAIN, opponentRight);
|
||||
HP_BAR(opponentRight);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_LEECH_SEED_DRAIN, opponentLeft);
|
||||
HP_BAR(opponentLeft);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_LEECH_SEED_DRAIN, playerRight);
|
||||
HP_BAR(playerRight);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_LEECH_SEED_DRAIN, playerLeft);
|
||||
HP_BAR(playerLeft);
|
||||
}
|
||||
}
|
||||
|
||||
TO_DO_BATTLE_TEST("Leech Seed doesn't affect already seeded targets")
|
||||
TO_DO_BATTLE_TEST("Leech Seed's effect is paused until a new battler replaces the original user's position") // Faint, can't be replaced, then revived.
|
||||
TO_DO_BATTLE_TEST("Leech Seed's effect pause still prevents it from being seeded again")
|
||||
|
||||
37
test/battle/move_effect/magic_room.c
Normal file
37
test/battle/move_effect/magic_room.c
Normal file
@ -0,0 +1,37 @@
|
||||
#include "global.h"
|
||||
#include "test/battle.h"
|
||||
|
||||
ASSUMPTIONS
|
||||
{
|
||||
ASSUME(GetMoveEffect(MOVE_MAGIC_ROOM) == EFFECT_MAGIC_ROOM);
|
||||
}
|
||||
|
||||
DOUBLE_BATTLE_TEST("Magic Room prevents item hold effects")
|
||||
{
|
||||
GIVEN {
|
||||
ASSUME(gItemsInfo[ITEM_BERRY_JUICE].holdEffect == HOLD_EFFECT_RESTORE_HP);
|
||||
ASSUME(GetMoveEffect(MOVE_DRAGON_RAGE) == EFFECT_FIXED_DAMAGE_ARG);
|
||||
ASSUME(GetMoveFixedDamage(MOVE_DRAGON_RAGE) == 40);
|
||||
|
||||
PLAYER(SPECIES_WOBBUFFET) { MaxHP(100); HP(60); Item(ITEM_BERRY_JUICE); }
|
||||
PLAYER(SPECIES_WOBBUFFET) { MaxHP(100); HP(60); Item(ITEM_BERRY_JUICE); }
|
||||
OPPONENT(SPECIES_WOBBUFFET) { MaxHP(100); HP(60); Item(ITEM_BERRY_JUICE); }
|
||||
OPPONENT(SPECIES_WOBBUFFET) { MaxHP(100); HP(60); Item(ITEM_BERRY_JUICE); }
|
||||
} WHEN {
|
||||
TURN { MOVE(playerLeft, MOVE_MAGIC_ROOM); }
|
||||
TURN {
|
||||
MOVE(playerLeft, MOVE_DRAGON_RAGE, target: opponentLeft);
|
||||
MOVE(opponentLeft, MOVE_DRAGON_RAGE, target: playerLeft);
|
||||
MOVE(playerRight, MOVE_DRAGON_RAGE, target: opponentRight);
|
||||
MOVE(opponentRight, MOVE_DRAGON_RAGE, target: playerRight);
|
||||
}
|
||||
TURN { MOVE(playerLeft, MOVE_MAGIC_ROOM); }
|
||||
} SCENE {
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_MAGIC_ROOM, playerLeft);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_MAGIC_ROOM, playerLeft);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_HELD_ITEM_EFFECT, playerLeft);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_HELD_ITEM_EFFECT, opponentLeft);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_HELD_ITEM_EFFECT, playerRight);
|
||||
ANIMATION(ANIM_TYPE_GENERAL, B_ANIM_HELD_ITEM_EFFECT, opponentRight);
|
||||
}
|
||||
}
|
||||
25
test/battle/move_effect/wish.c
Normal file
25
test/battle/move_effect/wish.c
Normal file
@ -0,0 +1,25 @@
|
||||
#include "global.h"
|
||||
#include "test/battle.h"
|
||||
|
||||
ASSUMPTIONS
|
||||
{
|
||||
ASSUME(GetMoveEffect(MOVE_WISH) == EFFECT_WISH);
|
||||
}
|
||||
|
||||
SINGLE_BATTLE_TEST("Wish restores 50% of max player HP")
|
||||
{
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_WYNAUT) { HP(50); MaxHP(100); }
|
||||
OPPONENT(SPECIES_WOBBUFFET);
|
||||
} WHEN {
|
||||
TURN { MOVE(player, MOVE_WISH); }
|
||||
TURN { }
|
||||
} SCENE {
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_WISH, player);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_CELEBRATE, player);
|
||||
MESSAGE("Wynaut's wish came true!");
|
||||
HP_BAR(player, hp: 100);
|
||||
MESSAGE("Wynaut's HP was restored.");
|
||||
}
|
||||
}
|
||||
|
||||
@ -24,22 +24,24 @@ SINGLE_BATTLE_TEST("Throat Chop prevents the usage of sound moves")
|
||||
}
|
||||
}
|
||||
|
||||
SINGLE_BATTLE_TEST("Throat Chop won't work through a substitute")
|
||||
SINGLE_BATTLE_TEST("Throat Chop prevents sound base moves for 2 turns")
|
||||
{
|
||||
GIVEN {
|
||||
PLAYER(SPECIES_INCINEROAR) { Speed(100); };
|
||||
OPPONENT(SPECIES_WOBBUFFET) { Speed(50); };
|
||||
PLAYER(SPECIES_WOBBUFFET);
|
||||
OPPONENT(SPECIES_WOBBUFFET) { Moves(MOVE_HYPER_VOICE, MOVE_ALLURING_VOICE, MOVE_OVERDRIVE, MOVE_ROUND); }
|
||||
} WHEN {
|
||||
TURN { MOVE(opponent, MOVE_SUBSTITUTE); }
|
||||
TURN { MOVE(player, MOVE_THROAT_CHOP); MOVE(opponent, MOVE_HYPER_VOICE); }
|
||||
TURN {}
|
||||
TURN { MOVE(opponent, MOVE_HYPER_VOICE); MOVE(player, MOVE_THROAT_CHOP); }
|
||||
TURN { FORCED_MOVE(opponent); }
|
||||
TURN { MOVE(opponent, MOVE_HYPER_VOICE); MOVE(player, MOVE_THROAT_CHOP); }
|
||||
TURN { FORCED_MOVE(opponent); }
|
||||
TURN { MOVE(opponent, MOVE_HYPER_VOICE); }
|
||||
} SCENE {
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_SUBSTITUTE, opponent);
|
||||
HP_BAR(opponent);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_HYPER_VOICE, opponent);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_THROAT_CHOP, player);
|
||||
NONE_OF {
|
||||
MESSAGE("The effects of Throat Chop prevent the opposing Wobbuffet from using certain moves!");
|
||||
}
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_STRUGGLE, opponent);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_HYPER_VOICE, opponent);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_THROAT_CHOP, player);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_STRUGGLE, opponent);
|
||||
ANIMATION(ANIM_TYPE_MOVE, MOVE_HYPER_VOICE, opponent);
|
||||
}
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user