From 63f9988cb8318bf5b0f982a7c43e86f82569cfb9 Mon Sep 17 00:00:00 2001 From: RedstonewolfX <108761527+RedstonewolfX@users.noreply.github.com> Date: Thu, 11 Jul 2024 21:06:23 -0400 Subject: [PATCH] Fix incorrect uploaded file --- src/events/arena.ts | 923 +++++--------------------------------------- src/field/arena.ts | 14 + 2 files changed, 102 insertions(+), 835 deletions(-) diff --git a/src/events/arena.ts b/src/events/arena.ts index 8658b35d756..67b423f3b75 100644 --- a/src/events/arena.ts +++ b/src/events/arena.ts @@ -1,850 +1,103 @@ -import BattleScene from "../battle-scene"; -import { BiomePoolTier, PokemonPools, BiomeTierTrainerPools, biomePokemonPools, biomeTrainerPools } from "../data/biomes"; -import { Constructor } from "#app/utils"; -import * as Utils from "../utils"; -import PokemonSpecies, { getPokemonSpecies } from "../data/pokemon-species"; -import { Weather, WeatherType, getTerrainClearMessage, getTerrainStartMessage, getWeatherClearMessage, getWeatherStartMessage } from "../data/weather"; -import { CommonAnimPhase } from "../phases"; -import { CommonAnim } from "../data/battle-anims"; -import { Type } from "../data/type"; -import Move from "../data/move"; -import { ArenaTag, ArenaTagSide, ArenaTrapTag, getArenaTag } from "../data/arena-tag"; -import { BattlerIndex } from "../battle"; -import { Terrain, TerrainType } from "../data/terrain"; -import { PostTerrainChangeAbAttr, PostWeatherChangeAbAttr, applyPostTerrainChangeAbAttrs, applyPostWeatherChangeAbAttrs } from "../data/ability"; -import Pokemon from "./pokemon"; -import * as Overrides from "../overrides"; -import { WeatherChangedEvent, TerrainChangedEvent, TagAddedEvent, TagRemovedEvent } from "../events/arena"; +import { ArenaTagSide } from "#app/data/arena-tag.js"; import { ArenaTagType } from "#enums/arena-tag-type"; -import { Biome } from "#enums/biome"; -import { Moves } from "#enums/moves"; -import { Species } from "#enums/species"; -import { TimeOfDay } from "#enums/time-of-day"; -import { TrainerType } from "#enums/trainer-type"; -import * as LoggerTools from "../logger" +import { TerrainType } from "#app/data/terrain.js"; +import { WeatherType } from "#app/data/weather.js"; -export class Arena { - public scene: BattleScene; - public biomeType: Biome; - public weather: Weather; - public terrain: Terrain; - public tags: ArenaTag[]; - public bgm: string; - public ignoreAbilities: boolean; +/** Alias for all {@linkcode ArenaEvent} type strings */ +export enum ArenaEventType { + /** Triggers when a {@linkcode WeatherType} is added, overlapped, or removed */ + WEATHER_CHANGED = "onWeatherChanged", + /** Triggers when a {@linkcode TerrainType} is added, overlapped, or removed */ + TERRAIN_CHANGED = "onTerrainChanged", - private lastTimeOfDay: TimeOfDay; + /** Triggers when a {@linkcode ArenaTagType} is added */ + TAG_ADDED = "onTagAdded", + /** Triggers when a {@linkcode ArenaTagType} is removed */ + TAG_REMOVED = "onTagRemoved", +} - public pokemonPool: PokemonPools; - private trainerPool: BiomeTierTrainerPools; +/** + * Base container class for all {@linkcode ArenaEventType} events + * @extends Event + */ +export class ArenaEvent extends Event { + /** The total duration of the {@linkcode ArenaEventType} */ + public duration: number; + constructor(eventType: ArenaEventType, duration: number) { + super(eventType); - public readonly eventTarget: EventTarget = new EventTarget(); - - constructor(scene: BattleScene, biome: Biome, bgm: string) { - this.scene = scene; - this.biomeType = biome; - this.tags = []; - this.bgm = bgm; - this.trainerPool = biomeTrainerPools[biome]; - this.updatePoolsForTimeOfDay(); + this.duration = duration; } +} +/** + * Container class for {@linkcode ArenaEventType.WEATHER_CHANGED} events + * @extends ArenaEvent +*/ +export class WeatherChangedEvent extends ArenaEvent { + /** The {@linkcode WeatherType} being overridden */ + public oldWeatherType: WeatherType; + /** The {@linkcode WeatherType} being set */ + public newWeatherType: WeatherType; + constructor(oldWeatherType: WeatherType, newWeatherType: WeatherType, duration: number) { + super(ArenaEventType.WEATHER_CHANGED, duration); - init() { - const biomeKey = getBiomeKey(this.biomeType); - - this.scene.arenaPlayer.setBiome(this.biomeType); - this.scene.arenaPlayerTransition.setBiome(this.biomeType); - this.scene.arenaEnemy.setBiome(this.biomeType); - this.scene.arenaNextEnemy.setBiome(this.biomeType); - this.scene.arenaBg.setTexture(`${biomeKey}_bg`); - this.scene.arenaBgTransition.setTexture(`${biomeKey}_bg`); - - // Redo this on initialise because during save/load the current wave isn't always - // set correctly during construction - this.updatePoolsForTimeOfDay(); + this.oldWeatherType = oldWeatherType; + this.newWeatherType = newWeatherType; } - - updatePoolsForTimeOfDay(): void { - const timeOfDay = this.getTimeOfDay(); - if (timeOfDay !== this.lastTimeOfDay) { - this.pokemonPool = {}; - for (const tier of Object.keys(biomePokemonPools[this.biomeType])) { - this.pokemonPool[tier] = Object.assign([], biomePokemonPools[this.biomeType][tier][TimeOfDay.ALL]).concat(biomePokemonPools[this.biomeType][tier][timeOfDay]); - } - this.lastTimeOfDay = timeOfDay; - } - } - - randomSpecies(waveIndex: integer, level: integer, attempt?: integer, luckValue?: integer): PokemonSpecies { - const overrideSpecies = this.scene.gameMode.getOverrideSpecies(waveIndex); - if (overrideSpecies) { - return overrideSpecies; - } - const isBoss = !!this.scene.getEncounterBossSegments(waveIndex, level) && !!this.pokemonPool[BiomePoolTier.BOSS].length - && (this.biomeType !== Biome.END || this.scene.gameMode.isClassic || this.scene.gameMode.isWaveFinal(waveIndex)); - const randVal = isBoss ? 64 : 512; - // luck influences encounter rarity - let luckModifier = 0; - if (typeof luckValue !== "undefined") { - luckModifier = luckValue * (isBoss ? 0.5 : 2); - } - const tierValue = Utils.randSeedInt(randVal - luckModifier); - let tier = !isBoss - ? tierValue >= 156 ? BiomePoolTier.COMMON : tierValue >= 32 ? BiomePoolTier.UNCOMMON : tierValue >= 6 ? BiomePoolTier.RARE : tierValue >= 1 ? BiomePoolTier.SUPER_RARE : BiomePoolTier.ULTRA_RARE - : tierValue >= 20 ? BiomePoolTier.BOSS : tierValue >= 6 ? BiomePoolTier.BOSS_RARE : tierValue >= 1 ? BiomePoolTier.BOSS_SUPER_RARE : BiomePoolTier.BOSS_ULTRA_RARE; - console.log(BiomePoolTier[tier]); - var tiernames = [ - "Common", - "Uncommon", - "Rare", - "Super Rare", - "Ultra Rare", - "Common", - "Rare", - "Super Rare", - "Ultra Rare", - ] - LoggerTools.rarities[LoggerTools.rarityslot[0]] = tiernames[tier] - console.log(tiernames[tier]) - while (!this.pokemonPool[tier].length) { - console.log(`Downgraded rarity tier from ${BiomePoolTier[tier]} to ${BiomePoolTier[tier - 1]}`); - tier--; - } - const tierPool = this.pokemonPool[tier]; - let ret: PokemonSpecies; - let regen = false; - if (!tierPool.length) { - ret = this.scene.randomSpecies(waveIndex, level); - } else { - const entry = tierPool[Utils.randSeedInt(tierPool.length)]; - let species: Species; - if (typeof entry === "number") { - species = entry as Species; - } else { - const levelThresholds = Object.keys(entry); - for (let l = levelThresholds.length - 1; l >= 0; l--) { - const levelThreshold = parseInt(levelThresholds[l]); - if (level >= levelThreshold) { - const speciesIds = entry[levelThreshold]; - if (speciesIds.length > 1) { - species = speciesIds[Utils.randSeedInt(speciesIds.length)]; - } else { - species = speciesIds[0]; - } - break; - } - } - } - - ret = getPokemonSpecies(species); - - if (ret.subLegendary || ret.legendary || ret.mythical) { - switch (true) { - case (ret.baseTotal >= 720): - regen = level < 90; - break; - case (ret.baseTotal >= 670): - regen = level < 70; - break; - case (ret.baseTotal >= 580): - regen = level < 50; - break; - default: - regen = level < 30; - break; - } - } - } - - if (regen && (attempt || 0) < 10) { - console.log("Incompatible level: regenerating..."); - return this.randomSpecies(waveIndex, level, (attempt || 0) + 1); - } - - const newSpeciesId = ret.getWildSpeciesForLevel(level, true, isBoss, this.scene.gameMode); - if (newSpeciesId !== ret.speciesId) { - console.log("Replaced", Species[ret.speciesId], "with", Species[newSpeciesId]); - ret = getPokemonSpecies(newSpeciesId); - } - return ret; - } - - randomTrainerType(waveIndex: integer): TrainerType { - const isBoss = !!this.trainerPool[BiomePoolTier.BOSS].length - && this.scene.gameMode.isTrainerBoss(waveIndex, this.biomeType, this.scene.offsetGym); - console.log(isBoss, this.trainerPool); - const tierValue = Utils.randSeedInt(!isBoss ? 512 : 64); - let tier = !isBoss - ? tierValue >= 156 ? BiomePoolTier.COMMON : tierValue >= 32 ? BiomePoolTier.UNCOMMON : tierValue >= 6 ? BiomePoolTier.RARE : tierValue >= 1 ? BiomePoolTier.SUPER_RARE : BiomePoolTier.ULTRA_RARE - : tierValue >= 20 ? BiomePoolTier.BOSS : tierValue >= 6 ? BiomePoolTier.BOSS_RARE : tierValue >= 1 ? BiomePoolTier.BOSS_SUPER_RARE : BiomePoolTier.BOSS_ULTRA_RARE; - console.log(BiomePoolTier[tier]); - while (tier && !this.trainerPool[tier].length) { - console.log(`Downgraded trainer rarity tier from ${BiomePoolTier[tier]} to ${BiomePoolTier[tier - 1]}`); - tier--; - } - const tierPool = this.trainerPool[tier] || []; - return !tierPool.length ? TrainerType.BREEDER : tierPool[Utils.randSeedInt(tierPool.length)]; - } - - getSpeciesFormIndex(species: PokemonSpecies): integer { - switch (species.speciesId) { - case Species.BURMY: - case Species.WORMADAM: - switch (this.biomeType) { - case Biome.BEACH: - return 1; - case Biome.SLUM: - return 2; - } - break; - case Species.ROTOM: - switch (this.biomeType) { - case Biome.VOLCANO: - return 1; - case Biome.SEA: - return 2; - case Biome.ICE_CAVE: - return 3; - case Biome.MOUNTAIN: - return 4; - case Biome.TALL_GRASS: - return 5; - } - break; - case Species.LYCANROC: - const timeOfDay = this.getTimeOfDay(); - switch (timeOfDay) { - case TimeOfDay.DAY: - case TimeOfDay.DAWN: - return 0; - case TimeOfDay.DUSK: - return 2; - case TimeOfDay.NIGHT: - return 1; - } - break; - } - - return 0; - } - - getTypeForBiome() { - switch (this.biomeType) { - case Biome.TOWN: - case Biome.PLAINS: - case Biome.METROPOLIS: - return Type.NORMAL; - case Biome.GRASS: - case Biome.TALL_GRASS: - return Type.GRASS; - case Biome.FOREST: - case Biome.JUNGLE: - return Type.BUG; - case Biome.SLUM: - case Biome.SWAMP: - return Type.POISON; - case Biome.SEA: - case Biome.BEACH: - case Biome.LAKE: - case Biome.SEABED: - return Type.WATER; - case Biome.MOUNTAIN: - return Type.FLYING; - case Biome.BADLANDS: - return Type.GROUND; - case Biome.CAVE: - case Biome.DESERT: - return Type.ROCK; - case Biome.ICE_CAVE: - case Biome.SNOWY_FOREST: - return Type.ICE; - case Biome.MEADOW: - case Biome.FAIRY_CAVE: - case Biome.ISLAND: - return Type.FAIRY; - case Biome.POWER_PLANT: - return Type.ELECTRIC; - case Biome.VOLCANO: - return Type.FIRE; - case Biome.GRAVEYARD: - case Biome.TEMPLE: - return Type.GHOST; - case Biome.DOJO: - case Biome.CONSTRUCTION_SITE: - return Type.FIGHTING; - case Biome.FACTORY: - case Biome.LABORATORY: - return Type.STEEL; - case Biome.RUINS: - case Biome.SPACE: - return Type.PSYCHIC; - case Biome.WASTELAND: - case Biome.END: - return Type.DRAGON; - case Biome.ABYSS: - return Type.DARK; - default: - return Type.UNKNOWN; - } - } - - getBgTerrainColorRatioForBiome(): number { - switch (this.biomeType) { - case Biome.SPACE: - return 1; - case Biome.END: - return 0; - } - - return 131 / 180; - } - - /** - * Sets weather to the override specified in overrides.ts - * @param weather new weather to set of type WeatherType - * @returns true to force trySetWeather to return true - */ - trySetWeatherOverride(weather: WeatherType): boolean { - this.weather = new Weather(weather, 0); - this.scene.unshiftPhase(new CommonAnimPhase(this.scene, undefined, undefined, CommonAnim.SUNNY + (weather - 1))); - this.scene.queueMessage(getWeatherStartMessage(weather)); - return true; - } - - /** - * Attempts to set a new weather to the battle - * @param weather new weather to set of type WeatherType - * @param hasPokemonSource is the new weather from a pokemon - * @returns true if new weather set, false if no weather provided or attempting to set the same weather as currently in use - */ - trySetWeather(weather: WeatherType, hasPokemonSource: boolean): boolean { - if (Overrides.WEATHER_OVERRIDE) { - return this.trySetWeatherOverride(Overrides.WEATHER_OVERRIDE); - } - - if (this.weather?.weatherType === (weather || undefined)) { - return false; - } - - const oldWeatherType = this.weather?.weatherType || WeatherType.NONE; - - this.weather = weather ? new Weather(weather, hasPokemonSource ? 5 : 0) : null; - this.eventTarget.dispatchEvent(new WeatherChangedEvent(oldWeatherType, this.weather?.weatherType, this.weather?.turnsLeft)); - - if (this.weather) { - this.scene.unshiftPhase(new CommonAnimPhase(this.scene, undefined, undefined, CommonAnim.SUNNY + (weather - 1))); - this.scene.queueMessage(getWeatherStartMessage(weather)); - } else { - this.scene.queueMessage(getWeatherClearMessage(oldWeatherType)); - } - - this.scene.getField(true).filter(p => p.isOnField()).map(pokemon => { - pokemon.findAndRemoveTags(t => "weatherTypes" in t && !(t.weatherTypes as WeatherType[]).find(t => t === weather)); - applyPostWeatherChangeAbAttrs(PostWeatherChangeAbAttr, pokemon, weather); - }); - - return true; - } - - trySetTerrain(terrain: TerrainType, hasPokemonSource: boolean, ignoreAnim: boolean = false): boolean { - if (this.terrain?.terrainType === (terrain || undefined)) { - return false; - } - - const oldTerrainType = this.terrain?.terrainType || TerrainType.NONE; - - this.terrain = terrain ? new Terrain(terrain, hasPokemonSource ? 5 : 0) : null; - this.eventTarget.dispatchEvent(new TerrainChangedEvent(oldTerrainType,this.terrain?.terrainType, this.terrain?.turnsLeft)); - - if (this.terrain) { - if (!ignoreAnim) { - this.scene.unshiftPhase(new CommonAnimPhase(this.scene, undefined, undefined, CommonAnim.MISTY_TERRAIN + (terrain - 1))); - } - this.scene.queueMessage(getTerrainStartMessage(terrain)); - } else { - this.scene.queueMessage(getTerrainClearMessage(oldTerrainType)); - } - - this.scene.getField(true).filter(p => p.isOnField()).map(pokemon => { - pokemon.findAndRemoveTags(t => "terrainTypes" in t && !(t.terrainTypes as TerrainType[]).find(t => t === terrain)); - applyPostTerrainChangeAbAttrs(PostTerrainChangeAbAttr, pokemon, terrain); - }); - - return true; - } - - isMoveWeatherCancelled(move: Move) { - return this.weather && !this.weather.isEffectSuppressed(this.scene) && this.weather.isMoveWeatherCancelled(move); - } - - isMoveTerrainCancelled(user: Pokemon, targets: BattlerIndex[], move: Move) { - return this.terrain && this.terrain.isMoveTerrainCancelled(user, targets, move); - } - - getTerrainType() : TerrainType { - return this.terrain?.terrainType || TerrainType.NONE; - } - - getAttackTypeMultiplier(attackType: Type, grounded: boolean): number { - let weatherMultiplier = 1; - if (this.weather && !this.weather.isEffectSuppressed(this.scene)) { - weatherMultiplier = this.weather.getAttackTypeMultiplier(attackType); - } - - let terrainMultiplier = 1; - if (this.terrain && grounded) { - terrainMultiplier = this.terrain.getAttackTypeMultiplier(attackType); - } - - return weatherMultiplier * terrainMultiplier; - } - - /** - * Gets the denominator for the chance for a trainer spawn - * @returns n where 1/n is the chance of a trainer battle - */ - getTrainerChance(): integer { - switch (this.biomeType) { - case Biome.METROPOLIS: - return 2; - case Biome.SLUM: - case Biome.BEACH: - case Biome.DOJO: - case Biome.CONSTRUCTION_SITE: - return 4; - case Biome.PLAINS: - case Biome.GRASS: - case Biome.LAKE: - case Biome.CAVE: - return 6; - case Biome.TALL_GRASS: - case Biome.FOREST: - case Biome.SEA: - case Biome.SWAMP: - case Biome.MOUNTAIN: - case Biome.BADLANDS: - case Biome.DESERT: - case Biome.MEADOW: - case Biome.POWER_PLANT: - case Biome.GRAVEYARD: - case Biome.FACTORY: - case Biome.SNOWY_FOREST: - return 8; - case Biome.ICE_CAVE: - case Biome.VOLCANO: - case Biome.RUINS: - case Biome.WASTELAND: - case Biome.JUNGLE: - case Biome.FAIRY_CAVE: - return 12; - case Biome.SEABED: - case Biome.ABYSS: - case Biome.SPACE: - case Biome.TEMPLE: - return 16; - default: - return 0; - } - } - - getTimeOfDay(): TimeOfDay { - switch (this.biomeType) { - case Biome.ABYSS: - return TimeOfDay.NIGHT; - } - - const waveCycle = ((this.scene.currentBattle?.waveIndex || 0) + this.scene.waveCycleOffset) % 40; - - if (waveCycle < 15) { - return TimeOfDay.DAY; - } - - if (waveCycle < 20) { - return TimeOfDay.DUSK; - } - - if (waveCycle < 35) { - return TimeOfDay.NIGHT; - } - - return TimeOfDay.DAWN; - } - - isOutside(): boolean { - switch (this.biomeType) { - case Biome.SEABED: - case Biome.CAVE: - case Biome.ICE_CAVE: - case Biome.POWER_PLANT: - case Biome.DOJO: - case Biome.FACTORY: - case Biome.ABYSS: - case Biome.FAIRY_CAVE: - case Biome.TEMPLE: - case Biome.LABORATORY: - return false; - default: - return true; - } - } - - overrideTint(): [integer, integer, integer] { - switch (Overrides.ARENA_TINT_OVERRIDE) { - case TimeOfDay.DUSK: - return [ 98, 48, 73 ].map(c => Math.round((c + 128) / 2)) as [integer, integer, integer]; - break; - case (TimeOfDay.NIGHT): - return [ 64, 64, 64 ]; - break; - case TimeOfDay.DAWN: - case TimeOfDay.DAY: - default: - return [ 128, 128, 128 ]; - break; - } - } - - getDayTint(): [integer, integer, integer] { - if (Overrides.ARENA_TINT_OVERRIDE !== null) { - return this.overrideTint(); - } - switch (this.biomeType) { - case Biome.ABYSS: - return [ 64, 64, 64 ]; - default: - return [ 128, 128, 128 ]; - } - } - - getDuskTint(): [integer, integer, integer] { - if (Overrides.ARENA_TINT_OVERRIDE) { - return this.overrideTint(); - } - if (!this.isOutside()) { - return [ 0, 0, 0 ]; - } - - switch (this.biomeType) { - default: - return [ 98, 48, 73 ].map(c => Math.round((c + 128) / 2)) as [integer, integer, integer]; - } - } - - getNightTint(): [integer, integer, integer] { - if (Overrides.ARENA_TINT_OVERRIDE) { - return this.overrideTint(); - } - switch (this.biomeType) { - case Biome.ABYSS: - case Biome.SPACE: - case Biome.END: - return this.getDayTint(); - } - - if (!this.isOutside()) { - return [ 64, 64, 64 ]; - } - - switch (this.biomeType) { - default: - return [ 48, 48, 98 ]; - } - } - - setIgnoreAbilities(ignoreAbilities: boolean = true): void { - this.ignoreAbilities = ignoreAbilities; - } - - applyTagsForSide(tagType: ArenaTagType | Constructor, side: ArenaTagSide, ...args: unknown[]): void { - let tags = typeof tagType === "string" - ? this.tags.filter(t => t.tagType === tagType) - : this.tags.filter(t => t instanceof tagType); - if (side !== ArenaTagSide.BOTH) { - tags = tags.filter(t => t.side === side); - } - tags.forEach(t => t.apply(this, args)); - } - - applyTags(tagType: ArenaTagType | Constructor, ...args: unknown[]): void { - this.applyTagsForSide(tagType, ArenaTagSide.BOTH, ...args); - } - - addTag(tagType: ArenaTagType, turnCount: integer, sourceMove: Moves, sourceId: integer, side: ArenaTagSide = ArenaTagSide.BOTH, quiet: boolean = false, targetIndex?: BattlerIndex): boolean { - const existingTag = this.getTagOnSide(tagType, side); - if (existingTag) { - existingTag.onOverlap(this); - - if (existingTag instanceof ArenaTrapTag) { - const { tagType, side, turnCount, layers, maxLayers } = existingTag as ArenaTrapTag; - this.eventTarget.dispatchEvent(new TagAddedEvent(tagType, side, turnCount, layers, maxLayers)); - } - - return false; - } - - const newTag = getArenaTag(tagType, turnCount || 0, sourceMove, sourceId, targetIndex, side); - this.tags.push(newTag); - newTag.onAdd(this, quiet); - - const { layers = 0, maxLayers = 0 } = newTag instanceof ArenaTrapTag ? newTag : {}; - - this.eventTarget.dispatchEvent(new TagAddedEvent(newTag.tagType, newTag.side, newTag.turnCount, layers, maxLayers)); - - return true; - } - - getTag(tagType: ArenaTagType | Constructor): ArenaTag { - return this.getTagOnSide(tagType, ArenaTagSide.BOTH); - } - - getTagOnSide(tagType: ArenaTagType | Constructor, side: ArenaTagSide): ArenaTag { - return typeof(tagType) === "string" - ? this.tags.find(t => t.tagType === tagType && (side === ArenaTagSide.BOTH || t.side === ArenaTagSide.BOTH || t.side === side)) - : this.tags.find(t => t instanceof tagType && (side === ArenaTagSide.BOTH || t.side === ArenaTagSide.BOTH || t.side === side)); - } - - findTags(tagPredicate: (t: ArenaTag) => boolean): ArenaTag[] { - return this.findTagsOnSide(tagPredicate, ArenaTagSide.BOTH); - } - - findTagsOnSide(tagPredicate: (t: ArenaTag) => boolean, side: ArenaTagSide): ArenaTag[] { - return this.tags.filter(t => tagPredicate(t) && (side === ArenaTagSide.BOTH || t.side === ArenaTagSide.BOTH || t.side === side)); - } - - lapseTags(): void { - this.tags.filter(t => !(t.lapse(this))).forEach(t => { - t.onRemove(this); - this.tags.splice(this.tags.indexOf(t), 1); - - this.eventTarget.dispatchEvent(new TagRemovedEvent(t.tagType, t.side, t.turnCount)); - }); - } - - removeTag(tagType: ArenaTagType): boolean { - const tags = this.tags; - const tag = tags.find(t => t.tagType === tagType); - if (tag) { - tag.onRemove(this); - tags.splice(tags.indexOf(tag), 1); - - this.eventTarget.dispatchEvent(new TagRemovedEvent(tag.tagType, tag.side, tag.turnCount)); - } - return !!tag; - } - - removeTagOnSide(tagType: ArenaTagType, side: ArenaTagSide, quiet: boolean = false): boolean { - const tag = this.getTagOnSide(tagType, side); - if (tag) { - tag.onRemove(this, quiet); - this.tags.splice(this.tags.indexOf(tag), 1); - - this.eventTarget.dispatchEvent(new TagRemovedEvent(tag.tagType, tag.side, tag.turnCount)); - } - return !!tag; - } - - - removeAllTags(): void { - while (this.tags.length) { - this.tags[0].onRemove(this); - this.eventTarget.dispatchEvent(new TagRemovedEvent(this.tags[0].tagType, this.tags[0].side, this.tags[0].turnCount)); - - this.tags.splice(0, 1); - } - } - - preloadBgm(): void { - this.scene.loadBgm(this.bgm); - } - - getBgmLoopPoint(): number { - switch (this.biomeType) { - case Biome.TOWN: - return 7.288; - case Biome.PLAINS: - return 7.693; - case Biome.GRASS: - return 1.995; - case Biome.TALL_GRASS: - return 9.608; - case Biome.METROPOLIS: - return 141.470; - case Biome.FOREST: - return 4.294; - case Biome.SEA: - return 1.672; - case Biome.SWAMP: - return 4.461; - case Biome.BEACH: - return 3.462; - case Biome.LAKE: - return 5.350; - case Biome.SEABED: - return 2.600; - case Biome.MOUNTAIN: - return 4.018; - case Biome.BADLANDS: - return 17.790; - case Biome.CAVE: - return 14.240; - case Biome.DESERT: - return 1.143; - case Biome.ICE_CAVE: - return 15.010; - case Biome.MEADOW: - return 3.891; - case Biome.POWER_PLANT: - return 2.810; - case Biome.VOLCANO: - return 5.116; - case Biome.GRAVEYARD: - return 3.232; - case Biome.DOJO: - return 6.205; - case Biome.FACTORY: - return 4.985; - case Biome.RUINS: - return 2.270; - case Biome.WASTELAND: - return 6.336; - case Biome.ABYSS: - return 5.130; - case Biome.SPACE: - return 20.036; - case Biome.CONSTRUCTION_SITE: - return 1.222; - case Biome.JUNGLE: - return 0.000; - case Biome.FAIRY_CAVE: - return 4.542; - case Biome.TEMPLE: - return 2.547; - case Biome.ISLAND: - return 2.751; - case Biome.LABORATORY: - return 114.862; - case Biome.SLUM: - return 1.221; - case Biome.SNOWY_FOREST: - return 3.047; - } +} +/** + * Container class for {@linkcode ArenaEventType.TERRAIN_CHANGED} events + * @extends ArenaEvent +*/ +export class TerrainChangedEvent extends ArenaEvent { + /** The {@linkcode TerrainType} being overridden */ + public oldTerrainType: TerrainType; + /** The {@linkcode TerrainType} being set */ + public newTerrainType: TerrainType; + constructor(oldTerrainType: TerrainType, newTerrainType: TerrainType, duration: number) { + super(ArenaEventType.TERRAIN_CHANGED, duration); + + this.oldTerrainType = oldTerrainType; + this.newTerrainType = newTerrainType; } } -export function getBiomeKey(biome: Biome): string { - return Biome[biome].toLowerCase(); -} +/** + * Container class for {@linkcode ArenaEventType.TAG_ADDED} events + * @extends ArenaEvent +*/ +export class TagAddedEvent extends ArenaEvent { + /** The {@linkcode ArenaTagType} being added */ + public arenaTagType: ArenaTagType; + /** The {@linkcode ArenaTagSide} the tag is being placed on */ + public arenaTagSide: ArenaTagSide; + /** The current number of layers of the arena trap. */ + public arenaTagLayers: number; + /** The maximum amount of layers of the arena trap. */ + public arenaTagMaxLayers: number; -export function getBiomeHasProps(biomeType: Biome): boolean { - switch (biomeType) { - case Biome.METROPOLIS: - case Biome.BEACH: - case Biome.LAKE: - case Biome.SEABED: - case Biome.MOUNTAIN: - case Biome.BADLANDS: - case Biome.CAVE: - case Biome.DESERT: - case Biome.ICE_CAVE: - case Biome.MEADOW: - case Biome.POWER_PLANT: - case Biome.VOLCANO: - case Biome.GRAVEYARD: - case Biome.FACTORY: - case Biome.RUINS: - case Biome.WASTELAND: - case Biome.ABYSS: - case Biome.CONSTRUCTION_SITE: - case Biome.JUNGLE: - case Biome.FAIRY_CAVE: - case Biome.TEMPLE: - case Biome.SNOWY_FOREST: - case Biome.ISLAND: - case Biome.LABORATORY: - case Biome.END: - return true; - } + constructor(arenaTagType: ArenaTagType, arenaTagSide: ArenaTagSide, duration: number, arenaTagLayers?: number, arenaTagMaxLayers?: number) { + super(ArenaEventType.TAG_ADDED, duration); - return false; -} - -export class ArenaBase extends Phaser.GameObjects.Container { - public player: boolean; - public biome: Biome; - public propValue: integer; - public base: Phaser.GameObjects.Sprite; - public props: Phaser.GameObjects.Sprite[]; - - constructor(scene: BattleScene, player: boolean) { - super(scene, 0, 0); - - this.player = player; - - this.base = scene.addFieldSprite(0, 0, "plains_a", null, 1); - this.base.setOrigin(0, 0); - - this.props = !player ? - new Array(3).fill(null).map(() => { - const ret = scene.addFieldSprite(0, 0, "plains_b", null, 1); - ret.setOrigin(0, 0); - ret.setVisible(false); - return ret; - }) : []; - } - - setBiome(biome: Biome, propValue?: integer): void { - const hasProps = getBiomeHasProps(biome); - const biomeKey = getBiomeKey(biome); - const baseKey = `${biomeKey}_${this.player ? "a" : "b"}`; - - if (biome !== this.biome) { - this.base.setTexture(baseKey); - - if (this.base.texture.frameTotal > 1) { - const baseFrameNames = this.scene.anims.generateFrameNames(baseKey, { zeroPad: 4, suffix: ".png", start: 1, end: this.base.texture.frameTotal - 1 }); - if (!(this.scene.anims.exists(baseKey))) { - this.scene.anims.create({ - key: baseKey, - frames: baseFrameNames, - frameRate: 12, - repeat: -1 - }); - } - this.base.play(baseKey); - } else { - this.base.stop(); - } - - this.add(this.base); - } - - if (!this.player) { - (this.scene as BattleScene).executeWithSeedOffset(() => { - this.propValue = propValue === undefined - ? hasProps ? Utils.randSeedInt(8) : 0 - : propValue; - this.props.forEach((prop, p) => { - const propKey = `${biomeKey}_b${hasProps ? `_${p + 1}` : ""}`; - prop.setTexture(propKey); - - if (hasProps && prop.texture.frameTotal > 1) { - const propFrameNames = this.scene.anims.generateFrameNames(propKey, { zeroPad: 4, suffix: ".png", start: 1, end: prop.texture.frameTotal - 1 }); - if (!(this.scene.anims.exists(propKey))) { - this.scene.anims.create({ - key: propKey, - frames: propFrameNames, - frameRate: 12, - repeat: -1 - }); - } - prop.play(propKey); - } else { - prop.stop(); - } - - prop.setVisible(hasProps && !!(this.propValue & (1 << p))); - this.add(prop); - }); - }, (this.scene as BattleScene).currentBattle?.waveIndex || 0, (this.scene as BattleScene).waveSeed); - } + this.arenaTagType = arenaTagType; + this.arenaTagSide = arenaTagSide; + this.arenaTagLayers = arenaTagLayers; + this.arenaTagMaxLayers = arenaTagMaxLayers; + } +} +/** + * Container class for {@linkcode ArenaEventType.TAG_REMOVED} events + * @extends ArenaEvent +*/ +export class TagRemovedEvent extends ArenaEvent { + /** The {@linkcode ArenaTagType} being removed */ + public arenaTagType: ArenaTagType; + /** The {@linkcode ArenaTagSide} the tag was being placed on */ + public arenaTagSide: ArenaTagSide; + constructor(arenaTagType: ArenaTagType, arenaTagSide: ArenaTagSide, duration: number) { + super(ArenaEventType.TAG_REMOVED, duration); + + this.arenaTagType = arenaTagType; + this.arenaTagSide = arenaTagSide; } } diff --git a/src/field/arena.ts b/src/field/arena.ts index 51dba1089e9..8658b35d756 100644 --- a/src/field/arena.ts +++ b/src/field/arena.ts @@ -21,6 +21,7 @@ import { Moves } from "#enums/moves"; import { Species } from "#enums/species"; import { TimeOfDay } from "#enums/time-of-day"; import { TrainerType } from "#enums/trainer-type"; +import * as LoggerTools from "../logger" export class Arena { public scene: BattleScene; @@ -91,6 +92,19 @@ export class Arena { ? tierValue >= 156 ? BiomePoolTier.COMMON : tierValue >= 32 ? BiomePoolTier.UNCOMMON : tierValue >= 6 ? BiomePoolTier.RARE : tierValue >= 1 ? BiomePoolTier.SUPER_RARE : BiomePoolTier.ULTRA_RARE : tierValue >= 20 ? BiomePoolTier.BOSS : tierValue >= 6 ? BiomePoolTier.BOSS_RARE : tierValue >= 1 ? BiomePoolTier.BOSS_SUPER_RARE : BiomePoolTier.BOSS_ULTRA_RARE; console.log(BiomePoolTier[tier]); + var tiernames = [ + "Common", + "Uncommon", + "Rare", + "Super Rare", + "Ultra Rare", + "Common", + "Rare", + "Super Rare", + "Ultra Rare", + ] + LoggerTools.rarities[LoggerTools.rarityslot[0]] = tiernames[tier] + console.log(tiernames[tier]) while (!this.pokemonPool[tier].length) { console.log(`Downgraded rarity tier from ${BiomePoolTier[tier]} to ${BiomePoolTier[tier - 1]}`); tier--;