diff --git a/src/battle-scene.ts b/src/battle-scene.ts index 606f484e092..b33a5696b7b 100644 --- a/src/battle-scene.ts +++ b/src/battle-scene.ts @@ -2084,6 +2084,24 @@ export default class BattleScene extends SceneBase { } } + /** + * Tries to add the input phase to index before target phase in the phaseQueue, else simply calls unshiftPhase() + * @param phase {@linkcode Phase} the phase to be added + * @param targetPhase {@linkcode Phase} the type of phase to search for in phaseQueue + * @returns boolean if a targetPhase was found and added + */ + prependToPhase(phase: Phase, targetPhase: Constructor): boolean { + const targetIndex = this.phaseQueue.findIndex(ph => ph instanceof targetPhase); + + if (targetIndex !== -1) { + this.phaseQueue.splice(targetIndex, 0, phase); + return true; + } else { + this.unshiftPhase(phase); + return false; + } + } + queueMessage(message: string, callbackDelay?: integer, prompt?: boolean, promptDelay?: integer, defer?: boolean) { const phase = new MessagePhase(this, message, callbackDelay, prompt, promptDelay); if (!defer) { diff --git a/src/data/move.ts b/src/data/move.ts index d977d60499e..4a77d89f9f1 100644 --- a/src/data/move.ts +++ b/src/data/move.ts @@ -1,5 +1,5 @@ import { ChargeAnim, MoveChargeAnim, initMoveAnim, loadMoveAnimAssets } from "./battle-anims"; -import { BattleEndPhase, MovePhase, NewBattlePhase, PartyStatusCurePhase, PokemonHealPhase, StatChangePhase, SwitchSummonPhase } from "../phases"; +import { BattleEndPhase, MoveEndPhase, MovePhase, NewBattlePhase, PartyStatusCurePhase, PokemonHealPhase, StatChangePhase, SwitchSummonPhase } from "../phases"; import { BattleStat, getBattleStatName } from "./battle-stat"; import { EncoreTag, HelpingHandTag, SemiInvulnerableTag, TypeBoostTag } from "./battler-tags"; import { getPokemonMessage, getPokemonNameWithAffix } from "../messages"; @@ -4578,10 +4578,11 @@ export class ForceSwitchOutAttr extends MoveEffectAttr { // This ensures that the switch out only happens when the conditions are met const switchOutTarget = this.user ? user : target; if (switchOutTarget instanceof PlayerPokemon) { - if (switchOutTarget.hp) { - applyPreSwitchOutAbAttrs(PreSwitchOutAbAttr, switchOutTarget); - (switchOutTarget as PlayerPokemon).switchOut(this.batonPass, true).then(() => resolve(true)); - } else { + if (switchOutTarget.hp > 0) { + applyPreSwitchOutAbAttrs(PreSwitchOutAbAttr, switchOutTarget); + // switchOut below sets the UI to select party(this is not a separate Phase), then adds a SwitchSummonPhase with selected 'mon + (switchOutTarget as PlayerPokemon).switchOut(this.batonPass, true).then(() => resolve(true)); + } else { resolve(false); } return; @@ -4594,8 +4595,9 @@ export class ForceSwitchOutAttr extends MoveEffectAttr { switchOutTarget.scene.field.remove(switchOutTarget); user.scene.triggerPokemonFormChange(switchOutTarget, SpeciesFormChangeActiveTrigger, true); - if (switchOutTarget.hp) { - user.scene.unshiftPhase(new SwitchSummonPhase(user.scene, switchOutTarget.getFieldIndex(), user.scene.currentBattle.trainer.getNextSummonIndex((switchOutTarget as EnemyPokemon).trainerSlot), false, this.batonPass, false)); + if (switchOutTarget.hp > 0) { + // for opponent switching out + user.scene.prependToPhase(new SwitchSummonPhase(user.scene, switchOutTarget.getFieldIndex(), user.scene.currentBattle.trainer.getNextSummonIndex((switchOutTarget as EnemyPokemon).trainerSlot), false, this.batonPass, false), MoveEndPhase); } } else { // Switch out logic for everything else diff --git a/src/field/pokemon.ts b/src/field/pokemon.ts index cb648766095..ecda7602569 100644 --- a/src/field/pokemon.ts +++ b/src/field/pokemon.ts @@ -17,7 +17,7 @@ import { initMoveAnim, loadMoveAnimAssets } from "../data/battle-anims"; import { Status, StatusEffect, getRandomStatus } from "../data/status-effect"; import { pokemonEvolutions, pokemonPrevolutions, SpeciesFormEvolution, SpeciesEvolutionCondition, FusionSpeciesFormEvolution } from "../data/pokemon-evolutions"; import { reverseCompatibleTms, tmSpecies, tmPoolTiers } from "../data/tms"; -import { DamagePhase, FaintPhase, LearnMovePhase, MoveEffectPhase, ObtainStatusEffectPhase, StatChangePhase, SwitchSummonPhase, ToggleDoublePositionPhase } from "../phases"; +import { DamagePhase, FaintPhase, LearnMovePhase, MoveEffectPhase, ObtainStatusEffectPhase, StatChangePhase, SwitchSummonPhase, ToggleDoublePositionPhase, MoveEndPhase } from "../phases"; import { BattleStat } from "../data/battle-stat"; import { BattlerTag, BattlerTagLapseType, EncoreTag, GroundedTag, HighestStatBoostTag, TypeImmuneTag, getBattlerTag, SemiInvulnerableTag, TypeBoostTag } from "../data/battler-tags"; import { WeatherType } from "../data/weather"; @@ -3087,7 +3087,7 @@ export class PlayerPokemon extends Pokemon { this.scene.ui.setMode(Mode.PARTY, PartyUiMode.FAINT_SWITCH, this.getFieldIndex(), (slotIndex: integer, option: PartyOption) => { if (slotIndex >= this.scene.currentBattle.getBattlerCount() && slotIndex < 6) { - this.scene.unshiftPhase(new SwitchSummonPhase(this.scene, this.getFieldIndex(), slotIndex, false, batonPass)); + this.scene.prependToPhase(new SwitchSummonPhase(this.scene, this.getFieldIndex(), slotIndex, false, batonPass), MoveEndPhase); } if (removeFromField) { this.setVisible(false); diff --git a/src/phases.ts b/src/phases.ts index b11abb33ca4..a28ad0612ab 100644 --- a/src/phases.ts +++ b/src/phases.ts @@ -1557,6 +1557,15 @@ export class SwitchSummonPhase extends SummonPhase { private lastPokemon: Pokemon; + /** + * Constructor for creating a new SwitchSummonPhase + * @param scene {@linkcode BattleScene} the scene the phase is associated with + * @param fieldIndex integer representing position on the battle field + * @param slotIndex integer for the index of pokemon (in party of 6) to switch into + * @param doReturn boolean whether to render "comeback" dialogue + * @param batonPass boolean if the switch is from baton pass + * @param player boolean if the switch is from the player + */ constructor(scene: BattleScene, fieldIndex: integer, slotIndex: integer, doReturn: boolean, batonPass: boolean, player?: boolean) { super(scene, fieldIndex, player !== undefined ? player : true); @@ -1580,6 +1589,8 @@ export class SwitchSummonPhase extends SummonPhase { } } + // if doReturn === False OR slotIndex !== -1 (slotIndex is valid) and the pokemon doesn't exist/is false + // then switchAndSummon(), manually pick pokemon to switch into if (!this.doReturn || (this.slotIndex !== -1 && !(this.player ? this.scene.getParty() : this.scene.getEnemyParty())[this.slotIndex])) { if (this.player) { return this.switchAndSummon();