mirror of
https://github.com/pagefaultgames/pokerogue.git
synced 2025-08-22 07:19:28 +02:00
Integrate MoveChargePhase
in battle phase sequence
This commit is contained in:
parent
e9f82af5ea
commit
d613ffe7a8
@ -289,10 +289,9 @@ export default class Move implements Localizable {
|
||||
}
|
||||
|
||||
/**
|
||||
* Getter function that returns if the move targets itself or an ally
|
||||
* Getter function that returns if the move targets the user or its ally
|
||||
* @returns boolean
|
||||
*/
|
||||
|
||||
isAllyTarget(): boolean {
|
||||
switch (this.moveTarget) {
|
||||
case MoveTarget.USER:
|
||||
@ -306,6 +305,10 @@ export default class Move implements Localizable {
|
||||
return false;
|
||||
}
|
||||
|
||||
isChargingMove(): this is ChargingMove {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the move is immune to certain types.
|
||||
* Currently looks at cases of Grass types with powder moves and Dark types with moves affected by Prankster.
|
||||
@ -884,7 +887,7 @@ export class SelfStatusMove extends Move {
|
||||
type SubMove = new (...args: any[]) => Move;
|
||||
|
||||
function ChargeMove<TBase extends SubMove>(Base: TBase) {
|
||||
return class ChargingMove extends Base {
|
||||
return class extends Base {
|
||||
/** The animation to play during the move's charging phase */
|
||||
public readonly chargeAnim: ChargeAnim = ChargeAnim[`${Moves[this.id]}_CHARGING`];
|
||||
/** The message to show during the move's charging phase */
|
||||
@ -893,6 +896,10 @@ function ChargeMove<TBase extends SubMove>(Base: TBase) {
|
||||
/** Move attributes that apply during the move's charging phase */
|
||||
public chargeAttrs: MoveAttr[] = [];
|
||||
|
||||
override isChargingMove(): this is ChargingMove {
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Sets the text to be displayed during this move's charging phase.
|
||||
* References to the user Pokemon should be written as "{USER}", and
|
||||
|
@ -1,7 +1,7 @@
|
||||
import BattleScene from "#app/battle-scene";
|
||||
import { BattlerIndex } from "#app/battle";
|
||||
import { MoveChargeAnim } from "#app/data/battle-anims";
|
||||
import { ChargingAttackMove, ChargingSelfStatusMove, applyMoveChargeAttrs, MoveEffectAttr, InstantChargeAttr } from "#app/data/move";
|
||||
import { applyMoveChargeAttrs, MoveEffectAttr, InstantChargeAttr } from "#app/data/move";
|
||||
import Pokemon, { PokemonMove } from "#app/field/pokemon";
|
||||
import { BooleanHolder } from "#app/utils";
|
||||
import { MovePhase } from "#app/phases/move-phase";
|
||||
@ -31,7 +31,7 @@ export class MoveChargePhase extends PokemonPhase {
|
||||
}
|
||||
|
||||
const move = this.move.getMove();
|
||||
if (!(move instanceof ChargingAttackMove || move instanceof ChargingSelfStatusMove)) {
|
||||
if (!(move.isChargingMove())) {
|
||||
return this.end();
|
||||
}
|
||||
|
||||
@ -39,11 +39,6 @@ export class MoveChargePhase extends PokemonPhase {
|
||||
move.showChargeText(user, target);
|
||||
user.getMoveQueue().push({ move: move.id, targets: [ target?.getBattlerIndex() ]});
|
||||
|
||||
if (move instanceof ChargingSelfStatusMove) {
|
||||
user.addTag(BattlerTagType.CHARGING, 1, move.id, user.id);
|
||||
return this.end();
|
||||
}
|
||||
|
||||
applyMoveChargeAttrs(MoveEffectAttr, user, target, move).then(() => {
|
||||
user.addTag(BattlerTagType.CHARGING, 1, move.id, user.id);
|
||||
this.end();
|
||||
@ -51,11 +46,12 @@ export class MoveChargePhase extends PokemonPhase {
|
||||
});
|
||||
}
|
||||
|
||||
/** Checks the move's instant charge conditions, then ends this phase. */
|
||||
end() {
|
||||
const user = this.getUserPokemon();
|
||||
const move = this.move.getMove();
|
||||
|
||||
if (move instanceof ChargingAttackMove || move instanceof ChargingSelfStatusMove) {
|
||||
if (move.isChargingMove()) {
|
||||
const instantCharge = new BooleanHolder(false);
|
||||
|
||||
applyMoveChargeAttrs(InstantChargeAttr, user, null, move, instantCharge);
|
||||
@ -69,11 +65,11 @@ export class MoveChargePhase extends PokemonPhase {
|
||||
super.end();
|
||||
}
|
||||
|
||||
getUserPokemon(): Pokemon {
|
||||
protected getUserPokemon(): Pokemon {
|
||||
return (this.player ? this.scene.getPlayerField() : this.scene.getEnemyField())[this.fieldIndex];
|
||||
}
|
||||
|
||||
getTargetPokemon(): Pokemon | undefined {
|
||||
protected getTargetPokemon(): Pokemon | undefined {
|
||||
return this.scene.getField(true).find((p) => this.targetIndex === p.getBattlerIndex());
|
||||
}
|
||||
}
|
||||
|
@ -4,7 +4,7 @@ import { applyPreAttackAbAttrs, AddSecondStrikeAbAttr, IgnoreMoveEffectsAbAttr,
|
||||
import { ArenaTagSide, ConditionalProtectTag } from "#app/data/arena-tag";
|
||||
import { MoveAnim } from "#app/data/battle-anims";
|
||||
import { BattlerTagLapseType, DamageProtectedTag, ProtectedTag, SemiInvulnerableTag, SubstituteTag } from "#app/data/battler-tags";
|
||||
import { MoveTarget, applyMoveAttrs, OverrideMoveEffectAttr, MultiHitAttr, AttackMove, FixedDamageAttr, VariableTargetAttr, MissEffectAttr, MoveFlags, applyFilteredMoveAttrs, MoveAttr, MoveEffectAttr, MoveEffectTrigger, ChargeAttr, MoveCategory, NoEffectAttr, HitsTagAttr, ToxicAccuracyAttr } from "#app/data/move";
|
||||
import { MoveTarget, applyMoveAttrs, OverrideMoveEffectAttr, MultiHitAttr, AttackMove, FixedDamageAttr, VariableTargetAttr, MissEffectAttr, MoveFlags, applyFilteredMoveAttrs, MoveAttr, MoveEffectAttr, MoveEffectTrigger, MoveCategory, NoEffectAttr, HitsTagAttr, ToxicAccuracyAttr } from "#app/data/move";
|
||||
import { SpeciesFormChangePostMoveTrigger } from "#app/data/pokemon-forms";
|
||||
import { BattlerTagType } from "#app/enums/battler-tag-type";
|
||||
import { Moves } from "#app/enums/moves";
|
||||
@ -239,15 +239,13 @@ export class MoveEffectPhase extends PokemonPhase {
|
||||
user, target, move).then(() => {
|
||||
// All other effects require the move to not have failed or have been cancelled to trigger
|
||||
if (hitResult !== HitResult.FAIL) {
|
||||
/** Are the move's effects tied to the first turn of a charge move? */
|
||||
const chargeEffect = !!move.getAttrs(ChargeAttr).find(ca => ca.usedChargeEffect(user, this.getTarget() ?? null, move));
|
||||
/**
|
||||
* If the invoked move's effects are meant to trigger during the move's "charge turn,"
|
||||
* ignore all effects after this point.
|
||||
* Otherwise, apply all self-targeted POST_APPLY effects.
|
||||
*/
|
||||
Utils.executeIf(!chargeEffect, () => applyFilteredMoveAttrs((attr: MoveAttr) => attr instanceof MoveEffectAttr && attr.trigger === MoveEffectTrigger.POST_APPLY
|
||||
&& attr.selfTarget && (!attr.firstHitOnly || firstHit) && (!attr.lastHitOnly || lastHit), user, target, move)).then(() => {
|
||||
applyFilteredMoveAttrs((attr: MoveAttr) => attr instanceof MoveEffectAttr && attr.trigger === MoveEffectTrigger.POST_APPLY
|
||||
&& attr.selfTarget && (!attr.firstHitOnly || firstHit) && (!attr.lastHitOnly || lastHit), user, target, move).then(() => {
|
||||
// All effects past this point require the move to have hit the target
|
||||
if (hitResult !== HitResult.NO_EFFECT) {
|
||||
// Apply all non-self-targeted POST_APPLY effects
|
||||
@ -265,7 +263,7 @@ export class MoveEffectPhase extends PokemonPhase {
|
||||
}
|
||||
}
|
||||
// If the move was not protected against, apply all HIT effects
|
||||
Utils.executeIf(!isProtected && !chargeEffect, () => applyFilteredMoveAttrs((attr: MoveAttr) => attr instanceof MoveEffectAttr && (attr as MoveEffectAttr).trigger === MoveEffectTrigger.HIT
|
||||
Utils.executeIf(!isProtected, () => applyFilteredMoveAttrs((attr: MoveAttr) => attr instanceof MoveEffectAttr && (attr as MoveEffectAttr).trigger === MoveEffectTrigger.HIT
|
||||
&& (!attr.firstHitOnly || firstHit) && (!attr.lastHitOnly || lastHit) && (!attr.firstTargetOnly || firstTarget), user, target, this.move.getMove()).then(() => {
|
||||
// Apply the target's post-defend ability effects (as long as the target is active or can otherwise apply them)
|
||||
return Utils.executeIf(!target.isFainted() || target.canApplyAbility(), () => applyPostDefendAbAttrs(PostDefendAbAttr, target, user, this.move.getMove(), hitResult).then(() => {
|
||||
|
@ -22,6 +22,7 @@ import { MoveEndPhase } from "#app/phases/move-end-phase";
|
||||
import { ShowAbilityPhase } from "#app/phases/show-ability-phase";
|
||||
import * as Utils from "#app/utils";
|
||||
import i18next from "i18next";
|
||||
import { MoveChargePhase } from "./move-charge-phase";
|
||||
|
||||
export class MovePhase extends BattlePhase {
|
||||
protected _pokemon: Pokemon;
|
||||
@ -132,6 +133,8 @@ export class MovePhase extends BattlePhase {
|
||||
|
||||
if (this.cancelled || this.failed) {
|
||||
this.handlePreMoveFailures();
|
||||
} else if (this.move.getMove().isChargingMove() && !this.pokemon.getTag(BattlerTagType.CHARGING)) {
|
||||
this.chargeMove();
|
||||
} else {
|
||||
this.useMove();
|
||||
}
|
||||
@ -295,6 +298,11 @@ export class MovePhase extends BattlePhase {
|
||||
}
|
||||
}
|
||||
|
||||
/** Queues a {@linkcode MoveChargePhase} for this phase's invoked move. */
|
||||
protected chargeMove() {
|
||||
this.scene.unshiftPhase(new MoveChargePhase(this.scene, this.pokemon.getBattlerIndex(), this.targets[0], this.move));
|
||||
}
|
||||
|
||||
/**
|
||||
* Queues a {@linkcode MoveEndPhase} if the move wasn't a {@linkcode followUp} and {@linkcode canMove()} returns `true`,
|
||||
* then ends the phase.
|
||||
|
Loading…
Reference in New Issue
Block a user