diff --git a/src/data/ability.ts b/src/data/ability.ts index b5e4a91a11c..2c472871bab 100644 --- a/src/data/ability.ts +++ b/src/data/ability.ts @@ -2396,18 +2396,42 @@ export class RunSuccessAbAttr extends AbAttr { } } +/** + * Base class for checking if a Pokemon is trapped by arena trap + * @extends AbAttr + * @see {@linkcode applyCheckTrapped} + */ export class CheckTrappedAbAttr extends AbAttr { constructor() { super(false); } - - applyCheckTrapped(pokemon: Pokemon, passive: boolean, trapped: Utils.BooleanHolder, args: any[]): boolean | Promise { + + applyCheckTrapped(pokemon: Pokemon, passive: boolean, trapped: Utils.BooleanHolder, otherPokemon: Pokemon, args: any[]): boolean | Promise { return false; } } +/** + * Determines whether a Pokemon is blocked from switching/running away + * because of a trapping ability or move. + * @extends CheckTrappedAbAttr + * @see {@linkcode applyCheckTrapped} + */ export class ArenaTrapAbAttr extends CheckTrappedAbAttr { - applyCheckTrapped(pokemon: Pokemon, passive: boolean, trapped: Utils.BooleanHolder, args: any[]): boolean { + /** + * Checks if enemy Pokemon is trapped by an Arena Trap-esque ability + * @param pokemon The {@link Pokemon} with this {@link AbAttr} + * @param passive N/A + * @param trapped {@link Utils.BooleanHolder} indicating whether the other Pokemon is trapped or not + * @param otherPokemon The {@link Pokemon} that is affected by an Arena Trap ability + * @param args N/A + * @returns if enemy Pokemon is trapped or not + */ + applyCheckTrapped(pokemon: Pokemon, passive: boolean, trapped: Utils.BooleanHolder, otherPokemon: Pokemon, args: any[]): boolean { + if (otherPokemon.getTypes().includes(Type.GHOST)){ + trapped.value = false; + return false; + } trapped.value = true; return true; } @@ -2916,8 +2940,8 @@ export function applyPostTerrainChangeAbAttrs(attrType: { new(...args: any[]): P } export function applyCheckTrappedAbAttrs(attrType: { new(...args: any[]): CheckTrappedAbAttr }, - pokemon: Pokemon, trapped: Utils.BooleanHolder, ...args: any[]): Promise { - return applyAbAttrsInternal(attrType, pokemon, (attr, passive) => attr.applyCheckTrapped(pokemon, passive, trapped, args), args, true); + pokemon: Pokemon, trapped: Utils.BooleanHolder, otherPokemon: Pokemon, ...args: any[]): Promise { + return applyAbAttrsInternal(attrType, pokemon, (attr, passive) => attr.applyCheckTrapped(pokemon, passive, trapped, otherPokemon, args), args, true); } export function applyPostBattleAbAttrs(attrType: { new(...args: any[]): PostBattleAbAttr }, diff --git a/src/phases.ts b/src/phases.ts index 1d4d0ba5f34..a6df54c4cea 100644 --- a/src/phases.ts +++ b/src/phases.ts @@ -1809,7 +1809,7 @@ export class CommandPhase extends FieldPhase { const trapped = new Utils.BooleanHolder(false); const batonPass = isSwitch && args[0] as boolean; if (!batonPass) - enemyField.forEach(enemyPokemon => applyCheckTrappedAbAttrs(CheckTrappedAbAttr, enemyPokemon, trapped)); + enemyField.forEach(enemyPokemon => applyCheckTrappedAbAttrs(CheckTrappedAbAttr, enemyPokemon, trapped, playerPokemon)); if (batonPass || (!trapTag && !trapped.value)) { this.scene.currentBattle.turnCommands[this.fieldIndex] = isSwitch ? { command: Command.POKEMON, cursor: cursor, args: args } @@ -1914,7 +1914,7 @@ export class EnemyCommandPhase extends FieldPhase { const trapTag = enemyPokemon.findTag(t => t instanceof TrappedTag) as TrappedTag; const trapped = new Utils.BooleanHolder(false); - opponents.forEach(playerPokemon => applyCheckTrappedAbAttrs(CheckTrappedAbAttr, playerPokemon, trapped)); + opponents.forEach(playerPokemon => applyCheckTrappedAbAttrs(CheckTrappedAbAttr, playerPokemon, trapped, enemyPokemon)); if (!trapTag && !trapped.value) { const partyMemberScores = trainer.getPartyMemberMatchupScores(enemyPokemon.trainerSlot, true);