diff --git a/include/battle.h b/include/battle.h index 1274ffcbfc4d..2032c5a3d40d 100644 --- a/include/battle.h +++ b/include/battle.h @@ -787,6 +787,7 @@ struct BattleStruct u8 trainerSlideDynamaxMsgDone:1; u8 pledgeMove:1; u8 isSkyBattle:1; + u8 poisonPuppeteerConfusion:1; u32 aiDelayTimer; // Counts number of frames AI takes to choose an action. u32 aiDelayFrames; // Number of frames it took to choose an action. u8 timesGotHit[NUM_BATTLE_SIDES][PARTY_SIZE]; diff --git a/src/battle_script_commands.c b/src/battle_script_commands.c index e3f6615832a3..feb0149c685f 100644 --- a/src/battle_script_commands.c +++ b/src/battle_script_commands.c @@ -3085,7 +3085,6 @@ void SetMoveEffect(bool32 primary, bool32 certain) } // for synchronize - if (gBattleScripting.moveEffect == MOVE_EFFECT_POISON || gBattleScripting.moveEffect == MOVE_EFFECT_TOXIC || gBattleScripting.moveEffect == MOVE_EFFECT_PARALYSIS @@ -3094,6 +3093,10 @@ void SetMoveEffect(bool32 primary, bool32 certain) gBattleStruct->synchronizeMoveEffect = gBattleScripting.moveEffect; gHitMarker |= HITMARKER_SYNCHRONISE_EFFECT; } + + if (gBattleScripting.moveEffect == MOVE_EFFECT_POISON || gBattleScripting.moveEffect == MOVE_EFFECT_TOXIC) + gBattleStruct->poisonPuppeteerConfusion = TRUE; + return; } else if (statusChanged == FALSE) @@ -6303,6 +6306,7 @@ static void Cmd_moveend(void) gBattleStruct->swapDamageCategory = FALSE; gBattleStruct->enduredDamage = 0; gBattleStruct->additionalEffectsCounter = 0; + gBattleStruct->poisonPuppeteerConfusion = FALSE; gBattleScripting.moveendState++; break; case MOVEEND_COUNT: diff --git a/src/battle_util.c b/src/battle_util.c index 55df4761ded7..0fd4bc37aadd 100644 --- a/src/battle_util.c +++ b/src/battle_util.c @@ -5762,6 +5762,18 @@ u32 AbilityBattleEffects(u32 caseID, u32 battler, u32 ability, u32 special, u32 effect++; } break; + case ABILITY_POISON_PUPPETEER: + if (gBattleMons[gBattlerAttacker].species == SPECIES_PECHARUNT + && gBattleStruct->poisonPuppeteerConfusion == TRUE + && CanBeConfused(gBattlerTarget)) + { + gBattleStruct->poisonPuppeteerConfusion = FALSE; + gBattleScripting.moveEffect = MOVE_EFFECT_CONFUSION; + PREPARE_ABILITY_BUFFER(gBattleTextBuff1, gLastUsedAbility); + BattleScriptPushCursor(); + gBattlescriptCurrInstr = BattleScript_AbilityStatusEffect; + effect++; + } } break; case ABILITYEFFECT_MOVE_END_OTHER: // Abilities that activate on *another* battler's moveend: Dancer, Soul-Heart, Receiver, Symbiosis diff --git a/test/battle/ability/poison_puppeteer.c b/test/battle/ability/poison_puppeteer.c new file mode 100644 index 000000000000..af5d5389fa65 --- /dev/null +++ b/test/battle/ability/poison_puppeteer.c @@ -0,0 +1,73 @@ +#include "global.h" +#include "test/battle.h" + +ASSUMPTIONS +{ +} + +SINGLE_BATTLE_TEST("Poison Puppeteer confuses target if it was poisoned by a damaging move") +{ + GIVEN { + ASSUME(MoveHasAdditionalEffect(MOVE_POISON_STING, MOVE_EFFECT_POISON) == TRUE); + PLAYER(SPECIES_PECHARUNT) { Ability(ABILITY_POISON_PUPPETEER); } + OPPONENT(SPECIES_WOBBUFFET); + } WHEN { + TURN { MOVE(player, MOVE_POISON_STING); } + } SCENE { + ANIMATION(ANIM_TYPE_MOVE, MOVE_POISON_STING, player); + HP_BAR(opponent); + ANIMATION(ANIM_TYPE_STATUS, B_ANIM_STATUS_PSN, opponent); + STATUS_ICON(opponent, poison: TRUE); + ABILITY_POPUP(player, ABILITY_POISON_PUPPETEER); + ANIMATION(ANIM_TYPE_STATUS, B_ANIM_STATUS_CONFUSION, opponent); + MESSAGE("Foe Wobbuffet became confused!"); + } +} + +SINGLE_BATTLE_TEST("Poison Puppeteer confuses target if it was (badly) poisoned by a status move") +{ + u32 move; + + PARAMETRIZE { move = MOVE_POISON_POWDER; } + PARAMETRIZE { move = MOVE_TOXIC; } + + GIVEN { + ASSUME(MoveHasAdditionalEffect(MOVE_POISON_STING, MOVE_EFFECT_POISON) == TRUE); + PLAYER(SPECIES_PECHARUNT) { Ability(ABILITY_POISON_PUPPETEER); } + OPPONENT(SPECIES_WOBBUFFET); + } WHEN { + TURN { MOVE(player, move); } + } SCENE { + ANIMATION(ANIM_TYPE_MOVE, move, player); + ANIMATION(ANIM_TYPE_STATUS, B_ANIM_STATUS_PSN, opponent); + if (move == MOVE_POISON_POWDER) + STATUS_ICON(opponent, poison: TRUE); + else + STATUS_ICON(opponent, badPoison: TRUE); + ABILITY_POPUP(player, ABILITY_POISON_PUPPETEER); + ANIMATION(ANIM_TYPE_STATUS, B_ANIM_STATUS_CONFUSION, opponent); + MESSAGE("Foe Wobbuffet became confused!"); + } +} + +SINGLE_BATTLE_TEST("Poison Puppeteer does not trigger if poison is Toxic Spikes induced") +{ + GIVEN { + ASSUME(gMovesInfo[MOVE_TOXIC_SPIKES].effect == EFFECT_TOXIC_SPIKES); + PLAYER(SPECIES_PECHARUNT) { Ability(ABILITY_POISON_PUPPETEER); } + OPPONENT(SPECIES_WOBBUFFET); + OPPONENT(SPECIES_WOBBUFFET); + } WHEN { + TURN { MOVE(player, MOVE_TOXIC_SPIKES);} + TURN { SWITCH(opponent, 1); } + } SCENE { + ANIMATION(ANIM_TYPE_MOVE, MOVE_TOXIC_SPIKES, player); + ANIMATION(ANIM_TYPE_STATUS, B_ANIM_STATUS_PSN, opponent); + STATUS_ICON(opponent, poison: TRUE); + NONE_OF { + ABILITY_POPUP(player, ABILITY_POISON_PUPPETEER); + ANIMATION(ANIM_TYPE_STATUS, B_ANIM_STATUS_CONFUSION, opponent); + MESSAGE("Foe Wobbuffet became confused!"); + } + } +}