diff --git a/src/data/abilities/ability.ts b/src/data/abilities/ability.ts index f5fd9b19f72..d3be67275b3 100644 --- a/src/data/abilities/ability.ts +++ b/src/data/abilities/ability.ts @@ -1463,7 +1463,6 @@ export class PostDefendAbilityGiveAbAttr extends PostDefendAbAttr { export class PostDefendMoveDisableAbAttr extends PostDefendAbAttr { private chance: number; private attacker: Pokemon; - private move: Move; constructor(chance: number) { super(); @@ -1479,11 +1478,9 @@ export class PostDefendMoveDisableAbAttr extends PostDefendAbAttr { ); } - override apply({ simulated, opponent: attacker, move, pokemon }: PostMoveInteractionAbAttrParams): void { - // TODO: investigate why this is setting properties + override apply({ simulated, opponent: attacker, pokemon }: PostMoveInteractionAbAttrParams): void { if (!simulated) { this.attacker = attacker; - this.move = move; this.attacker.addTag(BattlerTagType.DISABLED, 4, 0, pokemon.id); } } @@ -6345,10 +6342,13 @@ class ForceSwitchOutHelper { return !blockedByAbility.value; } - if (!player && globalScene.currentBattle.battleType === BattleType.WILD) { - if (!globalScene.currentBattle.waveIndex && globalScene.currentBattle.waveIndex % 10 === 0) { - return false; - } + if ( + !player && + globalScene.currentBattle.battleType === BattleType.WILD && + !globalScene.currentBattle.waveIndex && + globalScene.currentBattle.waveIndex % 10 === 0 + ) { + return false; } if ( diff --git a/src/data/balance/starters.ts b/src/data/balance/starters.ts index 99d5ad62e47..89f83e34d9b 100644 --- a/src/data/balance/starters.ts +++ b/src/data/balance/starters.ts @@ -616,7 +616,7 @@ export const speciesStarterCosts = { [SpeciesId.PALDEA_TAUROS]: 5, [SpeciesId.PALDEA_WOOPER]: 3, [SpeciesId.BLOODMOON_URSALUNA]: 5, -}; +} as const; const starterCandyCosts: { passive: number; costReduction: [number, number]; egg: number; }[] = [ { passive: 40, costReduction: [ 25, 60 ], egg: 30 }, // 1 Cost @@ -657,4 +657,3 @@ export function getValueReductionCandyCounts(starterCost: number): [number, numb export function getSameSpeciesEggCandyCounts(starterCost: number): number { return starterCandyCosts[starterCost - 1].egg; } - diff --git a/src/data/battle-anims.ts b/src/data/battle-anims.ts index 55a3cc4e916..684ac952b70 100644 --- a/src/data/battle-anims.ts +++ b/src/data/battle-anims.ts @@ -1397,6 +1397,7 @@ export class EncounterBattleAnim extends BattleAnim { } } +// biome-ignore-start lint/style/useForOf: This is being removed export async function populateAnims() { const commonAnimNames = getEnumKeys(CommonAnim).map(k => k.toLowerCase()); const commonAnimMatchNames = commonAnimNames.map(k => k.replace(/_/g, "")); @@ -1672,3 +1673,5 @@ export async function populateAnims() { })(); }*/ } + +// biome-ignore-end lint/style/useForOf: This is being removed diff --git a/src/data/battler-tags.ts b/src/data/battler-tags.ts index 1199ac581a6..15b4572f851 100644 --- a/src/data/battler-tags.ts +++ b/src/data/battler-tags.ts @@ -2537,12 +2537,10 @@ export class RoostedTag extends BattlerTag { let modifiedTypes: PokemonType[]; if (this.isBasePureFlying && !isCurrentlyDualType) { modifiedTypes = [PokemonType.NORMAL]; + } else if (!!pokemon.getTag(RemovedTypeTag) && isOriginallyDualType && !isCurrentlyDualType) { + modifiedTypes = [PokemonType.UNKNOWN]; } else { - if (!!pokemon.getTag(RemovedTypeTag) && isOriginallyDualType && !isCurrentlyDualType) { - modifiedTypes = [PokemonType.UNKNOWN]; - } else { - modifiedTypes = currentTypes.filter(type => type !== PokemonType.FLYING); - } + modifiedTypes = currentTypes.filter(type => type !== PokemonType.FLYING); } pokemon.summonData.types = modifiedTypes; pokemon.updateInfo(); diff --git a/src/data/daily-run.ts b/src/data/daily-run.ts index f0a20a0b02b..addaebdd238 100644 --- a/src/data/daily-run.ts +++ b/src/data/daily-run.ts @@ -42,10 +42,9 @@ export function getDailyRunStarters(seed: string): Starter[] { starterCosts.push(randSeedInt(9 - starterCosts[0], 1)); starterCosts.push(10 - (starterCosts[0] + starterCosts[1])); - for (let c = 0; c < starterCosts.length; c++) { - const cost = starterCosts[c]; + for (const cost of starterCosts) { const costSpecies = Object.keys(speciesStarterCosts) - .map(s => Number.parseInt(s) as SpeciesId) + .map(s => Number.parseInt(s) as SpeciesId) // TODO: Remove .filter(s => speciesStarterCosts[s] === cost); const randPkmSpecies = getPokemonSpecies(randSeedItem(costSpecies)); const starterSpecies = getPokemonSpecies( diff --git a/src/data/egg.ts b/src/data/egg.ts index 2c567686fc2..10eccb07cf9 100644 --- a/src/data/egg.ts +++ b/src/data/egg.ts @@ -419,10 +419,8 @@ export class Egg { const rand = randSeedInt(MANAPHY_EGG_MANAPHY_RATE) !== 1; return rand ? SpeciesId.PHIONE : SpeciesId.MANAPHY; } - if (this.tier === EggTier.LEGENDARY && this._sourceType === EggSourceType.GACHA_LEGENDARY) { - if (!randSeedInt(2)) { - return getLegendaryGachaSpeciesForTimestamp(this.timestamp); - } + if (this.tier === EggTier.LEGENDARY && this._sourceType === EggSourceType.GACHA_LEGENDARY && !randSeedInt(2)) { + return getLegendaryGachaSpeciesForTimestamp(this.timestamp); } let minStarterValue: number; diff --git a/src/data/mystery-encounters/encounters/absolute-avarice-encounter.ts b/src/data/mystery-encounters/encounters/absolute-avarice-encounter.ts index d6058eb9eaf..6406621e725 100644 --- a/src/data/mystery-encounters/encounters/absolute-avarice-encounter.ts +++ b/src/data/mystery-encounters/encounters/absolute-avarice-encounter.ts @@ -527,7 +527,8 @@ function doBerrySpritePile(isEat = false) { const encounter = globalScene.currentBattle.mysteryEncounter!; animationOrder.forEach((berry, i) => { const introVisualsIndex = encounter.spriteConfigs.findIndex(config => config.spriteKey?.includes(berry)); - let sprite: Phaser.GameObjects.Sprite, tintSprite: Phaser.GameObjects.Sprite; + let sprite: Phaser.GameObjects.Sprite; + let tintSprite: Phaser.GameObjects.Sprite; const sprites = encounter.introVisuals?.getSpriteAtIndex(introVisualsIndex); if (sprites) { sprite = sprites[0]; diff --git a/src/data/mystery-encounters/encounters/bug-type-superfan-encounter.ts b/src/data/mystery-encounters/encounters/bug-type-superfan-encounter.ts index c5553e9bb95..f40a8403a87 100644 --- a/src/data/mystery-encounters/encounters/bug-type-superfan-encounter.ts +++ b/src/data/mystery-encounters/encounters/bug-type-superfan-encounter.ts @@ -213,7 +213,8 @@ export const BugTypeSuperfanEncounter: MysteryEncounter = MysteryEncounterBuilde female: true, }); - let beedrillKeys: { spriteKey: string; fileRoot: string }, butterfreeKeys: { spriteKey: string; fileRoot: string }; + let beedrillKeys: { spriteKey: string; fileRoot: string }; + let butterfreeKeys: { spriteKey: string; fileRoot: string }; if (globalScene.currentBattle.waveIndex < WAVE_LEVEL_BREAKPOINTS[3]) { beedrillKeys = getSpriteKeysFromSpecies(SpeciesId.BEEDRILL, false); butterfreeKeys = getSpriteKeysFromSpecies(SpeciesId.BUTTERFREE, false); diff --git a/src/data/mystery-encounters/encounters/global-trade-system-encounter.ts b/src/data/mystery-encounters/encounters/global-trade-system-encounter.ts index ed49fccf190..e157b1a812f 100644 --- a/src/data/mystery-encounters/encounters/global-trade-system-encounter.ts +++ b/src/data/mystery-encounters/encounters/global-trade-system-encounter.ts @@ -289,16 +289,14 @@ export const GlobalTradeSystemEncounter: MysteryEncounter = MysteryEncounterBuil // Extra HA roll at base 1/64 odds (boosted by events and charms) const hiddenIndex = tradePokemon.species.ability2 ? 2 : 1; - if (tradePokemon.species.abilityHidden) { - if (tradePokemon.abilityIndex < hiddenIndex) { - const hiddenAbilityChance = new NumberHolder(64); - globalScene.applyModifiers(HiddenAbilityRateBoosterModifier, true, hiddenAbilityChance); + if (tradePokemon.species.abilityHidden && tradePokemon.abilityIndex < hiddenIndex) { + const hiddenAbilityChance = new NumberHolder(64); + globalScene.applyModifiers(HiddenAbilityRateBoosterModifier, true, hiddenAbilityChance); - const hasHiddenAbility = !randSeedInt(hiddenAbilityChance.value); + const hasHiddenAbility = !randSeedInt(hiddenAbilityChance.value); - if (hasHiddenAbility) { - tradePokemon.abilityIndex = hiddenIndex; - } + if (hasHiddenAbility) { + tradePokemon.abilityIndex = hiddenIndex; } } diff --git a/src/data/mystery-encounters/utils/encounter-phase-utils.ts b/src/data/mystery-encounters/utils/encounter-phase-utils.ts index b599f923534..a40d3d1b3b9 100644 --- a/src/data/mystery-encounters/utils/encounter-phase-utils.ts +++ b/src/data/mystery-encounters/utils/encounter-phase-utils.ts @@ -1107,12 +1107,10 @@ export function calculateMEAggregateStats(baseSpawnWeight: number) { } } else if (biomeLinks.hasOwnProperty(currentBiome)) { currentBiome = biomeLinks[currentBiome] as BiomeId; + } else if (!(i % 50)) { + currentBiome = BiomeId.END; } else { - if (!(i % 50)) { - currentBiome = BiomeId.END; - } else { - currentBiome = globalScene.generateRandomBiome(i); - } + currentBiome = globalScene.generateRandomBiome(i); } currentArena = globalScene.newArena(currentBiome); diff --git a/src/data/pokemon-species.ts b/src/data/pokemon-species.ts index 7bfe02d9086..dde2c007ecd 100644 --- a/src/data/pokemon-species.ts +++ b/src/data/pokemon-species.ts @@ -986,41 +986,39 @@ export class PokemonSpecies extends PokemonSpeciesForm implements Localizable { if (!forTrainer && isRegionalEvolution) { evolutionChance = 0; - } else { - if (ev.wildDelay === SpeciesWildEvolutionDelay.NONE) { - if (strength === PartyMemberStrength.STRONGER) { - evolutionChance = 1; - } else { - const maxLevelDiff = this.getStrengthLevelDiff(strength); //The maximum distance from the evolution level tolerated for the mon to not evolve - const minChance: number = 0.875 - 0.125 * strength; - - evolutionChance = Math.min( - minChance + easeInFunc(Math.min(level - ev.level, maxLevelDiff) / maxLevelDiff) * (1 - minChance), - 1, - ); - } + } else if (ev.wildDelay === SpeciesWildEvolutionDelay.NONE) { + if (strength === PartyMemberStrength.STRONGER) { + evolutionChance = 1; } else { - const preferredMinLevel = Math.max(ev.level - 1 + ev.wildDelay! * this.getStrengthLevelDiff(strength), 1); // TODO: is the bang correct? - let evolutionLevel = Math.max(ev.level > 1 ? ev.level : Math.floor(preferredMinLevel / 2), 1); - - if (ev.level <= 1 && pokemonPrevolutions.hasOwnProperty(this.speciesId)) { - const prevolutionLevel = pokemonEvolutions[pokemonPrevolutions[this.speciesId]].find( - ev => ev.speciesId === this.speciesId, - )!.level; // TODO: is the bang correct? - if (prevolutionLevel > 1) { - evolutionLevel = prevolutionLevel; - } - } + const maxLevelDiff = this.getStrengthLevelDiff(strength); //The maximum distance from the evolution level tolerated for the mon to not evolve + const minChance: number = 0.875 - 0.125 * strength; evolutionChance = Math.min( - 0.65 * easeInFunc(Math.min(Math.max(level - evolutionLevel, 0), preferredMinLevel) / preferredMinLevel) + - 0.35 * - easeOutFunc( - Math.min(Math.max(level - evolutionLevel, 0), preferredMinLevel * 2.5) / (preferredMinLevel * 2.5), - ), + minChance + easeInFunc(Math.min(level - ev.level, maxLevelDiff) / maxLevelDiff) * (1 - minChance), 1, ); } + } else { + const preferredMinLevel = Math.max(ev.level - 1 + ev.wildDelay! * this.getStrengthLevelDiff(strength), 1); // TODO: is the bang correct? + let evolutionLevel = Math.max(ev.level > 1 ? ev.level : Math.floor(preferredMinLevel / 2), 1); + + if (ev.level <= 1 && pokemonPrevolutions.hasOwnProperty(this.speciesId)) { + const prevolutionLevel = pokemonEvolutions[pokemonPrevolutions[this.speciesId]].find( + ev => ev.speciesId === this.speciesId, + )!.level; // TODO: is the bang correct? + if (prevolutionLevel > 1) { + evolutionLevel = prevolutionLevel; + } + } + + evolutionChance = Math.min( + 0.65 * easeInFunc(Math.min(Math.max(level - evolutionLevel, 0), preferredMinLevel) / preferredMinLevel) + + 0.35 * + easeOutFunc( + Math.min(Math.max(level - evolutionLevel, 0), preferredMinLevel * 2.5) / (preferredMinLevel * 2.5), + ), + 1, + ); } //TODO: Adjust templates and delays so we don't have to hardcode it @@ -1210,9 +1208,9 @@ export class PokemonSpecies extends PokemonSpeciesForm implements Localizable { } /** - * Generates a {@linkcode bigint} corresponding to the maximum unlocks possible for this species, + * Generates a {@linkcode BigInt} corresponding to the maximum unlocks possible for this species, * taking into account if the species has a male/female gender, and which variants are implemented. - * @returns {@linkcode bigint} Maximum unlocks, can be compared with {@linkcode DexEntry.caughtAttr}. + * @returns The maximum unlocks for the species as a `BigInt`; can be compared with {@linkcode DexEntry.caughtAttr}. */ getFullUnlocksData(): bigint { let caughtAttr = 0n; diff --git a/src/field/mystery-encounter-intro.ts b/src/field/mystery-encounter-intro.ts index d3776f349e6..f44fa9df830 100644 --- a/src/field/mystery-encounter-intro.ts +++ b/src/field/mystery-encounter-intro.ts @@ -6,6 +6,7 @@ import type { MysteryEncounter } from "#mystery-encounters/mystery-encounter"; import { loadPokemonVariantAssets } from "#sprites/pokemon-sprite"; import type { Variant } from "#sprites/variant"; import { isNullOrUndefined } from "#utils/common"; +import console from "node:console"; import type { GameObjects } from "phaser"; type PlayAnimationConfig = Phaser.Types.Animations.PlayAnimationConfig; @@ -87,6 +88,7 @@ export class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Container { variant: Variant; }[]; + // TODO: Refactor constructor(encounter: MysteryEncounter) { super(globalScene, -72, 76); this.encounter = encounter; @@ -193,17 +195,15 @@ export class MysteryEncounterIntroVisuals extends Phaser.GameObjects.Container { sprite.setPosition(sprite.x, sprite.y + y); tintSprite.setPosition(tintSprite.x, tintSprite.y + y); } - } else { // Single sprite - if (this.spriteConfigs.length === 1) { - sprite.x = origin; - tintSprite.x = origin; - } else { - // Do standard sprite spacing (not including offset sprites) - sprite.x = minX + (n + 0.5) * spacingValue + origin; - tintSprite.x = minX + (n + 0.5) * spacingValue + origin; - n++; - } + } else if (this.spriteConfigs.length === 1) { + sprite.x = origin; + tintSprite.x = origin; + } else { + // Do standard sprite spacing (not including offset sprites) + sprite.x = minX + (n + 0.5) * spacingValue + origin; + tintSprite.x = minX + (n + 0.5) * spacingValue + origin; + n++; } if (!isNullOrUndefined(pokemonShinySparkle)) { diff --git a/src/field/pokemon.ts b/src/field/pokemon.ts index 29f775ad094..205ab921f8a 100644 --- a/src/field/pokemon.ts +++ b/src/field/pokemon.ts @@ -2511,17 +2511,13 @@ export abstract class Pokemon extends Phaser.GameObjects.Container { defenderType, }); } - if (ignoreImmunity.value) { - if (multiplier.value === 0) { - return 1; - } + if (ignoreImmunity.value && multiplier.value === 0) { + return 1; } const exposedTags = this.findTags(tag => tag instanceof ExposedTag) as ExposedTag[]; - if (exposedTags.some(t => t.ignoreImmunity(defenderType, moveType))) { - if (multiplier.value === 0) { - return 1; - } + if (exposedTags.some(t => t.ignoreImmunity(defenderType, moveType)) && multiplier.value === 0) { + return 1; } } return multiplier.value; @@ -2960,10 +2956,8 @@ export abstract class Pokemon extends Phaser.GameObjects.Container { return false; } const haThreshold = new NumberHolder(thresholdOverride ?? BASE_HIDDEN_ABILITY_CHANCE); - if (applyModifiersToOverride) { - if (!this.hasTrainer()) { - globalScene.applyModifiers(HiddenAbilityRateBoosterModifier, true, haThreshold); - } + if (applyModifiersToOverride && !this.hasTrainer()) { + globalScene.applyModifiers(HiddenAbilityRateBoosterModifier, true, haThreshold); } if (randSeedInt(65536) < haThreshold.value) { @@ -3063,8 +3057,7 @@ export abstract class Pokemon extends Phaser.GameObjects.Container { return; } - for (let m = 0; m < allLevelMoves.length; m++) { - const levelMove = allLevelMoves[m]; + for (const levelMove of allLevelMoves) { if (this.level < levelMove[0]) { break; } @@ -4829,11 +4822,9 @@ export abstract class Pokemon extends Phaser.GameObjects.Container { return true; }); - if (this.isOfType(PokemonType.POISON) || this.isOfType(PokemonType.STEEL)) { - if (poisonImmunity.includes(true)) { - this.queueStatusImmuneMessage(quiet); - return false; - } + if ((this.isOfType(PokemonType.POISON) || this.isOfType(PokemonType.STEEL)) && poisonImmunity.includes(true)) { + this.queueStatusImmuneMessage(quiet); + return false; } break; } @@ -5013,10 +5004,8 @@ export abstract class Pokemon extends Phaser.GameObjects.Container { this.lapseTag(BattlerTagType.NIGHTMARE); } } - if (confusion) { - if (this.getTag(BattlerTagType.CONFUSED)) { - this.lapseTag(BattlerTagType.CONFUSED); - } + if (confusion && this.getTag(BattlerTagType.CONFUSED)) { + this.lapseTag(BattlerTagType.CONFUSED); } if (reloadAssets) { this.loadAssets(false).then(() => this.playAnim()); @@ -5500,8 +5489,8 @@ export abstract class Pokemon extends Phaser.GameObjects.Container { spriteColors.forEach((sc: number[], i: number) => { paletteDeltas.push([]); - for (let p = 0; p < palette.length; p++) { - paletteDeltas[i].push(deltaRgb(sc, palette[p])); + for (const p of palette) { + paletteDeltas[i].push(deltaRgb(sc, p)); } }); @@ -6774,10 +6763,12 @@ export class EnemyPokemon extends Pokemon { } canBypassBossSegments(segmentCount = 1): boolean { - if (globalScene.currentBattle.battleSpec === BattleSpec.FINAL_BOSS) { - if (!this.formIndex && this.bossSegmentIndex - segmentCount < 1) { - return false; - } + if ( + globalScene.currentBattle.battleSpec === BattleSpec.FINAL_BOSS && + !this.formIndex && + this.bossSegmentIndex - segmentCount < 1 + ) { + return false; } return true; diff --git a/src/field/trainer.ts b/src/field/trainer.ts index 584c9310932..356bdf9803a 100644 --- a/src/field/trainer.ts +++ b/src/field/trainer.ts @@ -403,16 +403,14 @@ export class Trainer extends Phaser.GameObjects.Container { } else { newSpeciesPool = speciesPoolFiltered; } - } else { // If the index is odd, use the species pool for the partner trainer (that way he only uses his own pokemon in battle) // Since the only currently allowed double battle with named trainers is Tate & Liza, we need to make sure that Solrock is the first pokemon in the party for Tate and Lunatone for Liza - if (index === 1 && TrainerType[this.config.trainerTypeDouble] === TrainerType[TrainerType.TATE]) { - newSpeciesPool = [SpeciesId.SOLROCK]; - } else if (index === 1 && TrainerType[this.config.trainerTypeDouble] === TrainerType[TrainerType.LIZA]) { - newSpeciesPool = [SpeciesId.LUNATONE]; - } else { - newSpeciesPool = speciesPoolPartnerFiltered; - } + } else if (index === 1 && TrainerType[this.config.trainerTypeDouble] === TrainerType[TrainerType.TATE]) { + newSpeciesPool = [SpeciesId.SOLROCK]; + } else if (index === 1 && TrainerType[this.config.trainerTypeDouble] === TrainerType[TrainerType.LIZA]) { + newSpeciesPool = [SpeciesId.LUNATONE]; + } else { + newSpeciesPool = speciesPoolPartnerFiltered; } // Fallback for when the species pool is empty if (newSpeciesPool.length === 0) { @@ -794,10 +792,12 @@ export class Trainer extends Phaser.GameObjects.Container { * @returns boolean Whether the EnemyPokemon should Terastalize this turn */ shouldTera(pokemon: EnemyPokemon): boolean { - if (this.config.trainerAI.teraMode === TeraAIMode.INSTANT_TERA) { - if (!pokemon.isTerastallized && this.config.trainerAI.instantTeras.includes(pokemon.initialTeamIndex)) { - return true; - } + if ( + this.config.trainerAI.teraMode === TeraAIMode.INSTANT_TERA && + !pokemon.isTerastallized && + this.config.trainerAI.instantTeras.includes(pokemon.initialTeamIndex) + ) { + return true; } return false; } diff --git a/src/modifier/modifier-type.ts b/src/modifier/modifier-type.ts index aca49313ff5..16da9e49f5e 100644 --- a/src/modifier/modifier-type.ts +++ b/src/modifier/modifier-type.ts @@ -1634,9 +1634,9 @@ export class FormChangeItemModifierTypeGenerator extends ModifierTypeGenerator { if (p.species.speciesId === SpeciesId.NECROZMA) { // technically we could use a simplified version and check for formChanges.length > 3, but in case any code changes later, this might break... - let foundULTRA_Z = false, - foundN_LUNA = false, - foundN_SOLAR = false; + let foundULTRA_Z = false; + let foundN_LUNA = false; + let foundN_SOLAR = false; formChangeItemTriggers.forEach((fc, _i) => { console.log("Checking ", fc.item); switch (fc.item) { diff --git a/src/phase-manager.ts b/src/phase-manager.ts index aa01a0ffc10..444055ce619 100644 --- a/src/phase-manager.ts +++ b/src/phase-manager.ts @@ -102,10 +102,13 @@ import { WeatherEffectPhase } from "#phases/weather-effect-phase"; import type { PhaseMap, PhaseString } from "#types/phase-types"; import { type Constructor, coerceArray } from "#utils/common"; -/* +/** + * @module * Manager for phases used by battle scene. * - * *This file must not be imported or used directly. The manager is exclusively used by the battle scene and is not intended for external use.* + * @remarks + * **This file must not be imported or used directly.** + * The manager is exclusively used by the Battle Scene and is NOT intended for external use. */ /** diff --git a/src/phases/command-phase.ts b/src/phases/command-phase.ts index ff9ee7cc197..1c95bcd7569 100644 --- a/src/phases/command-phase.ts +++ b/src/phases/command-phase.ts @@ -604,9 +604,8 @@ export class CommandPhase extends FieldPhase { * @returns Whether the command was successful */ handleCommand(command: Command.FIGHT | Command.TERA, cursor: number, useMode?: MoveUseMode, move?: TurnMove): boolean; - handleCommand(command: Command.BALL, cursor: number): boolean; handleCommand(command: Command.POKEMON, cursor: number, useBaton: boolean): boolean; - handleCommand(command: Command.RUN, cursor: number): boolean; + handleCommand(command: Command.BALL | Command.RUN, cursor: number): boolean; handleCommand(command: Command, cursor: number, useMode?: boolean | MoveUseMode, move?: TurnMove): boolean; public handleCommand( diff --git a/src/phases/move-effect-phase.ts b/src/phases/move-effect-phase.ts index 767d7a79968..6b670ebfa56 100644 --- a/src/phases/move-effect-phase.ts +++ b/src/phases/move-effect-phase.ts @@ -559,10 +559,11 @@ export class MoveEffectPhase extends PokemonPhase { // Strikes after the first in a multi-strike move are guaranteed to hit, // unless the move is flagged to check all hits and the user does not have Skill Link. - if (user.turnData.hitsLeft < user.turnData.hitCount) { - if (!move.hasFlag(MoveFlags.CHECK_ALL_HITS) || user.hasAbilityWithAttr("MaxMultiHitAbAttr")) { - return [HitCheckResult.HIT, effectiveness]; - } + if ( + user.turnData.hitsLeft < user.turnData.hitCount && + (!move.hasFlag(MoveFlags.CHECK_ALL_HITS) || user.hasAbilityWithAttr("MaxMultiHitAbAttr")) + ) { + return [HitCheckResult.HIT, effectiveness]; } const bypassAccuracy = diff --git a/src/phases/scan-ivs-phase.ts b/src/phases/scan-ivs-phase.ts index eebee28bfbb..da5086b6a35 100644 --- a/src/phases/scan-ivs-phase.ts +++ b/src/phases/scan-ivs-phase.ts @@ -23,25 +23,24 @@ export class ScanIvsPhase extends PokemonPhase { let enemyIvs: number[] = []; let statsContainer: Phaser.GameObjects.Sprite[] = []; let statsContainerLabels: Phaser.GameObjects.Sprite[] = []; - const enemyField = globalScene.getEnemyField(); const uiTheme = globalScene.uiTheme; // Assuming uiTheme is accessible - for (let e = 0; e < enemyField.length; e++) { - enemyIvs = enemyField[e].ivs; + for (const enemy of globalScene.getEnemyField()) { + enemyIvs = enemy.ivs; // we are using getRootSpeciesId() here because we want to check against the baby form, not the mid form if it exists - const currentIvs = globalScene.gameData.dexData[enemyField[e].species.getRootSpeciesId()].ivs; - statsContainer = enemyField[e].getBattleInfo().getStatsValueContainer().list as Phaser.GameObjects.Sprite[]; + const currentIvs = globalScene.gameData.dexData[enemy.species.getRootSpeciesId()].ivs; + statsContainer = enemy.getBattleInfo().getStatsValueContainer().list as Phaser.GameObjects.Sprite[]; statsContainerLabels = statsContainer.filter(m => m.name.indexOf("icon_stat_label") >= 0); - for (let s = 0; s < statsContainerLabels.length; s++) { - const ivStat = Stat[statsContainerLabels[s].frame.name]; + for (const statContainer of statsContainerLabels) { + const ivStat = Stat[statContainer.frame.name]; if (enemyIvs[ivStat] > currentIvs[ivStat] && PERMANENT_STATS.indexOf(Number(ivStat)) >= 0) { const hexColour = enemyIvs[ivStat] === 31 ? getTextColor(TextStyle.PERFECT_IV, false, uiTheme) : getTextColor(TextStyle.SUMMARY_GREEN, false, uiTheme); const hexTextColour = Phaser.Display.Color.HexStringToColor(hexColour).color; - statsContainerLabels[s].setTint(hexTextColour); + statContainer.setTint(hexTextColour); } - statsContainerLabels[s].setVisible(true); + statContainer.setVisible(true); } } diff --git a/src/phases/stat-stage-change-phase.ts b/src/phases/stat-stage-change-phase.ts index 140ef841929..414d2c4e714 100644 --- a/src/phases/stat-stage-change-phase.ts +++ b/src/phases/stat-stage-change-phase.ts @@ -22,6 +22,7 @@ export type StatStageChangeCallback = ( relativeChanges: number[], ) => void; +// TODO: Refactor this mess of a phase export class StatStageChangePhase extends PokemonPhase { public readonly phaseName = "StatStageChangePhase"; private stats: BattleStat[]; @@ -62,13 +63,12 @@ export class StatStageChangePhase extends PokemonPhase { start() { // Check if multiple stats are being changed at the same time, then run SSCPhase for each of them if (this.stats.length > 1) { - for (let i = 0; i < this.stats.length; i++) { - const stat = [this.stats[i]]; + for (const stat of this.stats) { globalScene.phaseManager.unshiftNew( "StatStageChangePhase", this.battlerIndex, this.selfTarget, - stat, + [stat], this.stages, this.showMessage, this.ignoreAbilities, @@ -100,20 +100,18 @@ export class StatStageChangePhase extends PokemonPhase { } }); } + } else if (!this.comingFromStickyWeb) { + opponentPokemon = globalScene.getPlayerField()[globalScene.currentBattle.lastPlayerInvolved]; } else { - if (!this.comingFromStickyWeb) { - opponentPokemon = globalScene.getPlayerField()[globalScene.currentBattle.lastPlayerInvolved]; - } else { - const stickyTagID = globalScene.arena.findTagsOnSide( - (t: ArenaTag) => t.tagType === ArenaTagType.STICKY_WEB, - ArenaTagSide.ENEMY, - )[0].sourceId; - globalScene.getPlayerField().forEach(e => { - if (e.id === stickyTagID) { - opponentPokemon = e; - } - }); - } + const stickyTagID = globalScene.arena.findTagsOnSide( + (t: ArenaTag) => t.tagType === ArenaTagType.STICKY_WEB, + ArenaTagSide.ENEMY, + )[0].sourceId; + globalScene.getPlayerField().forEach(e => { + if (e.id === stickyTagID) { + opponentPokemon = e; + } + }); } if (!pokemon.isActive(true)) { diff --git a/src/phases/trainer-victory-phase.ts b/src/phases/trainer-victory-phase.ts index 6f92dbe496d..ffb1a672f49 100644 --- a/src/phases/trainer-victory-phase.ts +++ b/src/phases/trainer-victory-phase.ts @@ -27,29 +27,28 @@ export class TrainerVictoryPhase extends BattlePhase { const trainerType = globalScene.currentBattle.trainer?.config.trainerType!; // TODO: is this bang correct? // Validate Voucher for boss trainers - if (vouchers.hasOwnProperty(TrainerType[trainerType])) { - if ( - !globalScene.validateVoucher(vouchers[TrainerType[trainerType]]) && - globalScene.currentBattle.trainer?.config.isBoss - ) { - if (timedEventManager.getUpgradeUnlockedVouchers()) { - globalScene.phaseManager.unshiftNew( - "ModifierRewardPhase", - [ - modifierTypes.VOUCHER_PLUS, - modifierTypes.VOUCHER_PLUS, - modifierTypes.VOUCHER_PLUS, - modifierTypes.VOUCHER_PREMIUM, - ][vouchers[TrainerType[trainerType]].voucherType], - ); - } else { - globalScene.phaseManager.unshiftNew( - "ModifierRewardPhase", - [modifierTypes.VOUCHER, modifierTypes.VOUCHER, modifierTypes.VOUCHER_PLUS, modifierTypes.VOUCHER_PREMIUM][ - vouchers[TrainerType[trainerType]].voucherType - ], - ); - } + if ( + vouchers.hasOwnProperty(TrainerType[trainerType]) && + !globalScene.validateVoucher(vouchers[TrainerType[trainerType]]) && + globalScene.currentBattle.trainer?.config.isBoss + ) { + if (timedEventManager.getUpgradeUnlockedVouchers()) { + globalScene.phaseManager.unshiftNew( + "ModifierRewardPhase", + [ + modifierTypes.VOUCHER_PLUS, + modifierTypes.VOUCHER_PLUS, + modifierTypes.VOUCHER_PLUS, + modifierTypes.VOUCHER_PREMIUM, + ][vouchers[TrainerType[trainerType]].voucherType], + ); + } else { + globalScene.phaseManager.unshiftNew( + "ModifierRewardPhase", + [modifierTypes.VOUCHER, modifierTypes.VOUCHER, modifierTypes.VOUCHER_PLUS, modifierTypes.VOUCHER_PREMIUM][ + vouchers[TrainerType[trainerType]].voucherType + ], + ); } } // Breeders in Space achievement diff --git a/src/plugins/api/pokerogue-session-savedata-api.ts b/src/plugins/api/pokerogue-session-savedata-api.ts index 4ffb0a5d8da..866da9844da 100644 --- a/src/plugins/api/pokerogue-session-savedata-api.ts +++ b/src/plugins/api/pokerogue-session-savedata-api.ts @@ -16,8 +16,8 @@ export class PokerogueSessionSavedataApi extends ApiBase { //#region Public /** - * Mark a session as cleared aka "newclear".\ - * *This is **NOT** the same as {@linkcode clear | clear()}.* + * Mark a session as cleared aka "newclear". \ + * _This is **NOT** the same as {@linkcode clear | clear()}._ * @param params The {@linkcode NewClearSessionSavedataRequest} to send * @returns The raw savedata as `string`. * @throws Error if the request fails @@ -94,8 +94,8 @@ export class PokerogueSessionSavedataApi extends ApiBase { } /** - * Clears the session savedata of the given slot.\ - * *This is **NOT** the same as {@linkcode newclear | newclear()}.* + * Clears the session savedata of the given slot. \ + * _This is **NOT** the same as {@linkcode newclear | newclear()}._ * @param params The {@linkcode ClearSessionSavedataRequest} to send * @param sessionData The {@linkcode SessionSaveData} object */ diff --git a/src/plugins/i18n.ts b/src/plugins/i18n.ts index 62fc73a10a3..b6a5bacc7ba 100644 --- a/src/plugins/i18n.ts +++ b/src/plugins/i18n.ts @@ -121,8 +121,8 @@ async function initFonts(language: string | undefined) { } /** - * I18n money formatter with. (useful for BBCode coloring of text)\ - * *If you don't want the BBCode tag applied, just use 'number' formatter* + * I18n money formatter with. (useful for BBCode coloring of text) \ + * _If you don't want the BBCode tag applied, just use 'number' formatter_ * @example Input: `{{myMoneyValue, money}}` * Output: `@[MONEY]{₽100,000,000}` * @param amount the money amount diff --git a/src/system/game-data.ts b/src/system/game-data.ts index ae559072e35..694ff01f808 100644 --- a/src/system/game-data.ts +++ b/src/system/game-data.ts @@ -1595,7 +1595,7 @@ export class GameData { globalScene.executeWithSeedOffset( () => { const neutralNatures = [Nature.HARDY, Nature.DOCILE, Nature.SERIOUS, Nature.BASHFUL, Nature.QUIRKY]; - for (let s = 0; s < defaultStarterSpecies.length; s++) { + for (const _ of defaultStarterSpecies) { defaultStarterNatures.push(randSeedItem(neutralNatures)); } }, diff --git a/src/system/settings/settings-gamepad.ts b/src/system/settings/settings-gamepad.ts index c334159cc3c..cc189d914ca 100644 --- a/src/system/settings/settings-gamepad.ts +++ b/src/system/settings/settings-gamepad.ts @@ -104,18 +104,16 @@ export function setSettingGamepad(setting: SettingGamepad, value: number): boole case SettingGamepad.Button_Speed_Up: case SettingGamepad.Button_Slow_Down: case SettingGamepad.Button_Submit: - if (value) { - if (globalScene.ui) { - const cancelHandler = (success = false): boolean => { - globalScene.ui.revertMode(); - (globalScene.ui.getHandler() as SettingsGamepadUiHandler).updateBindings(); - return success; - }; - globalScene.ui.setOverlayMode(UiMode.GAMEPAD_BINDING, { - target: setting, - cancelHandler: cancelHandler, - }); - } + if (value && globalScene.ui) { + const cancelHandler = (success = false): boolean => { + globalScene.ui.revertMode(); + (globalScene.ui.getHandler() as SettingsGamepadUiHandler).updateBindings(); + return success; + }; + globalScene.ui.setOverlayMode(UiMode.GAMEPAD_BINDING, { + target: setting, + cancelHandler: cancelHandler, + }); } break; case SettingGamepad.Controller: diff --git a/src/system/settings/settings-keyboard.ts b/src/system/settings/settings-keyboard.ts index 07f4f86bdb0..388ed57ab8f 100644 --- a/src/system/settings/settings-keyboard.ts +++ b/src/system/settings/settings-keyboard.ts @@ -167,18 +167,16 @@ export function setSettingKeyboard(setting: SettingKeyboard, value: number): boo case SettingKeyboard.Alt_Button_Speed_Up: case SettingKeyboard.Alt_Button_Slow_Down: case SettingKeyboard.Alt_Button_Submit: - if (value) { - if (globalScene.ui) { - const cancelHandler = (success = false): boolean => { - globalScene.ui.revertMode(); - (globalScene.ui.getHandler() as SettingsKeyboardUiHandler).updateBindings(); - return success; - }; - globalScene.ui.setOverlayMode(UiMode.KEYBOARD_BINDING, { - target: setting, - cancelHandler: cancelHandler, - }); - } + if (value && globalScene.ui) { + const cancelHandler = (success = false): boolean => { + globalScene.ui.revertMode(); + (globalScene.ui.getHandler() as SettingsKeyboardUiHandler).updateBindings(); + return success; + }; + globalScene.ui.setOverlayMode(UiMode.KEYBOARD_BINDING, { + target: setting, + cancelHandler: cancelHandler, + }); } break; } diff --git a/src/system/settings/settings.ts b/src/system/settings/settings.ts index 32d9e0ee2be..507fd1d1177 100644 --- a/src/system/settings/settings.ts +++ b/src/system/settings/settings.ts @@ -896,104 +896,102 @@ export function setSetting(setting: string, value: number): boolean { globalScene.typeHints = Setting[index].options[value].value === "On"; break; case SettingKeys.Language: - if (value) { - if (globalScene.ui) { - const cancelHandler = () => { - globalScene.ui.revertMode(); - (globalScene.ui.getHandler() as SettingsUiHandler).setOptionCursor(-1, 0, true); - }; - const changeLocaleHandler = (locale: string): boolean => { - try { - i18next.changeLanguage(locale); - localStorage.setItem("prLang", locale); - cancelHandler(); - // Reload the whole game to apply the new locale since also some constants are translated - window.location.reload(); - return true; - } catch (error) { - console.error("Error changing locale:", error); - return false; - } - }; - globalScene.ui.setOverlayMode(UiMode.OPTION_SELECT, { - options: [ - { - label: "English", - handler: () => changeLocaleHandler("en"), - }, - { - label: "Español (ES)", - handler: () => changeLocaleHandler("es-ES"), - }, - { - label: "Español (LATAM)", - handler: () => changeLocaleHandler("es-MX"), - }, - { - label: "Français", - handler: () => changeLocaleHandler("fr"), - }, - { - label: "Deutsch", - handler: () => changeLocaleHandler("de"), - }, - { - label: "Italiano", - handler: () => changeLocaleHandler("it"), - }, - { - label: "Português (BR)", - handler: () => changeLocaleHandler("pt-BR"), - }, - { - label: "한국어", - handler: () => changeLocaleHandler("ko"), - }, - { - label: "日本語", - handler: () => changeLocaleHandler("ja"), - }, - { - label: "简体中文", - handler: () => changeLocaleHandler("zh-CN"), - }, - { - label: "繁體中文", - handler: () => changeLocaleHandler("zh-TW"), - }, - { - label: "Català (Needs Help)", - handler: () => changeLocaleHandler("ca"), - }, - { - label: "Türkçe (Needs Help)", - handler: () => changeLocaleHandler("tr"), - }, - { - label: "Русский (Needs Help)", - handler: () => changeLocaleHandler("ru"), - }, - { - label: "Dansk (Needs Help)", - handler: () => changeLocaleHandler("da"), - }, - { - label: "Română (Needs Help)", - handler: () => changeLocaleHandler("ro"), - }, - { - label: "Tagalog (Needs Help)", - handler: () => changeLocaleHandler("tl"), - }, - { - label: i18next.t("settings:back"), - handler: () => cancelHandler(), - }, - ], - maxOptions: 7, - }); - return false; - } + if (value && globalScene.ui) { + const cancelHandler = () => { + globalScene.ui.revertMode(); + (globalScene.ui.getHandler() as SettingsUiHandler).setOptionCursor(-1, 0, true); + }; + const changeLocaleHandler = (locale: string): boolean => { + try { + i18next.changeLanguage(locale); + localStorage.setItem("prLang", locale); + cancelHandler(); + // Reload the whole game to apply the new locale since also some constants are translated + window.location.reload(); + return true; + } catch (error) { + console.error("Error changing locale:", error); + return false; + } + }; + globalScene.ui.setOverlayMode(UiMode.OPTION_SELECT, { + options: [ + { + label: "English", + handler: () => changeLocaleHandler("en"), + }, + { + label: "Español (ES)", + handler: () => changeLocaleHandler("es-ES"), + }, + { + label: "Español (LATAM)", + handler: () => changeLocaleHandler("es-MX"), + }, + { + label: "Français", + handler: () => changeLocaleHandler("fr"), + }, + { + label: "Deutsch", + handler: () => changeLocaleHandler("de"), + }, + { + label: "Italiano", + handler: () => changeLocaleHandler("it"), + }, + { + label: "Português (BR)", + handler: () => changeLocaleHandler("pt-BR"), + }, + { + label: "한국어", + handler: () => changeLocaleHandler("ko"), + }, + { + label: "日本語", + handler: () => changeLocaleHandler("ja"), + }, + { + label: "简体中文", + handler: () => changeLocaleHandler("zh-CN"), + }, + { + label: "繁體中文", + handler: () => changeLocaleHandler("zh-TW"), + }, + { + label: "Català (Needs Help)", + handler: () => changeLocaleHandler("ca"), + }, + { + label: "Türkçe (Needs Help)", + handler: () => changeLocaleHandler("tr"), + }, + { + label: "Русский (Needs Help)", + handler: () => changeLocaleHandler("ru"), + }, + { + label: "Dansk (Needs Help)", + handler: () => changeLocaleHandler("da"), + }, + { + label: "Română (Needs Help)", + handler: () => changeLocaleHandler("ro"), + }, + { + label: "Tagalog (Needs Help)", + handler: () => changeLocaleHandler("tl"), + }, + { + label: i18next.t("settings:back"), + handler: () => cancelHandler(), + }, + ], + maxOptions: 7, + }); + return false; } break; case SettingKeys.Shop_Overlay_Opacity: diff --git a/src/ui/arena-flyout.ts b/src/ui/arena-flyout.ts index e243bef342e..6176f32f36e 100644 --- a/src/ui/arena-flyout.ts +++ b/src/ui/arena-flyout.ts @@ -241,9 +241,7 @@ export class ArenaFlyout extends Phaser.GameObjects.Container { this.fieldEffectInfo.sort((infoA, infoB) => infoA.duration - infoB.duration); - for (let i = 0; i < this.fieldEffectInfo.length; i++) { - const fieldEffectInfo = this.fieldEffectInfo[i]; - + for (const fieldEffectInfo of this.fieldEffectInfo) { // Creates a proxy object to decide which text object needs to be updated let textObject: Phaser.GameObjects.Text; switch (fieldEffectInfo.effectType) { @@ -389,9 +387,7 @@ export class ArenaFlyout extends Phaser.GameObjects.Container { const fieldEffectInfo: ArenaEffectInfo[] = []; this.fieldEffectInfo.forEach(i => fieldEffectInfo.push(i)); - for (let i = 0; i < fieldEffectInfo.length; i++) { - const info = fieldEffectInfo[i]; - + for (const info of fieldEffectInfo) { if (info.maxDuration === 0) { continue; } diff --git a/src/ui/base-stats-overlay.ts b/src/ui/base-stats-overlay.ts index 3b432e13096..9b1e36b37ba 100644 --- a/src/ui/base-stats-overlay.ts +++ b/src/ui/base-stats-overlay.ts @@ -68,14 +68,14 @@ export class BaseStatsOverlay extends Phaser.GameObjects.Container implements In // show this component with infos for the specific move show(values: number[], total: number): boolean { for (let i = 0; i < 6; i++) { - this.statsLabels[i].setText(i18next.t(`pokemonInfo:Stat.${shortStats[i]}shortened`) + ": " + `${values[i]}`); + this.statsLabels[i].setText(`${i18next.t(`pokemonInfo:Stat.${shortStats[i]}shortened`)}: ${values[i]}`); // This accounts for base stats up to 200, might not be enough. // TODO: change color based on value. this.statsShadows[i].setSize(values[i] / 2, 5); this.statsRectangles[i].setSize(values[i] / 2, 5); } - this.statsTotalLabel.setText(i18next.t("pokedexUiHandler:baseTotal") + ": " + `${total}`); + this.statsTotalLabel.setText(`${i18next.t("pokedexUiHandler:baseTotal")}: ${total}`); this.setVisible(true); this.active = true; diff --git a/src/ui/battle-message-ui-handler.ts b/src/ui/battle-message-ui-handler.ts index 2ecca06172b..60e7066265c 100644 --- a/src/ui/battle-message-ui-handler.ts +++ b/src/ui/battle-message-ui-handler.ts @@ -153,16 +153,12 @@ export class BattleMessageUiHandler extends MessageUiHandler { processInput(button: Button): boolean { const ui = this.getUi(); - if (this.awaitingActionInput) { - if (button === Button.CANCEL || button === Button.ACTION) { - if (this.onActionInput) { - ui.playSelect(); - const originalOnActionInput = this.onActionInput; - this.onActionInput = null; - originalOnActionInput(); - return true; - } - } + if (this.awaitingActionInput && (button === Button.CANCEL || button === Button.ACTION) && this.onActionInput) { + ui.playSelect(); + const originalOnActionInput = this.onActionInput; + this.onActionInput = null; + originalOnActionInput(); + return true; } return false; diff --git a/src/ui/challenges-select-ui-handler.ts b/src/ui/challenges-select-ui-handler.ts index b37ddcc6a5f..2149f15c50f 100644 --- a/src/ui/challenges-select-ui-handler.ts +++ b/src/ui/challenges-select-ui-handler.ts @@ -400,75 +400,73 @@ export class GameChallengesUiHandler extends UiHandler { } else { success = false; } - } else { - if (this.cursorObj?.visible && !this.startCursor.visible) { - switch (button) { - case Button.UP: - if (this.cursor === 0) { - if (this.scrollCursor === 0) { - // When at the top of the menu and pressing UP, move to the bottommost item. - if (globalScene.gameMode.challenges.length > rowsToDisplay) { - // If there are more than 9 challenges, scroll to the bottom - // First, set the cursor to the last visible element, preparing for the scroll to the end. - const successA = this.setCursor(rowsToDisplay - 1); - // Then, adjust the scroll to display the bottommost elements of the menu. - const successB = this.setScrollCursor(globalScene.gameMode.challenges.length - rowsToDisplay); - success = successA && successB; // success is just there to play the little validation sound effect - } else { - // If there are 9 or less challenges, just move to the bottom one - success = this.setCursor(globalScene.gameMode.challenges.length - 1); - } - } else { - success = this.setScrollCursor(this.scrollCursor - 1); - } - } else { - success = this.setCursor(this.cursor - 1); - } - if (success) { - this.updateText(); - } - break; - case Button.DOWN: - if (this.cursor === rowsToDisplay - 1) { - if (this.scrollCursor < globalScene.gameMode.challenges.length - rowsToDisplay) { - // When at the bottom and pressing DOWN, scroll if possible. - success = this.setScrollCursor(this.scrollCursor + 1); - } else { - // When at the bottom of a scrolling menu and pressing DOWN, move to the topmost item. - // First, set the cursor to the first visible element, preparing for the scroll to the top. - const successA = this.setCursor(0); - // Then, adjust the scroll to display the topmost elements of the menu. - const successB = this.setScrollCursor(0); + } else if (this.cursorObj?.visible && !this.startCursor.visible) { + switch (button) { + case Button.UP: + if (this.cursor === 0) { + if (this.scrollCursor === 0) { + // When at the top of the menu and pressing UP, move to the bottommost item. + if (globalScene.gameMode.challenges.length > rowsToDisplay) { + // If there are more than 9 challenges, scroll to the bottom + // First, set the cursor to the last visible element, preparing for the scroll to the end. + const successA = this.setCursor(rowsToDisplay - 1); + // Then, adjust the scroll to display the bottommost elements of the menu. + const successB = this.setScrollCursor(globalScene.gameMode.challenges.length - rowsToDisplay); success = successA && successB; // success is just there to play the little validation sound effect + } else { + // If there are 9 or less challenges, just move to the bottom one + success = this.setCursor(globalScene.gameMode.challenges.length - 1); } - } else if ( - globalScene.gameMode.challenges.length < rowsToDisplay && - this.cursor === globalScene.gameMode.challenges.length - 1 - ) { - // When at the bottom of a non-scrolling menu and pressing DOWN, move to the topmost item. - success = this.setCursor(0); } else { - success = this.setCursor(this.cursor + 1); + success = this.setScrollCursor(this.scrollCursor - 1); } - if (success) { - this.updateText(); + } else { + success = this.setCursor(this.cursor - 1); + } + if (success) { + this.updateText(); + } + break; + case Button.DOWN: + if (this.cursor === rowsToDisplay - 1) { + if (this.scrollCursor < globalScene.gameMode.challenges.length - rowsToDisplay) { + // When at the bottom and pressing DOWN, scroll if possible. + success = this.setScrollCursor(this.scrollCursor + 1); + } else { + // When at the bottom of a scrolling menu and pressing DOWN, move to the topmost item. + // First, set the cursor to the first visible element, preparing for the scroll to the top. + const successA = this.setCursor(0); + // Then, adjust the scroll to display the topmost elements of the menu. + const successB = this.setScrollCursor(0); + success = successA && successB; // success is just there to play the little validation sound effect } - break; - case Button.LEFT: - // Moves the option cursor left, if possible. - success = this.getActiveChallenge().decreaseValue(); - if (success) { - this.updateText(); - } - break; - case Button.RIGHT: - // Moves the option cursor right, if possible. - success = this.getActiveChallenge().increaseValue(); - if (success) { - this.updateText(); - } - break; - } + } else if ( + globalScene.gameMode.challenges.length < rowsToDisplay && + this.cursor === globalScene.gameMode.challenges.length - 1 + ) { + // When at the bottom of a non-scrolling menu and pressing DOWN, move to the topmost item. + success = this.setCursor(0); + } else { + success = this.setCursor(this.cursor + 1); + } + if (success) { + this.updateText(); + } + break; + case Button.LEFT: + // Moves the option cursor left, if possible. + success = this.getActiveChallenge().decreaseValue(); + if (success) { + this.updateText(); + } + break; + case Button.RIGHT: + // Moves the option cursor right, if possible. + success = this.getActiveChallenge().increaseValue(); + if (success) { + this.updateText(); + } + break; } } diff --git a/src/ui/dropdown.ts b/src/ui/dropdown.ts index c13d1ab6482..a6d52487725 100644 --- a/src/ui/dropdown.ts +++ b/src/ui/dropdown.ts @@ -504,13 +504,11 @@ export class DropDown extends Phaser.GameObjects.Container { if (index === 0) { // we are on the All option > put all other options to the newState this.setAllOptions(newState); - } else { + } else if (newState === DropDownState.ON && this.checkForAllOn()) { // select the "all" option if all others are selected, other unselect it - if (newState === DropDownState.ON && this.checkForAllOn()) { - this.options[0].setOptionState(DropDownState.ON); - } else { - this.options[0].setOptionState(DropDownState.OFF); - } + this.options[0].setOptionState(DropDownState.ON); + } else { + this.options[0].setOptionState(DropDownState.OFF); } } else if (this.dropDownType === DropDownType.SINGLE) { if (option.state === DropDownState.OFF) { @@ -653,10 +651,8 @@ export class DropDown extends Phaser.GameObjects.Container { this.options[i].setDirection(SortDirection.ASC); this.options[i].toggle.setVisible(true); } - } else { - if (this.defaultSettings[i]) { - this.options[i].setOptionState(this.defaultSettings[i]["state"]); - } + } else if (this.defaultSettings[i]) { + this.options[i].setOptionState(this.defaultSettings[i]["state"]); } } @@ -699,11 +695,11 @@ export class DropDown extends Phaser.GameObjects.Container { autoSize(): void { let maxWidth = 0; let x = 0; - for (let i = 0; i < this.options.length; i++) { - const optionWidth = this.options[i].getWidth(); + for (const option of this.options) { + const optionWidth = option.getWidth(); if (optionWidth > maxWidth) { maxWidth = optionWidth; - x = this.options[i].getCurrentLabelX() ?? 0; + x = option.getCurrentLabelX() ?? 0; } } this.window.width = maxWidth + x - this.window.x + 9; diff --git a/src/ui/evolution-scene-handler.ts b/src/ui/evolution-scene-handler.ts index 0333594dc36..c8ed24dfa7c 100644 --- a/src/ui/evolution-scene-handler.ts +++ b/src/ui/evolution-scene-handler.ts @@ -62,16 +62,12 @@ export class EvolutionSceneHandler extends MessageUiHandler { } const ui = this.getUi(); - if (this.awaitingActionInput) { - if (button === Button.CANCEL || button === Button.ACTION) { - if (this.onActionInput) { - ui.playSelect(); - const originalOnActionInput = this.onActionInput; - this.onActionInput = null; - originalOnActionInput(); - return true; - } - } + if (this.awaitingActionInput && (button === Button.CANCEL || button === Button.ACTION) && this.onActionInput) { + ui.playSelect(); + const originalOnActionInput = this.onActionInput; + this.onActionInput = null; + originalOnActionInput(); + return true; } return false; diff --git a/src/ui/filter-bar.ts b/src/ui/filter-bar.ts index ea227655a97..b93e532022f 100644 --- a/src/ui/filter-bar.ts +++ b/src/ui/filter-bar.ts @@ -130,22 +130,20 @@ export class FilterBar extends Phaser.GameObjects.Container { * Move the leftmost dropdown to the left of the FilterBar instead of below it */ offsetHybridFilters(): void { - for (let i = 0; i < this.dropDowns.length; i++) { - if (this.dropDowns[i].dropDownType === DropDownType.HYBRID) { - this.dropDowns[i].autoSize(); - this.dropDowns[i].x = -this.dropDowns[i].getWidth(); - this.dropDowns[i].y = 0; + for (const dropDown of this.dropDowns) { + if (dropDown.dropDownType === DropDownType.HYBRID) { + dropDown.autoSize(); + dropDown.x = -dropDown.getWidth(); + dropDown.y = 0; } } } setCursor(cursor: number): void { - if (this.lastCursor > -1) { - if (this.dropDowns[this.lastCursor].visible) { - this.dropDowns[this.lastCursor].setVisible(false); - this.dropDowns[cursor].setVisible(true); - this.dropDowns[cursor].resetCursor(); - } + if (this.lastCursor > -1 && this.dropDowns[this.lastCursor].visible) { + this.dropDowns[this.lastCursor].setVisible(false); + this.dropDowns[cursor].setVisible(true); + this.dropDowns[cursor].resetCursor(); } this.cursorObj.setPosition(this.labels[cursor].x - this.cursorOffset + 2, 6); diff --git a/src/ui/login-form-ui-handler.ts b/src/ui/login-form-ui-handler.ts index 0f55faba5c4..f861a708267 100644 --- a/src/ui/login-form-ui-handler.ts +++ b/src/ui/login-form-ui-handler.ts @@ -234,9 +234,9 @@ export class LoginFormUiHandler extends FormModalUiHandler { const dataKeys = localStorageKeys.filter(ls => ls.indexOf(keyToFind) >= 0); if (dataKeys.length > 0 && dataKeys.length <= 2) { const options: OptionSelectItem[] = []; - for (let i = 0; i < dataKeys.length; i++) { + for (const key of dataKeys) { options.push({ - label: dataKeys[i].replace(keyToFind, ""), + label: key.replace(keyToFind, ""), handler: () => { globalScene.ui.revertMode(); this.infoContainer.disableInteractive(); @@ -261,7 +261,7 @@ export class LoginFormUiHandler extends FormModalUiHandler { } }); - this.saveDownloadImage.on("pointerdown", () => { + this.saveDownloadImage.on("pointerdown", async () => { // find all data_ and sessionData keys, put them in a .txt file and download everything in a single zip const localStorageKeys = Object.keys(localStorage); // this gets the keys for localStorage const keyToFind = "data_"; @@ -270,20 +270,19 @@ export class LoginFormUiHandler extends FormModalUiHandler { const sessionKeys = localStorageKeys.filter(ls => ls.indexOf(sessionKeyToFind) >= 0); if (dataKeys.length > 0 || sessionKeys.length > 0) { const zip = new JSZip(); - for (let i = 0; i < dataKeys.length; i++) { - zip.file(dataKeys[i] + ".prsv", localStorage.getItem(dataKeys[i])!); + for (const dataKey of dataKeys) { + zip.file(dataKey + ".prsv", localStorage.getItem(dataKey)!); } - for (let i = 0; i < sessionKeys.length; i++) { - zip.file(sessionKeys[i] + ".prsv", localStorage.getItem(sessionKeys[i])!); + for (const sessionKey of sessionKeys) { + zip.file(sessionKey + ".prsv", localStorage.getItem(sessionKey)!); } - zip.generateAsync({ type: "blob" }).then(content => { - const url = URL.createObjectURL(content); - const a = document.createElement("a"); - a.href = url; - a.download = "pokerogue_saves.zip"; - a.click(); - URL.revokeObjectURL(url); - }); + const content = await zip.generateAsync({ type: "blob" }); + const url = URL.createObjectURL(content); + const a = document.createElement("a"); + a.href = url; + a.download = "pokerogue_saves.zip"; + a.click(); + URL.revokeObjectURL(url); } else { return onFail(this.ERR_NO_SAVES); } diff --git a/src/ui/message-ui-handler.ts b/src/ui/message-ui-handler.ts index 57f054c9bf9..904ef69e82b 100644 --- a/src/ui/message-ui-handler.ts +++ b/src/ui/message-ui-handler.ts @@ -108,17 +108,17 @@ export abstract class MessageUiHandler extends AwaitableUiHandler { const textWords = text.split(" "); let lastLineCount = 1; let newText = ""; - for (let w = 0; w < textWords.length; w++) { - const nextWordText = newText ? `${newText} ${textWords[w]}` : textWords[w]; + for (const textWord of textWords) { + const nextWordText = newText ? `${newText} ${textWord}` : textWord; - if (textWords[w].includes("\n")) { + if (textWord.includes("\n")) { newText = nextWordText; lastLineCount++; } else { const lineCount = this.message.runWordWrap(nextWordText).split(/\n/g).length; if (lineCount > lastLineCount) { lastLineCount = lineCount; - newText = `${newText}\n${textWords[w]}`; + newText = `${newText}\n${textWord}`; } else { newText = nextWordText; } diff --git a/src/ui/modifier-select-ui-handler.ts b/src/ui/modifier-select-ui-handler.ts index a070b522050..5508ad8ed7b 100644 --- a/src/ui/modifier-select-ui-handler.ts +++ b/src/ui/modifier-select-ui-handler.ts @@ -480,12 +480,10 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler { } } else if (this.cursor) { success = this.setCursor(this.cursor - 1); + } else if (this.rowCursor === 1 && this.options.length === 0) { + success = false; } else { - if (this.rowCursor === 1 && this.options.length === 0) { - success = false; - } else { - success = this.setCursor(this.getRowItems(this.rowCursor) - 1); - } + success = this.setCursor(this.getRowItems(this.rowCursor) - 1); } break; case Button.RIGHT: @@ -514,12 +512,10 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler { } } else if (this.cursor < this.getRowItems(this.rowCursor) - 1) { success = this.setCursor(this.cursor + 1); + } else if (this.rowCursor === 1 && this.options.length === 0) { + success = this.setRowCursor(0); } else { - if (this.rowCursor === 1 && this.options.length === 0) { - success = this.setRowCursor(0); - } else { - success = this.setCursor(0); - } + success = this.setCursor(0); } break; } diff --git a/src/ui/mystery-encounter-ui-handler.ts b/src/ui/mystery-encounter-ui-handler.ts index 881c375fa8a..91e59d9ee23 100644 --- a/src/ui/mystery-encounter-ui-handler.ts +++ b/src/ui/mystery-encounter-ui-handler.ts @@ -156,14 +156,12 @@ export class MysteryEncounterUiHandler extends UiHandler { selected.optionMode === MysteryEncounterOptionMode.DISABLED_OR_SPECIAL)) ) { success = false; + } else if ( + (globalScene.phaseManager.getCurrentPhase() as MysteryEncounterPhase).handleOptionSelect(selected, cursor) + ) { + success = true; } else { - if ( - (globalScene.phaseManager.getCurrentPhase() as MysteryEncounterPhase).handleOptionSelect(selected, cursor) - ) { - success = true; - } else { - ui.playError(); - } + ui.playError(); } } else { // TODO: If we need to handle cancel option? Maybe default logic to leave/run from encounter idk diff --git a/src/ui/party-ui-handler.ts b/src/ui/party-ui-handler.ts index ff5e7246a6f..2cb4e3ae66c 100644 --- a/src/ui/party-ui-handler.ts +++ b/src/ui/party-ui-handler.ts @@ -614,34 +614,32 @@ export class PartyUiHandler extends MessageUiHandler { // TODO: Might need to check here for when this.transferMode is active. private processModifierTransferModeLeftRightInput(button: Button) { + if (!this.isItemManageMode()) { + return false; + } let success = false; const option = this.options[this.optionsCursor]; if (button === Button.LEFT) { /** Decrease quantity for the current item and update UI */ - if (this.isItemManageMode()) { - this.transferQuantities[option] = - this.transferQuantities[option] === 1 - ? this.transferQuantitiesMax[option] - : this.transferQuantities[option] - 1; - this.updateOptions(); - success = this.setCursor( - this.optionsCursor, - ); /** Place again the cursor at the same position. Necessary, otherwise the cursor disappears */ - } + this.transferQuantities[option] = + this.transferQuantities[option] === 1 + ? this.transferQuantitiesMax[option] + : this.transferQuantities[option] - 1; + this.updateOptions(); + success = this.setCursor( + this.optionsCursor, + ); /** Place again the cursor at the same position. Necessary, otherwise the cursor disappears */ } - if (button === Button.RIGHT) { /** Increase quantity for the current item and update UI */ - if (this.isItemManageMode()) { - this.transferQuantities[option] = - this.transferQuantities[option] === this.transferQuantitiesMax[option] - ? 1 - : this.transferQuantities[option] + 1; - this.updateOptions(); - success = this.setCursor( - this.optionsCursor, - ); /** Place again the cursor at the same position. Necessary, otherwise the cursor disappears */ - } + this.transferQuantities[option] = + this.transferQuantities[option] === this.transferQuantitiesMax[option] + ? 1 + : this.transferQuantities[option] + 1; + this.updateOptions(); + success = this.setCursor( + this.optionsCursor, + ); /** Place again the cursor at the same position. Necessary, otherwise the cursor disappears */ } return success; } @@ -930,10 +928,8 @@ export class PartyUiHandler extends MessageUiHandler { return this.moveOptionCursor(button); } - if (button === Button.LEFT || button === Button.RIGHT) { - if (this.isItemManageMode()) { - return this.processModifierTransferModeLeftRightInput(button); - } + if ((button === Button.LEFT || button === Button.RIGHT) && this.isItemManageMode()) { + return this.processModifierTransferModeLeftRightInput(button); } return false; @@ -1215,11 +1211,9 @@ export class PartyUiHandler extends MessageUiHandler { isScroll = true; this.optionsScrollCursor++; } - } else { - if (!cursor && this.optionsScrollCursor) { - isScroll = true; - this.optionsScrollCursor--; - } + } else if (!cursor && this.optionsScrollCursor) { + isScroll = true; + this.optionsScrollCursor--; } if (isScroll && this.optionsScrollCursor === 1) { this.optionsScrollCursor += isDown ? 1 : -1; @@ -1573,12 +1567,10 @@ export class PartyUiHandler extends MessageUiHandler { optionName = `${modifier.active ? i18next.t("partyUiHandler:DEACTIVATE") : i18next.t("partyUiHandler:ACTIVATE")} ${modifier.type.name}`; } else if (option === PartyOption.UNPAUSE_EVOLUTION) { optionName = `${pokemon.pauseEvolutions ? i18next.t("partyUiHandler:UNPAUSE_EVOLUTION") : i18next.t("partyUiHandler:PAUSE_EVOLUTION")}`; + } else if (this.localizedOptions.includes(option)) { + optionName = i18next.t(`partyUiHandler:${PartyOption[option]}`); } else { - if (this.localizedOptions.includes(option)) { - optionName = i18next.t(`partyUiHandler:${PartyOption[option]}`); - } else { - optionName = toTitleCase(PartyOption[option]); - } + optionName = toTitleCase(PartyOption[option]); } break; } @@ -1654,11 +1646,11 @@ export class PartyUiHandler extends MessageUiHandler { this.transferMode = false; this.transferAll = false; this.partySlots[this.transferCursor].setTransfer(false); - for (let i = 0; i < this.partySlots.length; i++) { - this.partySlots[i].slotDescriptionLabel.setVisible(false); - this.partySlots[i].slotHpBar.setVisible(true); - this.partySlots[i].slotHpOverlay.setVisible(true); - this.partySlots[i].slotHpText.setVisible(true); + for (const partySlot of this.partySlots) { + partySlot.slotDescriptionLabel.setVisible(false); + partySlot.slotHpBar.setVisible(true); + partySlot.slotHpOverlay.setVisible(true); + partySlot.slotHpText.setVisible(true); } } diff --git a/src/ui/pokedex-page-ui-handler.ts b/src/ui/pokedex-page-ui-handler.ts index 49658d9cfc9..132039218ca 100644 --- a/src/ui/pokedex-page-ui-handler.ts +++ b/src/ui/pokedex-page-ui-handler.ts @@ -1069,12 +1069,10 @@ export class PokedexPageUiHandler extends MessageUiHandler { ) { starterAttributes.female = !starterAttributes.female; } - } else { - if (caughtAttr & DexAttr.FEMALE) { - starterAttributes.female = true; - } else if (caughtAttr & DexAttr.MALE) { - starterAttributes.female = false; - } + } else if (caughtAttr & DexAttr.FEMALE) { + starterAttributes.female = true; + } else if (caughtAttr & DexAttr.MALE) { + starterAttributes.female = false; } return starterAttributes; @@ -1839,10 +1837,8 @@ export class PokedexPageUiHandler extends MessageUiHandler { if (this.isCaught() & DexAttr.VARIANT_2) { break; } - } else { - if (this.isCaught() & DexAttr.VARIANT_3) { - break; - } + } else if (this.isCaught() & DexAttr.VARIANT_3) { + break; } } while (newVariant !== props.variant); @@ -2362,10 +2358,8 @@ export class PokedexPageUiHandler extends MessageUiHandler { const defaultDexAttr = this.getCurrentDexProps(species.speciesId); // Set default attributes if for some reason starterAttributes does not exist or attributes missing const props: StarterAttributes = globalScene.gameData.getSpeciesDexAttrProps(species, defaultDexAttr); - if (starterAttributes?.variant && !Number.isNaN(starterAttributes.variant)) { - if (props.shiny) { - props.variant = starterAttributes.variant as Variant; - } + if (starterAttributes?.variant && !Number.isNaN(starterAttributes.variant) && props.shiny) { + props.variant = starterAttributes.variant as Variant; } props.form = starterAttributes?.form ?? props.form; props.female = starterAttributes?.female ?? props.female; @@ -2778,17 +2772,15 @@ export class PokedexPageUiHandler extends MessageUiHandler { props += DexAttr.SHINY; if (this.starterAttributes?.variant !== undefined) { props += BigInt(Math.pow(2, this.starterAttributes?.variant)) * DexAttr.DEFAULT_VARIANT; - } else { - /* This calculates the correct variant if there's no starter preferences for it. + /* This chunk calculates the correct variant if there's no starter preferences for it. * This gets the highest tier variant that you've caught and adds it to the temp props */ - if ((caughtAttr & DexAttr.VARIANT_3) > 0) { - props += DexAttr.VARIANT_3; - } else if ((caughtAttr & DexAttr.VARIANT_2) > 0) { - props += DexAttr.VARIANT_2; - } else { - props += DexAttr.DEFAULT_VARIANT; - } + } else if ((caughtAttr & DexAttr.VARIANT_3) > 0) { + props += DexAttr.VARIANT_3; + } else if ((caughtAttr & DexAttr.VARIANT_2) > 0) { + props += DexAttr.VARIANT_2; + } else { + props += DexAttr.DEFAULT_VARIANT; } } else { props += DexAttr.NON_SHINY; diff --git a/src/ui/pokedex-ui-handler.ts b/src/ui/pokedex-ui-handler.ts index aa2a5cda459..c1cb9d41c5b 100644 --- a/src/ui/pokedex-ui-handler.ts +++ b/src/ui/pokedex-ui-handler.ts @@ -709,11 +709,12 @@ export class PokedexUiHandler extends MessageUiHandler { } } - if (starterAttributes.female !== undefined) { - if (!(starterAttributes.female ? caughtAttr & DexAttr.FEMALE : caughtAttr & DexAttr.MALE)) { - // requested gender wasn't unlocked, purging setting - starterAttributes.female = undefined; - } + if ( + starterAttributes.female !== undefined && + !(starterAttributes.female ? caughtAttr & DexAttr.FEMALE : caughtAttr & DexAttr.MALE) + ) { + // requested gender wasn't unlocked, purging setting + starterAttributes.female = undefined; } if (starterAttributes.ability !== undefined) { @@ -1187,78 +1188,76 @@ export class PokedexUiHandler extends MessageUiHandler { break; } } + } else if (button === Button.ACTION) { + ui.setOverlayMode(UiMode.POKEDEX_PAGE, this.lastSpecies, null, this.filteredIndices); + success = true; } else { - if (button === Button.ACTION) { - ui.setOverlayMode(UiMode.POKEDEX_PAGE, this.lastSpecies, null, this.filteredIndices); - success = true; - } else { - switch (button) { - case Button.UP: - if (currentRow > 0) { - if (this.scrollCursor > 0 && currentRow - this.scrollCursor === 0) { - this.scrollCursor--; - this.updateScroll(); - success = this.setCursor(this.cursor); - } else { - success = this.setCursor(this.cursor - 9); - } - } else { - this.filterBarCursor = this.filterBar.getNearestFilter(this.pokemonContainers[this.cursor]); - this.setFilterMode(true); - success = true; - } - break; - case Button.DOWN: - if (currentRow < numOfRows - 1 && this.cursor + 9 < this.filteredPokemonData.length) { - // not last row - if (currentRow - this.scrollCursor === 8) { - // last row of visible pokemon - this.scrollCursor++; - this.updateScroll(); - success = this.setCursor(this.cursor); - } else { - success = this.setCursor(this.cursor + 9); - } - } else if (numOfRows > 1) { - // DOWN from last row of pokemon > Wrap around to first row - this.scrollCursor = 0; + switch (button) { + case Button.UP: + if (currentRow > 0) { + if (this.scrollCursor > 0 && currentRow - this.scrollCursor === 0) { + this.scrollCursor--; this.updateScroll(); - success = this.setCursor(this.cursor % 9); + success = this.setCursor(this.cursor); } else { - // DOWN from single row of pokemon > Go to filters - this.filterBarCursor = this.filterBar.getNearestFilter(this.pokemonContainers[this.cursor]); - this.setFilterMode(true); - success = true; + success = this.setCursor(this.cursor - 9); } - break; - case Button.LEFT: - if (this.cursor % 9 !== 0) { - success = this.setCursor(this.cursor - 1); - } else { - // LEFT from filtered pokemon, on the left edge - this.filterTextCursor = this.filterText.getNearestFilter(this.pokemonContainers[this.cursor]); - this.setFilterTextMode(true); - success = true; - } - break; - case Button.RIGHT: - // is not right edge - if (this.cursor % 9 < (currentRow < numOfRows - 1 ? 8 : (numberOfStarters - 1) % 9)) { - success = this.setCursor(this.cursor + 1); - } else { - // RIGHT from filtered pokemon, on the right edge - this.filterTextCursor = this.filterText.getNearestFilter(this.pokemonContainers[this.cursor]); - this.setFilterTextMode(true); - success = true; - } - break; - case Button.CYCLE_FORM: { - const species = this.pokemonContainers[this.cursor].species; - if (this.canShowFormTray) { - success = this.openFormTray(species); - } - break; + } else { + this.filterBarCursor = this.filterBar.getNearestFilter(this.pokemonContainers[this.cursor]); + this.setFilterMode(true); + success = true; } + break; + case Button.DOWN: + if (currentRow < numOfRows - 1 && this.cursor + 9 < this.filteredPokemonData.length) { + // not last row + if (currentRow - this.scrollCursor === 8) { + // last row of visible pokemon + this.scrollCursor++; + this.updateScroll(); + success = this.setCursor(this.cursor); + } else { + success = this.setCursor(this.cursor + 9); + } + } else if (numOfRows > 1) { + // DOWN from last row of pokemon > Wrap around to first row + this.scrollCursor = 0; + this.updateScroll(); + success = this.setCursor(this.cursor % 9); + } else { + // DOWN from single row of pokemon > Go to filters + this.filterBarCursor = this.filterBar.getNearestFilter(this.pokemonContainers[this.cursor]); + this.setFilterMode(true); + success = true; + } + break; + case Button.LEFT: + if (this.cursor % 9 !== 0) { + success = this.setCursor(this.cursor - 1); + } else { + // LEFT from filtered pokemon, on the left edge + this.filterTextCursor = this.filterText.getNearestFilter(this.pokemonContainers[this.cursor]); + this.setFilterTextMode(true); + success = true; + } + break; + case Button.RIGHT: + // is not right edge + if (this.cursor % 9 < (currentRow < numOfRows - 1 ? 8 : (numberOfStarters - 1) % 9)) { + success = this.setCursor(this.cursor + 1); + } else { + // RIGHT from filtered pokemon, on the right edge + this.filterTextCursor = this.filterText.getNearestFilter(this.pokemonContainers[this.cursor]); + this.setFilterTextMode(true); + success = true; + } + break; + case Button.CYCLE_FORM: { + const species = this.pokemonContainers[this.cursor].species; + if (this.canShowFormTray) { + success = this.openFormTray(species); + } + break; } } } @@ -1453,12 +1452,10 @@ export class PokedexUiHandler extends MessageUiHandler { } else { data.passive1 = false; } + } else if (starterData.passiveAttr > 0) { + data.passive2 = true; } else { - if (starterData.passiveAttr > 0) { - data.passive2 = true; - } else { - data.passive2 = false; - } + data.passive2 = false; } } @@ -2334,17 +2331,15 @@ export class PokedexUiHandler extends MessageUiHandler { props += DexAttr.SHINY; if (this.starterPreferences[speciesId]?.variant !== undefined) { props += BigInt(Math.pow(2, this.starterPreferences[speciesId]?.variant)) * DexAttr.DEFAULT_VARIANT; - } else { + } else if ((caughtAttr & DexAttr.VARIANT_3) > 0) { /* This calculates the correct variant if there's no starter preferences for it. * This gets the highest tier variant that you've caught and adds it to the temp props */ - if ((caughtAttr & DexAttr.VARIANT_3) > 0) { - props += DexAttr.VARIANT_3; - } else if ((caughtAttr & DexAttr.VARIANT_2) > 0) { - props += DexAttr.VARIANT_2; - } else { - props += DexAttr.DEFAULT_VARIANT; - } + props += DexAttr.VARIANT_3; + } else if ((caughtAttr & DexAttr.VARIANT_2) > 0) { + props += DexAttr.VARIANT_2; + } else { + props += DexAttr.DEFAULT_VARIANT; } } else { props += DexAttr.NON_SHINY; diff --git a/src/ui/run-info-ui-handler.ts b/src/ui/run-info-ui-handler.ts index 2def302c1d5..45b0215c8ef 100644 --- a/src/ui/run-info-ui-handler.ts +++ b/src/ui/run-info-ui-handler.ts @@ -683,32 +683,33 @@ export class RunInfoUiHandler extends UiHandler { */ private challengeParser(): string[] { const rules: string[] = []; - for (let i = 0; i < this.runInfo.challenges.length; i++) { - if (this.runInfo.challenges[i].value !== 0) { - switch (this.runInfo.challenges[i].id) { - case Challenges.SINGLE_GENERATION: - rules.push(i18next.t(`runHistory:challengeMonoGen${this.runInfo.challenges[i].value}`)); - break; - case Challenges.SINGLE_TYPE: { - const typeRule = PokemonType[this.runInfo.challenges[i].value - 1]; - const typeTextColor = `[color=${TypeColor[typeRule]}]`; - const typeShadowColor = `[shadow=${TypeShadow[typeRule]}]`; - const typeText = - typeTextColor + typeShadowColor + i18next.t(`pokemonInfo:Type.${typeRule}`)! + "[/color]" + "[/shadow]"; - rules.push(typeText); - break; - } - case Challenges.INVERSE_BATTLE: - rules.push(i18next.t("challenges:inverseBattle.shortName")); - break; - default: { - const localizationKey = Challenges[this.runInfo.challenges[i].id] - .split("_") - .map((f, i) => (i ? `${f[0]}${f.slice(1).toLowerCase()}` : f.toLowerCase())) - .join(""); - rules.push(i18next.t(`challenges:${localizationKey}.name`)); - break; - } + for (const challenge of this.runInfo.challenges) { + if (challenge.value === 0) { + continue; + } + switch (challenge.id) { + case Challenges.SINGLE_GENERATION: + rules.push(i18next.t(`runHistory:challengeMonoGen${challenge.value}`)); + break; + case Challenges.SINGLE_TYPE: { + const typeRule = PokemonType[challenge.value - 1]; + const typeTextColor = `[color=${TypeColor[typeRule]}]`; + const typeShadowColor = `[shadow=${TypeShadow[typeRule]}]`; + const typeText = + typeTextColor + typeShadowColor + i18next.t(`pokemonInfo:Type.${typeRule}`)! + "[/color][/shadow]"; + rules.push(typeText); + break; + } + case Challenges.INVERSE_BATTLE: + rules.push(i18next.t("challenges:inverseBattle.shortName")); + break; + default: { + const localizationKey = Challenges[challenge.id] + .split("_") + .map((f, i) => (i ? `${f[0]}${f.slice(1).toLowerCase()}` : f.toLowerCase())) + .join(""); + rules.push(i18next.t(`challenges:${localizationKey}.name`)); + break; } } } diff --git a/src/ui/starter-select-ui-handler.ts b/src/ui/starter-select-ui-handler.ts index fbcc6ae7e32..82b1df9edc3 100644 --- a/src/ui/starter-select-ui-handler.ts +++ b/src/ui/starter-select-ui-handler.ts @@ -336,7 +336,7 @@ export class StarterSelectUiHandler extends MessageUiHandler { private teraLabel: Phaser.GameObjects.Text; private goFilterLabel: Phaser.GameObjects.Text; /** Group holding the UI elements appearing in the instructionsContainer */ - /* TODO: Uncomment this once our testing infra supports mocks of `Phaser.GameObject.Group` + /* TODO: Uncomment this once our testing infra supports mocks of `Phaser.GameObject.Group` private instructionElemGroup: Phaser.GameObjects.Group; */ @@ -1217,11 +1217,12 @@ export class StarterSelectUiHandler extends MessageUiHandler { } } - if (starterAttributes.female !== undefined) { - if (!(starterAttributes.female ? caughtAttr & DexAttr.FEMALE : caughtAttr & DexAttr.MALE)) { - // requested gender wasn't unlocked, purging setting - starterAttributes.female = undefined; - } + if ( + starterAttributes.female !== undefined && + !(starterAttributes.female ? caughtAttr & DexAttr.FEMALE : caughtAttr & DexAttr.MALE) + ) { + // requested gender wasn't unlocked, purging setting + starterAttributes.female = undefined; } if (starterAttributes.ability !== undefined) { @@ -2342,11 +2343,9 @@ export class StarterSelectUiHandler extends MessageUiHandler { // TODO: is this bang correct? break; } - } else { - if (this.speciesStarterDexEntry!.caughtAttr & DexAttr.VARIANT_3) { - // TODO: is this bang correct? - break; - } + } else if (this.speciesStarterDexEntry!.caughtAttr & DexAttr.VARIANT_3) { + // TODO: is this bang correct? + break; } } while (newVariant !== props.variant); starterAttributes.variant = newVariant; // store the selected variant @@ -2422,10 +2421,8 @@ export class StarterSelectUiHandler extends MessageUiHandler { newAbilityIndex = (newAbilityIndex + 1) % abilityCount; } break; - } else { - if (abilityAttr & AbilityAttr.ABILITY_HIDDEN) { - break; - } + } else if (abilityAttr & AbilityAttr.ABILITY_HIDDEN) { + break; } } while (newAbilityIndex !== this.abilityCursor); starterAttributes.ability = newAbilityIndex; // store the selected ability @@ -2972,8 +2969,7 @@ export class StarterSelectUiHandler extends MessageUiHandler { } // this updates icons for previously saved pokemon - for (let i = 0; i < this.validStarterContainers.length; i++) { - const currentFilteredContainer = this.validStarterContainers[i]; + for (const currentFilteredContainer of this.validStarterContainers) { const starterSprite = currentFilteredContainer.icon as Phaser.GameObjects.Sprite; const currentDexAttr = this.getCurrentDexProps(currentFilteredContainer.species.speciesId); @@ -3562,10 +3558,8 @@ export class StarterSelectUiHandler extends MessageUiHandler { // load default nature from stater save data, if set const defaultNature = starterAttributes?.nature || globalScene.gameData.getSpeciesDefaultNature(species); props = globalScene.gameData.getSpeciesDexAttrProps(species, defaultDexAttr); - if (starterAttributes?.variant && !Number.isNaN(starterAttributes.variant)) { - if (props.shiny) { - props.variant = starterAttributes.variant as Variant; - } + if (starterAttributes?.variant && !Number.isNaN(starterAttributes.variant) && props.shiny) { + props.variant = starterAttributes.variant as Variant; } props.formIndex = starterAttributes?.form ?? props.formIndex; props.female = starterAttributes?.female ?? props.female; @@ -4350,13 +4344,13 @@ export class StarterSelectUiHandler extends MessageUiHandler { return true; } - /* This block checks to see if your party is valid + /** + * This block checks to see if your party is valid * It checks each pokemon against the challenge - noting that due to monotype challenges it needs to check the pokemon while ignoring their evolutions/form change items */ isPartyValid(): boolean { let canStart = false; - for (let s = 0; s < this.starterSpecies.length; s++) { - const species = this.starterSpecies[s]; + for (const species of this.starterSpecies) { const isValidForChallenge = checkStarterValidForChallenge( species, globalScene.gameData.getSpeciesDexAttrProps(species, this.getCurrentDexProps(species.speciesId)), @@ -4400,17 +4394,15 @@ export class StarterSelectUiHandler extends MessageUiHandler { props += DexAttr.SHINY; if (this.starterPreferences[speciesId]?.variant !== undefined) { props += BigInt(Math.pow(2, this.starterPreferences[speciesId]?.variant)) * DexAttr.DEFAULT_VARIANT; - } else { + } else if ((caughtAttr & DexAttr.VARIANT_3) > 0) { /* This calculates the correct variant if there's no starter preferences for it. * This gets the highest tier variant that you've caught and adds it to the temp props */ - if ((caughtAttr & DexAttr.VARIANT_3) > 0) { - props += DexAttr.VARIANT_3; - } else if ((caughtAttr & DexAttr.VARIANT_2) > 0) { - props += DexAttr.VARIANT_2; - } else { - props += DexAttr.DEFAULT_VARIANT; - } + props += DexAttr.VARIANT_3; + } else if ((caughtAttr & DexAttr.VARIANT_2) > 0) { + props += DexAttr.VARIANT_2; + } else { + props += DexAttr.DEFAULT_VARIANT; } } else { props += DexAttr.NON_SHINY; diff --git a/src/ui/summary-ui-handler.ts b/src/ui/summary-ui-handler.ts index b6ce0a706f8..416a2ae6d60 100644 --- a/src/ui/summary-ui-handler.ts +++ b/src/ui/summary-ui-handler.ts @@ -515,33 +515,31 @@ export class SummaryUiHandler extends UiHandler { if (this.pokemon && this.moveCursor < this.pokemon.moveset.length) { if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE) { this.moveSelectFunction?.(this.moveCursor); + } else if (this.selectedMoveIndex === -1) { + this.selectedMoveIndex = this.moveCursor; + this.setCursor(this.moveCursor); } else { - if (this.selectedMoveIndex === -1) { - this.selectedMoveIndex = this.moveCursor; - this.setCursor(this.moveCursor); - } else { - if (this.selectedMoveIndex !== this.moveCursor) { - const tempMove = this.pokemon?.moveset[this.selectedMoveIndex]; - this.pokemon.moveset[this.selectedMoveIndex] = this.pokemon.moveset[this.moveCursor]; - this.pokemon.moveset[this.moveCursor] = tempMove; + if (this.selectedMoveIndex !== this.moveCursor) { + const tempMove = this.pokemon?.moveset[this.selectedMoveIndex]; + this.pokemon.moveset[this.selectedMoveIndex] = this.pokemon.moveset[this.moveCursor]; + this.pokemon.moveset[this.moveCursor] = tempMove; - const selectedMoveRow = this.moveRowsContainer.getAt( - this.selectedMoveIndex, - ) as Phaser.GameObjects.Container; - const switchMoveRow = this.moveRowsContainer.getAt(this.moveCursor) as Phaser.GameObjects.Container; + const selectedMoveRow = this.moveRowsContainer.getAt( + this.selectedMoveIndex, + ) as Phaser.GameObjects.Container; + const switchMoveRow = this.moveRowsContainer.getAt(this.moveCursor) as Phaser.GameObjects.Container; - this.moveRowsContainer.moveTo(selectedMoveRow, this.moveCursor); - this.moveRowsContainer.moveTo(switchMoveRow, this.selectedMoveIndex); + this.moveRowsContainer.moveTo(selectedMoveRow, this.moveCursor); + this.moveRowsContainer.moveTo(switchMoveRow, this.selectedMoveIndex); - selectedMoveRow.setY(this.moveCursor * 16); - switchMoveRow.setY(this.selectedMoveIndex * 16); - } + selectedMoveRow.setY(this.moveCursor * 16); + switchMoveRow.setY(this.selectedMoveIndex * 16); + } - this.selectedMoveIndex = -1; - if (this.selectedMoveCursorObj) { - this.selectedMoveCursorObj.destroy(); - this.selectedMoveCursorObj = null; - } + this.selectedMoveIndex = -1; + if (this.selectedMoveCursorObj) { + this.selectedMoveCursorObj.destroy(); + this.selectedMoveCursorObj = null; } } success = true; @@ -575,78 +573,76 @@ export class SummaryUiHandler extends UiHandler { break; } } - } else { - if (button === Button.ACTION) { - if (this.cursor === Page.MOVES) { - this.showMoveSelect(); - success = true; - } else if (this.cursor === Page.PROFILE && this.pokemon?.hasPassive()) { - // if we're on the PROFILE page and this pokemon has a passive unlocked.. - // Since abilities are displayed by default, all we need to do is toggle visibility on all elements to show passives - this.abilityContainer.nameText?.setVisible(!this.abilityContainer.descriptionText?.visible); - this.abilityContainer.descriptionText?.setVisible(!this.abilityContainer.descriptionText.visible); - this.abilityContainer.labelImage.setVisible(!this.abilityContainer.labelImage.visible); - - this.passiveContainer.nameText?.setVisible(!this.passiveContainer.descriptionText?.visible); - this.passiveContainer.descriptionText?.setVisible(!this.passiveContainer.descriptionText.visible); - this.passiveContainer.labelImage.setVisible(!this.passiveContainer.labelImage.visible); - } else if (this.cursor === Page.STATS) { - //Show IVs - this.permStatsContainer.setVisible(!this.permStatsContainer.visible); - this.ivContainer.setVisible(!this.ivContainer.visible); - } - } else if (button === Button.CANCEL) { - if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE) { - this.hideMoveSelect(); - } else { - if (this.selectCallback instanceof Function) { - const selectCallback = this.selectCallback; - this.selectCallback = null; - selectCallback(); - } - - if (!fromPartyMode) { - ui.setMode(UiMode.MESSAGE); - } else { - ui.setMode(UiMode.PARTY); - } - } + } else if (button === Button.ACTION) { + if (this.cursor === Page.MOVES) { + this.showMoveSelect(); success = true; + } else if (this.cursor === Page.PROFILE && this.pokemon?.hasPassive()) { + // if we're on the PROFILE page and this pokemon has a passive unlocked.. + // Since abilities are displayed by default, all we need to do is toggle visibility on all elements to show passives + this.abilityContainer.nameText?.setVisible(!this.abilityContainer.descriptionText?.visible); + this.abilityContainer.descriptionText?.setVisible(!this.abilityContainer.descriptionText.visible); + this.abilityContainer.labelImage.setVisible(!this.abilityContainer.labelImage.visible); + + this.passiveContainer.nameText?.setVisible(!this.passiveContainer.descriptionText?.visible); + this.passiveContainer.descriptionText?.setVisible(!this.passiveContainer.descriptionText.visible); + this.passiveContainer.labelImage.setVisible(!this.passiveContainer.labelImage.visible); + } else if (this.cursor === Page.STATS) { + //Show IVs + this.permStatsContainer.setVisible(!this.permStatsContainer.visible); + this.ivContainer.setVisible(!this.ivContainer.visible); + } + } else if (button === Button.CANCEL) { + if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE) { + this.hideMoveSelect(); } else { - const pages = getEnumValues(Page); - switch (button) { - case Button.UP: - case Button.DOWN: { - if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE) { - break; - } - if (!fromPartyMode) { - break; - } - const isDown = button === Button.DOWN; - const party = globalScene.getPlayerParty(); - const partyMemberIndex = this.pokemon ? party.indexOf(this.pokemon) : -1; - if ((isDown && partyMemberIndex < party.length - 1) || (!isDown && partyMemberIndex)) { - const page = this.cursor; - this.clear(); - this.show([party[partyMemberIndex + (isDown ? 1 : -1)], this.summaryUiMode, page]); - } + if (this.selectCallback instanceof Function) { + const selectCallback = this.selectCallback; + this.selectCallback = null; + selectCallback(); + } + + if (!fromPartyMode) { + ui.setMode(UiMode.MESSAGE); + } else { + ui.setMode(UiMode.PARTY); + } + } + success = true; + } else { + const pages = getEnumValues(Page); + switch (button) { + case Button.UP: + case Button.DOWN: { + if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE) { break; } - case Button.LEFT: - if (this.cursor) { - success = this.setCursor(this.cursor - 1); - } - break; - case Button.RIGHT: - if (this.cursor < pages.length - 1) { - success = this.setCursor(this.cursor + 1); - if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE && this.cursor === Page.MOVES) { - this.moveSelect = true; - } - } + if (!fromPartyMode) { break; + } + const isDown = button === Button.DOWN; + const party = globalScene.getPlayerParty(); + const partyMemberIndex = this.pokemon ? party.indexOf(this.pokemon) : -1; + if ((isDown && partyMemberIndex < party.length - 1) || (!isDown && partyMemberIndex)) { + const page = this.cursor; + this.clear(); + this.show([party[partyMemberIndex + (isDown ? 1 : -1)], this.summaryUiMode, page]); + } + break; } + case Button.LEFT: + if (this.cursor) { + success = this.setCursor(this.cursor - 1); + } + break; + case Button.RIGHT: + if (this.cursor < pages.length - 1) { + success = this.setCursor(this.cursor + 1); + if (this.summaryUiMode === SummaryUiMode.LEARN_MOVE && this.cursor === Page.MOVES) { + this.moveSelect = true; + } + } + break; } } diff --git a/src/ui/target-select-ui-handler.ts b/src/ui/target-select-ui-handler.ts index 5ea89929cda..bc708c4542a 100644 --- a/src/ui/target-select-ui-handler.ts +++ b/src/ui/target-select-ui-handler.ts @@ -70,11 +70,12 @@ export class TargetSelectUiHandler extends UiHandler { * @param user the Pokemon using the move */ resetCursor(cursorN: number, user: Pokemon): void { - if (!isNullOrUndefined(cursorN)) { - if ([BattlerIndex.PLAYER, BattlerIndex.PLAYER_2].includes(cursorN) || user.tempSummonData.waveTurnCount === 1) { - // Reset cursor on the first turn of a fight or if an ally was targeted last turn - cursorN = -1; - } + if ( + !isNullOrUndefined(cursorN) && + ([BattlerIndex.PLAYER, BattlerIndex.PLAYER_2].includes(cursorN) || user.tempSummonData.waveTurnCount === 1) + ) { + // Reset cursor on the first turn of a fight or if an ally was targeted last turn + cursorN = -1; } this.setCursor(this.targets.includes(cursorN) ? cursorN : this.targets[0]); } @@ -92,10 +93,11 @@ export class TargetSelectUiHandler extends UiHandler { if (isNullOrUndefined(this.cursor0) || this.cursor0 !== this.cursor) { this.cursor0 = this.cursor; } - } else if (this.fieldIndex === BattlerIndex.PLAYER_2) { - if (isNullOrUndefined(this.cursor1) || this.cursor1 !== this.cursor) { - this.cursor1 = this.cursor; - } + } else if ( + this.fieldIndex === BattlerIndex.PLAYER_2 && + (isNullOrUndefined(this.cursor1) || this.cursor1 !== this.cursor) + ) { + this.cursor1 = this.cursor; } } else if (this.isMultipleTargets) { success = false; diff --git a/src/ui/ui-theme.ts b/src/ui/ui-theme.ts index f2d434c024a..2c1b5b7c9aa 100644 --- a/src/ui/ui-theme.ts +++ b/src/ui/ui-theme.ts @@ -117,10 +117,8 @@ export function updateWindowType(windowTypeIndex: number): void { } else if (object.texture?.key === "namebox") { themedObjects.push(object); } - } else if (object instanceof Phaser.GameObjects.Sprite) { - if (object.texture?.key === "bg") { - themedObjects.push(object); - } + } else if (object instanceof Phaser.GameObjects.Sprite && object.texture?.key === "bg") { + themedObjects.push(object); } }; diff --git a/src/ui/ui.ts b/src/ui/ui.ts index d5baea07ed5..a6767ddcc00 100644 --- a/src/ui/ui.ts +++ b/src/ui/ui.ts @@ -374,10 +374,12 @@ export class UI extends Phaser.GameObjects.Container { } shouldSkipDialogue(i18nKey: string): boolean { - if (i18next.exists(i18nKey)) { - if (globalScene.skipSeenDialogues && globalScene.gameData.getSeenDialogues()[i18nKey] === true) { - return true; - } + if ( + i18next.exists(i18nKey) && + globalScene.skipSeenDialogues && + globalScene.gameData.getSeenDialogues()[i18nKey] === true + ) { + return true; } return false; } diff --git a/src/utils/challenge-utils.ts b/src/utils/challenge-utils.ts index 43297027e04..88e9c8da269 100644 --- a/src/utils/challenge-utils.ts +++ b/src/utils/challenge-utils.ts @@ -1,3 +1,5 @@ +// biome-ignore-all lint/nursery/useUnifiedTypeSignature: Rule does not allow stuff with JSDoc comments + import type { FixedBattleConfig } from "#app/battle"; import { globalScene } from "#app/global-scene"; import { pokemonEvolutions } from "#balance/pokemon-evolutions"; diff --git a/src/utils/cookies.ts b/src/utils/cookies.ts index 06391e6f4c7..e82895d1fac 100644 --- a/src/utils/cookies.ts +++ b/src/utils/cookies.ts @@ -23,13 +23,11 @@ export function getCookie(cName: string): string { } const name = `${cName}=`; const ca = document.cookie.split(";"); - for (let i = 0; i < ca.length; i++) { - let c = ca[i]; - while (c.charAt(0) === " ") { - c = c.substring(1); - } - if (c.indexOf(name) === 0) { - return c.substring(name.length, c.length); + // Check all cookies in the document and see if any of them match, grabbing the first one whose value lines up + for (const c of ca) { + const cTrimmed = c.trim(); + if (cTrimmed.startsWith(name)) { + return c.slice(name.length, c.length); } } return ""; diff --git a/test/abilities/power-construct.test.ts b/test/abilities/power-construct.test.ts index 34e02851daf..6c504359370 100644 --- a/test/abilities/power-construct.test.ts +++ b/test/abilities/power-construct.test.ts @@ -33,8 +33,8 @@ describe("Abilities - POWER CONSTRUCT", () => { }); test("check if fainted 50% Power Construct Pokemon switches to base form on arena reset", async () => { - const baseForm = 2, - completeForm = 4; + const baseForm = 2; + const completeForm = 4; game.override.startingWave(4).starterForms({ [SpeciesId.ZYGARDE]: completeForm, }); @@ -59,8 +59,8 @@ describe("Abilities - POWER CONSTRUCT", () => { }); test("check if fainted 10% Power Construct Pokemon switches to base form on arena reset", async () => { - const baseForm = 3, - completeForm = 5; + const baseForm = 3; + const completeForm = 5; game.override.startingWave(4).starterForms({ [SpeciesId.ZYGARDE]: completeForm, }); diff --git a/test/abilities/schooling.test.ts b/test/abilities/schooling.test.ts index fea919c7c5a..5c908d39866 100644 --- a/test/abilities/schooling.test.ts +++ b/test/abilities/schooling.test.ts @@ -29,8 +29,8 @@ describe("Abilities - SCHOOLING", () => { }); test("check if fainted pokemon switches to base form on arena reset", async () => { - const soloForm = 0, - schoolForm = 1; + const soloForm = 0; + const schoolForm = 1; game.override.startingWave(4).starterForms({ [SpeciesId.WISHIWASHI]: schoolForm, }); diff --git a/test/abilities/shields-down.test.ts b/test/abilities/shields-down.test.ts index 98a1cfffa8e..d55f0b19249 100644 --- a/test/abilities/shields-down.test.ts +++ b/test/abilities/shields-down.test.ts @@ -34,8 +34,8 @@ describe("Abilities - SHIELDS DOWN", () => { }); test("check if fainted pokemon switched to base form on arena reset", async () => { - const meteorForm = 0, - coreForm = 7; + const meteorForm = 0; + const coreForm = 7; game.override.startingWave(4).starterForms({ [SpeciesId.MINIOR]: coreForm, }); diff --git a/test/escape-calculations.test.ts b/test/escape-calculations.test.ts index f1bb955582a..fb677e81a45 100644 --- a/test/escape-calculations.test.ts +++ b/test/escape-calculations.test.ts @@ -76,9 +76,9 @@ describe("Escape chance calculations", () => { { pokemonSpeedRatio: 2, escapeAttempts: 3, expectedEscapeChance: 80 }, ]; - for (let i = 0; i < escapeChances.length; i++) { - // sets the number of escape attempts to the required amount - game.scene.currentBattle.escapeAttempts = escapeChances[i].escapeAttempts; + for (const check of escapeChances) { + // set the number of escape attempts to the required amount + game.scene.currentBattle.escapeAttempts = check.escapeAttempts; // set playerPokemon's speed to a multiple of the enemySpeed vi.spyOn(playerPokemon[0], "stats", "get").mockReturnValue([ 20, @@ -86,10 +86,10 @@ describe("Escape chance calculations", () => { 20, 20, 20, - escapeChances[i].pokemonSpeedRatio * enemySpeed, + check.pokemonSpeedRatio * enemySpeed, ]); const chance = phase.calculateEscapeChance(game.scene.currentBattle.escapeAttempts); - expect(chance).toBe(escapeChances[i].expectedEscapeChance); + expect(chance).toBe(check.expectedEscapeChance); } }); @@ -146,9 +146,9 @@ describe("Escape chance calculations", () => { { pokemonSpeedRatio: 2, escapeAttempts: 10, expectedEscapeChance: 95 }, ]; - for (let i = 0; i < escapeChances.length; i++) { + for (const check of escapeChances) { // sets the number of escape attempts to the required amount - game.scene.currentBattle.escapeAttempts = escapeChances[i].escapeAttempts; + game.scene.currentBattle.escapeAttempts = check.escapeAttempts; // set the first playerPokemon's speed to a multiple of the enemySpeed vi.spyOn(playerPokemon[0], "stats", "get").mockReturnValue([ 20, @@ -156,7 +156,7 @@ describe("Escape chance calculations", () => { 20, 20, 20, - Math.floor(escapeChances[i].pokemonSpeedRatio * totalEnemySpeed * playerASpeedPercentage), + Math.floor(check.pokemonSpeedRatio * totalEnemySpeed * playerASpeedPercentage), ]); // set the second playerPokemon's speed to the remaining value of speed vi.spyOn(playerPokemon[1], "stats", "get").mockReturnValue([ @@ -165,15 +165,13 @@ describe("Escape chance calculations", () => { 20, 20, 20, - escapeChances[i].pokemonSpeedRatio * totalEnemySpeed - playerPokemon[0].stats[5], + check.pokemonSpeedRatio * totalEnemySpeed - playerPokemon[0].stats[5], ]); const chance = phase.calculateEscapeChance(game.scene.currentBattle.escapeAttempts); // checks to make sure the escape values are the same - expect(chance).toBe(escapeChances[i].expectedEscapeChance); + expect(chance).toBe(check.expectedEscapeChance); // checks to make sure the sum of the player's speed for all pokemon is equal to the appropriate ratio of the total enemy speed - expect(playerPokemon[0].stats[5] + playerPokemon[1].stats[5]).toBe( - escapeChances[i].pokemonSpeedRatio * totalEnemySpeed, - ); + expect(playerPokemon[0].stats[5] + playerPokemon[1].stats[5]).toBe(check.pokemonSpeedRatio * totalEnemySpeed); } }); @@ -238,9 +236,9 @@ describe("Escape chance calculations", () => { { pokemonSpeedRatio: 6.1, escapeAttempts: 3, expectedEscapeChance: 25 }, ]; - for (let i = 0; i < escapeChances.length; i++) { + for (const check of escapeChances) { // sets the number of escape attempts to the required amount - game.scene.currentBattle.escapeAttempts = escapeChances[i].escapeAttempts; + game.scene.currentBattle.escapeAttempts = check.escapeAttempts; // set playerPokemon's speed to a multiple of the enemySpeed vi.spyOn(playerPokemon[0], "stats", "get").mockReturnValue([ 20, @@ -248,10 +246,10 @@ describe("Escape chance calculations", () => { 20, 20, 20, - escapeChances[i].pokemonSpeedRatio * enemySpeed, + check.pokemonSpeedRatio * enemySpeed, ]); const chance = phase.calculateEscapeChance(game.scene.currentBattle.escapeAttempts); - expect(chance).toBe(escapeChances[i].expectedEscapeChance); + expect(chance).toBe(check.expectedEscapeChance); } }); @@ -321,9 +319,9 @@ describe("Escape chance calculations", () => { { pokemonSpeedRatio: 5.2, escapeAttempts: 2, expectedEscapeChance: 25 }, ]; - for (let i = 0; i < escapeChances.length; i++) { + for (const check of escapeChances) { // sets the number of escape attempts to the required amount - game.scene.currentBattle.escapeAttempts = escapeChances[i].escapeAttempts; + game.scene.currentBattle.escapeAttempts = check.escapeAttempts; // set the first playerPokemon's speed to a multiple of the enemySpeed vi.spyOn(playerPokemon[0], "stats", "get").mockReturnValue([ 20, @@ -331,7 +329,7 @@ describe("Escape chance calculations", () => { 20, 20, 20, - Math.floor(escapeChances[i].pokemonSpeedRatio * totalEnemySpeed * playerASpeedPercentage), + Math.floor(check.pokemonSpeedRatio * totalEnemySpeed * playerASpeedPercentage), ]); // set the second playerPokemon's speed to the remaining value of speed vi.spyOn(playerPokemon[1], "stats", "get").mockReturnValue([ @@ -340,15 +338,13 @@ describe("Escape chance calculations", () => { 20, 20, 20, - escapeChances[i].pokemonSpeedRatio * totalEnemySpeed - playerPokemon[0].stats[5], + check.pokemonSpeedRatio * totalEnemySpeed - playerPokemon[0].stats[5], ]); const chance = phase.calculateEscapeChance(game.scene.currentBattle.escapeAttempts); // checks to make sure the escape values are the same - expect(chance).toBe(escapeChances[i].expectedEscapeChance); + expect(chance).toBe(check.expectedEscapeChance); // checks to make sure the sum of the player's speed for all pokemon is equal to the appropriate ratio of the total enemy speed - expect(playerPokemon[0].stats[5] + playerPokemon[1].stats[5]).toBe( - escapeChances[i].pokemonSpeedRatio * totalEnemySpeed, - ); + expect(playerPokemon[0].stats[5] + playerPokemon[1].stats[5]).toBe(check.pokemonSpeedRatio * totalEnemySpeed); } }); }); diff --git a/test/moves/aurora-veil.test.ts b/test/moves/aurora-veil.test.ts index 3c7c86c7fdf..6b28505e096 100644 --- a/test/moves/aurora-veil.test.ts +++ b/test/moves/aurora-veil.test.ts @@ -139,17 +139,15 @@ const getMockedMoveDamage = (defender: Pokemon, attacker: Pokemon, move: Move) = const multiplierHolder = new NumberHolder(1); const side = defender.isPlayer() ? ArenaTagSide.PLAYER : ArenaTagSide.ENEMY; - if (globalScene.arena.getTagOnSide(ArenaTagType.AURORA_VEIL, side)) { - if (move.getAttrs("CritOnlyAttr").length === 0) { - globalScene.arena.applyTagsForSide( - ArenaTagType.AURORA_VEIL, - side, - false, - attacker, - move.category, - multiplierHolder, - ); - } + if (globalScene.arena.getTagOnSide(ArenaTagType.AURORA_VEIL, side) && move.getAttrs("CritOnlyAttr").length === 0) { + globalScene.arena.applyTagsForSide( + ArenaTagType.AURORA_VEIL, + side, + false, + attacker, + move.category, + multiplierHolder, + ); } return move.power * multiplierHolder.value; diff --git a/test/moves/light-screen.test.ts b/test/moves/light-screen.test.ts index c8282037f20..b81b77558b4 100644 --- a/test/moves/light-screen.test.ts +++ b/test/moves/light-screen.test.ts @@ -127,17 +127,15 @@ const getMockedMoveDamage = (defender: Pokemon, attacker: Pokemon, move: Move) = const multiplierHolder = new NumberHolder(1); const side = defender.isPlayer() ? ArenaTagSide.PLAYER : ArenaTagSide.ENEMY; - if (globalScene.arena.getTagOnSide(ArenaTagType.LIGHT_SCREEN, side)) { - if (move.getAttrs("CritOnlyAttr").length === 0) { - globalScene.arena.applyTagsForSide( - ArenaTagType.LIGHT_SCREEN, - side, - false, - attacker, - move.category, - multiplierHolder, - ); - } + if (globalScene.arena.getTagOnSide(ArenaTagType.LIGHT_SCREEN, side) && move.getAttrs("CritOnlyAttr").length === 0) { + globalScene.arena.applyTagsForSide( + ArenaTagType.LIGHT_SCREEN, + side, + false, + attacker, + move.category, + multiplierHolder, + ); } return move.power * multiplierHolder.value; diff --git a/test/moves/reflect.test.ts b/test/moves/reflect.test.ts index b8fa2b1ce80..c010efa5a59 100644 --- a/test/moves/reflect.test.ts +++ b/test/moves/reflect.test.ts @@ -143,10 +143,8 @@ const getMockedMoveDamage = (defender: Pokemon, attacker: Pokemon, move: Move) = const multiplierHolder = new NumberHolder(1); const side = defender.isPlayer() ? ArenaTagSide.PLAYER : ArenaTagSide.ENEMY; - if (globalScene.arena.getTagOnSide(ArenaTagType.REFLECT, side)) { - if (move.getAttrs("CritOnlyAttr").length === 0) { - globalScene.arena.applyTagsForSide(ArenaTagType.REFLECT, side, false, attacker, move.category, multiplierHolder); - } + if (globalScene.arena.getTagOnSide(ArenaTagType.REFLECT, side) && move.getAttrs("CritOnlyAttr").length === 0) { + globalScene.arena.applyTagsForSide(ArenaTagType.REFLECT, side, false, attacker, move.category, multiplierHolder); } return move.power * multiplierHolder.value; diff --git a/test/test-utils/helpers/classic-mode-helper.ts b/test/test-utils/helpers/classic-mode-helper.ts index 5d73dc07615..f8009a97c3d 100644 --- a/test/test-utils/helpers/classic-mode-helper.ts +++ b/test/test-utils/helpers/classic-mode-helper.ts @@ -18,8 +18,10 @@ import { GameManagerHelper } from "#test/test-utils/helpers/game-manager-helper" export class ClassicModeHelper extends GameManagerHelper { /** * Runs the classic game to the summon phase. - * @param species - An array of {@linkcode Species} to summon. + * @param species - An array of {@linkcode SpeciesId} to summon. * @returns A promise that resolves when the summon phase is reached. + * @remarks + * Do not use this when {@linkcode startBattle} can be used! */ async runToSummon(species: SpeciesId[]): Promise; /** @@ -29,6 +31,7 @@ export class ClassicModeHelper extends GameManagerHelper { * @returns A promise that resolves when the summon phase is reached. * @deprecated - Specifying the starters helps prevent inconsistencies from internal RNG changes. */ + // biome-ignore lint/nursery/useUnifiedTypeSignature: Marks the overload for deprecation async runToSummon(): Promise; async runToSummon(species: SpeciesId[] | undefined): Promise; async runToSummon(species?: SpeciesId[]): Promise { @@ -60,7 +63,7 @@ export class ClassicModeHelper extends GameManagerHelper { /** * Transitions to the start of a battle. - * @param species - An array of {@linkcode Species} to start the battle with. + * @param species - An array of {@linkcode SpeciesId} to start the battle with. * @returns A promise that resolves when the battle is started. */ async startBattle(species: SpeciesId[]): Promise; @@ -71,6 +74,7 @@ export class ClassicModeHelper extends GameManagerHelper { * @returns A promise that resolves when the battle is started. * @deprecated - Specifying the starters helps prevent inconsistencies from internal RNG changes. */ + // biome-ignore lint/nursery/useUnifiedTypeSignature: Marks the overload for deprecation async startBattle(): Promise; async startBattle(species?: SpeciesId[]): Promise { await this.runToSummon(species); diff --git a/test/test-utils/helpers/move-helper.ts b/test/test-utils/helpers/move-helper.ts index 6a01e4110da..d88a6f9cb06 100644 --- a/test/test-utils/helpers/move-helper.ts +++ b/test/test-utils/helpers/move-helper.ts @@ -227,11 +227,9 @@ export class MoveHelper extends GameManagerHelper { vi.spyOn(Overrides, "MOVESET_OVERRIDE", "get").mockReturnValue([]); console.warn("Player moveset override disabled due to use of `game.move.changeMoveset`!"); } - } else { - if (coerceArray(Overrides.OPP_MOVESET_OVERRIDE).length > 0) { - vi.spyOn(Overrides, "OPP_MOVESET_OVERRIDE", "get").mockReturnValue([]); - console.warn("Enemy moveset override disabled due to use of `game.move.changeMoveset`!"); - } + } else if (coerceArray(Overrides.OPP_MOVESET_OVERRIDE).length > 0) { + vi.spyOn(Overrides, "OPP_MOVESET_OVERRIDE", "get").mockReturnValue([]); + console.warn("Enemy moveset override disabled due to use of `game.move.changeMoveset`!"); } moveset = coerceArray(moveset); expect(moveset.length, "Cannot assign more than 4 moves to a moveset!").toBeLessThanOrEqual(4); diff --git a/test/test-utils/mocks/mocks-container/mock-text.ts b/test/test-utils/mocks/mocks-container/mock-text.ts index ad2fce80972..691a6724bbe 100644 --- a/test/test-utils/mocks/mocks-container/mock-text.ts +++ b/test/test-utils/mocks/mocks-container/mock-text.ts @@ -53,13 +53,11 @@ export class MockText implements MockGameObject { wordWidthWithSpace += whiteSpaceWidth; } - if (wordWidthWithSpace > spaceLeft) { - // Skip printing the newline if it's the first word of the line that is greater - // than the word wrap width. - if (j > 0) { - result += "\n"; - spaceLeft = this.wordWrapWidth; - } + // Skip printing the newline if it's the first word of the line that is greater + // than the word wrap width. + if (wordWidthWithSpace > spaceLeft && j > 0) { + result += "\n"; + spaceLeft = this.wordWrapWidth; } result += word;